This repository has been archived on 2025-02-27. You can view files and clone it, but cannot push or open issues or pull requests.
CnC_Renegade/Code/Tools/LevelEdit/PhysObjEditTab.cpp

301 lines
7.5 KiB
C++

/*
** 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 <http://www.gnu.org/licenses/>.
*/
// PhysObjEditDialog.cpp : implementation file
//
#include "stdafx.h"
#include "leveledit.h"
#include "PhysObjEditTab.h"
#include "SpecSheet.h"
#include "definitionmgr.h"
#include "definitionfactorymgr.h"
#include "definition.h"
#include "definitionfactory.h"
#include "Utils.h"
#include "phys.h"
#include "parameter.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
/////////////////////////////////////////////////////////////////////////////
//
// PhysObjEditTabClass
//
/////////////////////////////////////////////////////////////////////////////
PhysObjEditTabClass::PhysObjEditTabClass (void)
: m_ParamSheet (NULL),
m_PhysDefParam (NULL),
m_DefinitionID (0),
m_IsTemp (false),
m_ReadOnly (false),
DockableFormClass (PhysObjEditTabClass::IDD)
{
//{{AFX_DATA_INIT(PhysObjEditTabClass)
// NOTE: the ClassWizard will add member initialization here
//}}AFX_DATA_INIT
return ;
}
/////////////////////////////////////////////////////////////////////////////
//
// ~PhysObjEditTabClass
//
/////////////////////////////////////////////////////////////////////////////
PhysObjEditTabClass::~PhysObjEditTabClass (void)
{
return ;
}
/////////////////////////////////////////////////////////////////////////////
//
// DoDataExchange
//
/////////////////////////////////////////////////////////////////////////////
void
PhysObjEditTabClass::DoDataExchange (CDataExchange* pDX)
{
DockableFormClass::DoDataExchange(pDX);
//{{AFX_DATA_MAP(PhysObjEditTabClass)
DDX_Control(pDX, IDC_TYPE_COMBO, m_ObjTypeCombo);
DDX_Control(pDX, IDC_SETTINGS_GROUP, m_SettingsGroup);
//}}AFX_DATA_MAP
return ;
}
BEGIN_MESSAGE_MAP(PhysObjEditTabClass, DockableFormClass)
//{{AFX_MSG_MAP(PhysObjEditTabClass)
ON_WM_DESTROY()
ON_CBN_SELCHANGE(IDC_TYPE_COMBO, OnSelChangeTypeCombo)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
//
// HandleInitDialog
//
/////////////////////////////////////////////////////////////////////////////
void
PhysObjEditTabClass::HandleInitDialog (void)
{
DefinitionClass *default_definition = DefinitionMgrClass::Find_Definition (m_DefinitionID, false);
uint32 default_classid = 0;
if (default_definition != NULL) {
default_classid = default_definition->Get_Class_ID ();
}
//
// Fill in the list of all the definition types
//
DefinitionFactoryClass *factory = NULL;
for ( factory = DefinitionFactoryMgrClass::Get_First (CLASSID_PHYSICS);
factory != NULL;
factory = DefinitionFactoryMgrClass::Get_Next (factory, CLASSID_PHYSICS))
{
//
// If this is the default definition, then add the existing
// definition instead of creating a new one.
//
if (default_classid == factory->Get_Class_ID ()) {
int index = m_ObjTypeCombo.AddString (factory->Get_Name ());
m_ObjTypeCombo.SetItemData (index, (ULONG)default_definition);
m_ObjTypeCombo.SetCurSel (index);
} else {
DefinitionClass *definition = factory->Create ();
if (definition != NULL) {
//
// If this definition passes the filter, then add it to
// the combo-box, otherwise delete it
//
if (((PhysDefClass *)definition)->Is_Type (m_FilterString)) {
int index = m_ObjTypeCombo.AddString (factory->Get_Name ());
m_ObjTypeCombo.SetItemData (index, (ULONG)definition);
} else {
SAFE_DELETE (definition);
}
}
}
}
if (default_classid == 0) {
m_ObjTypeCombo.SetCurSel (0);
}
if (m_ReadOnly) {
m_ObjTypeCombo.EnableWindow (FALSE);
}
// Update the spec sheet based on the current object type
OnSelChangeTypeCombo ();
return ;
}
/////////////////////////////////////////////////////////////////////////////
//
// Apply_Changes
//
/////////////////////////////////////////////////////////////////////////////
bool
PhysObjEditTabClass::Apply_Changes (void)
{
CWaitCursor wait_cursor;
if (m_ParamSheet != NULL) {
// Save the UI changes to the definition
m_ParamSheet->Apply ();
//
// Determine what definition ID to store
//
DefinitionClass *definition = m_ParamSheet->Get_Definition ();
m_DefinitionID = 0;
if (definition != NULL) {
//
// Does the definition already have an ID?
//
m_DefinitionID = definition->Get_ID ();
if (m_DefinitionID == 0) {
//
// Give the definition a new ID
//
if (m_IsTemp) {
m_DefinitionID = ::Get_Next_Temp_ID ();
} else {
m_DefinitionID = DefinitionMgrClass::Get_New_ID (definition->Get_Class_ID ());
}
definition->Set_ID (m_DefinitionID);
}
//
// Incorporate this definition into the framework
//
DefinitionMgrClass::Register_Definition (definition);
//
// Pass this new definition ID onto the parameter-object we
// are editing (if there was one...)
//
if (m_PhysDefParam != NULL) {
m_PhysDefParam->Set_Value (m_DefinitionID);
}
}
}
return true;
}
/////////////////////////////////////////////////////////////////////////////
//
// OnDestroy
//
/////////////////////////////////////////////////////////////////////////////
void
PhysObjEditTabClass::OnDestroy (void)
{
SAFE_DELETE (m_ParamSheet);
for (int index = 0; index < m_ObjTypeCombo.GetCount (); index ++) {
DefinitionClass *definition = (DefinitionClass *)m_ObjTypeCombo.GetItemData (index);
if (definition != NULL) {
//
// Delete all the definitions EXCEPT for the one we
// will be returning to the caller.
//
if (definition->Get_ID () != m_DefinitionID) {
DefinitionMgrClass::Unregister_Definition (definition);
delete definition;
}
}
}
DockableFormClass::OnDestroy ();
return ;
}
/////////////////////////////////////////////////////////////////////////////
//
// OnSelChangeTypeCombo
//
/////////////////////////////////////////////////////////////////////////////
void
PhysObjEditTabClass::OnSelChangeTypeCombo (void)
{
if (::IsWindow (m_ObjTypeCombo)) {
SetRedraw (false);
//
// Free the old param sheet if necessary
//
if (m_ParamSheet != NULL) {
m_ParamSheet->Apply ();
m_ParamSheet->DestroyWindow ();
SAFE_DELETE (m_ParamSheet);
}
//
// Determine which definition to display
//
int index = m_ObjTypeCombo.GetCurSel ();
if (index != CB_ERR) {
DefinitionClass *definition = (DefinitionClass *)m_ObjTypeCombo.GetItemData (index);
//
// Create the param sheet that is used to edit the definition's settings
//
CRect rect;
m_SettingsGroup.GetWindowRect (&rect);
ScreenToClient (&rect);
rect.left += 10;
rect.right -= 10;
rect.top += 15;
rect.bottom -= 10;
m_ParamSheet = new SpecSheetClass (definition);
m_ParamSheet->Set_Is_Temp (m_IsTemp);
m_ParamSheet->Set_Read_Only (m_ReadOnly);
m_ParamSheet->Create ("static", "", WS_CHILD | WS_VISIBLE, rect, this, 101);
}
SetRedraw (true);
InvalidateRect (NULL, FALSE);
UpdateWindow ();
}
return ;
}