You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
2004 lines
44 KiB
2004 lines
44 KiB
//========= Copyright Valve Corporation, All rights reserved. ============// |
|
// |
|
// Purpose: |
|
// |
|
// $NoKeywords: $ |
|
// |
|
//=============================================================================// |
|
#include "cbase.h" |
|
#include "workspacemanager.h" |
|
#include "workspacebrowser.h" |
|
#include "workspace.h" |
|
#include "statuswindow.h" |
|
#include "SoundEmitterSystem/isoundemittersystembase.h" |
|
#include "drawhelper.h" |
|
#include "InputProperties.h" |
|
#include "filesystem.h" |
|
#include "cmdlib.h" |
|
#include "project.h" |
|
#include "scene.h" |
|
#include <KeyValues.h> |
|
#include "utlbuffer.h" |
|
#include "iscenemanagersound.h" |
|
#include "soundentry.h" |
|
#include "vcdfile.h" |
|
#include "soundbrowser.h" |
|
#include "wavebrowser.h" |
|
#include "VSSProperties.h" |
|
#include "resource.h" |
|
#include "soundproperties.h" |
|
#include "waveproperties.h" |
|
#include "wavefile.h" |
|
#include "ifileloader.h" |
|
#include "MultipleRequest.h" |
|
#include <vgui/ILocalize.h> |
|
#include "tier3/tier3.h" |
|
|
|
char g_appTitle[] = "Source Engine SceneManager"; |
|
static char g_appTitleFmt[] = "%s - SceneManager Workspace (%s)"; |
|
static char g_appTitleFmtModified[] = "%s * - SceneManager Workspace (%s)"; |
|
|
|
#define RECENT_FILES_FILE "scenemanager.rf" |
|
|
|
enum |
|
{ |
|
// Menu options |
|
IDC_WSM_FILE_EXIT = 1000, |
|
|
|
IDC_WSM_FILE_WS_NEW, |
|
IDC_WSM_FILE_WS_OPEN, |
|
IDC_WSM_FILE_WS_CLOSE, |
|
IDC_WSM_FILE_WS_SAVE, |
|
|
|
IDC_WSM_FILE_WS_REFRESH, |
|
|
|
IDC_WSM_FILE_WS_VSSPROPERTIES, |
|
IDC_WSM_FILE_WS_CHECKOUT, |
|
IDC_WSM_FILE_WS_CHECKIN, |
|
|
|
IDC_WSM_FILE_SCENE_NEW, // + prompt for add to active project |
|
|
|
IDC_WSM_PROJECT_PRJ_NEW, // + Prompt for add to workspace |
|
|
|
IDC_WSM_PROJECT_PRJ_INSERT, |
|
IDC_WSM_PROJECT_PRJ_REMOVE, |
|
IDC_WSM_PROJECT_PRJ_MODIFYCOMMENTS, |
|
|
|
IDC_WSM_PROJECT_SCENE_NEW, |
|
IDC_WSM_SCENE_REMOVE, |
|
|
|
IDC_WSM_SOUNDENTRY_PLAY, |
|
IDC_WSM_SOUNDENTRY_TOGGLEVOICEDUCK, |
|
IDC_WSM_SOUNDENTRY_EDITTEXT, |
|
IDC_WSM_SOUNDENTRY_SHOWINBROWSERS, |
|
IDC_WSM_SOUNDENTRY_PROPERTIES, |
|
|
|
IDC_WSM_SCENE_VCD_ADD, |
|
IDC_WSM_SCENE_VCD_REMOVE, |
|
IDC_WSM_SCENE_EDIT_COMMENTS, |
|
|
|
IDC_WSM_VCD_EDIT_COMMENTS, |
|
|
|
IDC_WSM_SELECTION_CHECKOUT, |
|
IDC_WSM_SELECTION_CHECKIN, |
|
|
|
IDC_WSM_SELECTION_MOVEUP, |
|
IDC_WSM_SELECTION_MOVEDOWN, |
|
|
|
IDC_WSM_WAVEFILE_PROPERTIES, |
|
|
|
// Controls |
|
IDC_WS_BROWSER, |
|
IDC_WS_SOUNDBROWSER, |
|
IDC_WS_WAVEBROWSER, |
|
|
|
// These should be the final entriex |
|
IDC_WSM_FILE_RECENT_WORKSPACE_START = 1500, |
|
IDC_WSM_FILE_RECENT_WORKSPACE_END = 1510, |
|
|
|
IDC_WSM_OPTIONS_LANGUAGESTART = 1600, |
|
IDC_WSM_OPTIONS_LANGUAGEEND = 1600 + CC_NUM_LANGUAGES, |
|
}; |
|
|
|
static CWorkspaceManager *g_pManager = NULL; |
|
CWorkspaceManager *GetWorkspaceManager() |
|
{ |
|
Assert( g_pManager ); |
|
return g_pManager; |
|
} |
|
|
|
class CWorkspaceWorkArea : public mxWindow |
|
{ |
|
public: |
|
CWorkspaceWorkArea( mxWindow *parent ) |
|
: mxWindow( parent, 0, 0, 0, 0, "" ) |
|
{ |
|
SceneManager_AddWindowStyle( this, WS_VISIBLE | WS_CLIPCHILDREN | WS_CLIPSIBLINGS ); |
|
} |
|
|
|
virtual void redraw() |
|
{ |
|
CDrawHelper helper( this, RGB( 200, 200, 200 ) ); |
|
} |
|
}; |
|
|
|
CWorkspaceManager::CWorkspaceManager() |
|
: mxWindow (0, 0, 0, 0, 0, g_appTitle, mxWindow::Normal) |
|
{ |
|
m_lEnglishCaptionsFileChangeTime = -1L; |
|
m_nLanguageId = CC_ENGLISH; |
|
|
|
g_pManager = this; |
|
|
|
g_pStatusWindow = new CStatusWindow( this, 0, 0, 1024, 150, "" ); |
|
g_pStatusWindow->setVisible( true ); |
|
|
|
m_pWorkArea = new CWorkspaceWorkArea( this ); |
|
|
|
Con_Printf( "Initializing\n" ); |
|
|
|
Con_Printf( "CSoundEmitterSystemBase::Init()\n" ); |
|
|
|
m_nRecentMenuItems = 0; |
|
|
|
// create menu stuff |
|
m_pMenuBar = new mxMenuBar (this); |
|
m_pFileMenu = new mxMenu (); |
|
m_pProjectMenu = new mxMenu (); |
|
m_pOptionsMenu = new mxMenu(); |
|
|
|
{ |
|
m_pMenuCloseCaptionLanguages = new mxMenu(); |
|
|
|
for ( int i = 0; i < CC_NUM_LANGUAGES; i++ ) |
|
{ |
|
int id = IDC_WSM_OPTIONS_LANGUAGESTART + i; |
|
m_pMenuCloseCaptionLanguages->add( CSentence::NameForLanguage( i ), id ); |
|
} |
|
// Check the first item |
|
m_pMenuCloseCaptionLanguages->setChecked( IDC_WSM_OPTIONS_LANGUAGESTART + CC_ENGLISH, true ); |
|
m_pOptionsMenu->addMenu( "CC Language", m_pMenuCloseCaptionLanguages ); |
|
|
|
} |
|
|
|
m_pMenuBar->addMenu ("File", m_pFileMenu ); |
|
m_pMenuBar->addMenu( "Project", m_pProjectMenu ); |
|
m_pMenuBar->addMenu ( "Options", m_pOptionsMenu ); |
|
|
|
CreateFileMenu( m_pFileMenu ); |
|
CreateProjectMenu( m_pProjectMenu ); |
|
|
|
setMenuBar ( m_pMenuBar ); |
|
|
|
Con_Printf( "Creating browser\n" ); |
|
|
|
m_pBrowser = new CWorkspaceBrowser( m_pWorkArea, this, IDC_WS_BROWSER ); |
|
|
|
m_pSoundBrowser = NULL; |
|
m_pWaveBrowser = NULL; |
|
|
|
int w = 1280; |
|
setBounds (10, 10, w, 960); |
|
|
|
setVisible (true); |
|
|
|
Con_Printf( "Creating wave browser\n" ); |
|
|
|
m_pWaveBrowser = new CWaveBrowser( m_pWorkArea, this, IDC_WS_WAVEBROWSER ); |
|
|
|
Con_Printf( "Creating sound browser\n" ); |
|
|
|
m_pSoundBrowser = new CSoundBrowser( m_pWorkArea, this, IDC_WS_SOUNDBROWSER ); |
|
|
|
GetBrowser()->SetWorkspace( NULL ); |
|
|
|
// See if command line requested workspace |
|
|
|
// Default layout |
|
PerformLayout( true ); |
|
|
|
LoadRecentFilesMenuFromDisk(); |
|
} |
|
|
|
CWorkspaceManager::~CWorkspaceManager() |
|
{ |
|
} |
|
|
|
bool CWorkspaceManager::Closing() |
|
{ |
|
Con_Printf( "Checking for sound script changes...\n" ); |
|
|
|
MultipleRequestChangeContext(); |
|
|
|
// Save any changed sound script files |
|
int c = g_pSoundEmitterSystem->GetNumSoundScripts(); |
|
for ( int i = 0; i < c; i++ ) |
|
{ |
|
if ( !g_pSoundEmitterSystem->IsSoundScriptDirty( i ) ) |
|
continue; |
|
|
|
char const *scriptname = g_pSoundEmitterSystem->GetSoundScriptName( i ); |
|
if ( !scriptname ) |
|
continue; |
|
|
|
Assert( filesystem->FileExists( scriptname ) ); |
|
|
|
bool save = true; |
|
|
|
if ( filesystem->FileExists( scriptname ) ) |
|
{ |
|
if ( !filesystem->IsFileWritable( scriptname ) ) |
|
{ |
|
int retval = MultipleRequest( va( "Check out '%s'?", scriptname )); |
|
// Cancel |
|
if ( retval == 2 ) |
|
return false; |
|
|
|
if ( retval == 0 ) |
|
{ |
|
VSS_Checkout( scriptname ); |
|
|
|
if ( !filesystem->IsFileWritable( scriptname ) ) |
|
{ |
|
mxMessageBox( NULL, va( "Aborting shutdown, %s, not writable!!", scriptname ), g_appTitle, MX_MB_OK ); |
|
return false; |
|
} |
|
} |
|
else if ( retval == 1 ) |
|
{ |
|
// Don't save |
|
save = false; |
|
} |
|
} |
|
|
|
if ( filesystem->IsFileWritable( scriptname ) ) |
|
{ |
|
int retval = mxMessageBox( NULL, va( "Save changes to out '%s'?", scriptname ), g_appTitle, MX_MB_YESNOCANCEL ); |
|
// Cancel |
|
if ( retval == 2 ) |
|
return false; |
|
|
|
if ( retval == 0 ) |
|
{ |
|
if ( !filesystem->IsFileWritable( scriptname ) ) |
|
{ |
|
mxMessageBox( NULL, va( "Aborting shutdown, %s, not writable!!", scriptname ), g_appTitle, MX_MB_OK ); |
|
return false; |
|
} |
|
} |
|
else if ( retval == 1 ) |
|
{ |
|
// Skip changes!!! |
|
save = false; |
|
} |
|
} |
|
} |
|
|
|
// Try and save it |
|
if ( !save ) |
|
continue; |
|
|
|
g_pSoundEmitterSystem->SaveChangesToSoundScript( i ); |
|
} |
|
|
|
return CloseWorkspace(); |
|
} |
|
|
|
void CWorkspaceManager::OnDelete() |
|
{ |
|
SaveRecentFilesMenuToDisk(); |
|
} |
|
|
|
void CWorkspaceManager::CreateFileMenu( mxMenu *m ) |
|
{ |
|
m->add ("&New Workspace", IDC_WSM_FILE_WS_NEW ); |
|
m->addSeparator(); |
|
m->add ("Open &Workspace...", IDC_WSM_FILE_WS_OPEN ); |
|
m->add ("Sa&ve Workspace", IDC_WSM_FILE_WS_SAVE ); |
|
m->add ("Close Wor&kspace", IDC_WSM_FILE_WS_CLOSE ); |
|
m->addSeparator(); |
|
m->add ("&Create New Scene...", IDC_WSM_FILE_SCENE_NEW ); |
|
m->addSeparator(); |
|
|
|
m->add( "V&SS Properties...", IDC_WSM_FILE_WS_VSSPROPERTIES ); |
|
m->addSeparator(); |
|
|
|
m->add( "Refresh\tF5", IDC_WSM_FILE_WS_REFRESH ); |
|
|
|
m->addSeparator(); |
|
|
|
m_pRecentFileMenu = new mxMenu (); |
|
m->addMenu ("Recent Files", m_pRecentFileMenu); |
|
|
|
m->addSeparator(); |
|
m->add ("E&xit", IDC_WSM_FILE_EXIT ); |
|
} |
|
|
|
void CWorkspaceManager::UpdateMenus() |
|
{ |
|
CWorkspace *ws = GetBrowser()->GetWorkspace(); |
|
|
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
|
|
bool hasworkspace = ws != NULL ? true : false; |
|
//bool workspacedirty = ws && ws->IsDirty() ? true : false; |
|
bool hasproject = item && item->GetProject() ? true : false; |
|
|
|
m_pMenuBar->setEnabled( IDC_WSM_FILE_WS_SAVE, true ); |
|
m_pMenuBar->setEnabled( IDC_WSM_FILE_WS_CLOSE, hasworkspace ); |
|
|
|
|
|
if ( hasproject ) |
|
{ |
|
m_pMenuBar->modify( IDC_WSM_FILE_SCENE_NEW, IDC_WSM_FILE_SCENE_NEW, va( "&Create Scene in '%s'", item->GetProject()->GetName() ) ); |
|
} |
|
else |
|
{ |
|
m_pMenuBar->modify( IDC_WSM_FILE_SCENE_NEW, IDC_WSM_FILE_SCENE_NEW, "&Create New Scene..." ); |
|
} |
|
m_pMenuBar->setEnabled( IDC_WSM_FILE_SCENE_NEW, hasproject ); |
|
|
|
} |
|
|
|
void CWorkspaceManager::CreateProjectMenu( mxMenu *m ) |
|
{ |
|
m->add ("Create New Project...", IDC_WSM_PROJECT_PRJ_NEW ); |
|
m->addSeparator(); |
|
m->add ("Insert Project...", IDC_WSM_PROJECT_PRJ_INSERT ); |
|
m->add ("Remove Project...", IDC_WSM_PROJECT_PRJ_REMOVE ); |
|
m->addSeparator(); |
|
m->add ("Properties...", IDC_WSM_PROJECT_PRJ_MODIFYCOMMENTS ); |
|
} |
|
|
|
CWorkspaceBrowser *CWorkspaceManager::GetBrowser() |
|
{ |
|
return m_pBrowser; |
|
} |
|
|
|
CSoundBrowser *CWorkspaceManager::GetSoundBrowser() |
|
{ |
|
return m_pSoundBrowser; |
|
} |
|
|
|
CWaveBrowser *CWorkspaceManager::GetWaveBrowser() |
|
{ |
|
return m_pWaveBrowser; |
|
} |
|
|
|
int CWorkspaceManager::GetMaxRecentFiles() const |
|
{ |
|
return IDC_WSM_FILE_RECENT_WORKSPACE_END - IDC_WSM_FILE_RECENT_WORKSPACE_START; |
|
} |
|
|
|
#define MAX_FPS 250.0f |
|
#define MIN_TIMESTEP ( 1.0f / MAX_FPS ) |
|
|
|
double realtime = 0.0f; |
|
|
|
void CWorkspaceManager::Think( float dt ) |
|
{ |
|
sound->Update( dt ); |
|
int c = fileloader->ProcessCompleted(); |
|
if ( c > 0 ) |
|
{ |
|
RefreshBrowsers(); |
|
Con_Printf( "Thread loaded %i sounds\n", c ); |
|
} |
|
} |
|
|
|
void CWorkspaceManager::Frame( void ) |
|
{ |
|
static bool recursion_guard = false; |
|
|
|
static double prev = 0.0; |
|
double curr = (double) mx::getTickCount () / 1000.0; |
|
double dt = ( curr - prev ); |
|
|
|
if ( recursion_guard ) |
|
return; |
|
|
|
recursion_guard = true; |
|
|
|
// clamp to MAX_FPS |
|
if ( dt >= 0.0 && dt < MIN_TIMESTEP ) |
|
{ |
|
Sleep( max( 0, (int)( ( MIN_TIMESTEP - dt ) * 1000.0f ) ) ); |
|
|
|
recursion_guard = false; |
|
return; |
|
} |
|
|
|
if ( prev != 0.0 ) |
|
{ |
|
dt = min( 0.1, dt ); |
|
|
|
Think( dt ); |
|
|
|
realtime += dt; |
|
} |
|
|
|
prev = curr; |
|
|
|
recursion_guard = false; |
|
} |
|
|
|
int CWorkspaceManager::handleEvent( mxEvent *event ) |
|
{ |
|
int iret = 0; |
|
switch ( event->event ) |
|
{ |
|
default: |
|
break; |
|
case mxEvent::Activate: |
|
{ |
|
if (event->action) |
|
{ |
|
mx::setIdleWindow( this ); |
|
// Force reload of localization data |
|
OnChangeLanguage( GetLanguageId(), true ); |
|
} |
|
else |
|
{ |
|
mx::setIdleWindow( 0 ); |
|
} |
|
iret = 1; |
|
} |
|
break; |
|
case mxEvent::Idle: |
|
{ |
|
iret = 1; |
|
Frame(); |
|
} |
|
break; |
|
case mxEvent::KeyUp: |
|
{ |
|
if ( event->key == VK_F5 ) |
|
{ |
|
RefreshBrowsers(); |
|
} |
|
} |
|
break; |
|
case mxEvent::Action: |
|
{ |
|
iret = 1; |
|
switch ( event->action ) |
|
{ |
|
default: |
|
{ |
|
if ( event->action >= IDC_WSM_FILE_RECENT_WORKSPACE_START && |
|
event->action < IDC_WSM_FILE_RECENT_WORKSPACE_END ) |
|
{ |
|
OnRecentWorkspace( event->action - IDC_WSM_FILE_RECENT_WORKSPACE_START ); |
|
} |
|
else if ( event->action >= IDC_WSM_OPTIONS_LANGUAGESTART && |
|
event->action < IDC_WSM_OPTIONS_LANGUAGEEND ) |
|
{ |
|
OnChangeLanguage( event->action - IDC_WSM_OPTIONS_LANGUAGESTART ); |
|
} |
|
else |
|
{ |
|
iret = 0; |
|
} |
|
} |
|
break; |
|
case IDC_WSM_FILE_EXIT: |
|
{ |
|
mx::quit(); |
|
} |
|
break; |
|
case IDC_WSM_FILE_WS_REFRESH: |
|
{ |
|
RefreshBrowsers(); |
|
} |
|
break; |
|
case IDC_WSM_FILE_WS_NEW: |
|
{ |
|
OnNewWorkspace(); |
|
} |
|
break; |
|
case IDC_WSM_FILE_WS_OPEN: |
|
{ |
|
OnOpenWorkspace(); |
|
} |
|
break; |
|
case IDC_WSM_FILE_WS_CLOSE: |
|
{ |
|
OnCloseWorkspace(); |
|
} |
|
break; |
|
case IDC_WSM_FILE_WS_SAVE: |
|
{ |
|
OnSaveWorkspace(); |
|
} |
|
break; |
|
case IDC_WSM_FILE_WS_VSSPROPERTIES: |
|
{ |
|
OnChangeVSSProperites(); |
|
} |
|
break; |
|
case IDC_WSM_FILE_WS_CHECKOUT: |
|
{ |
|
OnCheckoutWorkspace(); |
|
} |
|
break; |
|
case IDC_WSM_FILE_WS_CHECKIN: |
|
{ |
|
OnCheckinWorkspace(); |
|
} |
|
break; |
|
case IDC_WSM_PROJECT_PRJ_NEW: |
|
{ |
|
OnNewProject(); |
|
} |
|
break; |
|
case IDC_WSM_PROJECT_PRJ_INSERT: |
|
{ |
|
OnInsertProject(); |
|
} |
|
break; |
|
case IDC_WSM_PROJECT_PRJ_REMOVE: |
|
{ |
|
OnRemoveProject(); |
|
} |
|
break; |
|
case IDC_WSM_PROJECT_PRJ_MODIFYCOMMENTS: |
|
{ |
|
OnModifyProjectComments(); |
|
} |
|
break; |
|
case IDC_WSM_PROJECT_SCENE_NEW: |
|
{ |
|
OnNewScene(); |
|
} |
|
break; |
|
case IDC_WSM_SOUNDENTRY_PLAY: |
|
{ |
|
OnSoundPlay(); |
|
} |
|
break; |
|
case IDC_WSM_SOUNDENTRY_TOGGLEVOICEDUCK: |
|
{ |
|
OnSoundToggleVoiceDuck(); |
|
} |
|
break; |
|
case IDC_WSM_SOUNDENTRY_EDITTEXT: |
|
{ |
|
OnSoundEditText(); |
|
} |
|
break; |
|
case IDC_WSM_SOUNDENTRY_PROPERTIES: |
|
{ |
|
OnSoundProperties(); |
|
} |
|
break; |
|
case IDC_WSM_SCENE_VCD_ADD: |
|
{ |
|
OnSceneAddVCD(); |
|
} |
|
break; |
|
case IDC_WSM_SCENE_VCD_REMOVE: |
|
{ |
|
OnSceneRemoveVCD(); |
|
} |
|
break; |
|
case IDC_WSM_SCENE_EDIT_COMMENTS: |
|
{ |
|
OnModifySceneComments(); |
|
} |
|
break; |
|
case IDC_WSM_VCD_EDIT_COMMENTS: |
|
{ |
|
OnModifyVCDComments(); |
|
} |
|
break; |
|
case IDC_WSM_SCENE_REMOVE: |
|
{ |
|
OnRemoveScene(); |
|
} |
|
break; |
|
case IDC_WSM_SOUNDENTRY_SHOWINBROWSERS: |
|
{ |
|
OnSoundShowInBrowsers(); |
|
} |
|
break; |
|
case IDC_WSM_SELECTION_CHECKOUT: |
|
{ |
|
OnCheckout(); |
|
} |
|
break; |
|
case IDC_WSM_SELECTION_CHECKIN: |
|
{ |
|
OnCheckin(); |
|
} |
|
break; |
|
case IDC_WSM_SELECTION_MOVEUP: |
|
{ |
|
OnMoveUp(); |
|
} |
|
break; |
|
case IDC_WSM_SELECTION_MOVEDOWN: |
|
{ |
|
OnMoveDown(); |
|
} |
|
break; |
|
case IDC_WSM_WAVEFILE_PROPERTIES: |
|
{ |
|
OnWaveProperties(); |
|
} |
|
break; |
|
} |
|
} |
|
break; |
|
case mxEvent::Size: |
|
{ |
|
iret = 1; |
|
PerformLayout( false ); |
|
} |
|
break; |
|
} |
|
|
|
return iret; |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::PerformLayout( bool movebrowsers ) |
|
{ |
|
int width = w2(); |
|
int height = h2(); |
|
|
|
int statush = 100; |
|
m_pWorkArea->setBounds( 0, 0, width, height - statush ); |
|
if ( movebrowsers ) |
|
{ |
|
GetBrowser()->setBounds( 0, 0, m_pWorkArea->w2(), m_pWorkArea->h2() / 3 ); |
|
if ( GetSoundBrowser() ) |
|
{ |
|
GetSoundBrowser()->setBounds( 0, m_pWorkArea->h2() / 3, m_pWorkArea->w2(), m_pWorkArea->h2() / 3 ); |
|
} |
|
if ( GetWaveBrowser() ) |
|
{ |
|
GetWaveBrowser()->setBounds( 0, 2 * m_pWorkArea->h2() / 3, m_pWorkArea->w2(), m_pWorkArea->h2() / 3 ); |
|
} |
|
} |
|
|
|
g_pStatusWindow->setBounds( 0, height - statush, width, statush ); |
|
|
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
// Output : Returns true on success, false on failure. |
|
//----------------------------------------------------------------------------- |
|
bool CWorkspaceManager::CloseWorkspace() |
|
{ |
|
CWorkspace *ws = GetBrowser()->GetWorkspace(); |
|
if ( !ws ) |
|
return true; |
|
|
|
if ( !ws->CanClose() ) |
|
return false; |
|
|
|
delete ws; |
|
|
|
SetWorkspace( NULL ); |
|
|
|
return true; |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::OnUpdateTitle( void ) |
|
{ |
|
CWorkspace *ws = GetBrowser()->GetWorkspace(); |
|
|
|
char szTitle[ 256 ]; |
|
if ( ws ) |
|
{ |
|
char const *fmt = g_appTitleFmt; |
|
if ( ws->IsDirty() ) |
|
{ |
|
fmt = g_appTitleFmtModified; |
|
} |
|
Q_snprintf( szTitle, sizeof( szTitle ), fmt, ws->GetName(), CSentence::NameForLanguage( m_nLanguageId ) ); |
|
} |
|
else |
|
{ |
|
Q_snprintf( szTitle, sizeof( szTitle ), g_appTitle ); |
|
} |
|
|
|
setLabel( szTitle ); |
|
|
|
UpdateMenus(); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
// Input : *ws - |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::SetWorkspace( CWorkspace *ws ) |
|
{ |
|
GetBrowser()->SetWorkspace( ws ); |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::OnNewWorkspace() |
|
{ |
|
// Show file io |
|
const char *fullpath = mxGetSaveFileName( |
|
0, |
|
".", |
|
"*.vsw" ); |
|
|
|
if ( !fullpath || !fullpath[ 0 ] ) |
|
return; |
|
|
|
// Strip game directory and slash |
|
char workspace_name[ 512 ]; |
|
filesystem->FullPathToRelativePath( fullpath, workspace_name, sizeof( workspace_name ) ); |
|
|
|
Q_StripExtension( workspace_name, workspace_name, sizeof( workspace_name ) ); |
|
Q_DefaultExtension( workspace_name, ".vsw", sizeof( workspace_name ) ); |
|
|
|
if ( filesystem->FileExists( workspace_name ) ) |
|
{ |
|
Con_Printf( "%s exists already!\n", workspace_name ); |
|
Assert( 0 ); |
|
return; |
|
} |
|
|
|
LoadWorkspace( workspace_name ); |
|
} |
|
|
|
void CWorkspaceManager::AddFileToRecentWorkspaceList( char const *filename ) |
|
{ |
|
int i; |
|
int c = m_RecentFiles.Count(); |
|
|
|
for ( i = 0; i < c; i++ ) |
|
{ |
|
if (!Q_stricmp( m_RecentFiles[i].filename, filename )) |
|
break; |
|
} |
|
|
|
// swap existing recent file |
|
if ( i < c ) |
|
{ |
|
RecentFile rf = m_RecentFiles[0]; |
|
m_RecentFiles[ 0 ] = m_RecentFiles[ i ]; |
|
m_RecentFiles[ i ] = rf; |
|
} |
|
// insert recent file |
|
else |
|
{ |
|
RecentFile rf; |
|
Q_strcpy( rf.filename, filename ); |
|
|
|
m_RecentFiles.AddToHead( rf ); |
|
} |
|
|
|
while( m_RecentFiles.Count() > GetMaxRecentFiles() ) |
|
{ |
|
m_RecentFiles.Remove( m_RecentFiles.Count() - 1 ); |
|
} |
|
|
|
UpdateRecentFilesMenu(); |
|
} |
|
|
|
void CWorkspaceManager::LoadRecentFilesMenuFromDisk() |
|
{ |
|
KeyValues *kv = new KeyValues( "recentfiles" ); |
|
if ( kv->LoadFromFile( filesystem, RECENT_FILES_FILE ) ) |
|
{ |
|
for ( KeyValues *sub = kv->GetFirstSubKey(); sub; sub = sub->GetNextKey() ) |
|
{ |
|
RecentFile rf; |
|
Q_strncpy( rf.filename, sub->GetString(), sizeof( rf ) ); |
|
m_RecentFiles.AddToTail( rf ); |
|
} |
|
} |
|
kv->deleteThis(); |
|
|
|
UpdateRecentFilesMenu(); |
|
} |
|
|
|
void CWorkspaceManager::AutoLoad( char const *workspace ) |
|
{ |
|
if ( workspace ) |
|
{ |
|
LoadWorkspace( workspace ); |
|
} |
|
else |
|
{ |
|
if ( m_RecentFiles.Count() > 0 ) |
|
{ |
|
LoadWorkspace( m_RecentFiles[ 0 ].filename ); |
|
} |
|
} |
|
} |
|
|
|
void CWorkspaceManager::SaveRecentFilesMenuToDisk() |
|
{ |
|
int i; |
|
int c = m_RecentFiles.Count(); |
|
|
|
CUtlBuffer buf( 0, 0, CUtlBuffer::TEXT_BUFFER ); |
|
|
|
buf.Printf( "recentfiles\n{\n" ); |
|
|
|
for ( i = 0; i < c; i++ ) |
|
{ |
|
buf.Printf( "\t\"%i\"\t\"%s\"\n", i + 1, m_RecentFiles[ i ].filename ); |
|
} |
|
|
|
buf.Printf( "}\n" ); |
|
|
|
char const *recentfiles = RECENT_FILES_FILE; |
|
|
|
// Write it out baby |
|
FileHandle_t fh = filesystem->Open( recentfiles, "wt" ); |
|
if (fh) |
|
{ |
|
filesystem->Write( buf.Base(), buf.TellPut(), fh ); |
|
filesystem->Close(fh); |
|
} |
|
else |
|
{ |
|
Con_Printf( "CWorkspace::SaveRecentFilesMenuToDisk: Unable to write file %s!!!\n", recentfiles ); |
|
} |
|
} |
|
|
|
void CWorkspaceManager::UpdateRecentFilesMenu() |
|
{ |
|
int c = m_RecentFiles.Count(); |
|
|
|
while ( c > m_nRecentMenuItems ) |
|
{ |
|
m_pRecentFileMenu->add( "(empty)", IDC_WSM_FILE_RECENT_WORKSPACE_START + m_nRecentMenuItems++ ); |
|
} |
|
|
|
for (int i = 0; i < c; i++) |
|
{ |
|
m_pMenuBar->modify (IDC_WSM_FILE_RECENT_WORKSPACE_START + i, IDC_WSM_FILE_RECENT_WORKSPACE_START + i, m_RecentFiles[i].filename ); |
|
} |
|
} |
|
|
|
void CWorkspaceManager::LoadWorkspace( char const *filename ) |
|
{ |
|
if ( !CloseWorkspace() ) |
|
return; |
|
|
|
Con_Printf( "Loading workspace %s\n", filename ); |
|
|
|
CWorkspace *wks = new CWorkspace( filename ); |
|
SetWorkspace( wks ); |
|
|
|
AddFileToRecentWorkspaceList( filename ); |
|
|
|
OnUpdateTitle(); |
|
|
|
UpdateMenus(); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::OnOpenWorkspace() |
|
{ |
|
// Show file io |
|
const char *fullpath = mxGetOpenFileName( |
|
0, |
|
".", |
|
"*.vsw" ); |
|
|
|
if ( !fullpath || !fullpath[ 0 ] ) |
|
return; |
|
|
|
// Strip game directory and slash |
|
char workspace_name[ 512 ]; |
|
filesystem->FullPathToRelativePath( fullpath, workspace_name, sizeof( workspace_name ) ); |
|
|
|
LoadWorkspace( workspace_name ); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::OnCloseWorkspace() |
|
{ |
|
if ( !CloseWorkspace() ) |
|
return; |
|
|
|
Con_Printf( "Closed workspace\n" ); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::OnSaveWorkspace() |
|
{ |
|
CWorkspace *ws = GetBrowser()->GetWorkspace(); |
|
if ( ws ) |
|
{ |
|
ws->SaveChanges(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::OnNewProject() |
|
{ |
|
Con_Printf( "OnNewProject()\n" ); |
|
|
|
// Show file io |
|
const char *fullpath = mxGetSaveFileName( |
|
0, |
|
".", |
|
"*.vsp" ); |
|
|
|
if ( !fullpath || !fullpath[ 0 ] ) |
|
return; |
|
|
|
// Strip game directory and slash |
|
char project_name[ 512 ]; |
|
filesystem->FullPathToRelativePath( fullpath, project_name, sizeof( project_name ) ); |
|
|
|
Q_StripExtension( project_name, project_name, sizeof( project_name ) ); |
|
Q_DefaultExtension( project_name, ".vsp", sizeof( project_name ) ); |
|
|
|
if ( filesystem->FileExists( project_name ) ) |
|
{ |
|
Con_Printf( "%s exists already!\n", project_name ); |
|
Assert( 0 ); |
|
return; |
|
} |
|
|
|
CWorkspace *ws = GetBrowser()->GetWorkspace(); |
|
if ( !ws ) |
|
{ |
|
// Create one on the fly |
|
char workspace_name[ 512 ]; |
|
Q_StripExtension( project_name, workspace_name, sizeof( workspace_name ) ); |
|
Q_DefaultExtension( workspace_name, ".vsw", sizeof( workspace_name ) ); |
|
|
|
if ( !filesystem->FileExists( workspace_name ) ) |
|
{ |
|
int retval = mxMessageBox( NULL, va( "Automatically create workspace %s?", workspace_name ), g_appTitle, MX_MB_YESNOCANCEL ); |
|
if ( retval != 0 ) |
|
{ |
|
Con_Printf( "Canceling project creation\n" ); |
|
return; |
|
} |
|
} |
|
else |
|
{ |
|
Con_Printf( "Found workspace '%s', automatically loading...\n", workspace_name ); |
|
} |
|
|
|
LoadWorkspace( workspace_name ); |
|
|
|
ws = GetBrowser()->GetWorkspace(); |
|
} |
|
|
|
if ( ws && ws->FindProjectFile( project_name ) ) |
|
{ |
|
Con_Printf( "Project %s already exists in workspace\n", project_name ); |
|
return; |
|
} |
|
|
|
// Create a new project and add it into current workspace |
|
CProject *proj = new CProject( ws, project_name ); |
|
Assert( proj ); |
|
Assert( ws ); |
|
|
|
if ( ws ) |
|
{ |
|
GetBrowser()->AddProject( proj ); |
|
} |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::OnInsertProject() |
|
{ |
|
Con_Printf( "OnInsertProject()\n" ); |
|
|
|
// Show file io |
|
const char *fullpath = mxGetOpenFileName( |
|
0, |
|
".", |
|
"*.vsp" ); |
|
|
|
if ( !fullpath || !fullpath[ 0 ] ) |
|
return; |
|
|
|
// Strip game directory and slash |
|
char project_name[ 512 ]; |
|
filesystem->FullPathToRelativePath( fullpath, project_name, sizeof( project_name ) ); |
|
|
|
Q_StripExtension( project_name, project_name, sizeof( project_name ) ); |
|
Q_DefaultExtension( project_name, ".vsp", sizeof( project_name ) ); |
|
|
|
CWorkspace *ws = GetBrowser()->GetWorkspace(); |
|
if ( !ws ) |
|
{ |
|
// Create one on the fly |
|
char workspace_name[ 512 ]; |
|
Q_StripExtension( project_name, workspace_name, sizeof( workspace_name ) ); |
|
Q_DefaultExtension( workspace_name, ".vsw", sizeof( workspace_name ) ); |
|
|
|
if ( !filesystem->FileExists( workspace_name ) ) |
|
{ |
|
int retval = mxMessageBox( NULL, va( "Automatically create workspace %s?", workspace_name ), g_appTitle, MX_MB_YESNOCANCEL ); |
|
if ( retval != 0 ) |
|
{ |
|
Con_Printf( "Canceling project creation\n" ); |
|
return; |
|
} |
|
} |
|
else |
|
{ |
|
Con_Printf( "Found workspace '%s', automatically loading...\n", workspace_name ); |
|
} |
|
|
|
LoadWorkspace( workspace_name ); |
|
|
|
ws = GetBrowser()->GetWorkspace(); |
|
} |
|
|
|
if ( ws && ws->FindProjectFile( project_name ) ) |
|
{ |
|
Con_Printf( "Project %s already exists in workspace\n", project_name ); |
|
return; |
|
} |
|
|
|
// Create a new project and add it into current workspace |
|
CProject *proj = new CProject( ws, project_name ); |
|
Assert( proj ); |
|
Assert( ws ); |
|
|
|
if ( ws ) |
|
{ |
|
GetBrowser()->AddProject( proj ); |
|
} |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::OnRemoveProject() |
|
{ |
|
Con_Printf( "OnRemoveProject()\n" ); |
|
|
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
CProject *project = item->GetProject(); |
|
if ( !project ) |
|
{ |
|
Con_Printf( "Can't remove project, item is not a project\n" ); |
|
return; |
|
} |
|
|
|
CWorkspace *ws = GetBrowser()->GetWorkspace(); |
|
if ( !ws ) |
|
{ |
|
Con_Printf( "Can't remove project '%s', no current workspace?!\n", |
|
project->GetName() ); |
|
return; |
|
} |
|
|
|
ws->RemoveProject( project ); |
|
Con_Printf( "Removed project '%s'\n", project->GetName() ); |
|
delete project; |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
void CWorkspaceManager::OnRemoveScene() |
|
{ |
|
Con_Printf( "OnRemoveScene()\n" ); |
|
|
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
CScene *scene = item->GetScene(); |
|
if ( !scene ) |
|
{ |
|
Con_Printf( "Can't remove scene, item is not a scene\n" ); |
|
return; |
|
} |
|
|
|
CProject *project = scene->GetOwnerProject(); |
|
if ( !project ) |
|
{ |
|
Con_Printf( "Can't remove scene '%s', no current owner project?!\n", |
|
scene->GetName() ); |
|
return; |
|
} |
|
|
|
project->RemoveScene( scene ); |
|
Con_Printf( "Removed scene '%s'\n", scene->GetName() ); |
|
delete scene; |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
void CWorkspaceManager::OnNewScene() |
|
{ |
|
Con_Printf( "OnNewScene()\n" ); |
|
|
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
CProject *project = item->GetProject(); |
|
if ( !project ) |
|
{ |
|
Con_Printf( "Can't add new scene, selected item is not a project\n" ); |
|
return; |
|
} |
|
|
|
CInputParams params; |
|
memset( ¶ms, 0, sizeof( params ) ); |
|
Q_snprintf( params.m_szDialogTitle, sizeof( params.m_szDialogTitle ), "Create scene in '%s'", project->GetName() ); |
|
Q_strcpy( params.m_szPrompt, "Scene Name:" ); |
|
Q_strcpy( params.m_szInputText, "" ); |
|
|
|
if ( !InputProperties( ¶ms ) ) |
|
return; |
|
|
|
if ( !params.m_szInputText[ 0 ] ) |
|
{ |
|
Con_Printf( "You must name the scene!\n" ); |
|
return; |
|
} |
|
|
|
CScene *scene = new CScene( project, params.m_szInputText ); |
|
Assert( scene ); |
|
|
|
project->AddScene( scene ); |
|
|
|
Con_Printf( "Added scene '%s' to project '%s'\n", scene->GetName(), |
|
project->GetName() ); |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::OnModifyProjectComments() |
|
{ |
|
Con_Printf( "OnModifyProjectComments()\n" ); |
|
|
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
CProject *project = item->GetProject(); |
|
if ( !project ) |
|
{ |
|
Con_Printf( "Can't modify comments, item is not a project\n" ); |
|
return; |
|
} |
|
|
|
CInputParams params; |
|
memset( ¶ms, 0, sizeof( params ) ); |
|
Q_snprintf( params.m_szDialogTitle, sizeof( params.m_szDialogTitle ), "Edit comments for '%s'", project->GetName() ); |
|
Q_strcpy( params.m_szPrompt, "Comments:" ); |
|
Q_strncpy( params.m_szInputText, project->GetComments(), sizeof( params.m_szInputText ) ); |
|
|
|
if ( !InputProperties( ¶ms ) ) |
|
return; |
|
|
|
if ( !Q_strcmp( params.m_szInputText, project->GetComments() ) ) |
|
return; |
|
|
|
project->SetComments( params.m_szInputText ); |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
// Input : index - |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::OnRecentWorkspace( int index ) |
|
{ |
|
if ( index < 0 || index >= m_RecentFiles.Count() ) |
|
return; |
|
|
|
LoadWorkspace( m_RecentFiles[ index ].filename ); |
|
} |
|
|
|
int CWorkspaceManager::GetLanguageId() const |
|
{ |
|
return m_nLanguageId; |
|
} |
|
|
|
void CWorkspaceManager::OnChangeLanguage( int lang_index, bool force /* = false */ ) |
|
{ |
|
bool changed = m_nLanguageId != lang_index; |
|
m_nLanguageId = lang_index; |
|
|
|
if ( changed || force ) |
|
{ |
|
// Update the menu |
|
for ( int i = 0; i < CC_NUM_LANGUAGES; i++ ) |
|
{ |
|
int id = IDC_WSM_OPTIONS_LANGUAGESTART + i; |
|
m_pMenuCloseCaptionLanguages->setChecked( id, i == m_nLanguageId ); |
|
} |
|
|
|
bool filechanged = false; |
|
|
|
char const *suffix = CSentence::NameForLanguage( lang_index ); |
|
if ( Q_stricmp( suffix, "unknown_language" ) ) |
|
{ |
|
char fn[ MAX_PATH ]; |
|
Q_snprintf( fn, sizeof( fn ), "resource/closecaption_%s.txt", suffix ); |
|
|
|
long filetimestamp = filesystem->GetFileTime( fn ); |
|
|
|
|
|
if ( filesystem->FileExists( fn ) ) |
|
{ |
|
if ( m_lEnglishCaptionsFileChangeTime != filetimestamp ) |
|
{ |
|
filechanged = true; |
|
m_lEnglishCaptionsFileChangeTime = filetimestamp; |
|
//Con_Printf( "Reloading close caption data from '%s'\n", fn ); |
|
g_pVGuiLocalize->RemoveAll(); |
|
g_pVGuiLocalize->AddFile( fn ); |
|
} |
|
} |
|
else |
|
{ |
|
Con_Printf( "CWorkspaceManager::OnChangeLanguage Warning, can't find localization file %s\n", fn ); |
|
} |
|
} |
|
|
|
if ( !force || filechanged ) |
|
{ |
|
// Update all text for items. |
|
RefreshBrowsers(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
} |
|
} |
|
|
|
void CWorkspaceManager::OnDoubleClicked( ITreeItem *item ) |
|
{ |
|
CSoundEntry *s = item->GetSoundEntry(); |
|
if ( s ) |
|
{ |
|
s->Play(); |
|
return; |
|
} |
|
} |
|
|
|
void CWorkspaceManager::OnSoundPlay() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( item->GetSoundEntry() ) |
|
{ |
|
item->GetSoundEntry()->Play(); |
|
} |
|
else if ( item->GetWaveFile() ) |
|
{ |
|
item->GetWaveFile()->Play(); |
|
} |
|
} |
|
|
|
void CWorkspaceManager::OnSoundToggleVoiceDuck() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( item->GetWaveFile() ) |
|
{ |
|
item->GetWaveFile()->ToggleVoiceDucking(); |
|
} |
|
} |
|
|
|
void CWorkspaceManager::OnSoundEditText() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
CWaveFile *s = item->GetWaveFile(); |
|
if ( !s ) |
|
return; |
|
|
|
CInputParams params; |
|
memset( ¶ms, 0, sizeof( params ) ); |
|
Q_snprintf( params.m_szDialogTitle, sizeof( params.m_szDialogTitle ), "Edit text of '%s'", s->GetName() ); |
|
Q_strcpy( params.m_szPrompt, "Sentence text:" ); |
|
V_strcpy_safe( params.m_szInputText, s->GetSentenceText() ); |
|
|
|
if ( !InputProperties( ¶ms ) ) |
|
return; |
|
|
|
if ( !Q_stricmp( params.m_szInputText, s->GetSentenceText() ) ) |
|
{ |
|
return; |
|
} |
|
|
|
s->SetSentenceText( params.m_szInputText ); |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
// Scene entries |
|
void CWorkspaceManager::OnSceneAddVCD() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
CScene *scene = item->GetScene(); |
|
if ( !scene ) |
|
return; |
|
|
|
// Show file io |
|
const char *fullpath = mxGetOpenFileName( |
|
0, |
|
".", |
|
"*.vcd" ); |
|
|
|
if ( !fullpath || !fullpath[ 0 ] ) |
|
return; |
|
|
|
// Strip game directory and slash |
|
char vcd_name[ 512 ]; |
|
filesystem->FullPathToRelativePath( fullpath, vcd_name, sizeof( vcd_name ) ); |
|
|
|
Q_StripExtension( vcd_name, vcd_name, sizeof( vcd_name ) ); |
|
Q_DefaultExtension( vcd_name, ".vcd", sizeof( vcd_name ) ); |
|
|
|
if ( scene->FindVCD( vcd_name ) ) |
|
{ |
|
Con_Printf( "File '%s' is already in scene '%s'\n", vcd_name, scene->GetName() ); |
|
return; |
|
} |
|
|
|
CVCDFile *vcd = new CVCDFile( scene, vcd_name ); |
|
|
|
scene->AddVCD( vcd ); |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
void CWorkspaceManager::OnModifySceneComments() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
CScene *scene = item->GetScene(); |
|
if ( !scene ) |
|
return; |
|
|
|
CInputParams params; |
|
memset( ¶ms, 0, sizeof( params ) ); |
|
Q_snprintf( params.m_szDialogTitle, sizeof( params.m_szDialogTitle ), "Edit comments for '%s'", scene->GetName() ); |
|
Q_strcpy( params.m_szPrompt, "Comments:" ); |
|
Q_strncpy( params.m_szInputText, scene->GetComments(), sizeof( params.m_szInputText ) ); |
|
|
|
if ( !InputProperties( ¶ms ) ) |
|
return; |
|
|
|
if ( !Q_strcmp( params.m_szInputText, scene->GetComments() ) ) |
|
return; |
|
|
|
scene->SetComments( params.m_szInputText ); |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
void CWorkspaceManager::OnModifyVCDComments() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
CVCDFile *file = item->GetVCDFile(); |
|
if ( !file ) |
|
return; |
|
|
|
CInputParams params; |
|
memset( ¶ms, 0, sizeof( params ) ); |
|
Q_snprintf( params.m_szDialogTitle, sizeof( params.m_szDialogTitle ), "Edit comments for '%s'", file->GetName() ); |
|
Q_strcpy( params.m_szPrompt, "Comments:" ); |
|
Q_strncpy( params.m_szInputText, file->GetComments(), sizeof( params.m_szInputText ) ); |
|
|
|
if ( !InputProperties( ¶ms ) ) |
|
return; |
|
|
|
if ( !Q_strcmp( params.m_szInputText, file->GetComments() ) ) |
|
return; |
|
|
|
file->SetComments( params.m_szInputText ); |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
void CWorkspaceManager::OnSceneRemoveVCD() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
CVCDFile *file = item->GetVCDFile(); |
|
if ( !file ) |
|
return; |
|
|
|
CScene *scene = file->GetOwnerScene(); |
|
if ( !scene ) |
|
return; |
|
|
|
scene->RemoveVCD( file ); |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
void CWorkspaceManager::ShowContextMenu( int x, int y, ITreeItem *p ) |
|
{ |
|
CWorkspace *w = p->GetWorkspace(); |
|
if ( w ) |
|
{ |
|
ShowContextMenu_Workspace( x, y, w ); |
|
return; |
|
} |
|
|
|
CProject *proj = p->GetProject(); |
|
if ( proj ) |
|
{ |
|
ShowContextMenu_Project( x, y, proj ); |
|
return; |
|
} |
|
|
|
CScene *scene = p->GetScene(); |
|
if ( scene ) |
|
{ |
|
ShowContextMenu_Scene( x, y, scene ); |
|
return; |
|
} |
|
|
|
CVCDFile *vcd = p->GetVCDFile(); |
|
if ( vcd ) |
|
{ |
|
ShowContextMenu_VCD( x, y, vcd ); |
|
return; |
|
} |
|
|
|
CSoundEntry *sound = p->GetSoundEntry(); |
|
if ( sound ) |
|
{ |
|
ShowContextMenu_SoundEntry( x, y, sound ); |
|
return; |
|
} |
|
|
|
CWaveFile *wave = p->GetWaveFile(); |
|
if ( wave ) |
|
{ |
|
ShowContextMenu_WaveFile( x, y, wave ); |
|
return; |
|
} |
|
|
|
Con_Printf( "unknown tree item type\n" ); |
|
Assert( 0 ); |
|
} |
|
|
|
void CWorkspaceManager::ShowContextMenu_Workspace( int x, int y, CWorkspace *ws ) |
|
{ |
|
if ( !ws ) |
|
return; |
|
|
|
// New project and insert project |
|
mxPopupMenu *pop = new mxPopupMenu(); |
|
|
|
pop->add ("Create New Project...", IDC_WSM_PROJECT_PRJ_NEW ); |
|
pop->add ("Insert Project...", IDC_WSM_PROJECT_PRJ_INSERT ); |
|
pop->addSeparator(); |
|
pop->add( "VSS Properties...", IDC_WSM_FILE_WS_VSSPROPERTIES ); |
|
|
|
if ( !filesystem->IsFileWritable( ws->GetFileName() ) ) |
|
{ |
|
pop->add( va( "Checkout '%s'", ws->GetName() ), IDC_WSM_SELECTION_CHECKOUT ); |
|
} |
|
else |
|
{ |
|
pop->add( va( "Checkin '%s'", ws->GetName() ), IDC_WSM_SELECTION_CHECKIN ); |
|
} |
|
|
|
pop->popup( this, x, y ); |
|
} |
|
|
|
void CWorkspaceManager::ShowContextMenu_Project( int x, int y, CProject *project ) |
|
{ |
|
// New scene, edit comments |
|
mxPopupMenu *pop = new mxPopupMenu(); |
|
|
|
pop->add ("Create New Scene...", IDC_WSM_PROJECT_SCENE_NEW ); |
|
pop->addSeparator(); |
|
pop->add ("Remove Project...", IDC_WSM_PROJECT_PRJ_REMOVE ); |
|
pop->addSeparator(); |
|
pop->add( "Edit comments...", IDC_WSM_PROJECT_PRJ_MODIFYCOMMENTS ); |
|
if ( !project->IsFirstChild() || !project->IsLastChild() ) |
|
{ |
|
pop->addSeparator(); |
|
if( !project->IsFirstChild() ) |
|
{ |
|
pop->add( va( "Move '%s' Up", project->GetName() ), IDC_WSM_SELECTION_MOVEUP ); |
|
} |
|
if( !project->IsLastChild() ) |
|
{ |
|
pop->add( va( "Move '%s' Down", project->GetName() ), IDC_WSM_SELECTION_MOVEDOWN ); |
|
} |
|
} |
|
pop->addSeparator(); |
|
|
|
if ( !filesystem->IsFileWritable( project->GetFileName() ) ) |
|
{ |
|
pop->add( va( "Checkout '%s'", project->GetName() ), IDC_WSM_SELECTION_CHECKOUT ); |
|
} |
|
else |
|
{ |
|
pop->add( va( "Checkin '%s'", project->GetName() ), IDC_WSM_SELECTION_CHECKIN ); |
|
} |
|
|
|
pop->popup( this, x, y ); |
|
} |
|
|
|
void CWorkspaceManager::ShowContextMenu_Scene( int x, int y, CScene *scene ) |
|
{ |
|
// New scene, edit comments |
|
mxPopupMenu *pop = new mxPopupMenu(); |
|
|
|
pop->add( va( "Add VCD to '%s'...", scene->GetName() ), IDC_WSM_SCENE_VCD_ADD ); |
|
pop->addSeparator(); |
|
pop->add ("Remove Scene", IDC_WSM_SCENE_REMOVE ); |
|
pop->addSeparator(); |
|
pop->add( va( "Edit comments..." ), IDC_WSM_SCENE_EDIT_COMMENTS ); |
|
if ( !scene->IsFirstChild() || !scene->IsLastChild() ) |
|
{ |
|
pop->addSeparator(); |
|
if( !scene->IsFirstChild() ) |
|
{ |
|
pop->add( va( "Move '%s' Up", scene->GetName() ), IDC_WSM_SELECTION_MOVEUP ); |
|
} |
|
if( !scene->IsLastChild() ) |
|
{ |
|
pop->add( va( "Move '%s' Down", scene->GetName() ), IDC_WSM_SELECTION_MOVEDOWN ); |
|
} |
|
} |
|
|
|
pop->popup( this, x, y ); |
|
} |
|
|
|
void CWorkspaceManager::ShowContextMenu_VCD( int x, int y, CVCDFile *vcd ) |
|
{ |
|
// New scene, edit comments |
|
mxPopupMenu *pop = new mxPopupMenu(); |
|
|
|
pop->add( va( "Remove VCD" ), IDC_WSM_SCENE_VCD_REMOVE ); |
|
pop->addSeparator(); |
|
pop->add( va( "Edit comments..." ), IDC_WSM_VCD_EDIT_COMMENTS ); |
|
if ( !vcd->IsFirstChild() || !vcd->IsLastChild() ) |
|
{ |
|
pop->addSeparator(); |
|
if( !vcd->IsFirstChild() ) |
|
{ |
|
pop->add( va( "Move '%s' Up", vcd->GetName() ), IDC_WSM_SELECTION_MOVEUP ); |
|
} |
|
if( !vcd->IsLastChild() ) |
|
{ |
|
pop->add( va( "Move '%s' Down", vcd->GetName() ), IDC_WSM_SELECTION_MOVEDOWN ); |
|
} |
|
} |
|
pop->addSeparator(); |
|
if ( !filesystem->IsFileWritable( vcd->GetName() ) ) |
|
{ |
|
pop->add( va( "Checkout '%s'", vcd->GetName() ), IDC_WSM_SELECTION_CHECKOUT ); |
|
} |
|
else |
|
{ |
|
pop->add( va( "Checkin '%s'", vcd->GetName() ), IDC_WSM_SELECTION_CHECKIN ); |
|
} |
|
|
|
pop->popup( this, x, y ); |
|
} |
|
|
|
void CWorkspaceManager::ShowContextMenu_SoundEntry( int x, int y, CSoundEntry *entry ) |
|
{ |
|
// New scene, edit comments |
|
mxPopupMenu *pop = new mxPopupMenu(); |
|
|
|
pop->add ("&Play", IDC_WSM_SOUNDENTRY_PLAY ); |
|
// pop->add( "&Jump To", IDC_WSM_SOUNDENTRY_SHOWINBROWSERS ); |
|
pop->addSeparator(); |
|
|
|
pop->add( "Properties...", IDC_WSM_SOUNDENTRY_PROPERTIES ); |
|
|
|
pop->popup( this, x, y ); |
|
} |
|
|
|
void CWorkspaceManager::ShowContextMenu_WaveFile( int x, int y, CWaveFile *entry ) |
|
{ |
|
// New scene, edit comments |
|
mxPopupMenu *pop = new mxPopupMenu(); |
|
|
|
pop->add ("&Play", IDC_WSM_SOUNDENTRY_PLAY ); |
|
// pop->add( "&Jump To", IDC_WSM_SOUNDENTRY_SHOWINBROWSERS ); |
|
|
|
if ( entry->GetVoiceDuck() ) |
|
{ |
|
pop->add ("Disable &voice duck", IDC_WSM_SOUNDENTRY_TOGGLEVOICEDUCK ); |
|
} |
|
else |
|
{ |
|
pop->add ("Enable &voice duck", IDC_WSM_SOUNDENTRY_TOGGLEVOICEDUCK ); |
|
} |
|
pop->add( "&Edit sentence text...", IDC_WSM_SOUNDENTRY_EDITTEXT ); |
|
pop->addSeparator(); |
|
if ( !filesystem->IsFileWritable( entry->GetFileName() ) ) |
|
{ |
|
pop->add( va( "Checkout '%s'", entry->GetName() ), IDC_WSM_SELECTION_CHECKOUT ); |
|
} |
|
else |
|
{ |
|
pop->add( va( "Checkin '%s'", entry->GetName() ), IDC_WSM_SELECTION_CHECKIN ); |
|
} |
|
pop->addSeparator(); |
|
pop->add( "Properties...", IDC_WSM_WAVEFILE_PROPERTIES ); |
|
|
|
pop->popup( this, x, y ); |
|
} |
|
|
|
|
|
void CWorkspaceManager::OnChangeVSSProperites() |
|
{ |
|
CWorkspace *ws = GetBrowser()->GetWorkspace(); |
|
if ( !ws ) |
|
{ |
|
return; |
|
} |
|
|
|
CVSSParams params; |
|
memset( ¶ms, 0, sizeof( params ) ); |
|
Q_snprintf( params.m_szDialogTitle, sizeof( params.m_szDialogTitle ), "VSS Properites" ); |
|
V_strcpy_safe( params.m_szUserName, ws->GetVSSUserName() ); |
|
V_strcpy_safe( params.m_szProject, ws->GetVSSProject() ); |
|
|
|
if ( !VSSProperties( ¶ms ) ) |
|
return; |
|
|
|
if ( !params.m_szUserName[ 0 ] ) |
|
{ |
|
Con_Printf( "You must enter a user name\n" ); |
|
return; |
|
} |
|
|
|
if ( !params.m_szProject[ 0 ] ) |
|
{ |
|
Con_Printf( "You must enter a project name\n" ); |
|
return; |
|
} |
|
|
|
ws->SetVSSUserName( params.m_szUserName ); |
|
ws->SetVSSProject( params.m_szProject ); |
|
|
|
ws->SetDirty( true ); |
|
|
|
Con_Printf( "VSS user = '%s', project = '%s'\n", |
|
ws->GetVSSUserName(), ws->GetVSSProject() ); |
|
} |
|
|
|
void CWorkspaceManager::OnCheckoutWorkspace() |
|
{ |
|
CWorkspace *ws = GetBrowser()->GetWorkspace(); |
|
if ( !ws ) |
|
{ |
|
return; |
|
} |
|
|
|
ws->Checkout(); |
|
} |
|
|
|
void CWorkspaceManager::OnCheckinWorkspace() |
|
{ |
|
CWorkspace *ws = GetBrowser()->GetWorkspace(); |
|
if ( !ws ) |
|
{ |
|
return; |
|
} |
|
|
|
ws->Checkin(); |
|
} |
|
|
|
|
|
#define CX_ICON 16 |
|
#define CY_ICON 16 |
|
|
|
HIMAGELIST CWorkspaceManager::CreateImageList() |
|
{ |
|
HIMAGELIST list; |
|
|
|
list = ImageList_Create( CX_ICON, CY_ICON, |
|
FALSE, NUM_IMAGES, 0 ); |
|
|
|
// Load the icon resources, and add the icons to the image list. |
|
HICON hicon; |
|
int slot; |
|
#if defined( DBGFLAG_ASSERT ) |
|
int c = 0; |
|
#endif |
|
|
|
hicon = LoadIcon( GetModuleHandle( 0 ), MAKEINTRESOURCE(IDI_WORKSPACE)); |
|
slot = ImageList_AddIcon(list, hicon); |
|
Assert( slot == c++ ); |
|
DeleteObject( hicon ); |
|
|
|
hicon = LoadIcon( GetModuleHandle( 0 ), MAKEINTRESOURCE(IDI_WORKSPACE_CHECKEDOUT)); |
|
slot = ImageList_AddIcon(list, hicon); |
|
Assert( slot == c++ ); |
|
DeleteObject( hicon ); |
|
|
|
hicon = LoadIcon(GetModuleHandle( 0 ), MAKEINTRESOURCE(IDI_PROJECT)); |
|
slot = ImageList_AddIcon(list, hicon); |
|
Assert( slot == c++ ); |
|
DeleteObject( hicon ); |
|
|
|
hicon = LoadIcon(GetModuleHandle( 0 ), MAKEINTRESOURCE(IDI_PROJECT_CHECKEDOUT)); |
|
slot = ImageList_AddIcon(list, hicon); |
|
Assert( slot == c++ ); |
|
DeleteObject( hicon ); |
|
|
|
hicon = LoadIcon(GetModuleHandle( 0 ), MAKEINTRESOURCE(IDI_SCENE)); |
|
slot = ImageList_AddIcon(list, hicon); |
|
Assert( slot == c++ ); |
|
DeleteObject( hicon ); |
|
|
|
// hicon = LoadIcon(GetModuleHandle( 0 ), MAKEINTRESOURCE(IDI_SCENE_CHECKEDOUT)); |
|
// slot = ImageList_AddIcon(list, hicon); |
|
// Assert( slot == c++ ); |
|
// DeleteObject( hicon ); |
|
|
|
hicon = LoadIcon(GetModuleHandle( 0 ), MAKEINTRESOURCE(IDI_VCD)); |
|
slot = ImageList_AddIcon(list, hicon); |
|
Assert( slot == c++ ); |
|
DeleteObject( hicon ); |
|
|
|
hicon = LoadIcon(GetModuleHandle( 0 ), MAKEINTRESOURCE(IDI_VCD_CHECKEDOUT )); |
|
slot = ImageList_AddIcon(list, hicon); |
|
Assert( slot == c++ ); |
|
DeleteObject( hicon ); |
|
|
|
hicon = LoadIcon(GetModuleHandle( 0 ), MAKEINTRESOURCE(IDI_WAV)); |
|
slot = ImageList_AddIcon(list, hicon); |
|
Assert( slot == c++ ); |
|
DeleteObject( hicon ); |
|
|
|
hicon = LoadIcon(GetModuleHandle( 0 ), MAKEINTRESOURCE(IDI_WAV_CHECKEDOUT)); |
|
slot = ImageList_AddIcon(list, hicon); |
|
Assert( slot == c++ ); |
|
DeleteObject( hicon ); |
|
|
|
hicon = LoadIcon(GetModuleHandle( 0 ), MAKEINTRESOURCE(IDI_SPEAK)); |
|
slot = ImageList_AddIcon(list, hicon); |
|
Assert( slot == c++ ); |
|
DeleteObject( hicon ); |
|
|
|
hicon = LoadIcon(GetModuleHandle( 0 ), MAKEINTRESOURCE(IDI_SPEAK_CHECKEDOUT)); |
|
slot = ImageList_AddIcon(list, hicon); |
|
Assert( slot == c++ ); |
|
DeleteObject( hicon ); |
|
|
|
return list; |
|
} |
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::RefreshBrowsers() |
|
{ |
|
if ( GetBrowser() ) |
|
{ |
|
GetBrowser()->PopulateTree(); |
|
} |
|
|
|
if ( GetSoundBrowser() ) |
|
{ |
|
GetSoundBrowser()->RepopulateTree(); |
|
} |
|
|
|
if ( GetWaveBrowser() ) |
|
{ |
|
GetWaveBrowser()->RepopulateTree(); |
|
} |
|
} |
|
|
|
void CWorkspaceManager::OnSoundShowInBrowsers() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
CSoundEntry *se = item->GetSoundEntry(); |
|
if ( se ) |
|
{ |
|
GetSoundBrowser()->JumpToItem( se ); |
|
return; |
|
} |
|
|
|
CWaveFile *wave = item->GetWaveFile(); |
|
if ( wave ) |
|
{ |
|
GetWaveBrowser()->JumpToItem( wave ); |
|
if ( wave->GetOwnerSoundEntry() ) |
|
{ |
|
GetSoundBrowser()->JumpToItem( wave->GetOwnerSoundEntry() ); |
|
} |
|
} |
|
} |
|
|
|
void CWorkspaceManager::OnCheckout() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
item->Checkout(); |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
void CWorkspaceManager::OnCheckin() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
item->Checkin(); |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
} |
|
|
|
void CWorkspaceManager::OnMoveUp() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
ITreeItem *parent = item->GetParentItem(); |
|
if ( !parent ) |
|
return; |
|
|
|
parent->MoveChildUp( item ); |
|
|
|
parent->SetDirty( true ); |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
|
|
GetBrowser()->JumpTo( item ); |
|
} |
|
|
|
void CWorkspaceManager::OnMoveDown() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
ITreeItem *parent = item->GetParentItem(); |
|
if ( !parent ) |
|
return; |
|
|
|
parent->MoveChildDown( item ); |
|
|
|
parent->SetDirty( true ); |
|
|
|
GetBrowser()->PopulateTree(); |
|
|
|
OnUpdateTitle(); |
|
|
|
GetBrowser()->JumpTo( item ); |
|
} |
|
|
|
void CWorkspaceManager::SetWorkspaceDirty() |
|
{ |
|
CWorkspace *ws = GetBrowser()->GetWorkspace(); |
|
if ( ws ) |
|
{ |
|
ws->SetDirty( true ); |
|
} |
|
OnUpdateTitle(); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::OnSoundProperties() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
CSoundEntry *entry = item->GetSoundEntry(); |
|
if ( !entry ) |
|
return; |
|
|
|
CSoundParams params; |
|
memset( ¶ms, 0, sizeof( params ) ); |
|
|
|
Q_snprintf( params.m_szDialogTitle, sizeof( params.m_szDialogTitle ), "Sound Properties" ); |
|
|
|
params.items.AddToTail( entry ); |
|
|
|
SoundProperties( ¶ms ); |
|
} |
|
|
|
|
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CWorkspaceManager::OnWaveProperties() |
|
{ |
|
ITreeItem *item = GetBrowser()->GetSelectedItem(); |
|
if ( !item ) |
|
return; |
|
|
|
CWaveFile *wave = item->GetWaveFile(); |
|
if ( !wave ) |
|
return; |
|
|
|
CWaveParams params; |
|
memset( ¶ms, 0, sizeof( params ) ); |
|
|
|
Q_snprintf( params.m_szDialogTitle, sizeof( params.m_szDialogTitle ), "Wave Properties" ); |
|
|
|
params.items.AddToTail( wave ); |
|
|
|
WaveProperties( ¶ms ); |
|
}
|
|
|