2 ===========================================================================
5 Copyright (C) 1999-2011 id Software LLC, a ZeniMax Media company.
7 This file is part of the Doom 3 GPL Source Code (?Doom 3 Source Code?).
9 Doom 3 Source Code is free software: you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation, either version 3 of the License, or
12 (at your option) any later version.
14 Doom 3 Source Code is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with Doom 3 Source Code. If not, see <http://www.gnu.org/licenses/>.
22 In addition, the Doom 3 Source Code is also subject to certain additional terms. You should have received a copy of these additional terms immediately following the terms and conditions of the GNU General Public License which accompanied the Doom 3 Source Code. If not, please request a copy in writing from id Software at the address below.
24 If you have questions concerning this license or the applicable additional terms, you may contact in writing id Software LLC, c/o ZeniMax Media Inc., Suite 120, Rockville, Maryland 20850 USA.
26 ===========================================================================
29 #include "../../idlib/precompiled.h"
32 #include "../../sys/win32/rc/AFEditor_resource.h"
35 #include "DialogAFName.h"
36 #include "DialogAFConstraint.h"
37 #include "DialogAFBody.h"
44 cm_type_t modelTypes[] = {
45 { TRM_INVALID, "invalid" },
47 { TRM_OCTAHEDRON, "octahedron" },
48 { TRM_DODECAHEDRON, "dodecahedron" },
49 { TRM_CYLINDER, "cylinder" },
52 { TRM_CUSTOM, "custom" },
56 const char *ModelTypeToString( int type ) {
57 for ( int i = 0; modelTypes[i].name; i++ ) {
58 if ( modelTypes[i].type == type ) {
59 return modelTypes[i].name;
65 traceModel_t StringToModelType( const char *str ) {
66 for ( int i = 0; modelTypes[i].name; i++ ) {
67 if ( idStr::Icmp( modelTypes[i].name, str ) == 0 ) {
68 return modelTypes[i].type;
74 // DialogAFBody dialog
76 toolTip_t DialogAFBody::toolTips[] = {
77 { IDC_COMBO_BODIES, "select body for editing" },
78 { IDC_BUTTON_NEWBODY, "create a new body" },
79 { IDC_BUTTON_RENAMEBODY, "rename the selected body" },
80 { IDC_BUTTON_DELETEBODY, "delete the selected body" },
81 { IDC_COMBO_CM_TYPE, "collision model type" },
82 { IDC_EDIT_CM_NAME, "custom collision model" },
83 { IDC_BUTTON_CM_BROWSE, "browse custom collision model" },
84 { IDC_COMBO_BONE_JOINT1, "first joint of bone collision model" },
85 { IDC_COMBO_BONE_JOINT2, "second joint of bone collision model" },
86 { IDC_EDIT_CM_HEIGHT, "hieght of the collision model" },
87 { IDC_EDIT_CM_WIDTH, "width of the collision model" },
88 { IDC_EDIT_CM_LENGTH, "length of the collision model" },
89 { IDC_EDIT_CM_NUMSIDES, "number of sides of the collision model" },
90 { IDC_EDIT_CM_DENSITY, "collision model density" },
91 { IDC_EDIT_CM_INERTIASCALE, "inertia tensor scale" },
92 { IDC_RADIO_ORIGIN_COORDINATES, "use absolute coordinates for the body origin" },
93 { IDC_RADIO_ORIGIN_BONECENTER, "use the center of a bone for the body origin" },
94 { IDC_RADIO_ORIGIN_JOINT, "use the position of a joint for the body origin" },
95 { IDC_EDIT_AF_VECTOR_X, "x-coordinate" },
96 { IDC_EDIT_AF_VECTOR_Y, "y-coordinate" },
97 { IDC_EDIT_AF_VECTOR_Z, "z-coordinate" },
98 { IDC_COMBO_ORIGIN_BONECENTER_JOINT1, "bone start joint" },
99 { IDC_COMBO_ORIGIN_BONECENTER_JOINT2, "bone end joint" },
100 { IDC_COMBO_ORIGIN_JOINT, "joint name" },
101 { IDC_EDIT_ANGLES_PITCH, "pitch angle of body" },
102 { IDC_EDIT_ANGLES_YAW, "yaw angle of body" },
103 { IDC_EDIT_ANGLES_ROLL, "roll angle of body" },
104 { IDC_EDIT_LINEARFRICTION, "translational friction" },
105 { IDC_EDIT_ANGULARFRICTION, "rotational friction" },
106 { IDC_EDIT_CONTACTFRICTION, "friction with contact surfaces" },
107 { IDC_CHECK_SELFCOLLISION, "collide with other bodies of this articulated figure" },
108 { IDC_EDIT_CONTENTS, "content of body" },
109 { IDC_EDIT_CLIPMASK, "collide with these content types" },
110 { IDC_EDIT_FRICTIONDIRECTION, "single friction direction relative to body" },
111 { IDC_EDIT_CONTACTMOTORDIRECTION, "contact motor direction" },
112 { IDC_COMBO_MODIFIEDJOINT, "the joint modified by the relative rotation of the body" },
113 { IDC_RADIO_MODIFY_ORIENTATION, "modify the joint orientation" },
114 { IDC_RADIO_MODIFY_POSITION, "modify the joint position" },
115 { IDC_RADIO_MODIFY_BOTH, "modify the joint orientation and position" },
116 { IDC_EDIT_CONTAINEDJOINTS, "all the joints contained by this body" },
120 IMPLEMENT_DYNAMIC(DialogAFBody, CDialog)
124 DialogAFBody::DialogAFBody
127 DialogAFBody::DialogAFBody( CWnd* pParent /*=NULL*/ )
128 : CDialog(DialogAFBody::IDD, pParent)
129 , constraintDlg(NULL)
142 , m_selfCollision(false)
143 , m_linearFriction(0)
144 , m_angularFriction(0)
145 , m_contactFriction(0)
149 Create( IDD_DIALOG_AF_BODY, pParent );
150 EnableToolTips( TRUE );
155 DialogAFBody::~DialogAFBody
158 DialogAFBody::~DialogAFBody() {
163 DialogAFBody::DoDataExchange
166 void DialogAFBody::DoDataExchange( CDataExchange* pDX ) {
167 CDialog::DoDataExchange( pDX );
168 //{{AFX_DATA_MAP(DialogAFBody)
169 DDX_Control(pDX, IDC_COMBO_BODIES, bodyList);
170 DDX_Control(pDX, IDC_COMBO_CM_TYPE, cm_comboType);
171 DDX_Text(pDX, IDC_EDIT_CM_LENGTH, cm_length);
172 DDX_Text(pDX, IDC_EDIT_CM_HEIGHT, cm_height);
173 DDX_Text(pDX, IDC_EDIT_CM_WIDTH, cm_width);
174 DDX_Text(pDX, IDC_EDIT_CM_NUMSIDES, cm_numSides);
175 DDX_Control(pDX, IDC_COMBO_BONE_JOINT1, cm_comboBoneJoint1 );
176 DDX_Control(pDX, IDC_COMBO_BONE_JOINT2, cm_comboBoneJoint2 );
177 DDX_Text(pDX, IDC_EDIT_CM_DENSITY, cm_density);
178 DDX_Control(pDX, IDC_EDIT_CM_INERTIASCALE, cm_inertiaScale);
179 DDX_Text(pDX, IDC_EDIT_AF_VECTOR_X, cm_origin_x);
180 DDX_Text(pDX, IDC_EDIT_AF_VECTOR_Y, cm_origin_y);
181 DDX_Text(pDX, IDC_EDIT_AF_VECTOR_Z, cm_origin_z);
182 DDX_Control(pDX, IDC_COMBO_ORIGIN_BONECENTER_JOINT1, cm_originBoneCenterJoint1);
183 DDX_Control(pDX, IDC_COMBO_ORIGIN_BONECENTER_JOINT2, cm_originBoneCenterJoint2);
184 DDX_Control(pDX, IDC_COMBO_ORIGIN_JOINT, cm_originJoint);
185 DDX_Text(pDX, IDC_EDIT_ANGLES_PITCH, cm_angles_pitch);
186 DDX_Text(pDX, IDC_EDIT_ANGLES_YAW, cm_angles_yaw);
187 DDX_Text(pDX, IDC_EDIT_ANGLES_ROLL, cm_angles_roll);
188 DDX_Check(pDX, IDC_CHECK_SELFCOLLISION, m_selfCollision);
189 DDX_Control(pDX, IDC_EDIT_CONTENTS, m_editContents);
190 DDX_Control(pDX, IDC_EDIT_CLIPMASK, m_editClipMask);
191 DDX_Text(pDX, IDC_EDIT_LINEARFRICTION, m_linearFriction);
192 DDX_Text(pDX, IDC_EDIT_ANGULARFRICTION, m_angularFriction);
193 DDX_Text(pDX, IDC_EDIT_CONTACTFRICTION, m_contactFriction);
194 DDX_Control(pDX, IDC_EDIT_FRICTIONDIRECTION, m_frictionDirection);
195 DDX_Control(pDX, IDC_EDIT_CONTACTMOTORDIRECTION, m_contactMotorDirection);
196 DDX_Control(pDX, IDC_COMBO_MODIFIEDJOINT, m_comboModifiedJoint);
197 DDX_Control(pDX, IDC_EDIT_CONTAINEDJOINTS, m_editContainedJoints);
203 DialogAFBody::InitBodyList
206 void DialogAFBody::InitBodyList( void ) {
209 bodyList.ResetContent();
213 for ( int i = 0; i < file->bodies.Num(); i++ ) {
214 bodyList.AddString( file->bodies[i]->name.c_str() );
216 if ( bodyList.GetCount() != 0 ) {
217 bodyList.SetCurSel( 0 );
218 bodyList.GetLBText( 0, str );
225 DialogAFBody::InitJointLists
227 initialize the joint lists for bone collision models
230 void DialogAFBody::InitJointLists( void ) {
233 cm_comboBoneJoint1.ResetContent();
234 cm_comboBoneJoint2.ResetContent();
235 cm_originBoneCenterJoint1.ResetContent();
236 cm_originBoneCenterJoint2.ResetContent();
237 cm_originJoint.ResetContent();
244 const idRenderModel *model = gameEdit->ANIM_GetModelFromName( file->model );
249 numJoints = model->NumJoints();
250 for ( int i = 0; i < numJoints; i++ ) {
251 const char *jointName = model->GetJointName( (jointHandle_t) i );
252 cm_comboBoneJoint1.AddString( jointName );
253 cm_comboBoneJoint2.AddString( jointName );
254 cm_originBoneCenterJoint1.AddString( jointName );
255 cm_originBoneCenterJoint2.AddString( jointName );
256 cm_originJoint.AddString( jointName );
262 DialogAFBody::InitCollisionModelType
265 void DialogAFBody::InitCollisionModelType( void ) {
266 int showBone, showOther;
271 cm_comboType.GetLBText( cm_comboType.GetCurSel(), str );
272 traceModel_t type = StringToModelType( str );
273 if ( type == TRM_BONE ) {
277 GetDlgItem( IDC_STATIC_CM_LENGTH )->SetWindowText( "Joint 1" );
278 GetDlgItem( IDC_STATIC_CM_HEIGHT )->SetWindowText( "Joint 2" );
279 CheckRadioButton( IDC_RADIO_ORIGIN_COORDINATES,
280 IDC_RADIO_ORIGIN_JOINT,
281 IDC_RADIO_ORIGIN_BONECENTER );
287 GetDlgItem( IDC_STATIC_CM_LENGTH )->SetWindowText( "Length" );
288 GetDlgItem( IDC_STATIC_CM_HEIGHT )->SetWindowText( "Height" );
290 GetDlgItem( IDC_COMBO_BONE_JOINT1 )->ShowWindow( showBone );
291 GetDlgItem( IDC_COMBO_BONE_JOINT2 )->ShowWindow( showBone );
292 GetDlgItem( IDC_EDIT_CM_LENGTH )->ShowWindow( showOther );
293 GetDlgItem( IDC_SPIN_CM_LENGTH )->ShowWindow( showOther );
294 GetDlgItem( IDC_EDIT_CM_HEIGHT )->ShowWindow( showOther );
295 GetDlgItem( IDC_SPIN_CM_HEIGHT )->ShowWindow( showOther );
297 // enable/disable origin controls
298 GetDlgItem( IDC_EDIT_AF_VECTOR_X )->EnableWindow( enableOther );
299 GetDlgItem( IDC_SPIN_AF_VECTOR_X )->EnableWindow( enableOther );
300 GetDlgItem( IDC_EDIT_AF_VECTOR_Y )->EnableWindow( enableOther );
301 GetDlgItem( IDC_SPIN_AF_VECTOR_Y )->EnableWindow( enableOther );
302 GetDlgItem( IDC_EDIT_AF_VECTOR_Z )->EnableWindow( enableOther );
303 GetDlgItem( IDC_SPIN_AF_VECTOR_Z )->EnableWindow( enableOther );
305 // enable/disable joint controls
306 GetDlgItem( IDC_COMBO_ORIGIN_BONECENTER_JOINT1 )->EnableWindow( enableOther );
307 GetDlgItem( IDC_COMBO_ORIGIN_BONECENTER_JOINT2 )->EnableWindow( enableOther );
308 GetDlgItem( IDC_COMBO_ORIGIN_JOINT )->EnableWindow( enableOther );
310 // enable/disable angles controls
311 GetDlgItem( IDC_STATIC_ANGLES_PITCH )->EnableWindow( enableOther );
312 GetDlgItem( IDC_EDIT_ANGLES_PITCH )->EnableWindow( enableOther );
313 GetDlgItem( IDC_SPIN_ANGLES_PITCH )->EnableWindow( enableOther );
314 GetDlgItem( IDC_STATIC_ANGLES_YAW )->EnableWindow( enableOther );
315 GetDlgItem( IDC_EDIT_ANGLES_YAW )->EnableWindow( enableOther );
316 GetDlgItem( IDC_SPIN_ANGLES_YAW )->EnableWindow( enableOther );
317 GetDlgItem( IDC_STATIC_ANGLES_ROLL )->EnableWindow( enableOther );
318 GetDlgItem( IDC_EDIT_ANGLES_ROLL )->EnableWindow( enableOther );
319 GetDlgItem( IDC_SPIN_ANGLES_ROLL )->EnableWindow( enableOther );
321 GetDlgItem( IDC_RADIO_ORIGIN_COORDINATES )->EnableWindow( enableOther );
322 GetDlgItem( IDC_RADIO_ORIGIN_BONECENTER )->EnableWindow( enableOther );
323 GetDlgItem( IDC_RADIO_ORIGIN_JOINT )->EnableWindow( enableOther );
325 if ( type == TRM_CONE || type == TRM_CYLINDER ) {
326 GetDlgItem( IDC_EDIT_CM_NUMSIDES )->EnableWindow( true );
327 GetDlgItem( IDC_SPIN_CM_NUMSIDES )->EnableWindow( true );
330 GetDlgItem( IDC_EDIT_CM_NUMSIDES )->EnableWindow( false );
331 GetDlgItem( IDC_SPIN_CM_NUMSIDES )->EnableWindow( false );
337 DialogAFBody::InitModifiedJointList
340 void DialogAFBody::InitModifiedJointList( void ) {
344 m_comboModifiedJoint.ResetContent();
350 const idRenderModel *model = gameEdit->ANIM_GetModelFromName( file->model );
355 numJoints = model->NumJoints();
356 for ( i = 0; i < numJoints; i++ ) {
357 const char *jointName = model->GetJointName( (jointHandle_t) i );
358 for ( j = 0; j < file->bodies.Num(); j++ ) {
359 if ( file->bodies[j] == body ) {
362 if ( file->bodies[j]->jointName.Icmp( jointName ) == 0 ) {
366 if ( j < file->bodies.Num() ) {
369 m_comboModifiedJoint.AddString( jointName );
373 if ( body->jointName.Length() == 0 ) {
374 m_comboModifiedJoint.GetLBText( 0, str );
375 body->jointName = str;
377 SetSafeComboBoxSelection( &m_comboModifiedJoint, body->jointName, -1 );
378 // cannot change the body which modifies the origin joint
379 if ( body->jointName.Icmp( "origin" ) == 0 ) {
380 // check if there is another body which modifies the "origin" joint
381 for ( i = 0; i < file->bodies.Num(); i++ ) {
382 if ( file->bodies[i] == body ) {
385 if ( file->bodies[i]->jointName.Icmp( "origin" ) == 0 ) {
389 // if there is another body which modifies the "origin" joint
390 if ( i < file->bodies.Num() ) {
391 GetDlgItem( IDC_COMBO_MODIFIEDJOINT )->EnableWindow( true );
394 GetDlgItem( IDC_COMBO_MODIFIEDJOINT )->EnableWindow( false );
398 GetDlgItem( IDC_COMBO_MODIFIEDJOINT )->EnableWindow( true );
405 DialogAFBody::InitNewRenameDeleteButtons
408 void DialogAFBody::InitNewRenameDeleteButtons( void ) {
409 if ( file && numJoints > file->bodies.Num() ) {
410 GetDlgItem( IDC_BUTTON_NEWBODY )->EnableWindow( true );
413 GetDlgItem( IDC_BUTTON_NEWBODY )->EnableWindow( false );
416 if ( file && bodyList.GetCount() >= 1 ) {
417 GetDlgItem( IDC_BUTTON_RENAMEBODY )->EnableWindow( true );
418 GetDlgItem( IDC_BUTTON_DELETEBODY )->EnableWindow( true );
421 GetDlgItem( IDC_BUTTON_RENAMEBODY )->EnableWindow( false );
422 GetDlgItem( IDC_BUTTON_DELETEBODY )->EnableWindow( false );
428 DialogAFBody::LoadFile
431 void DialogAFBody::LoadFile( idDeclAF *af ) {
436 InitNewRenameDeleteButtons();
441 DialogAFBody::SaveFile
444 void DialogAFBody::SaveFile( void ) {
450 DialogAFBody::LoadBody
453 void DialogAFBody::LoadBody( const char *name ) {
460 for ( i = 0; i < file->bodies.Num(); i++ ) {
461 if ( file->bodies[i]->name.Icmp( name ) == 0 ) {
465 if ( i >= file->bodies.Num() ) {
468 body = file->bodies[i];
470 // load collision model from the current idDeclAF_Body
471 SetSafeComboBoxSelection( &cm_comboType, ModelTypeToString( body->modelType ), -1 );
472 if ( body->modelType == TRM_BONE ) {
473 s1 = SetSafeComboBoxSelection( &cm_comboBoneJoint1, body->v1.joint1.c_str(), -1 );
474 s2 = SetSafeComboBoxSelection( &cm_comboBoneJoint2, body->v2.joint1.c_str(), s1 );
475 cm_width = body->width;
476 cm_length = cm_height = 20.0f;
477 s1 = SetSafeComboBoxSelection( &cm_originBoneCenterJoint1, body->v1.joint1.c_str(), -1 );
478 s2 = SetSafeComboBoxSelection( &cm_originBoneCenterJoint2, body->v2.joint1.c_str(), s1 );
481 cm_length = body->v2.ToVec3().x - body->v1.ToVec3().x;
482 cm_height = body->v2.ToVec3().z - body->v1.ToVec3().z;
483 cm_width = body->v2.ToVec3().y - body->v1.ToVec3().y;
484 cm_origin_x = body->origin.ToVec3().x;
485 cm_origin_y = body->origin.ToVec3().y;
486 cm_origin_z = body->origin.ToVec3().z;
487 s1 = SetSafeComboBoxSelection( &cm_originBoneCenterJoint1, body->origin.joint1.c_str(), -1 );
488 s2 = SetSafeComboBoxSelection( &cm_originBoneCenterJoint2, body->origin.joint2.c_str(), s1 );
489 s1 = SetSafeComboBoxSelection( &cm_originJoint, body->origin.joint1.c_str(), -1 );
490 cm_angles_pitch = body->angles.pitch;
491 cm_angles_yaw = body->angles.yaw;
492 cm_angles_roll = body->angles.roll;
493 if ( body->origin.type == idAFVector::VEC_BONECENTER ) {
494 i = IDC_RADIO_ORIGIN_BONECENTER;
496 else if ( body->origin.type == idAFVector::VEC_JOINT ) {
497 i = IDC_RADIO_ORIGIN_JOINT;
500 i = IDC_RADIO_ORIGIN_COORDINATES;
502 CheckRadioButton( IDC_RADIO_ORIGIN_COORDINATES, IDC_RADIO_ORIGIN_JOINT, i );
504 cm_numSides = body->numSides;
505 cm_density = body->density;
506 if ( body->inertiaScale == mat3_identity ) {
507 cm_inertiaScale.SetWindowText( "none" );
510 cm_inertiaScale.SetWindowText( body->inertiaScale.ToString( 1 ) );
513 // load collision detection settings from the current idDeclAF_Body
514 m_selfCollision = body->selfCollision;
515 idDeclAF::ContentsToString( body->contents, str );
516 m_editContents.SetWindowText( str );
517 idDeclAF::ContentsToString( body->clipMask, str );
518 m_editClipMask.SetWindowText( str );
520 // load friction settings from the current idDeclAF_Body
521 m_linearFriction = body->linearFriction;
522 m_angularFriction = body->angularFriction;
523 m_contactFriction = body->contactFriction;
525 // friction direction and contact motor direction
526 if ( body->frictionDirection.ToVec3() != vec3_origin ) {
527 idFile_Memory file( "frictionDirection" );
528 file.WriteFloatString( "%f %f %f", body->frictionDirection.ToVec3().x, body->frictionDirection.ToVec3().y, body->frictionDirection.ToVec3().z );
529 m_frictionDirection.SetWindowText( file.GetDataPtr() );
531 m_frictionDirection.SetWindowText( "" );
533 if ( body->contactMotorDirection.ToVec3() != vec3_origin ) {
534 idFile_Memory file( "contactMotorDirection" );
535 file.WriteFloatString( "%f %f %f", body->contactMotorDirection.ToVec3().x, body->contactMotorDirection.ToVec3().y, body->contactMotorDirection.ToVec3().z );
536 m_contactMotorDirection.SetWindowText( file.GetDataPtr() );
538 m_contactMotorDirection.SetWindowText( "" );
541 // load joint settings from the current idDeclAF_Body
542 InitModifiedJointList();
543 if ( body->jointMod == DECLAF_JOINTMOD_AXIS ) {
544 i = IDC_RADIO_MODIFY_ORIENTATION;
545 } else if ( body->jointMod == DECLAF_JOINTMOD_ORIGIN ) {
546 i = IDC_RADIO_MODIFY_POSITION;
547 } else if ( body->jointMod == DECLAF_JOINTMOD_BOTH ) {
548 i = IDC_RADIO_MODIFY_BOTH;
550 i = IDC_RADIO_MODIFY_ORIENTATION;
552 CheckRadioButton( IDC_RADIO_MODIFY_ORIENTATION, IDC_RADIO_MODIFY_BOTH, i );
553 m_editContainedJoints.SetWindowText( body->containedJoints.c_str() );
555 // update displayed values
558 InitCollisionModelType(); // CComboBox::SetCurSel doesn't call this
560 if ( GetStyle() & WS_VISIBLE ) {
561 // highlight the current body ingame
562 cvarSystem->SetCVarString( "af_highlightBody", name );
568 DialogAFBody::SaveBody
571 void DialogAFBody::SaveBody( void ) {
575 if ( !file || !body ) {
580 // save the collision model to the current idDeclAF_Body
581 cm_comboType.GetLBText( cm_comboType.GetCurSel(), str );
582 body->modelType = StringToModelType( str );
583 if ( body->modelType == TRM_BONE ) {
584 body->origin.type = idAFVector::VEC_BONECENTER;
585 s1 = GetSafeComboBoxSelection( &cm_comboBoneJoint1, str, -1 );
586 body->v1.type = idAFVector::VEC_JOINT;
587 body->v1.joint1 = str;
588 body->origin.joint1 = str;
589 s2 = GetSafeComboBoxSelection( &cm_comboBoneJoint2, str, s1 );
590 body->v2.type = idAFVector::VEC_JOINT;
591 body->v2.joint1 = str;
592 body->origin.joint2 = str;
593 body->width = cm_width;
596 body->v1.type = idAFVector::VEC_COORDS;
597 body->v1.ToVec3().x = -0.5f * cm_length;
598 body->v1.ToVec3().y = -0.5f * cm_width;
599 body->v1.ToVec3().z = -0.5f * cm_height;
600 body->v2.type = idAFVector::VEC_COORDS;
601 body->v2.ToVec3().x = 0.5f * cm_length;
602 body->v2.ToVec3().y = 0.5f * cm_width;
603 body->v2.ToVec3().z = 0.5f * cm_height;
604 body->origin.ToVec3().x = cm_origin_x;
605 body->origin.ToVec3().y = cm_origin_y;
606 body->origin.ToVec3().z = cm_origin_z;
607 body->angles.pitch = cm_angles_pitch;
608 body->angles.yaw = cm_angles_yaw;
609 body->angles.roll = cm_angles_roll;
610 if ( body->origin.type == idAFVector::VEC_JOINT ) {
611 s1 = GetSafeComboBoxSelection( &cm_originJoint, str, -1 );
612 body->origin.joint1 = str;
615 s1 = GetSafeComboBoxSelection( &cm_originBoneCenterJoint1, str, -1 );
616 body->origin.joint1 = str;
618 s2 = GetSafeComboBoxSelection( &cm_originBoneCenterJoint2, str, s1 );
619 body->origin.joint2 = str;
621 body->numSides = cm_numSides;
622 body->density = cm_density;
623 cm_inertiaScale.GetWindowText( str );
624 if ( idStr::Icmp( str, "none" ) == 0 ) {
625 body->inertiaScale.Identity();
627 idLexer src( str, str.GetLength(), "inertiaScale" );
628 src.SetFlags( LEXFL_NOERRORS | LEXFL_NOWARNINGS );
629 for ( int i = 0; i < 3; i++ ) {
630 for ( int j = 0; j < 3; j++ ) {
631 body->inertiaScale[i][j] = src.ParseFloat();
636 // save the collision detection settings to the current idDeclAF_Body
637 body->selfCollision = ( m_selfCollision != FALSE );
638 m_editContents.GetWindowText( str );
639 body->contents = idDeclAF::ContentsFromString( str );
640 m_editClipMask.GetWindowText( str );
641 body->clipMask = idDeclAF::ContentsFromString( str );
643 // save friction settings to the current idDeclAF_Body
644 body->linearFriction = m_linearFriction;
645 body->angularFriction = m_angularFriction;
646 body->contactFriction = m_contactFriction;
648 // friction direction and contact motor direction
649 m_frictionDirection.GetWindowText( str );
650 if ( str.GetLength() != 0 ) {
651 body->frictionDirection.ToVec3().Zero();
652 sscanf( str, "%f %f %f", &body->frictionDirection.ToVec3().x, &body->frictionDirection.ToVec3().y, &body->frictionDirection.ToVec3().z );
654 m_contactMotorDirection.GetWindowText( str );
655 if ( str.GetLength() != 0 ) {
656 body->contactMotorDirection.ToVec3().Zero();
657 sscanf( str, "%f %f %f", &body->contactMotorDirection.ToVec3().x, &body->contactMotorDirection.ToVec3().y, &body->contactMotorDirection.ToVec3().z );
660 // save joint settings to the current idDeclAF_Body
661 GetSafeComboBoxSelection( &m_comboModifiedJoint, str, -1 );
662 body->jointName = str;
663 m_editContainedJoints.GetWindowText( str );
664 body->containedJoints = str;
666 AFDialogSetFileModified();
671 DialogAFBody::UpdateFile
674 void DialogAFBody::UpdateFile( void ) {
677 gameEdit->AF_UpdateEntities( file->GetName() );
683 DialogAFBody::OnInitDialog
686 BOOL DialogAFBody::OnInitDialog() {
688 CDialog::OnInitDialog();
690 // initialize the collision model types
691 cm_comboType.ResetContent();
692 for ( int i = 0; modelTypes[i].name; i++ ) {
693 if ( modelTypes[i].type == TRM_INVALID || modelTypes[i].type == TRM_CUSTOM ) {
696 cm_comboType.AddString( modelTypes[i].name );
699 InitNewRenameDeleteButtons();
701 return TRUE; // return TRUE unless you set the focus to a control
702 // EXCEPTION: OCX Property Pages should return FALSE
707 DialogAFBody::OnToolHitTest
710 int DialogAFBody::OnToolHitTest( CPoint point, TOOLINFO* pTI ) const {
711 CDialog::OnToolHitTest( point, pTI );
712 return DefaultOnToolHitTest( toolTips, this, point, pTI );
715 BEGIN_MESSAGE_MAP(DialogAFBody, CDialog)
716 ON_NOTIFY_EX_RANGE(TTN_NEEDTEXTW, 0, 0xFFFF, OnToolTipNotify)
717 ON_NOTIFY_EX_RANGE(TTN_NEEDTEXTA, 0, 0xFFFF, OnToolTipNotify)
719 ON_CBN_SELCHANGE(IDC_COMBO_BODIES, OnCbnSelchangeComboBodies)
720 ON_BN_CLICKED(IDC_BUTTON_NEWBODY, OnBnClickedButtonNewbody)
721 ON_BN_CLICKED(IDC_BUTTON_RENAMEBODY, OnBnClickedButtonRenamebody)
722 ON_BN_CLICKED(IDC_BUTTON_DELETEBODY, OnBnClickedButtonDeletebody)
723 ON_CBN_SELCHANGE(IDC_COMBO_CM_TYPE, OnCbnSelchangeComboCmType)
724 ON_EN_CHANGE(IDC_EDIT_CM_LENGTH, OnEnChangeEditCmLength)
725 ON_EN_CHANGE(IDC_EDIT_CM_HEIGHT, OnEnChangeEditCmHeight)
726 ON_EN_CHANGE(IDC_EDIT_CM_WIDTH, OnEnChangeEditCmWidth)
727 ON_EN_CHANGE(IDC_EDIT_CM_NUMSIDES, OnEnChangeEditCmNumsides)
728 ON_CBN_SELCHANGE(IDC_COMBO_BONE_JOINT1, OnCbnSelchangeComboBoneJoint1)
729 ON_CBN_SELCHANGE(IDC_COMBO_BONE_JOINT2, OnCbnSelchangeComboBoneJoint2)
730 ON_EN_CHANGE(IDC_EDIT_CM_DENSITY, OnEnChangeEditCmDensity)
731 ON_EN_CHANGE(IDC_EDIT_CM_INERTIASCALE, OnEnChangeEditCmInertiascale)
732 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_CM_LENGTH, OnDeltaposSpinCmLength)
733 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_CM_HEIGHT, OnDeltaposSpinCmHeight)
734 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_CM_WIDTH, OnDeltaposSpinCmWidth)
735 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_CM_NUMSIDES, OnDeltaposSpinCmNumsides)
736 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_CM_DENSITY, OnDeltaposSpinCmDensity)
737 ON_BN_CLICKED(IDC_RADIO_ORIGIN_COORDINATES, OnBnClickedRadioOriginCoordinates)
738 ON_BN_CLICKED(IDC_RADIO_ORIGIN_BONECENTER, OnBnClickedRadioOriginBonecenter)
739 ON_BN_CLICKED(IDC_RADIO_ORIGIN_JOINT, OnBnClickedRadioOriginJoint)
740 ON_EN_CHANGE(IDC_EDIT_AF_VECTOR_X, OnEnChangeEditAfVectorX)
741 ON_EN_CHANGE(IDC_EDIT_AF_VECTOR_Y, OnEnChangeEditAfVectorY)
742 ON_EN_CHANGE(IDC_EDIT_AF_VECTOR_Z, OnEnChangeEditAfVectorZ)
743 ON_CBN_SELCHANGE(IDC_COMBO_ORIGIN_BONECENTER_JOINT1, OnOnCbnSelchangeComboOriginBoneCenterJoint1)
744 ON_CBN_SELCHANGE(IDC_COMBO_ORIGIN_BONECENTER_JOINT2, OnOnCbnSelchangeComboOriginBoneCenterJoint2)
745 ON_CBN_SELCHANGE(IDC_COMBO_ORIGIN_JOINT, OnOnCbnSelchangeComboOriginJoint)
746 ON_EN_CHANGE(IDC_EDIT_ANGLES_PITCH, OnEnChangeEditAnglesPitch)
747 ON_EN_CHANGE(IDC_EDIT_ANGLES_YAW, OnEnChangeEditAnglesYaw)
748 ON_EN_CHANGE(IDC_EDIT_ANGLES_ROLL, OnEnChangeEditAnglesRoll)
749 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_AF_VECTOR_X, OnDeltaposSpinAfVectorX)
750 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_AF_VECTOR_Y, OnDeltaposSpinAfVectorY)
751 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_AF_VECTOR_Z, OnDeltaposSpinAfVectorZ)
752 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_ANGLES_PITCH, OnDeltaposSpinAnglesPitch)
753 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_ANGLES_YAW, OnDeltaposSpinAnglesYaw)
754 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_ANGLES_ROLL, OnDeltaposSpinAnglesRoll)
755 ON_BN_CLICKED(IDC_CHECK_SELFCOLLISION, OnBnClickedCheckSelfcollision)
756 ON_EN_CHANGE(IDC_EDIT_CONTENTS, OnEnChangeEditContents)
757 ON_EN_CHANGE(IDC_EDIT_CLIPMASK, OnEnChangeEditClipmask)
758 ON_EN_CHANGE(IDC_EDIT_LINEARFRICTION, OnEnChangeEditLinearfriction)
759 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_LINEARFRICTION, OnDeltaposSpinLinearfriction)
760 ON_EN_CHANGE(IDC_EDIT_ANGULARFRICTION, OnEnChangeEditAngularfriction)
761 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_ANGULARFRICTION, OnDeltaposSpinAngularfriction)
762 ON_EN_CHANGE(IDC_EDIT_CONTACTFRICTION, OnEnChangeEditContactfriction)
763 ON_NOTIFY(UDN_DELTAPOS, IDC_SPIN_CONTACTFRICTION, OnDeltaposSpinContactfriction)
764 ON_EN_CHANGE(IDC_EDIT_FRICTIONDIRECTION, OnEnChangeEditFrictionDirection)
765 ON_EN_CHANGE(IDC_EDIT_CONTACTMOTORDIRECTION, OnEnChangeEditContactMotorDirection)
766 ON_CBN_SELCHANGE(IDC_COMBO_MODIFIEDJOINT, OnCbnSelchangeComboModifiedjoint)
767 ON_BN_CLICKED(IDC_RADIO_MODIFY_ORIENTATION, OnBnClickedRadioModifyOrientation)
768 ON_BN_CLICKED(IDC_RADIO_MODIFY_POSITION, OnBnClickedRadioModifyPosition)
769 ON_BN_CLICKED(IDC_RADIO_MODIFY_BOTH, OnBnClickedRadioModifyBoth)
770 ON_EN_CHANGE(IDC_EDIT_CONTAINEDJOINTS, OnEnChangeEditContainedjoints)
774 // DialogAFBody message handlers
776 BOOL DialogAFBody::OnToolTipNotify( UINT id, NMHDR *pNMHDR, LRESULT *pResult ) {
777 return DefaultOnToolTipNotify( toolTips, id, pNMHDR, pResult );
780 void DialogAFBody::OnShowWindow( BOOL bShow, UINT nStatus ) {
781 if ( bShow && body ) {
782 cvarSystem->SetCVarString( "af_highlightBody", body->name.c_str() );
784 cvarSystem->SetCVarString( "af_highlightBody", "" );
786 CDialog::OnShowWindow( bShow, nStatus );
789 void DialogAFBody::OnCbnSelchangeComboBodies() {
792 GetSafeComboBoxSelection( &bodyList, str, -1 );
796 void DialogAFBody::OnBnClickedButtonNewbody() {
797 DialogAFName nameDlg;
801 // the names 'origin' and 'world' are reserved for constraints bound to the world
802 bodyList.AddString( "origin" );
803 bodyList.AddString( "world" );
805 nameDlg.SetComboBox( &bodyList );
806 res = nameDlg.DoModal();
808 bodyList.DeleteString( bodyList.FindString( -1, "origin" ) );
809 bodyList.DeleteString( bodyList.FindString( -1, "world" ) );
812 nameDlg.GetName( str );
814 file->NewBody( str );
815 bodyList.SetCurSel( bodyList.AddString( str ) );
817 constraintDlg->LoadFile( file );
818 gameEdit->AF_UpdateEntities( file->GetName() );
819 AFDialogSetFileModified();
821 InitNewRenameDeleteButtons();
824 void DialogAFBody::OnBnClickedButtonRenamebody() {
826 CString name, newName;
827 DialogAFName nameDlg;
829 if ( !file || !body ) {
833 i = bodyList.GetCurSel();
835 bodyList.GetLBText( i, name );
836 nameDlg.SetName( name );
837 nameDlg.SetComboBox( &bodyList );
838 if ( nameDlg.DoModal() == IDOK ) {
839 nameDlg.GetName( newName );
841 file->RenameBody( name, newName );
842 bodyList.DeleteString( i );
843 bodyList.SetCurSel( bodyList.AddString( newName ) );
845 constraintDlg->LoadFile( file );
846 gameEdit->AF_UpdateEntities( file->GetName() );
847 AFDialogSetFileModified();
852 void DialogAFBody::OnBnClickedButtonDeletebody() {
856 if ( !file || !body ) {
860 i = bodyList.GetCurSel();
862 if ( MessageBox( "Are you sure you want to delete this body and all attached constraints ?", "Delete Body", MB_YESNO | MB_ICONQUESTION ) == IDYES ) {
863 bodyList.GetLBText( i, str );
864 // delete currently selected body
865 file->DeleteBody( str );
866 bodyList.DeleteString( i );
868 OnCbnSelchangeComboBodies();
869 constraintDlg->LoadFile( file );
870 gameEdit->AF_UpdateEntities( file->GetName() );
871 AFDialogSetFileModified();
874 InitNewRenameDeleteButtons();
877 void DialogAFBody::OnCbnSelchangeComboCmType() {
878 InitCollisionModelType();
882 void DialogAFBody::ValidateCollisionModelLength( bool update ) {
883 if ( cm_length < 1.0f ) {
892 void DialogAFBody::OnEnChangeEditCmLength() {
893 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_CM_LENGTH ) ) ) {
894 ValidateCollisionModelLength( false );
898 cm_length = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_CM_LENGTH ), false );
902 void DialogAFBody::OnDeltaposSpinCmLength(NMHDR *pNMHDR, LRESULT *pResult) {
903 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
904 if ( pNMUpDown->iDelta < 0 ) {
907 else if ( cm_length >= 2.0f ) {
910 ValidateCollisionModelLength( true );
915 void DialogAFBody::ValidateCollisionModelHeight( bool update ) {
916 if ( cm_height < 1.0f ) {
925 void DialogAFBody::OnEnChangeEditCmHeight() {
926 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_CM_HEIGHT ) ) ) {
927 ValidateCollisionModelHeight( false );
931 cm_height = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_CM_HEIGHT ), false );
935 void DialogAFBody::OnDeltaposSpinCmHeight(NMHDR *pNMHDR, LRESULT *pResult) {
936 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
937 if ( pNMUpDown->iDelta < 0 ) {
940 else if ( cm_height >= 2.0f ) {
943 ValidateCollisionModelHeight( true );
948 void DialogAFBody::ValidateCollisionModelWidth( bool update ) {
949 if ( cm_width < 1.0f ) {
958 void DialogAFBody::OnEnChangeEditCmWidth() {
959 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_CM_WIDTH ) ) ) {
960 ValidateCollisionModelWidth( false );
964 cm_width = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_CM_WIDTH ), false );
968 void DialogAFBody::OnDeltaposSpinCmWidth(NMHDR *pNMHDR, LRESULT *pResult) {
969 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
970 if ( pNMUpDown->iDelta < 0 ) {
973 else if ( cm_width >= 2.0f ) {
976 ValidateCollisionModelWidth( true );
981 void DialogAFBody::ValidateCollisionModelNumSides( bool update ) {
982 cm_numSides = (int) cm_numSides;
983 if ( cm_numSides < 3 ) {
987 else if ( cm_numSides > 10 ) {
996 void DialogAFBody::OnEnChangeEditCmNumsides() {
997 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_CM_NUMSIDES ) ) ) {
998 ValidateCollisionModelNumSides( false );
1003 void DialogAFBody::OnDeltaposSpinCmNumsides(NMHDR *pNMHDR, LRESULT *pResult) {
1004 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
1005 if ( pNMUpDown->iDelta < 0 ) {
1008 else if ( cm_numSides > 3 ) {
1011 ValidateCollisionModelNumSides( true );
1016 void DialogAFBody::OnCbnSelchangeComboBoneJoint1() {
1018 GetSafeComboBoxSelection( &cm_comboBoneJoint1, str, -1 );
1019 UnsetSafeComboBoxSelection( &cm_comboBoneJoint2, str );
1023 void DialogAFBody::OnCbnSelchangeComboBoneJoint2() {
1025 GetSafeComboBoxSelection( &cm_comboBoneJoint2, str, -1 );
1026 UnsetSafeComboBoxSelection( &cm_comboBoneJoint1, str );
1030 void DialogAFBody::ValidateCollisionModelDensity( bool update ) {
1031 if ( cm_density < 1e-6f ) {
1036 UpdateData( FALSE );
1040 void DialogAFBody::OnEnChangeEditCmDensity() {
1041 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_CM_DENSITY ) ) ) {
1042 ValidateCollisionModelDensity( false );
1046 cm_density = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_CM_DENSITY ), false );
1050 void DialogAFBody::OnDeltaposSpinCmDensity(NMHDR *pNMHDR, LRESULT *pResult) {
1051 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
1052 cm_density = EditSpinFloat( (CEdit *)GetDlgItem( IDC_EDIT_CM_DENSITY ), pNMUpDown->iDelta < 0 );
1053 ValidateCollisionModelDensity( false );
1058 void DialogAFBody::OnEnChangeEditCmInertiascale() {
1059 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_CM_INERTIASCALE ) ) ) {
1064 void DialogAFBody::OnBnClickedRadioOriginCoordinates() {
1065 if ( IsDlgButtonChecked( IDC_RADIO_ORIGIN_COORDINATES ) ) {
1067 body->origin.type = idAFVector::VEC_COORDS;
1073 void DialogAFBody::OnBnClickedRadioOriginBonecenter() {
1074 if ( IsDlgButtonChecked( IDC_RADIO_ORIGIN_BONECENTER ) ) {
1076 body->origin.type = idAFVector::VEC_BONECENTER;
1082 void DialogAFBody::OnBnClickedRadioOriginJoint() {
1083 if ( IsDlgButtonChecked( IDC_RADIO_ORIGIN_JOINT ) ) {
1085 body->origin.type = idAFVector::VEC_JOINT;
1091 void DialogAFBody::OnEnChangeEditAfVectorX() {
1092 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_AF_VECTOR_X ) ) ) {
1096 cm_origin_x = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_AF_VECTOR_X ) );
1100 void DialogAFBody::OnDeltaposSpinAfVectorX(NMHDR *pNMHDR, LRESULT *pResult) {
1101 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
1102 if ( pNMUpDown->iDelta < 0 ) {
1108 UpdateData( FALSE );
1113 void DialogAFBody::OnEnChangeEditAfVectorY() {
1114 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_AF_VECTOR_Y ) ) ) {
1118 cm_origin_y = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_AF_VECTOR_Y ) );
1122 void DialogAFBody::OnDeltaposSpinAfVectorY(NMHDR *pNMHDR, LRESULT *pResult) {
1123 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
1124 if ( pNMUpDown->iDelta < 0 ) {
1130 UpdateData( FALSE );
1135 void DialogAFBody::OnEnChangeEditAfVectorZ() {
1136 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_AF_VECTOR_Z ) ) ) {
1140 cm_origin_z = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_AF_VECTOR_Z ) );
1144 void DialogAFBody::OnDeltaposSpinAfVectorZ(NMHDR *pNMHDR, LRESULT *pResult) {
1145 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
1146 if ( pNMUpDown->iDelta < 0 ) {
1152 UpdateData( FALSE );
1157 void DialogAFBody::OnOnCbnSelchangeComboOriginBoneCenterJoint1() {
1159 GetSafeComboBoxSelection( &cm_originBoneCenterJoint1, str, -1 );
1160 UnsetSafeComboBoxSelection( &cm_originBoneCenterJoint2, str );
1164 void DialogAFBody::OnOnCbnSelchangeComboOriginBoneCenterJoint2() {
1166 GetSafeComboBoxSelection( &cm_originBoneCenterJoint2, str, -1 );
1167 UnsetSafeComboBoxSelection( &cm_originBoneCenterJoint1, str );
1171 void DialogAFBody::OnOnCbnSelchangeComboOriginJoint() {
1175 void DialogAFBody::OnEnChangeEditAnglesPitch() {
1176 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_ANGLES_PITCH ) ) ) {
1180 cm_angles_pitch = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_ANGLES_PITCH ) );
1184 void DialogAFBody::OnDeltaposSpinAnglesPitch(NMHDR *pNMHDR, LRESULT *pResult) {
1185 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
1186 if ( pNMUpDown->iDelta < 0 ) {
1187 cm_angles_pitch += 1;
1190 cm_angles_pitch -= 1;
1192 cm_angles_pitch = idMath::AngleNormalize360( cm_angles_pitch );
1193 UpdateData( FALSE );
1198 void DialogAFBody::OnEnChangeEditAnglesYaw() {
1199 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_ANGLES_YAW ) ) ) {
1203 cm_angles_yaw = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_ANGLES_YAW ) );
1207 void DialogAFBody::OnDeltaposSpinAnglesYaw(NMHDR *pNMHDR, LRESULT *pResult) {
1208 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
1209 if ( pNMUpDown->iDelta < 0 ) {
1215 cm_angles_yaw = idMath::AngleNormalize360( cm_angles_yaw );
1216 UpdateData( FALSE );
1221 void DialogAFBody::OnEnChangeEditAnglesRoll() {
1222 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_ANGLES_ROLL ) ) ) {
1226 cm_angles_roll = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_ANGLES_ROLL ) );
1230 void DialogAFBody::OnDeltaposSpinAnglesRoll(NMHDR *pNMHDR, LRESULT *pResult) {
1231 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
1232 if ( pNMUpDown->iDelta < 0 ) {
1233 cm_angles_roll += 1;
1236 cm_angles_roll -= 1;
1238 cm_angles_roll = idMath::AngleNormalize360( cm_angles_roll );
1239 UpdateData( FALSE );
1244 void DialogAFBody::OnBnClickedCheckSelfcollision() {
1248 void DialogAFBody::OnEnChangeEditContents() {
1249 if ( EditControlEnterHit( &m_editContents ) ) {
1254 void DialogAFBody::OnEnChangeEditClipmask() {
1255 if ( EditControlEnterHit( &m_editClipMask ) ) {
1260 void DialogAFBody::OnEnChangeEditLinearfriction() {
1261 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_LINEARFRICTION ) ) ) {
1265 m_linearFriction = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_LINEARFRICTION ), false );
1269 void DialogAFBody::OnDeltaposSpinLinearfriction(NMHDR *pNMHDR, LRESULT *pResult) {
1270 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
1271 m_linearFriction = EditSpinFloat( (CEdit *)GetDlgItem( IDC_EDIT_LINEARFRICTION ), pNMUpDown->iDelta < 0 );
1276 void DialogAFBody::OnEnChangeEditAngularfriction() {
1277 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_ANGULARFRICTION ) ) ) {
1281 m_angularFriction = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_ANGULARFRICTION ), false );
1285 void DialogAFBody::OnDeltaposSpinAngularfriction(NMHDR *pNMHDR, LRESULT *pResult) {
1286 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
1287 m_angularFriction = EditSpinFloat( (CEdit *)GetDlgItem( IDC_EDIT_ANGULARFRICTION ), pNMUpDown->iDelta < 0 );
1292 void DialogAFBody::OnEnChangeEditContactfriction() {
1293 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_CONTACTFRICTION ) ) ) {
1297 m_contactFriction = EditVerifyFloat( (CEdit *) GetDlgItem( IDC_EDIT_CONTACTFRICTION ), false );
1301 void DialogAFBody::OnDeltaposSpinContactfriction(NMHDR *pNMHDR, LRESULT *pResult) {
1302 LPNMUPDOWN pNMUpDown = reinterpret_cast<LPNMUPDOWN>(pNMHDR);
1303 m_contactFriction = EditSpinFloat( (CEdit *)GetDlgItem( IDC_EDIT_CONTACTFRICTION ), pNMUpDown->iDelta < 0 );
1308 void DialogAFBody::OnEnChangeEditFrictionDirection() {
1309 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_FRICTIONDIRECTION ) ) ) {
1314 void DialogAFBody::OnEnChangeEditContactMotorDirection() {
1315 if ( EditControlEnterHit( (CEdit *) GetDlgItem( IDC_EDIT_CONTACTMOTORDIRECTION ) ) ) {
1320 void DialogAFBody::OnCbnSelchangeComboModifiedjoint() {
1324 void DialogAFBody::OnBnClickedRadioModifyOrientation() {
1325 if ( IsDlgButtonChecked( IDC_RADIO_MODIFY_ORIENTATION ) ) {
1327 body->jointMod = DECLAF_JOINTMOD_AXIS;
1333 void DialogAFBody::OnBnClickedRadioModifyPosition() {
1334 if ( IsDlgButtonChecked( IDC_RADIO_MODIFY_POSITION ) ) {
1336 body->jointMod = DECLAF_JOINTMOD_ORIGIN;
1342 void DialogAFBody::OnBnClickedRadioModifyBoth() {
1343 if ( IsDlgButtonChecked( IDC_RADIO_MODIFY_BOTH ) ) {
1345 body->jointMod = DECLAF_JOINTMOD_BOTH;
1351 void DialogAFBody::OnEnChangeEditContainedjoints() {
1352 if ( EditControlEnterHit( &m_editContainedJoints ) ) {