GrabHandles.cpp 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339
  1. /*
  2. ** Command & Conquer Renegade(tm)
  3. ** Copyright 2025 Electronic Arts Inc.
  4. **
  5. ** This program is free software: you can redistribute it and/or modify
  6. ** it under the terms of the GNU General Public License as published by
  7. ** the Free Software Foundation, either version 3 of the License, or
  8. ** (at your option) any later version.
  9. **
  10. ** This program is distributed in the hope that it will be useful,
  11. ** but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. ** GNU General Public License for more details.
  14. **
  15. ** You should have received a copy of the GNU General Public License
  16. ** along with this program. If not, see <http://www.gnu.org/licenses/>.
  17. */
  18. /***********************************************************************************************
  19. *** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
  20. ***********************************************************************************************
  21. * *
  22. * Project Name : LevelEdit *
  23. * *
  24. * $Archive:: /Commando/Code/Tools/LevelEdit/GrabHandles.cpp $*
  25. * *
  26. * Author:: Patrick Smith *
  27. * *
  28. * $Modtime:: 3/28/01 3:16p $*
  29. * *
  30. * $Revision:: 8 $*
  31. * *
  32. *---------------------------------------------------------------------------------------------*
  33. * Functions: *
  34. * - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
  35. #include "stdafx.h"
  36. #include "grabhandles.h"
  37. #include "sceneeditor.h"
  38. #include "node.h"
  39. #include "hittestinfo.h"
  40. #include "utils.h"
  41. #include "mousemgr.h"
  42. //////////////////////////////////////////////////////////////////////
  43. //
  44. // GrabHandlesClass
  45. //
  46. //////////////////////////////////////////////////////////////////////
  47. GrabHandlesClass::GrabHandlesClass (void)
  48. : m_bIsAddedToScene (false),
  49. m_pNode (NULL)
  50. {
  51. Initialize ();
  52. return ;
  53. }
  54. //////////////////////////////////////////////////////////////////////
  55. //
  56. // GrabHandlesClass
  57. //
  58. //////////////////////////////////////////////////////////////////////
  59. GrabHandlesClass::GrabHandlesClass (const GrabHandlesClass &ref)
  60. : m_bIsAddedToScene (false),
  61. m_pNode (NULL)
  62. {
  63. *this = ref;
  64. Initialize ();
  65. return ;
  66. }
  67. //////////////////////////////////////////////////////////////////////
  68. //
  69. // ~GrabHandlesClass
  70. //
  71. //////////////////////////////////////////////////////////////////////
  72. GrabHandlesClass::~GrabHandlesClass (void)
  73. {
  74. // Loop through and destroy all the handles
  75. for (int handle = 0; handle < 8; handle ++) {
  76. MEMBER_RELEASE (m_pHandles[handle]);
  77. }
  78. return ;
  79. }
  80. //////////////////////////////////////////////////////////////////////
  81. //
  82. // Initialize
  83. //
  84. //////////////////////////////////////////////////////////////////////
  85. void
  86. GrabHandlesClass::Initialize (void)
  87. {
  88. // Create a default vertex material for the handles
  89. VertexMaterialClass *vmat = new VertexMaterialClass;
  90. vmat->Set_Emissive (1,1,1);
  91. vmat->Set_Diffuse (0,0,0);
  92. vmat->Set_Opacity (1.0F);
  93. // Loop through and create all the handles
  94. for (int handle = 0; handle < 8; handle ++) {
  95. m_pHandles[handle] = new GrabHandlePhysClass (handle, this);
  96. // Modify the color of this box to be solid black
  97. Box3DClass *pbox = m_pHandles[handle]->Get_Box ();
  98. pbox->Set_Shader (ShaderClass::_PresetOpaqueSolidShader);
  99. pbox->Set_Vertex_Material (vmat);
  100. pbox->Set_Color (Vector3 (0.0F, 0.0F, 0.0F));
  101. pbox->Disable_Sort ();
  102. pbox->Enable_Bounding_Sphere ();
  103. pbox->Enable_Bounding_Box ();
  104. }
  105. MEMBER_RELEASE (vmat);
  106. return ;
  107. }
  108. //////////////////////////////////////////////////////////////////////
  109. //
  110. // operator=
  111. //
  112. //////////////////////////////////////////////////////////////////////
  113. const GrabHandlesClass &
  114. GrabHandlesClass::operator= (const GrabHandlesClass &ref)
  115. {
  116. m_pNode = ref.m_pNode;
  117. // Return a reference to ourselves
  118. return *this;
  119. }
  120. //////////////////////////////////////////////////////////////////////
  121. //
  122. // Remove_From_Scene
  123. //
  124. //////////////////////////////////////////////////////////////////////
  125. void
  126. GrabHandlesClass::Remove_From_Scene (void)
  127. {
  128. if (m_bIsAddedToScene) {
  129. // Get a pointer to the current scene
  130. SceneEditorClass *pscene = ::Get_Scene_Editor ();
  131. // Were we successful in getting the scene pointer?
  132. ASSERT (pscene != NULL);
  133. if (pscene != NULL) {
  134. // Loop through and remove all the handles from the scene
  135. for (int handle = 0; handle < 8; handle ++) {
  136. if (m_pHandles[handle] != NULL) {
  137. pscene->Remove_Object (m_pHandles[handle]);
  138. }
  139. }
  140. // Success!
  141. m_bIsAddedToScene = false;
  142. }
  143. }
  144. return ;
  145. }
  146. //////////////////////////////////////////////////////////////////////
  147. //
  148. // Hide
  149. //
  150. //////////////////////////////////////////////////////////////////////
  151. void
  152. GrabHandlesClass::Hide (bool bhide)
  153. {
  154. // Loop through and hide all the handles
  155. for (int handle = 0; handle < 8; handle ++) {
  156. if (m_pHandles[handle] != NULL) {
  157. m_pHandles[handle]->Peek_Model ()->Set_Hidden (bhide);
  158. if (bhide == true) {
  159. m_pHandles[handle]->Inc_Ignore_Counter();
  160. } else if (m_pHandles[handle]->Is_Ignore_Me()) {
  161. m_pHandles[handle]->Dec_Ignore_Counter();
  162. }
  163. }
  164. }
  165. return ;
  166. }
  167. //////////////////////////////////////////////////////////////////////
  168. //
  169. // Position_Around_Node
  170. //
  171. //////////////////////////////////////////////////////////////////////
  172. void
  173. GrabHandlesClass::Position_Around_Node (NodeClass *node)
  174. {
  175. RenderObjClass *render_obj = node->Peek_Render_Obj ();
  176. if (render_obj != NULL) {
  177. //
  178. // Get the object's bounding box so we know where to
  179. // position the grab handles
  180. //
  181. AABoxClass bounding_box;
  182. render_obj->Get_Obj_Space_Bounding_Box (bounding_box);
  183. const Matrix3D &transform = render_obj->Get_Transform ();
  184. // Alias the extent vector
  185. Vector3 extent = bounding_box.Extent;
  186. extent.X = ::fabs (extent.X);
  187. extent.Y = ::fabs (extent.Y);
  188. extent.Z = ::fabs (extent.Z);
  189. //
  190. // Determine the new size for each grab handle
  191. //
  192. float largest_dim = max (extent.X, extent.Y);
  193. largest_dim = max (largest_dim, extent.Z);
  194. float size = max (largest_dim / 25.0F, 0.1F);
  195. // Calculate the positions of the eight verticies
  196. Vector3 verticies[8];
  197. verticies[0] = bounding_box.Center + Vector3 (-extent.X, extent.Y, -extent.Z);
  198. verticies[1] = bounding_box.Center + Vector3 (-extent.X, -extent.Y, -extent.Z);
  199. verticies[2] = bounding_box.Center + Vector3 (-extent.X, -extent.Y, extent.Z);
  200. verticies[3] = bounding_box.Center + Vector3 (-extent.X, extent.Y, extent.Z);
  201. verticies[4] = bounding_box.Center + Vector3 (extent.X, extent.Y, -extent.Z);
  202. verticies[5] = bounding_box.Center + Vector3 (extent.X, -extent.Y, -extent.Z);
  203. verticies[6] = bounding_box.Center + Vector3 (extent.X, -extent.Y, extent.Z);
  204. verticies[7] = bounding_box.Center + Vector3 (extent.X, extent.Y, extent.Z);
  205. // Now add 'handles' centered around each of the 8 verticies
  206. for (int vertex = 0; vertex < 8; vertex ++) {
  207. // Rotate these verticies using the item's current transform
  208. verticies[vertex] = transform * verticies[vertex];
  209. // Resize the box
  210. Box3DClass *pbox = m_pHandles[vertex]->Get_Box ();
  211. pbox->Set_Dimensions (Vector3 (size, size, size));
  212. //pbox->Set_Dimensions (Vector3 (1, 1, 1));
  213. // Reposition this handle so its centered around the vertex
  214. Matrix3D handle_transform = m_pHandles[vertex]->Get_Transform ();
  215. handle_transform.Set_Translation (verticies[vertex]);
  216. m_pHandles[vertex]->Set_Transform (handle_transform);
  217. }
  218. if (m_bIsAddedToScene == false) {
  219. // Get a pointer to the current scene
  220. SceneEditorClass *pscene = ::Get_Scene_Editor ();
  221. // Were we successful in getting the scene pointer?
  222. ASSERT (pscene != NULL);
  223. if (pscene != NULL) {
  224. // Loop through all the handles and add them to the scene
  225. for (int handle = 0; handle < 8; handle ++) {
  226. pscene->Add_Dynamic_Object (m_pHandles[handle]);
  227. }
  228. // Success!
  229. m_bIsAddedToScene = true;
  230. }
  231. }
  232. }
  233. m_pNode = node;
  234. return ;
  235. }
  236. //*********************************************************************************************//
  237. //
  238. // End of GrabHandlesClass
  239. //
  240. //*********************************************************************************************//
  241. //*********************************************************************************************//
  242. //
  243. // Start of GrabHandlePhysClass
  244. //
  245. //*********************************************************************************************//
  246. //////////////////////////////////////////////////////////////////////
  247. //
  248. // On_Click
  249. //
  250. //////////////////////////////////////////////////////////////////////
  251. void
  252. GrabHandlePhysClass::On_Click (void)
  253. {
  254. if (m_pParent != NULL) {
  255. // Switch to the 'grabhandle drag' mode
  256. MouseMgrClass *mousemgr = ::Get_Mouse_Mgr ();
  257. mousemgr->Set_Mouse_Mode (MouseMgrClass::MODE_GRABHANDLE_DRAG);
  258. // Pass on the node/vertex information onto the mode mgr
  259. MMGrabHandleDragClass *mode = (MMGrabHandleDragClass *)mousemgr->Get_Mode_Mgr ();
  260. if (mode != NULL) {
  261. mode->Set_Node_Info (m_pParent->Get_Node (), m_iVertex);
  262. }
  263. }
  264. return ;
  265. }
  266. //////////////////////////////////////////////////////////////////////
  267. //
  268. // Initialize
  269. //
  270. //////////////////////////////////////////////////////////////////////
  271. void
  272. GrabHandlePhysClass::Initialize (void)
  273. {
  274. Peek_Model ()->Set_User_Data (&m_HitTestInfo, FALSE);
  275. return ;
  276. }
  277. //*********************************************************************************************//
  278. //
  279. // End of GrabHandlePhysClass
  280. //
  281. //*********************************************************************************************//