guiObjectView.cpp 32 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003
  1. //-----------------------------------------------------------------------------
  2. // Copyright (c) 2012 GarageGames, LLC
  3. //
  4. // Permission is hereby granted, free of charge, to any person obtaining a copy
  5. // of this software and associated documentation files (the "Software"), to
  6. // deal in the Software without restriction, including without limitation the
  7. // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
  8. // sell copies of the Software, and to permit persons to whom the Software is
  9. // furnished to do so, subject to the following conditions:
  10. //
  11. // The above copyright notice and this permission notice shall be included in
  12. // all copies or substantial portions of the Software.
  13. //
  14. // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  15. // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  16. // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  17. // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  18. // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
  19. // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
  20. // IN THE SOFTWARE.
  21. //-----------------------------------------------------------------------------
  22. #include "T3D/guiObjectView.h"
  23. #include "renderInstance/renderPassManager.h"
  24. #include "lighting/lightManager.h"
  25. #include "lighting/lightInfo.h"
  26. #include "core/resourceManager.h"
  27. #include "scene/sceneManager.h"
  28. #include "scene/sceneRenderState.h"
  29. #include "console/consoleTypes.h"
  30. #include "math/mathTypes.h"
  31. #include "gfx/gfxTransformSaver.h"
  32. #include "console/engineAPI.h"
  33. IMPLEMENT_CONOBJECT( GuiObjectView );
  34. ConsoleDocClass( GuiObjectView,
  35. "@brief GUI control which displays a 3D model.\n\n"
  36. "Model displayed in the control can have other objects mounted onto it, and the light settings can be adjusted.\n\n"
  37. "@tsexample\n"
  38. " new GuiObjectView(ObjectPreview)\n"
  39. " {\n"
  40. " shapeFile = \"art/shapes/items/kit/healthkit.dts\";\n"
  41. " mountedNode = \"mount0\";\n"
  42. " lightColor = \"1 1 1 1\";\n"
  43. " lightAmbient = \"0.5 0.5 0.5 1\";\n"
  44. " lightDirection = \"0 0.707 -0.707\";\n"
  45. " orbitDiststance = \"2\";\n"
  46. " minOrbitDiststance = \"0.917688\";\n"
  47. " maxOrbitDiststance = \"5\";\n"
  48. " cameraSpeed = \"0.01\";\n"
  49. " cameraZRot = \"0\";\n"
  50. " forceFOV = \"0\";\n"
  51. " reflectPriority = \"0\";\n"
  52. " };\n"
  53. "@endtsexample\n\n"
  54. "@see GuiControl\n\n"
  55. "@ingroup Gui3D\n"
  56. );
  57. IMPLEMENT_CALLBACK( GuiObjectView, onMouseEnter, void, (),(),
  58. "@brief Called whenever the mouse enters the control.\n\n"
  59. "@tsexample\n"
  60. "// The mouse has entered the control, causing the callback to occur\n"
  61. "GuiObjectView::onMouseEnter(%this)\n"
  62. " {\n"
  63. " // Code to run when the mouse enters this control\n"
  64. " }\n"
  65. "@endtsexample\n\n"
  66. "@see GuiControl\n\n"
  67. );
  68. IMPLEMENT_CALLBACK( GuiObjectView, onMouseLeave, void, (),(),
  69. "@brief Called whenever the mouse leaves the control.\n\n"
  70. "@tsexample\n"
  71. "// The mouse has left the control, causing the callback to occur\n"
  72. "GuiObjectView::onMouseLeave(%this)\n"
  73. " {\n"
  74. " // Code to run when the mouse leaves this control\n"
  75. " }\n"
  76. "@endtsexample\n\n"
  77. "@see GuiControl\n\n"
  78. );
  79. //------------------------------------------------------------------------------
  80. GuiObjectView::GuiObjectView()
  81. : mMouseState( None ),
  82. mLastMousePoint( 0, 0 ),
  83. mModelInstance(NULL),
  84. mMaxOrbitDist( 5.0f ),
  85. mMinOrbitDist( 0.0f ),
  86. mCameraRotation( 0.0f, 0.0f, 0.0f ),
  87. mOrbitDist( 5.0f ),
  88. mCameraSpeed( 0.01f ),
  89. mMountNode( -1 ),
  90. mMountNodeName( "mount0" ),
  91. mMountedModelInstance( NULL ),
  92. mAnimationSeq( -1 ),
  93. mRunThread( NULL ),
  94. mLastRenderTime( 0 ),
  95. mLight( NULL ),
  96. mLightColor( 1.0f, 1.0f, 1.0f ),
  97. mLightAmbient( 1.0f, 1.0f, 1.0f ),
  98. mLightDirection( 0.f, 0.707f, -0.707f )
  99. {
  100. mCameraMatrix.identity();
  101. mCameraRot.set( 0.0f, 0.0f, 3.9f );
  102. mCameraPos.set( 0.0f, 0.0f, 0.0f );
  103. mCameraMatrix.setColumn( 3, mCameraPos );
  104. mOrbitPos.set( 0.0f, 0.0f, 0.0f );
  105. // By default don't do dynamic reflection
  106. // updates for this viewport.
  107. mReflectPriority = 0.0f;
  108. INIT_ASSET(Model);
  109. INIT_ASSET(MountedModel);
  110. }
  111. //------------------------------------------------------------------------------
  112. GuiObjectView::~GuiObjectView()
  113. {
  114. if( mLight )
  115. SAFE_DELETE( mLight );
  116. }
  117. //------------------------------------------------------------------------------
  118. void GuiObjectView::initPersistFields()
  119. {
  120. docsURL;
  121. addGroup( "Model" );
  122. INITPERSISTFIELD_SHAPEASSET(Model, GuiObjectView, "The source shape asset.");
  123. addField( "skin", TypeRealString, Offset( mSkinName, GuiObjectView ),
  124. "The skin to use on the object model." );
  125. endGroup( "Model" );
  126. addGroup( "Animation" );
  127. addField( "animSequence", TypeRealString, Offset( mAnimationSeqName, GuiObjectView ),
  128. "The animation sequence to play on the model." );
  129. endGroup( "Animation" );
  130. addGroup( "Mounting" );
  131. INITPERSISTFIELD_SHAPEASSET(MountedModel, GuiObjectView, "The mounted shape asset.");
  132. addField( "mountedSkin", TypeRealString, Offset( mMountSkinName, GuiObjectView ),
  133. "Skin name used on mounted shape file." );
  134. addField( "mountedNode", TypeRealString, Offset( mMountNodeName, GuiObjectView ),
  135. "Name of node on primary model to which to mount the secondary shape." );
  136. endGroup( "Mounting" );
  137. addGroup( "Lighting" );
  138. addField( "lightColor", TypeColorF, Offset( mLightColor, GuiObjectView ),
  139. "Diffuse color of the sunlight used to render the model." );
  140. addField( "lightAmbient", TypeColorF, Offset( mLightAmbient, GuiObjectView ),
  141. "Ambient color of the sunlight used to render the model." );
  142. addField( "lightDirection", TypePoint3F, Offset( mLightDirection, GuiObjectView ),
  143. "Direction from which the model is illuminated." );
  144. endGroup( "Lighting" );
  145. addGroup( "Camera" );
  146. addField( "orbitDiststance", TypeF32, Offset( mOrbitDist, GuiObjectView ),
  147. "Distance from which to render the model." );
  148. addField( "minOrbitDiststance", TypeF32, Offset( mMinOrbitDist, GuiObjectView ),
  149. "Maxiumum distance to which the camera can be zoomed out." );
  150. addField( "maxOrbitDiststance", TypeF32, Offset( mMaxOrbitDist, GuiObjectView ),
  151. "Minimum distance below which the camera will not zoom in further." );
  152. addField( "cameraSpeed", TypeF32, Offset( mCameraSpeed, GuiObjectView ),
  153. "Multiplier for mouse camera operations." );
  154. addField( "cameraRotation", TypePoint3F, Offset( mCameraRotation, GuiObjectView ),
  155. "Set the camera rotation." );
  156. endGroup( "Camera" );
  157. Parent::initPersistFields();
  158. }
  159. //------------------------------------------------------------------------------
  160. void GuiObjectView::onStaticModified( StringTableEntry slotName, const char* newValue )
  161. {
  162. Parent::onStaticModified( slotName, newValue );
  163. static StringTableEntry sSkin = StringTable->insert( "skin" );
  164. static StringTableEntry sMountedSkin = StringTable->insert( "mountedSkin" );
  165. static StringTableEntry sMountedNode = StringTable->insert( "mountedNode" );
  166. static StringTableEntry sLightColor = StringTable->insert( "lightColor" );
  167. static StringTableEntry sLightAmbient = StringTable->insert( "lightAmbient" );
  168. static StringTableEntry sLightDirection = StringTable->insert( "lightDirection" );
  169. static StringTableEntry sOrbitDistance = StringTable->insert( "orbitDistance" );
  170. static StringTableEntry sMinOrbitDistance = StringTable->insert( "minOrbitDistance" );
  171. static StringTableEntry sMaxOrbitDistance = StringTable->insert( "maxOrbitDistance" );
  172. static StringTableEntry sCameraRotation = StringTable->insert( "cameraRotation" );
  173. static StringTableEntry sAnimSequence = StringTable->insert( "animSequence" );
  174. if( slotName == sSkin )
  175. setSkin( String( mSkinName ) );
  176. else if( slotName == sMountedSkin )
  177. setMountSkin( String( mMountSkinName ) );
  178. else if( slotName == sMountedNode )
  179. setMountNode( String( mMountNodeName ) );
  180. else if( slotName == sLightColor )
  181. setLightColor( mLightColor );
  182. else if( slotName == sLightAmbient )
  183. setLightAmbient( mLightAmbient );
  184. else if( slotName == sLightDirection )
  185. setLightDirection( mLightDirection );
  186. else if( slotName == sOrbitDistance || slotName == sMinOrbitDistance || slotName == sMaxOrbitDistance )
  187. setOrbitDistance( mOrbitDist );
  188. else if( slotName == sCameraRotation )
  189. setCameraRotation( mCameraRotation );
  190. else if( slotName == sAnimSequence )
  191. setObjectAnimation( String( mAnimationSeqName ) );
  192. }
  193. //------------------------------------------------------------------------------
  194. bool GuiObjectView::onWake()
  195. {
  196. if( !Parent::onWake() )
  197. return false;
  198. if( !mLight )
  199. {
  200. mLight = LIGHTMGR->createLightInfo();
  201. mLight->setColor( mLightColor );
  202. mLight->setAmbient( mLightAmbient );
  203. mLight->setDirection( mLightDirection );
  204. }
  205. return true;
  206. }
  207. //------------------------------------------------------------------------------
  208. void GuiObjectView::onMouseDown( const GuiEvent &event )
  209. {
  210. if( !mActive || !mVisible || !mAwake )
  211. return;
  212. mMouseState = Rotating;
  213. mLastMousePoint = event.mousePoint;
  214. mouseLock();
  215. }
  216. //------------------------------------------------------------------------------
  217. void GuiObjectView::onMouseUp( const GuiEvent &event )
  218. {
  219. mouseUnlock();
  220. mMouseState = None;
  221. }
  222. //------------------------------------------------------------------------------
  223. void GuiObjectView::onMouseDragged( const GuiEvent &event )
  224. {
  225. if( mMouseState != Rotating )
  226. return;
  227. Point2I delta = event.mousePoint - mLastMousePoint;
  228. mLastMousePoint = event.mousePoint;
  229. mCameraRot.x += ( delta.y * mCameraSpeed );
  230. mCameraRot.z += ( delta.x * mCameraSpeed );
  231. }
  232. //------------------------------------------------------------------------------
  233. void GuiObjectView::onRightMouseDown( const GuiEvent &event )
  234. {
  235. mMouseState = Zooming;
  236. mLastMousePoint = event.mousePoint;
  237. mouseLock();
  238. }
  239. //------------------------------------------------------------------------------
  240. void GuiObjectView::onRightMouseUp( const GuiEvent &event )
  241. {
  242. mouseUnlock();
  243. mMouseState = None;
  244. }
  245. //------------------------------------------------------------------------------
  246. void GuiObjectView::onRightMouseDragged( const GuiEvent &event )
  247. {
  248. if( mMouseState != Zooming )
  249. return;
  250. S32 delta = event.mousePoint.y - mLastMousePoint.y;
  251. mLastMousePoint = event.mousePoint;
  252. mOrbitDist += ( delta * mCameraSpeed );
  253. }
  254. //------------------------------------------------------------------------------
  255. void GuiObjectView::setObjectAnimation( S32 index )
  256. {
  257. mAnimationSeq = index;
  258. mAnimationSeqName = String();
  259. if(mModelInstance)
  260. _initAnimation();
  261. }
  262. //------------------------------------------------------------------------------
  263. void GuiObjectView::setObjectAnimation( const String& sequenceName )
  264. {
  265. mAnimationSeq = -1;
  266. mAnimationSeqName = sequenceName;
  267. if(mModelInstance)
  268. _initAnimation();
  269. }
  270. //------------------------------------------------------------------------------
  271. bool GuiObjectView::setObjectModel( const String& modelName )
  272. {
  273. mRunThread = 0;
  274. // Load the shape.
  275. _setModel(modelName);
  276. if( !getModelResource())
  277. {
  278. Con::warnf( "GuiObjectView::setObjectModel - Failed to load model '%s'", modelName.c_str() );
  279. return false;
  280. }
  281. if (!getModelResource()->preloadMaterialList(getModelResource().getPath())) return false;
  282. // Instantiate it.
  283. mModelInstance = new TSShapeInstance(getModelResource(), true );
  284. mModelInstance->resetMaterialList();
  285. mModelInstance->cloneMaterialList();
  286. if( !mSkinName.isEmpty() )
  287. mModelInstance->reSkin( mSkinName );
  288. TSMaterialList* pMatList = mModelInstance->getMaterialList();
  289. pMatList->setTextureLookupPath(mModelAsset->getShapeFileName());
  290. mModelInstance->initMaterialList();
  291. // Initialize camera values.
  292. mOrbitPos = getModelResource()->center;
  293. mMinOrbitDist = getModelResource()->mRadius;
  294. // Initialize animation.
  295. _initAnimation();
  296. _initMount();
  297. return true;
  298. }
  299. void GuiObjectView::onModelChanged()
  300. {
  301. }
  302. //------------------------------------------------------------------------------
  303. void GuiObjectView::setSkin( const String& name )
  304. {
  305. if(mModelInstance)
  306. mModelInstance->reSkin( name, mSkinName );
  307. mSkinName = name;
  308. }
  309. //------------------------------------------------------------------------------
  310. bool GuiObjectView::setMountedObject( const String& modelName )
  311. {
  312. // Load the model.
  313. _setMountedModel(modelName);
  314. if (!getMountedModelResource())
  315. {
  316. Con::warnf("GuiObjectView::setMountedObject - Failed to load model '%s'", modelName.c_str());
  317. return false;
  318. }
  319. if (!getMountedModelResource()->preloadMaterialList(getMountedModelResource().getPath())) return false;
  320. mMountedModelInstance = new TSShapeInstance(getMountedModelResource(), true);
  321. mMountedModelInstance->resetMaterialList();
  322. mMountedModelInstance->cloneMaterialList();
  323. if( !mMountSkinName.isEmpty() )
  324. mMountedModelInstance->reSkin( mMountSkinName );
  325. mMountedModelInstance->initMaterialList();
  326. if(mMountedModelInstance)
  327. _initMount();
  328. return true;
  329. }
  330. void GuiObjectView::onMountedModelChanged()
  331. {
  332. }
  333. //------------------------------------------------------------------------------
  334. void GuiObjectView::setMountSkin(const String& name)
  335. {
  336. if (mMountedModelInstance)
  337. mMountedModelInstance->reSkin(name, mMountSkinName);
  338. mMountSkinName = name;
  339. }
  340. //------------------------------------------------------------------------------
  341. void GuiObjectView::setMountNode(S32 index)
  342. {
  343. setMountNode(String::ToString("mount%i", index));
  344. }
  345. //------------------------------------------------------------------------------
  346. void GuiObjectView::setMountNode(const String& name)
  347. {
  348. mMountNodeName = name;
  349. if (mModelInstance)
  350. _initMount();
  351. }
  352. //------------------------------------------------------------------------------
  353. bool GuiObjectView::processCameraQuery( CameraQuery* query )
  354. {
  355. // Adjust the camera so that we are still facing the model.
  356. Point3F vec;
  357. MatrixF xRot, zRot;
  358. xRot.set( EulerF( mCameraRot.x, 0.0f, 0.0f ) );
  359. zRot.set( EulerF( 0.0f, 0.0f, mCameraRot.z ) );
  360. mCameraMatrix.mul( zRot, xRot );
  361. mCameraMatrix.getColumn( 1, &vec );
  362. vec *= mOrbitDist;
  363. mCameraPos = mOrbitPos - vec;
  364. query->farPlane = 2100.0f;
  365. query->nearPlane = query->farPlane / 5000.0f;
  366. query->fov = 45.0f;
  367. mCameraMatrix.setColumn( 3, mCameraPos );
  368. query->cameraMatrix = mCameraMatrix;
  369. return true;
  370. }
  371. //------------------------------------------------------------------------------
  372. void GuiObjectView::onMouseEnter( const GuiEvent & event )
  373. {
  374. onMouseEnter_callback();
  375. }
  376. //------------------------------------------------------------------------------
  377. void GuiObjectView::onMouseLeave( const GuiEvent & event )
  378. {
  379. onMouseLeave_callback();
  380. }
  381. //------------------------------------------------------------------------------
  382. void GuiObjectView::renderWorld( const RectI& updateRect )
  383. {
  384. if( !mModelInstance)
  385. return;
  386. GFXTransformSaver _saveTransforms;
  387. // Determine the camera position, and store off render state.
  388. MatrixF modelview;
  389. MatrixF mv;
  390. Point3F cp;
  391. modelview = GFX->getWorldMatrix();
  392. mv = modelview;
  393. mv.inverse();
  394. mv.getColumn( 3, &cp );
  395. RenderPassManager* renderPass = gClientSceneGraph->getDefaultRenderPass();
  396. S32 time = Platform::getVirtualMilliseconds();
  397. S32 dt = time - mLastRenderTime;
  398. mLastRenderTime = time;
  399. LIGHTMGR->unregisterAllLights();
  400. LIGHTMGR->setSpecialLight( LightManager::slSunLightType, mLight );
  401. GFX->setStateBlock( mDefaultGuiSB );
  402. F32 left, right, top, bottom, nearPlane, farPlane;
  403. bool isOrtho;
  404. GFX->getFrustum( &left, &right, &bottom, &top, &nearPlane, &farPlane, &isOrtho );
  405. Frustum frust( false, left, right, top, bottom, nearPlane, farPlane, MatrixF::Identity );
  406. SceneRenderState state
  407. (
  408. gClientSceneGraph,
  409. SPT_Diffuse,
  410. SceneCameraState( GFX->getViewport(), frust, MatrixF::Identity, GFX->getProjectionMatrix() ),
  411. renderPass,
  412. true
  413. );
  414. // Set up our TS render state here.
  415. TSRenderState rdata;
  416. rdata.setSceneState( &state );
  417. // We might have some forward lit materials
  418. // so pass down a query to gather lights.
  419. LightQuery query;
  420. query.init( SphereF( Point3F::Zero, 1.0f ) );
  421. rdata.setLightQuery( &query );
  422. // Render primary model.
  423. if(mModelInstance)
  424. {
  425. if( mRunThread )
  426. {
  427. mModelInstance->advanceTime( dt / 1000.f, mRunThread );
  428. mModelInstance->animate();
  429. }
  430. mModelInstance->render( rdata );
  431. }
  432. // Render mounted model.
  433. if( mMountedModelInstance && mMountNode != -1 )
  434. {
  435. GFX->pushWorldMatrix();
  436. GFX->multWorld(mModelInstance->mNodeTransforms[ mMountNode ] );
  437. GFX->multWorld( mMountTransform );
  438. mMountedModelInstance->render( rdata );
  439. GFX->popWorldMatrix();
  440. }
  441. renderPass->renderPass( &state );
  442. // Make sure to remove our fake sun.
  443. LIGHTMGR->unregisterAllLights();
  444. }
  445. //------------------------------------------------------------------------------
  446. void GuiObjectView::setOrbitDistance( F32 distance )
  447. {
  448. // Make sure the orbit distance is within the acceptable range
  449. mOrbitDist = mClampF( distance, mMinOrbitDist, mMaxOrbitDist );
  450. }
  451. //------------------------------------------------------------------------------
  452. void GuiObjectView::setCameraSpeed( F32 factor )
  453. {
  454. mCameraSpeed = factor;
  455. }
  456. //------------------------------------------------------------------------------
  457. void GuiObjectView::setCameraRotation( const EulerF& rotation )
  458. {
  459. mCameraRot.set(rotation);
  460. }
  461. //------------------------------------------------------------------------------
  462. void GuiObjectView::setLightColor( const LinearColorF& color )
  463. {
  464. mLightColor = color;
  465. if( mLight )
  466. mLight->setColor( color );
  467. }
  468. //------------------------------------------------------------------------------
  469. void GuiObjectView::setLightAmbient( const LinearColorF& color )
  470. {
  471. mLightAmbient = color;
  472. if( mLight )
  473. mLight->setAmbient( color );
  474. }
  475. //------------------------------------------------------------------------------
  476. void GuiObjectView::setLightDirection( const Point3F& direction )
  477. {
  478. mLightDirection = direction;
  479. if( mLight )
  480. mLight->setDirection( direction );
  481. }
  482. //------------------------------------------------------------------------------
  483. void GuiObjectView::_initAnimation()
  484. {
  485. AssertFatal(getModelResource(), "GuiObjectView::_initAnimation - No model loaded!" );
  486. if( mAnimationSeqName.isEmpty() && mAnimationSeq == -1 )
  487. return;
  488. // Look up sequence by name.
  489. if( !mAnimationSeqName.isEmpty() )
  490. {
  491. mAnimationSeq = getModelResource()->findSequence( mAnimationSeqName );
  492. if( mAnimationSeq == -1 )
  493. {
  494. Con::errorf( "GuiObjectView::_initAnimation - Cannot find animation sequence '%s' on '%s'",
  495. mAnimationSeqName.c_str(),
  496. mModelName
  497. );
  498. return;
  499. }
  500. }
  501. // Start sequence.
  502. if( mAnimationSeq != -1 )
  503. {
  504. if( mAnimationSeq >= getModelResource()->sequences.size() )
  505. {
  506. Con::errorf( "GuiObjectView::_initAnimation - Sequence '%i' out of range for model '%s'",
  507. mAnimationSeq,
  508. mModelName
  509. );
  510. mAnimationSeq = -1;
  511. return;
  512. }
  513. if( !mRunThread )
  514. mRunThread = mModelInstance->addThread();
  515. mModelInstance->setSequence( mRunThread, mAnimationSeq, 0.f );
  516. }
  517. mLastRenderTime = Platform::getVirtualMilliseconds();
  518. }
  519. //------------------------------------------------------------------------------
  520. void GuiObjectView::_initMount()
  521. {
  522. AssertFatal(mModelInstance, "GuiObjectView::_initMount - No model loaded!" );
  523. if( !mModelInstance)
  524. return;
  525. mMountTransform.identity();
  526. // Look up the node to which to mount to.
  527. if( !mMountNodeName.isEmpty() )
  528. {
  529. mMountNode = getModelResource()->findNode( mMountNodeName );
  530. if( mMountNode == -1 )
  531. {
  532. Con::errorf( "GuiObjectView::_initMount - No node '%s' on '%s'",
  533. mMountNodeName.c_str(),
  534. mModelName
  535. );
  536. return;
  537. }
  538. }
  539. // Make sure mount node is valid.
  540. if( mMountNode != -1 && mMountNode >= getModelResource()->nodes.size() )
  541. {
  542. Con::errorf( "GuiObjectView::_initMount - Mount node index '%i' out of range for '%s'",
  543. mMountNode,
  544. mModelName
  545. );
  546. mMountNode = -1;
  547. return;
  548. }
  549. // Look up node on the mounted model from
  550. // which to mount to the primary model's node.
  551. if (!getMountedModelResource()) return;
  552. S32 mountPoint = getMountedModelResource()->findNode( "mountPoint" );
  553. if( mountPoint != -1 )
  554. {
  555. getMountedModelResource()->getNodeWorldTransform(mountPoint, &mMountTransform),
  556. mMountTransform.inverse();
  557. }
  558. }
  559. //=============================================================================
  560. // Console Methods.
  561. //=============================================================================
  562. // MARK: ---- Console Methods ----
  563. //-----------------------------------------------------------------------------
  564. DefineEngineMethod( GuiObjectView, getModel, const char*, (),,
  565. "@brief Return the model displayed in this view.\n\n"
  566. "@tsexample\n"
  567. "// Request the displayed model name from the GuiObjectView object.\n"
  568. "%modelName = %thisGuiObjectView.getModel();\n"
  569. "@endtsexample\n\n"
  570. "@return Name of the displayed model.\n\n"
  571. "@see GuiControl")
  572. {
  573. return Con::getReturnBuffer( object->getModel() );
  574. }
  575. //-----------------------------------------------------------------------------
  576. DefineEngineMethod( GuiObjectView, setModel, bool, (const char* shapeName),,
  577. "@brief Sets the model to be displayed in this control.\n\n"
  578. "@param shapeName Name of the model to display.\n"
  579. "@tsexample\n"
  580. "// Define the model we want to display\n"
  581. "%shapeName = \"gideon.dts\";\n\n"
  582. "// Tell the GuiObjectView object to display the defined model\n"
  583. "%thisGuiObjectView.setModel(%shapeName);\n"
  584. "@endtsexample\n\n"
  585. "@see GuiControl")
  586. {
  587. return object->setObjectModel( shapeName );
  588. }
  589. //-----------------------------------------------------------------------------
  590. DefineEngineMethod( GuiObjectView, getMountedModel, const char*, (),,
  591. "@brief Return the name of the mounted model.\n\n"
  592. "@tsexample\n"
  593. "// Request the name of the mounted model from the GuiObjectView object\n"
  594. "%mountedModelName = %thisGuiObjectView.getMountedModel();\n"
  595. "@endtsexample\n\n"
  596. "@return Name of the mounted model.\n\n"
  597. "@see GuiControl")
  598. {
  599. return Con::getReturnBuffer( object->getMountedModel() );
  600. }
  601. //-----------------------------------------------------------------------------
  602. DefineEngineMethod( GuiObjectView, setMountedModel, void, (const char* shapeName),,
  603. "@brief Sets the model to be mounted on the primary model.\n\n"
  604. "@param shapeName Name of the model to mount.\n"
  605. "@tsexample\n"
  606. "// Define the model name to mount\n"
  607. "%modelToMount = \"GideonGlasses.dts\";\n\n"
  608. "// Inform the GuiObjectView object to mount the defined model to the existing model in the control\n"
  609. "%thisGuiObjectView.setMountedModel(%modelToMount);\n"
  610. "@endtsexample\n\n"
  611. "@see GuiControl")
  612. {
  613. object->setObjectModel(shapeName);
  614. }
  615. //-----------------------------------------------------------------------------
  616. DefineEngineMethod( GuiObjectView, getSkin, const char*, (),,
  617. "@brief Return the name of skin used on the primary model.\n\n"
  618. "@tsexample\n"
  619. "// Request the name of the skin used on the primary model in the control\n"
  620. "%skinName = %thisGuiObjectView.getSkin();\n"
  621. "@endtsexample\n\n"
  622. "@return Name of the skin used on the primary model.\n\n"
  623. "@see GuiControl")
  624. {
  625. return Con::getReturnBuffer( object->getSkin() );
  626. }
  627. //-----------------------------------------------------------------------------
  628. DefineEngineMethod( GuiObjectView, setSkin, void, (const char* skinName),,
  629. "@brief Sets the skin to use on the model being displayed.\n\n"
  630. "@param skinName Name of the skin to use.\n"
  631. "@tsexample\n"
  632. "// Define the skin we want to apply to the main model in the control\n"
  633. "%skinName = \"disco_gideon\";\n\n"
  634. "// Inform the GuiObjectView control to update the skin the to defined skin\n"
  635. "%thisGuiObjectView.setSkin(%skinName);\n"
  636. "@endtsexample\n\n"
  637. "@see GuiControl")
  638. {
  639. object->setSkin( skinName );
  640. }
  641. //-----------------------------------------------------------------------------
  642. DefineEngineMethod( GuiObjectView, getMountSkin, const char*, ( S32 param1, S32 param2),,
  643. "@brief Return the name of skin used on the mounted model.\n\n"
  644. "@tsexample\n"
  645. "// Request the skin name from the model mounted on to the main model in the control\n"
  646. "%mountModelSkin = %thisGuiObjectView.getMountSkin();\n"
  647. "@endtsexample\n\n"
  648. "@return Name of the skin used on the mounted model.\n\n"
  649. "@see GuiControl")
  650. {
  651. return Con::getReturnBuffer( object->getMountSkin() );
  652. }
  653. //-----------------------------------------------------------------------------
  654. DefineEngineMethod( GuiObjectView, setMountSkin, void, (const char* skinName),,
  655. "@brief Sets the skin to use on the mounted model.\n\n"
  656. "@param skinName Name of the skin to set on the model mounted to the main model in the control\n"
  657. "@tsexample\n"
  658. "// Define the name of the skin\n"
  659. "%skinName = \"BronzeGlasses\";\n\n"
  660. "// Inform the GuiObjectView Control of the skin to use on the mounted model\n"
  661. "%thisGuiObjectViewCtrl.setMountSkin(%skinName);\n"
  662. "@endtsexample\n\n"
  663. "@see GuiControl")
  664. {
  665. object->setMountSkin(skinName);
  666. }
  667. //-----------------------------------------------------------------------------
  668. DefineEngineMethod( GuiObjectView, setSeq, void, (const char* indexOrName),,
  669. "@brief Sets the animation to play for the viewed object.\n\n"
  670. "@param indexOrName The index or name of the animation to play.\n"
  671. "@tsexample\n"
  672. "// Set the animation index value, or animation sequence name.\n"
  673. "%indexVal = \"3\";\n"
  674. "//OR:\n"
  675. "%indexVal = \"idle\";\n\n"
  676. "// Inform the GuiObjectView object to set the animation sequence of the object in the control.\n"
  677. "%thisGuiObjectVew.setSeq(%indexVal);\n"
  678. "@endtsexample\n\n"
  679. "@see GuiControl")
  680. {
  681. if( dIsdigit( indexOrName[0] ) )
  682. object->setObjectAnimation( dAtoi( indexOrName ) );
  683. else
  684. object->setObjectAnimation( indexOrName );
  685. }
  686. //-----------------------------------------------------------------------------
  687. DefineEngineMethod( GuiObjectView, setMount, void, ( const char* shapeName, const char* mountNodeIndexOrName),,
  688. "@brief Mounts the given model to the specified mount point of the primary model displayed in this control.\n\n"
  689. "Detailed description\n\n"
  690. "@param shapeName Name of the model to mount.\n"
  691. "@param mountNodeIndexOrName Index or name of the mount point to be mounted to. If index, corresponds to \"mountN\" in your shape where N is the number passed here.\n"
  692. "@tsexample\n"
  693. "// Set the shapeName to mount\n"
  694. "%shapeName = \"GideonGlasses.dts\"\n\n"
  695. "// Set the mount node of the primary model in the control to mount the new shape at\n"
  696. "%mountNodeIndexOrName = \"3\";\n"
  697. "//OR:\n"
  698. "%mountNodeIndexOrName = \"Face\";\n\n"
  699. "// Inform the GuiObjectView object to mount the shape at the specified node.\n"
  700. "%thisGuiObjectView.setMount(%shapeName,%mountNodeIndexOrName);\n"
  701. "@endtsexample\n\n"
  702. "@see GuiControl")
  703. {
  704. if( dIsdigit( mountNodeIndexOrName[0] ) )
  705. object->setMountNode( dAtoi( mountNodeIndexOrName ) );
  706. else
  707. object->setMountNode( mountNodeIndexOrName );
  708. object->setMountedObject( shapeName );
  709. }
  710. //-----------------------------------------------------------------------------
  711. DefineEngineMethod( GuiObjectView, getOrbitDistance, F32, (),,
  712. "@brief Return the current distance at which the camera orbits the object.\n\n"
  713. "@tsexample\n"
  714. "// Request the current orbit distance\n"
  715. "%orbitDistance = %thisGuiObjectView.getOrbitDistance();\n"
  716. "@endtsexample\n\n"
  717. "@return The distance at which the camera orbits the object.\n\n"
  718. "@see GuiControl")
  719. {
  720. return object->getOrbitDistance();
  721. }
  722. //-----------------------------------------------------------------------------
  723. DefineEngineMethod( GuiObjectView, setOrbitDistance, void, (F32 distance),,
  724. "@brief Sets the distance at which the camera orbits the object. Clamped to the acceptable range defined in the class by min and max orbit distances.\n\n"
  725. "Detailed description\n\n"
  726. "@param distance The distance to set the orbit to (will be clamped).\n"
  727. "@tsexample\n"
  728. "// Define the orbit distance value\n"
  729. "%orbitDistance = \"1.5\";\n\n"
  730. "// Inform the GuiObjectView object to set the orbit distance to the defined value\n"
  731. "%thisGuiObjectView.setOrbitDistance(%orbitDistance);\n"
  732. "@endtsexample\n\n"
  733. "@see GuiControl")
  734. {
  735. object->setOrbitDistance( distance );
  736. }
  737. //-----------------------------------------------------------------------------
  738. DefineEngineMethod( GuiObjectView, getCameraSpeed, F32, (),,
  739. "@brief Return the current multiplier for camera zooming and rotation.\n\n"
  740. "@tsexample\n"
  741. "// Request the current camera zooming and rotation multiplier value\n"
  742. "%multiplier = %thisGuiObjectView.getCameraSpeed();\n"
  743. "@endtsexample\n\n"
  744. "@return Camera zooming / rotation multiplier value.\n\n"
  745. "@see GuiControl")
  746. {
  747. return object->getCameraSpeed();
  748. }
  749. //-----------------------------------------------------------------------------
  750. DefineEngineMethod( GuiObjectView, setCameraSpeed, void, (F32 factor),,
  751. "@brief Sets the multiplier for the camera rotation and zoom speed.\n\n"
  752. "@param factor Multiplier for camera rotation and zoom speed.\n"
  753. "@tsexample\n"
  754. "// Set the factor value\n"
  755. "%factor = \"0.75\";\n\n"
  756. "// Inform the GuiObjectView object to set the camera speed.\n"
  757. "%thisGuiObjectView.setCameraSpeed(%factor);\n"
  758. "@endtsexample\n\n"
  759. "@see GuiControl")
  760. {
  761. object->setCameraSpeed( factor );
  762. }
  763. //-----------------------------------------------------------------------------
  764. DefineEngineMethod( GuiObjectView, setLightColor, void, ( LinearColorF color),,
  765. "@brief Set the light color on the sun object used to render the model.\n\n"
  766. "@param color Color of sunlight.\n"
  767. "@tsexample\n"
  768. "// Set the color value for the sun\n"
  769. "%color = \"1.0 0.4 0.5\";\n\n"
  770. "// Inform the GuiObjectView object to change the sun color to the defined value\n"
  771. "%thisGuiObjectView.setLightColor(%color);\n"
  772. "@endtsexample\n\n"
  773. "@see GuiControl")
  774. {
  775. object->setLightColor( color );
  776. }
  777. //-----------------------------------------------------------------------------
  778. DefineEngineMethod( GuiObjectView, setLightAmbient, void, (LinearColorF color),,
  779. "@brief Set the light ambient color on the sun object used to render the model.\n\n"
  780. "@param color Ambient color of sunlight.\n"
  781. "@tsexample\n"
  782. "// Define the sun ambient color value\n"
  783. "%color = \"1.0 0.4 0.6\";\n\n"
  784. "// Inform the GuiObjectView object to set the sun ambient color to the requested value\n"
  785. "%thisGuiObjectView.setLightAmbient(%color);\n"
  786. "@endtsexample\n\n"
  787. "@see GuiControl")
  788. {
  789. object->setLightAmbient( color );
  790. }
  791. //-----------------------------------------------------------------------------
  792. DefineEngineMethod( GuiObjectView, setLightDirection, void, (Point3F direction),,
  793. "@brief Set the light direction from which to light the model.\n\n"
  794. "@param direction XYZ direction from which the light will shine on the model\n"
  795. "@tsexample\n"
  796. "// Set the light direction\n"
  797. "%direction = \"1.0 0.2 0.4\"\n\n"
  798. "// Inform the GuiObjectView object to change the light direction to the defined value\n"
  799. "%thisGuiObjectView.setLightDirection(%direction);\n"
  800. "@endtsexample\n\n"
  801. "@see GuiControl")
  802. {
  803. object->setLightDirection( direction );
  804. }