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/W3DView/EditLODDialog.cpp

505 lines
15 KiB
C++
Raw Permalink Normal View History

/*
** 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/>.
*/
// EditLODDialog.cpp : implementation file
//
#include "stdafx.h"
#include "W3DView.h"
#include "EditLODDialog.h"
#include "DistLod.H"
#include "Utils.H"
#include "RendObj.H"
#include "W3DViewDoc.H"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
/////////////////////////////////////////////////////////////
//
// Local Constants
//
const int COL_NAME = 0;
const int COL_SWITCH_UP = 1;
const int COL_SWITCH_DN = 2;
/////////////////////////////////////////////////////////////
//
// CEditLODDialog
//
CEditLODDialog::CEditLODDialog(CWnd* pParent /*=NULL*/)
: m_spinIncrement (0.5F),
CDialog(CEditLODDialog::IDD, pParent)
{
//{{AFX_DATA_INIT(CEditLODDialog)
//}}AFX_DATA_INIT
return ;
}
/////////////////////////////////////////////////////////////
//
// DoDataExchange
//
void
CEditLODDialog::DoDataExchange (CDataExchange* pDX)
{
// Allow the base class to process this message
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CEditLODDialog)
DDX_Control(pDX, IDC_SWITCH_UP_SPIN, m_switchUpSpin);
DDX_Control(pDX, IDC_SWITCH_DN_SPIN, m_switchDownSpin);
DDX_Control(pDX, IDC_HIERARCHY_LIST, m_hierarchyListCtrl);
//}}AFX_DATA_MAP
return ;
}
BEGIN_MESSAGE_MAP(CEditLODDialog, CDialog)
//{{AFX_MSG_MAP(CEditLODDialog)
ON_NOTIFY(UDN_DELTAPOS, IDC_SWITCH_UP_SPIN, OnDeltaposSwitchUpSpin)
ON_NOTIFY(UDN_DELTAPOS, IDC_SWITCH_DN_SPIN, OnDeltaposSwitchDnSpin)
ON_NOTIFY(LVN_ITEMCHANGED, IDC_HIERARCHY_LIST, OnItemChangedHierarchyList)
ON_EN_UPDATE(IDC_SWITCH_DN_EDIT, OnUpdateSwitchDnEdit)
ON_EN_UPDATE(IDC_SWITCH_UP_EDIT, OnUpdateSwitchUpEdit)
ON_BN_CLICKED(IDC_RECALC, OnRecalc)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////
//
// OnInitDialog
//
BOOL
CEditLODDialog::OnInitDialog (void)
{
// Allow the base class to process this message
CDialog::OnInitDialog ();
// Center the dialog around the data tree view instead
// of the direct center of the screen
::CenterDialogAroundTreeView (m_hWnd);
// Get a pointer to the doc
CW3DViewDoc *pCDoc = ::GetCurrentDocument ();
if (pCDoc)
{
// Get the current LOD from the doc
DistLODClass *pLOD = (DistLODClass *)pCDoc->GetDisplayedObject ();
ASSERT (pLOD);
if (pLOD)
{
int iSubObjects = pLOD->Get_Num_Sub_Objects ();
// Add the columns to the list control
m_hierarchyListCtrl.InsertColumn (COL_NAME, "Name");
m_hierarchyListCtrl.InsertColumn (COL_SWITCH_UP, "Switch Up");
m_hierarchyListCtrl.InsertColumn (COL_SWITCH_DN, "Switch Down");
RenderObjClass *pfirst_subobj = pLOD->Get_Sub_Object (0);
if (pfirst_subobj != NULL) {
m_spinIncrement = pfirst_subobj->Get_Bounding_Sphere ().Radius / 5.0F;
MEMBER_RELEASE (pfirst_subobj);
}
// Loop through all the subobjects
for (int iObject = 0;
(iObject < iSubObjects);
iObject ++)
{
// Get this subobject
RenderObjClass *pCSubObject = pLOD->Get_Sub_Object (iObject);
if (pCSubObject)
{
// Add this object to the list
int iIndex = m_hierarchyListCtrl.InsertItem (COL_NAME, pCSubObject->Get_Name ());
CString stringTemp;
stringTemp.Format ("%.2f", pLOD->Get_Switch_Up_Dist (iObject));
m_hierarchyListCtrl.SetItemText (iIndex, COL_SWITCH_UP, stringTemp);
stringTemp.Format ("%.2f", pLOD->Get_Switch_Down_Dist (iObject));
m_hierarchyListCtrl.SetItemText (iIndex, COL_SWITCH_DN, stringTemp);
// Free this object
MEMBER_RELEASE (pCSubObject);
}
}
m_switchUpSpin.SetRange (-20, UD_MAXVAL-20);
m_switchDownSpin.SetRange (-20, UD_MAXVAL-20);
// Resize the columns so they are wide enough to display the largest string
m_hierarchyListCtrl.SetColumnWidth (COL_NAME, LVSCW_AUTOSIZE);
m_hierarchyListCtrl.SetColumnWidth (COL_SWITCH_UP, LVSCW_AUTOSIZE_USEHEADER);
m_hierarchyListCtrl.SetColumnWidth (COL_SWITCH_DN, LVSCW_AUTOSIZE_USEHEADER);
// Select the first item in the list
m_hierarchyListCtrl.SetItemState (0, LVIS_SELECTED, LVIS_SELECTED);
}
}
return TRUE;
}
/////////////////////////////////////////////////////////////
//
// OnOK
//
void
CEditLODDialog::OnOK (void)
{
// Get a pointer to the doc
CW3DViewDoc *pCDoc = ::GetCurrentDocument ();
if (pCDoc)
{
// Get the current LOD from the doc
DistLODClass *pLOD = (DistLODClass *)pCDoc->GetDisplayedObject ();
ASSERT (pLOD);
if (pLOD)
{
int iSubObjects = pLOD->Get_Num_Sub_Objects ();
// Loop through all the subobjects and add them to the list control
for (int iObject = 0;
(iObject < iSubObjects);
iObject ++)
{
// Get the switch up distance from the list control
CString stringTemp = m_hierarchyListCtrl.GetItemText (iObject, COL_SWITCH_UP);
// Convert the string to a float and pass this value
// onto the LOD manager
float switchDistance = ::atof (stringTemp);
pLOD->Set_Switch_Up_Dist (iObject, switchDistance);
// Get the switch down distance from the list control
stringTemp = m_hierarchyListCtrl.GetItemText (iObject, COL_SWITCH_DN);
// Convert the string to a float and pass this value
// onto the LOD manager
switchDistance = ::atof (stringTemp);
pLOD->Set_Switch_Down_Dist (iObject, switchDistance);
}
}
}
// Allow the base class to process this message
CDialog::OnOK ();
return ;
}
/////////////////////////////////////////////////////////////
//
// OnCancel
//
void
CEditLODDialog::OnCancel (void)
{
// Allow the base class to process this message
CDialog::OnCancel ();
return ;
}
/////////////////////////////////////////////////////////////
//
// OnDeltaposSwitchUpSpin
//
void
CEditLODDialog::OnDeltaposSwitchUpSpin
(
NMHDR* pNMHDR,
LRESULT* pResult
)
{
NM_UPDOWN* pNMUpDown = (NM_UPDOWN*)pNMHDR;
if (pNMUpDown)
{
float newVal = float(pNMUpDown->iPos) / 10.00F;
// Change the switching distance in the edit control
CString stringTemp;
stringTemp.Format ("%.2f", newVal);
SetDlgItemText (IDC_SWITCH_UP_EDIT, stringTemp);
// Find the selected item in the list control
int iIndex = m_hierarchyListCtrl.GetNextItem (-1, LVNI_ALL | LVNI_SELECTED);
if (iIndex != -1)
{
// Change the switching distance in the list control
m_hierarchyListCtrl.SetItemText (iIndex, COL_SWITCH_UP, stringTemp);
}
}
*pResult = 0;
return ;
}
/////////////////////////////////////////////////////////////
//
// OnDeltaposSwitchDnSpin
//
void
CEditLODDialog::OnDeltaposSwitchDnSpin
(
NMHDR* pNMHDR,
LRESULT* pResult
)
{
NM_UPDOWN* pNMUpDown = (NM_UPDOWN*)pNMHDR;
if (pNMUpDown)
{
float newVal = float(pNMUpDown->iPos) / 10.00F;
// Change the switching distance in the edit control
CString stringTemp;
stringTemp.Format ("%.2f", newVal);
SetDlgItemText (IDC_SWITCH_DN_EDIT, stringTemp);
// Find the selected item in the list control
int iIndex = m_hierarchyListCtrl.GetNextItem (-1, LVNI_ALL | LVNI_SELECTED);
if (iIndex != -1)
{
// Change the switching distance in the list control
m_hierarchyListCtrl.SetItemText (iIndex, COL_SWITCH_DN, stringTemp);
}
}
*pResult = 0;
return ;
}
/////////////////////////////////////////////////////////////
//
// OnItemChangedHierarchyList
//
void
CEditLODDialog::OnItemChangedHierarchyList
(
NMHDR* pNMHDR,
LRESULT* pResult
)
{
// Did the 'state' of the entry change?
NM_LISTVIEW* pNMListView = (NM_LISTVIEW*)pNMHDR;
if (pNMListView &&
(pNMListView->uChanged & LVIF_STATE) == LVIF_STATE)
{
if ((pNMListView->uNewState & LVIS_SELECTED) != LVIS_SELECTED)
{
// Is there a selected item in the list control?
if (m_hierarchyListCtrl.GetNextItem (-1, LVNI_ALL | LVNI_SELECTED) == -1)
{
// Disabled the edit and spin controls
EnableControls (FALSE);
}
}
else
{
// Enable the edit and spin controls
EnableControls (TRUE);
// Load the control with data for the selected item.
ResetControls (pNMListView->iItem);
}
}
*pResult = 0;
return ;
}
/////////////////////////////////////////////////////////////
//
// ResetControls
//
void
CEditLODDialog::ResetControls (int iIndex)
{
//
// Set the text of the group box
//
CString stringTemp = m_hierarchyListCtrl.GetItemText (iIndex, COL_NAME);
// Set the text of the group box
CString stringTitle;
stringTitle.Format ("Settings (%s)", (LPCTSTR)stringTemp);
SetDlgItemText (IDC_SETTINGS_GROUP, stringTitle);
//
// Reset the switch up controls
//
// Get the switch up distance from the list control
stringTemp = m_hierarchyListCtrl.GetItemText (iIndex, COL_SWITCH_UP);
// Set the text of the edit control to reflect the switching distance
SetDlgItemText (IDC_SWITCH_UP_EDIT, stringTemp);
// Set the current position of the spin control
float switchDistance = ::atof (stringTemp);
m_switchUpSpin.SetPos (int(switchDistance * 10.00F));
//
// Reset the switch down controls
//
// Get the switch down distance from the list control
stringTemp = m_hierarchyListCtrl.GetItemText (iIndex, COL_SWITCH_DN);
// Set the text of the edit control to reflect the switching distance
SetDlgItemText (IDC_SWITCH_DN_EDIT, stringTemp);
// Set the current position of the spin control
switchDistance = ::atof (stringTemp);
m_switchDownSpin.SetPos (int(switchDistance * 10.00F));
return ;
}
/////////////////////////////////////////////////////////////
//
// EnableControls
//
void
CEditLODDialog::EnableControls (BOOL bEnable)
{
// Enable or disable the windows
::EnableWindow (::GetDlgItem (m_hWnd, IDC_SETTINGS_GROUP), bEnable);
::EnableWindow (::GetDlgItem (m_hWnd, IDC_SWITCH_UP_SPIN), bEnable);
::EnableWindow (::GetDlgItem (m_hWnd, IDC_SWITCH_UP_EDIT), bEnable);
::EnableWindow (::GetDlgItem (m_hWnd, IDC_SWITCH_DN_SPIN), bEnable);
::EnableWindow (::GetDlgItem (m_hWnd, IDC_SWITCH_DN_EDIT), bEnable);
::EnableWindow (::GetDlgItem (m_hWnd, IDC_RECALC), bEnable);
return ;
}
/////////////////////////////////////////////////////////////
//
// OnUpdateSwitchDnEdit
//
void
CEditLODDialog::OnUpdateSwitchDnEdit (void)
{
// Get the switching distance from the edit control
CString stringTemp;
GetDlgItemText (IDC_SWITCH_DN_EDIT, stringTemp);
float newVal = ::atof (stringTemp);
// Change the switching distance in the spin control
m_switchDownSpin.SetPos (int(newVal * 10.00F));
// Find the selected item in the list control
int iIndex = m_hierarchyListCtrl.GetNextItem (-1, LVNI_ALL | LVNI_SELECTED);
if (iIndex != -1)
{
// Change the switching distance in the list control
m_hierarchyListCtrl.SetItemText (iIndex, COL_SWITCH_DN, stringTemp);
}
return ;
}
/////////////////////////////////////////////////////////////
//
// OnUpdateSwitchUpEdit
//
void CEditLODDialog::OnUpdateSwitchUpEdit (void)
{
// Get the switching distance from the edit control
CString stringTemp;
GetDlgItemText (IDC_SWITCH_UP_EDIT, stringTemp);
float newVal = ::atof (stringTemp);
// Change the switching distance in the spin control
m_switchUpSpin.SetPos (int(newVal * 10.00F));
// Find the selected item in the list control
int iIndex = m_hierarchyListCtrl.GetNextItem (-1, LVNI_ALL | LVNI_SELECTED);
if (iIndex != -1)
{
// Change the switching distance in the list control
m_hierarchyListCtrl.SetItemText (iIndex, COL_SWITCH_UP, stringTemp);
}
return ;
}
/////////////////////////////////////////////////////////////
//
// OnRecalc
//
void CEditLODDialog::OnRecalc (void)
{
// Get the up switching distance from the edit control
CString stringTemp;
GetDlgItemText (IDC_SWITCH_UP_EDIT, stringTemp);
float switchUp = ::atof (stringTemp);
// Get the down switching distance from the edit control
stringTemp;
GetDlgItemText (IDC_SWITCH_DN_EDIT, stringTemp);
float switchDown = ::atof (stringTemp);
if (switchUp < switchDown)
{
// Calculate the current range
float switchDelta = switchDown - switchUp;
float switchOverlap = switchDelta * 0.1F;
// Get a pointer to the doc
CW3DViewDoc *pCDoc = ::GetCurrentDocument ();
if (pCDoc)
{
// Get the current LOD from the doc
DistLODClass *pLOD = (DistLODClass *)pCDoc->GetDisplayedObject ();
ASSERT (pLOD);
if (pLOD)
{
int iSubObjects = pLOD->Get_Num_Sub_Objects ();
switchUp = switchDown - switchOverlap;
// Loop through all the subobjects (following the highlighted one)
for (int iObject = m_hierarchyListCtrl.GetNextItem (-1, LVNI_ALL | LVNI_SELECTED) + 1;
(iObject < iSubObjects);
iObject ++)
{
// Set the text of the switch up column
CString stringTemp;
stringTemp.Format ("%.2f", switchUp);
m_hierarchyListCtrl.SetItemText (iObject, COL_SWITCH_UP, stringTemp);
// Set the text of the switch dn column
stringTemp.Format ("%.2f", switchUp+switchDelta);
m_hierarchyListCtrl.SetItemText (iObject, COL_SWITCH_DN, stringTemp);
// Add the range to the switch up distance
switchUp += switchDelta-switchOverlap;
}
}
}
}
return ;
}