/* ** Command & Conquer Renegade(tm) ** Copyright 2025 Electronic Arts Inc. ** ** This program is free software: you can redistribute it and/or modify ** it under the terms of the GNU General Public License as published by ** the Free Software Foundation, either version 3 of the License, or ** (at your option) any later version. ** ** This program is distributed in the hope that it will be useful, ** but WITHOUT ANY WARRANTY; without even the implied warranty of ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ** GNU General Public License for more details. ** ** You should have received a copy of the GNU General Public License ** along with this program. If not, see . */ // W3DView.cpp : Defines the class behaviors for the application. // #include "stdafx.h" #include "w3dview.h" #include "mainfrm.h" #include "w3dviewdoc.h" #include "w3dviewview.h" #include "utils.h" #include "colorutils.h" #include "verchk.h" #include "wwmath.h" #include "wwaudio.h" #include "viewerassetmgr.h" #include "globals.h" #include "animatedsoundoptionsdialog.h" #include "animatedsoundmgr.h" #undef STRICT #include "ww3d.h" #include "AssetMgr.H" #ifdef _DEBUG #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif ///////////////////////////////////////////////////////////////////////////// // // Local prototypes // BOOL CALLBACK fnTopLevelWindowSearch (HWND hwnd, LPARAM lParam); ///////////////////////////////////////////////////////////////////////////// // // CW3DViewApp // BEGIN_MESSAGE_MAP(CW3DViewApp, CWinApp) //{{AFX_MSG_MAP(CW3DViewApp) ON_COMMAND(ID_APP_ABOUT, OnAppAbout) // NOTE - the ClassWizard will add and remove mapping macros here. // DO NOT EDIT what you see in these blocks of generated code! //}}AFX_MSG_MAP // Standard file based document commands ON_COMMAND(ID_FILE_NEW, CWinApp::OnFileNew) ON_COMMAND(ID_FILE_OPEN, CWinApp::OnFileOpen) END_MESSAGE_MAP() ///////////////////////////////////////////////////////////////////////////// // // CW3DViewApp construction // CW3DViewApp::CW3DViewApp (void) : m_bInitialized (false) { // TODO: add construction code here, // Place all significant initialization in InitInstance } ///////////////////////////////////////////////////////////////////////////// // The one and only CW3DViewApp object CW3DViewApp theApp; extern int AFXAPI AfxWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPTSTR lpCmdLine, int nCmdShow); int WINAPI WinMain ( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPTSTR lpCmdLine, int nCmdShow ) { int retcode = 0; #ifndef _DEBUG try { #endif //_DEBUG //::AfxWinInit (hInstance, hPrevInstance, lpCmdLine, nCmdShow); //::AfxInitialize (FALSE, _MFC_VER); AFX_MODULE_STATE* pModuleState = AfxGetModuleState(); pModuleState->m_bDLL = (BYTE)FALSE; #ifdef _MBCS // set correct multi-byte code-page for Win32 apps _setmbcp(_MB_CP_ANSI); #endif //_MBCS retcode = ::AfxWinMain (hInstance, hPrevInstance, lpCmdLine, nCmdShow); #ifndef _DEBUG } catch (...) { ::MessageBox (NULL, "Internal Application Error", "Unrecoverable Error", MB_ICONERROR | MB_OK); } #endif //_DEBUG return retcode; } /////////////////////////////////////////////////////////////// // // Do_Version_Check // //////////////////////////////////////////////////////////// void Do_Version_Check (void) { char curr_filename[MAX_PATH]; ::GetModuleFileName (NULL, curr_filename, MAX_PATH); CString filename = "\\\\cabal\\mis\\r&d\\w3d\\w3dview\\"; filename += ::Get_Filename_From_Path (curr_filename); // // Check the version of the viewer that is out on the network // against the version we are running. // if (Compare_EXE_Version ((int)::AfxGetInstanceHandle (), filename) < 0) { ::MessageBox (NULL, "There is a newer version of the W3DViewer, please run W3DUpdate to upgrade your local copy.", "Version Info", MB_ICONEXCLAMATION | MB_OK | MB_SETFOREGROUND | MB_SYSTEMMODAL); } return ; } ///////////////////////////////////////////////////////////////////////////// // // InitInstance // BOOL CW3DViewApp::InitInstance (void) { // Standard initialization // If you are not using these features and wish to reduce the size // of your final executable, you should remove from the following // the specific initialization routines you do not need. #ifdef _AFXDLL Enable3dControls(); // Call this when using MFC in a shared DLL #else Enable3dControlsStatic(); // Call this when linking to MFC statically #endif Do_Version_Check (); RegisterColorPicker (::AfxGetInstanceHandle ()); RegisterColorBar (::AfxGetInstanceHandle ()); // Is there already an instance of the viewer running? HWND hprev_instance = NULL; ::EnumWindows (fnTopLevelWindowSearch, (LPARAM)&hprev_instance); if (hprev_instance == NULL) { // Change the registry key under which our settings are stored. // You should modify this string to be something appropriate // such as the name of your company or organization. SetRegistryKey(_T("Westwood Studios")); // // Load standard INI file options (including MRU) // LoadStdProfileSettings (9); // // Initialize the libraries // WWMath::Init (); AnimatedSoundOptionsDialogClass::Load_Animated_Sound_Settings (); // // Disable the 3DFX logo // _putenv ("FX_GLIDE_NO_SPLASH=1"); // Register the application's document templates. Document templates // serve as the connection between documents, frame windows and views. CSingleDocTemplate* pDocTemplate; pDocTemplate = new CSingleDocTemplate( IDR_MAINFRAME, RUNTIME_CLASS(CW3DViewDoc), RUNTIME_CLASS(CMainFrame), // main SDI frame window RUNTIME_CLASS(CW3DViewView)); AddDocTemplate(pDocTemplate); // Enable DDE Execute open EnableShellOpen(); RegisterShellFileTypes(TRUE); // Parse command line for standard shell commands, DDE, file open CCommandLineInfo cmdInfo; ParseCommandLine(cmdInfo); // // Allocate an asset manager // _TheAssetMgr = new ViewerAssetMgrClass; // Dispatch commands specified on the command line if (!ProcessShellCommand(cmdInfo)) return FALSE; // The one and only window has been initialized, so show and update it. m_pMainWnd->ShowWindow(SW_SHOW); m_pMainWnd->UpdateWindow(); ::SetProp (*m_pMainWnd, "WW3DVIEWER", (HANDLE)1); // Enable drag/drop open m_pMainWnd->DragAcceptFiles(); m_bInitialized = true; } else { // Make the previous instance in the foreground ::ShowWindow (hprev_instance, SW_NORMAL); ::BringWindowToTop (hprev_instance); ::SetForegroundWindow (hprev_instance); } return (hprev_instance == NULL); } ///////////////////////////////////////////////////////////////////////////// // CAboutDlg dialog used for App About class CAboutDlg : public CDialog { public: CAboutDlg(); // Dialog Data //{{AFX_DATA(CAboutDlg) enum { IDD = IDD_ABOUTBOX }; //}}AFX_DATA // ClassWizard generated virtual function overrides //{{AFX_VIRTUAL(CAboutDlg) protected: virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support //}}AFX_VIRTUAL // Implementation protected: //{{AFX_MSG(CAboutDlg) virtual BOOL OnInitDialog(); //}}AFX_MSG DECLARE_MESSAGE_MAP() }; CAboutDlg::CAboutDlg() : CDialog(CAboutDlg::IDD) { //{{AFX_DATA_INIT(CAboutDlg) //}}AFX_DATA_INIT } void CAboutDlg::DoDataExchange(CDataExchange* pDX) { CDialog::DoDataExchange(pDX); //{{AFX_DATA_MAP(CAboutDlg) //}}AFX_DATA_MAP } BEGIN_MESSAGE_MAP(CAboutDlg, CDialog) //{{AFX_MSG_MAP(CAboutDlg) //}}AFX_MSG_MAP END_MESSAGE_MAP() // App command to run the dialog void CW3DViewApp::OnAppAbout() { CAboutDlg aboutDlg; aboutDlg.DoModal(); } /* ** */ void Debug_Refs(void) { #ifndef NDEBUG TRACE("Detecting Active Refs...\r\n"); //ODS("At time %s", cMiscUtil::Get_Text_Time()); RefCountNodeClass * first = RefCountClass::ActiveRefList.First(); RefCountNodeClass * node = first; while (node->Is_Valid()) { RefCountClass * obj = node->Get(); ActiveRefStruct * ref = &(obj->ActiveRefInfo); bool display = true; int count = 0; RefCountNodeClass * search = first; while (search->Is_Valid()) { if (search == node) { // if this is not the first one if (count != 0) { display = false; break; } } RefCountClass * search_obj = search->Get(); ActiveRefStruct * search_ref = &(search_obj->ActiveRefInfo); if ( ref->File && search_ref->File && !strcmp(search_ref->File, ref->File) && (search_ref->Line == ref->Line) ) { count++; } else if ( (ref->File == NULL) && (search_ref->File == NULL) ) { count++; } search = search->Next(); } if ( display ) { TRACE ( "%d Active Ref: %s %d %p\n", count, ref->File,ref->Line,obj); static int num_printed = 0; if (++num_printed > 20) { TRACE( "And Many More......\n"); break; } } node = node->Next(); } TRACE("Done.\r\n"); //ODS("At time %s", cMiscUtil::Get_Text_Time()); #endif } ///////////////////////////////////////////////////////////////////////////// // // CW3DViewApp // int CW3DViewApp::ExitInstance() { // // Free any resources the WW3D engine allocated // if (m_bInitialized) { // // Shutdown the audio system // WWAudioClass::Get_Instance ()->Shutdown (); // // Shutdown W3D // WW3DAssetManager::Get_Instance()->Free_Assets (); WW3D::Shutdown (); // // Shutdown the libraries // WWMath::Shutdown (); AnimatedSoundMgrClass::Shutdown (); // // Free the asset manager // delete _TheAssetMgr; _TheAssetMgr = NULL; } Debug_Refs (); return CWinApp::ExitInstance (); } ////////////////////////////////////////////////////////////////////////////// // // fnTopLevelWindowSearch // BOOL CALLBACK fnTopLevelWindowSearch ( HWND hwnd, LPARAM lParam ) { BOOL bcontinue = TRUE; // Is this a viewer window? if (::GetProp (hwnd, "WW3DVIEWER") != 0) { bcontinue = false; (*((HWND *)lParam)) = hwnd; } // Return the TRUE/FALSE result code return bcontinue; } ////////////////////////////////////////////////////////////////////////////// // // OnInitDialog // BOOL CAboutDlg::OnInitDialog (void) { // Allow the base class to process this message CDialog::OnInitDialog (); // Version 1.0 by default DWORD version_major = 1; DWORD version_minor = 0; // Get the name and path of the currently executing application TCHAR filename[MAX_PATH]; ::GetModuleFileName (NULL, filename, sizeof (filename)); // Get the version information for this file DWORD dummy_var = 0; DWORD version_size = ::GetFileVersionInfoSize (filename, &dummy_var); if (version_size > 0) { // Get the file version block LPBYTE pblock = new BYTE[version_size]; if (::GetFileVersionInfo (filename, 0L, version_size, pblock)) { // Query the block for the file version information UINT version_len = 0; VS_FIXEDFILEINFO *pversion_info = NULL; if (::VerQueryValue (pblock, "\\", (LPVOID *)&pversion_info, &version_len)) { version_major = pversion_info->dwFileVersionMS; version_minor = pversion_info->dwFileVersionLS; } } SAFE_DELETE (pblock); } // Put the version string into the dialog CString version_string; version_string.Format (IDS_VERSION, (version_major >> 16), (version_major & 0xFFFF)); SetDlgItemText (IDC_VERSION, version_string); return TRUE; }