SimulatedObjectModel.cpp 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452
  1. /*
  2. * Copyright (c) Contributors to the Open 3D Engine Project.
  3. * For complete copyright and license terms please see the LICENSE at the root of this distribution.
  4. *
  5. * SPDX-License-Identifier: Apache-2.0 OR MIT
  6. *
  7. */
  8. #include <EMotionFX/Source/AnimGraphInstance.h>
  9. #include <EMotionFX/Source/BlendTreeSimulatedObjectNode.h>
  10. #include <EMotionFX/Source/Skeleton.h>
  11. #include <EMotionFX/CommandSystem/Source/CommandManager.h>
  12. #include <EMotionFX/CommandSystem/Source/SimulatedObjectCommands.h>
  13. #include <EMotionFX/CommandSystem/Source/ColliderCommands.h>
  14. #include <Source/Editor/SimulatedObjectModel.h>
  15. #include <QtGui/QFont>
  16. #include <Editor/QtMetaTypes.h>
  17. namespace EMotionFX
  18. {
  19. int SimulatedObjectModel::s_columnCount = 1;
  20. const char* SimulatedObjectModel::s_simulatedObjectIconPath = ":/EMotionFX/SimulatedObject.svg";
  21. SimulatedObjectModel::SimulatedObjectModel()
  22. : m_selectionModel(new QItemSelectionModel(this))
  23. , m_objectIcon(s_simulatedObjectIconPath)
  24. {
  25. m_selectionModel->setModel(this);
  26. ActorInstance* selectedActorInstance = nullptr;
  27. ActorEditorRequestBus::BroadcastResult(selectedActorInstance, &ActorEditorRequests::GetSelectedActorInstance);
  28. if (selectedActorInstance)
  29. {
  30. SetActorInstance(selectedActorInstance);
  31. }
  32. else
  33. {
  34. Actor* selectedActor = nullptr;
  35. ActorEditorRequestBus::BroadcastResult(selectedActor, &ActorEditorRequests::GetSelectedActor);
  36. SetActor(selectedActor);
  37. }
  38. m_objectIcon.addFile(s_simulatedObjectIconPath, QSize(), QIcon::Selected);
  39. RegisterCommandCallbacks();
  40. }
  41. SimulatedObjectModel::~SimulatedObjectModel()
  42. {
  43. for (auto* callback : m_commandCallbacks)
  44. {
  45. CommandSystem::GetCommandManager()->RemoveCommandCallback(callback, false);
  46. delete callback;
  47. }
  48. }
  49. void SimulatedObjectModel::RegisterCommandCallbacks()
  50. {
  51. CommandSystem::GetCommandManager()->RegisterCommandCallback<CommandAddSimulatedObjectPreCallback>(CommandAddSimulatedObject::s_commandName, m_commandCallbacks, this, true, true);
  52. CommandSystem::GetCommandManager()->RegisterCommandCallback<CommandAddSimulatedObjectPostCallback>(CommandAddSimulatedObject::s_commandName, m_commandCallbacks, this);
  53. CommandSystem::GetCommandManager()->RegisterCommandCallback<CommandRemoveSimulatedObjectPreCallback>(CommandRemoveSimulatedObject::s_commandName, m_commandCallbacks, this, true, true);
  54. CommandSystem::GetCommandManager()->RegisterCommandCallback<CommandRemoveSimulatedObjectPostCallback>(CommandRemoveSimulatedObject::s_commandName, m_commandCallbacks, this);
  55. CommandSystem::GetCommandManager()->RegisterCommandCallback<CommandAdjustSimulatedObjectPostCallback>(CommandAdjustSimulatedObject::s_commandName, m_commandCallbacks, this, false, false);
  56. CommandSystem::GetCommandManager()->RegisterCommandCallback<CommandAddSimulatedJointsPreCallback>(CommandAddSimulatedJoints::s_commandName, m_commandCallbacks, this, true, true);
  57. CommandSystem::GetCommandManager()->RegisterCommandCallback<CommandAddSimulatedJointsPostCallback>(CommandAddSimulatedJoints::s_commandName, m_commandCallbacks, this);
  58. CommandSystem::GetCommandManager()->RegisterCommandCallback<CommandRemoveSimulatedJointsPreCallback>(CommandRemoveSimulatedJoints::s_commandName, m_commandCallbacks, this, true, true);
  59. CommandSystem::GetCommandManager()->RegisterCommandCallback<CommandRemoveSimulatedJointsPostCallback>(CommandRemoveSimulatedJoints::s_commandName, m_commandCallbacks, this);
  60. CommandSystem::GetCommandManager()->RegisterCommandCallback<CommandAdjustSimulatedJointPostCallback>(CommandAdjustSimulatedJoint::s_commandName, m_commandCallbacks, this, false, false);
  61. }
  62. void SimulatedObjectModel::SetActor(Actor* actor)
  63. {
  64. m_actorInstance = nullptr;
  65. m_actor = actor;
  66. m_skeleton = nullptr;
  67. if (m_actor)
  68. {
  69. m_skeleton = actor->GetSkeleton();
  70. }
  71. InitModel(actor);
  72. }
  73. void SimulatedObjectModel::SetActorInstance(ActorInstance* actorInstance)
  74. {
  75. m_actorInstance = actorInstance;
  76. m_actor = nullptr;
  77. m_skeleton = nullptr;
  78. if (m_actorInstance)
  79. {
  80. m_actor = actorInstance->GetActor();
  81. m_skeleton = m_actor->GetSkeleton();
  82. }
  83. InitModel(m_actor);
  84. }
  85. void SimulatedObjectModel::InitModel([[maybe_unused]] Actor* actor)
  86. {
  87. AZ_Assert(actor == m_actor, "Expected actor member to already be equal to specified actor pointer.");
  88. // Clear the model contents.
  89. beginResetModel();
  90. endResetModel();
  91. }
  92. QModelIndex SimulatedObjectModel::index(int row, int column, const QModelIndex& parent) const
  93. {
  94. if (!m_actor)
  95. {
  96. return QModelIndex();
  97. }
  98. const SimulatedObjectSetup* simulatedObjectSetup = m_actor->GetSimulatedObjectSetup().get();
  99. if (!simulatedObjectSetup || simulatedObjectSetup->GetNumSimulatedObjects() == 0)
  100. {
  101. // Can't build model index because there isn't any simulated object
  102. return QModelIndex();
  103. }
  104. if (!parent.isValid())
  105. {
  106. // Parent are not valid. This must be a simulated object.
  107. if (row >= static_cast<int>(simulatedObjectSetup->GetNumSimulatedObjects()))
  108. {
  109. return QModelIndex();
  110. }
  111. SimulatedObject* object = simulatedObjectSetup->GetSimulatedObject(row);
  112. return createIndex(row, column, object);
  113. }
  114. else
  115. {
  116. // Parent are valid. Is parent a simulated object or a simulated joint?
  117. const SimulatedCommon* common = static_cast<const SimulatedCommon*>(parent.internalPointer());
  118. if (azrtti_istypeof<SimulatedJoint>(common))
  119. {
  120. const SimulatedJoint* parentJoint = static_cast<SimulatedJoint*>(parent.internalPointer());
  121. SimulatedJoint* childJoint = parentJoint->FindChildSimulatedJoint(row);
  122. return createIndex(row, column, childJoint);
  123. }
  124. else
  125. {
  126. SimulatedObject* object = static_cast<SimulatedObject*>(parent.internalPointer());
  127. SimulatedJoint* joint = object->GetSimulatedRootJoint(row);
  128. return createIndex(row, column, joint);
  129. }
  130. }
  131. }
  132. QModelIndex SimulatedObjectModel::parent(const QModelIndex& child) const
  133. {
  134. if (!m_actor)
  135. {
  136. AZ_Assert(false, "Cannot get parent model index. Actor invalid.");
  137. return QModelIndex();
  138. }
  139. const SimulatedObjectSetup* simulatedObjectSetup = m_actor->GetSimulatedObjectSetup().get();
  140. AZ_Assert(child.isValid(), "Expected valid child model index.");
  141. const SimulatedCommon* common = static_cast<const SimulatedCommon*>(child.internalPointer());
  142. if (azrtti_istypeof<SimulatedJoint>(common))
  143. {
  144. const SimulatedJoint* childJoint = static_cast<const SimulatedJoint*>(common);
  145. SimulatedObject* simulatedObject = simulatedObjectSetup->FindSimulatedObjectByJoint(childJoint);
  146. if (simulatedObject)
  147. {
  148. SimulatedJoint* parentJoint = childJoint->FindParentSimulatedJoint();
  149. if (parentJoint)
  150. {
  151. return createIndex(aznumeric_caster(parentJoint->CalculateChildIndex()), 0, parentJoint);
  152. }
  153. else
  154. {
  155. const AZ::Outcome<size_t> simulatedObjectIndex = simulatedObjectSetup->FindSimulatedObjectIndex(simulatedObject);
  156. if (simulatedObjectIndex.IsSuccess())
  157. {
  158. return createIndex(static_cast<int>(simulatedObjectIndex.GetValue()), 0, simulatedObject);
  159. }
  160. }
  161. }
  162. }
  163. return QModelIndex();
  164. }
  165. int SimulatedObjectModel::rowCount(const QModelIndex& parent) const
  166. {
  167. if (!m_actor)
  168. {
  169. return 0;
  170. }
  171. const SimulatedObjectSetup* simulatedObjectSetup = m_actor->GetSimulatedObjectSetup().get();
  172. if (!simulatedObjectSetup || simulatedObjectSetup->GetNumSimulatedObjects() == 0)
  173. {
  174. return 0;
  175. }
  176. if (parent.isValid())
  177. {
  178. const SimulatedCommon* common = static_cast<const SimulatedCommon*>(parent.internalPointer());
  179. if (azrtti_istypeof<SimulatedJoint>(common))
  180. {
  181. const SimulatedJoint* joint = static_cast<SimulatedJoint*>(parent.internalPointer());
  182. const size_t childJointCount = joint->CalculateNumChildSimulatedJoints();
  183. return static_cast<int>(childJointCount);
  184. }
  185. else
  186. {
  187. const SimulatedObject* simulatedObject = static_cast<const SimulatedObject*>(common);
  188. return static_cast<int>(simulatedObject->GetNumSimulatedRootJoints());
  189. }
  190. }
  191. else
  192. {
  193. return static_cast<int>(simulatedObjectSetup->GetNumSimulatedObjects());
  194. }
  195. }
  196. int SimulatedObjectModel::columnCount([[maybe_unused]] const QModelIndex& parent) const
  197. {
  198. return s_columnCount;
  199. }
  200. QVariant SimulatedObjectModel::headerData(int section, Qt::Orientation orientation, int role) const
  201. {
  202. if (orientation == Qt::Horizontal && role == Qt::DisplayRole)
  203. {
  204. switch (section)
  205. {
  206. case COLUMN_NAME:
  207. return "Name";
  208. default:
  209. return "";
  210. }
  211. }
  212. return QVariant();
  213. }
  214. Qt::ItemFlags SimulatedObjectModel::flags(const QModelIndex& index) const
  215. {
  216. Qt::ItemFlags result = Qt::ItemIsSelectable | Qt::ItemIsEnabled | Qt::ItemIsUserCheckable;
  217. if (!m_skeleton || !index.isValid())
  218. {
  219. AZ_Assert(false, "Cannot get model data. Skeleton or model index invalid.");
  220. return Qt::NoItemFlags;
  221. }
  222. return result;
  223. }
  224. QVariant SimulatedObjectModel::data(const QModelIndex& index, int role) const
  225. {
  226. if (!m_actor || !m_skeleton || !index.isValid())
  227. {
  228. AZ_Assert(false, "Cannot get model data. Skeleton or model index invalid.");
  229. return QVariant();
  230. }
  231. SimulatedObject* object = nullptr;
  232. SimulatedJoint* joint = nullptr;
  233. const SimulatedObjectSetup* simulatedObjectSetup = m_actor->GetSimulatedObjectSetup().get();
  234. SimulatedCommon* simulatedCommon = static_cast<SimulatedCommon*>(index.internalPointer());
  235. if (azrtti_istypeof<SimulatedJoint>(simulatedCommon))
  236. {
  237. joint = static_cast<SimulatedJoint*>(simulatedCommon);
  238. }
  239. else
  240. {
  241. object = static_cast<SimulatedObject*>(simulatedCommon);
  242. }
  243. switch (role)
  244. {
  245. case Qt::DisplayRole:
  246. {
  247. switch (index.column())
  248. {
  249. case COLUMN_NAME:
  250. {
  251. if (object)
  252. {
  253. return object->GetName().c_str();
  254. }
  255. if (joint)
  256. {
  257. EMotionFX::Node* node = m_skeleton->GetNode(joint->GetSkeletonJointIndex());
  258. return node->GetName();
  259. }
  260. }
  261. default:
  262. break;
  263. }
  264. break;
  265. }
  266. case Qt::CheckStateRole:
  267. {
  268. break;
  269. }
  270. case Qt::DecorationRole:
  271. {
  272. if (index.column() == COLUMN_NAME && object)
  273. {
  274. return m_objectIcon;
  275. }
  276. break;
  277. }
  278. case ROLE_OBJECT_PTR:
  279. {
  280. return QVariant::fromValue(object);
  281. }
  282. case ROLE_OBJECT_INDEX:
  283. {
  284. if (!object)
  285. {
  286. object = simulatedObjectSetup->FindSimulatedObjectByJoint(joint);
  287. }
  288. AZ::Outcome<size_t> outcome = simulatedObjectSetup->FindSimulatedObjectIndex(object);
  289. if (outcome.IsSuccess())
  290. {
  291. return static_cast<quint64>(outcome.GetValue());
  292. }
  293. }
  294. case ROLE_OBJECT_NAME:
  295. {
  296. if (!object)
  297. {
  298. object = simulatedObjectSetup->FindSimulatedObjectByJoint(joint);
  299. }
  300. return object->GetName().c_str();
  301. }
  302. case ROLE_JOINT_PTR:
  303. {
  304. return QVariant::fromValue(joint);
  305. }
  306. case ROLE_JOINT_BOOL:
  307. {
  308. return joint != nullptr;
  309. }
  310. case ROLE_ACTOR_PTR:
  311. {
  312. return QVariant::fromValue(m_actor);
  313. }
  314. default:
  315. break;
  316. }
  317. return QVariant();
  318. }
  319. QModelIndex SimulatedObjectModel::GetModelIndexByObjectIndex(size_t objectIndex)
  320. {
  321. return index(static_cast<int>(objectIndex), 0);
  322. }
  323. QModelIndex SimulatedObjectModel::FindModelIndex(SimulatedObject* object)
  324. {
  325. if (!m_actor || !m_actor->GetSimulatedObjectSetup())
  326. {
  327. return QModelIndex();
  328. }
  329. const SimulatedObjectSetup* simulatedObjectSetup = m_actor->GetSimulatedObjectSetup().get();
  330. AZ::Outcome<size_t> result = simulatedObjectSetup->FindSimulatedObjectIndex(object);
  331. if (result.IsSuccess())
  332. {
  333. return index(static_cast<int>(result.GetValue()), 0);
  334. }
  335. return QModelIndex();
  336. }
  337. void SimulatedObjectModel::AddJointsToSelection(QItemSelection& selection, size_t objectIndex, const AZStd::vector<size_t>& jointIndices)
  338. {
  339. if (!m_actor || !m_actor->GetSimulatedObjectSetup())
  340. {
  341. return;
  342. }
  343. const SimulatedObjectSetup* simulatedObjectSetup = m_actor->GetSimulatedObjectSetup().get();
  344. const SimulatedObject* object = simulatedObjectSetup->GetSimulatedObject(objectIndex);
  345. if (!object)
  346. {
  347. AZ_Warning("EMotionFX", false, "Simulated object at index %zu does not exist", objectIndex);
  348. return;
  349. }
  350. for (const size_t jointIndex : jointIndices)
  351. {
  352. SimulatedJoint* joint = object->FindSimulatedJointBySkeletonJointIndex(jointIndex);
  353. if (!joint)
  354. {
  355. AZ_Warning("EMotionFX", false, "Simulated joint with joint index %zu does not exist", jointIndex);
  356. continue;
  357. }
  358. int row = static_cast<int>(joint->CalculateChildIndex());
  359. QModelIndex modelIndex = createIndex(row, 0, joint);
  360. selection.select(modelIndex, modelIndex);
  361. }
  362. }
  363. void SimulatedObjectModel::PreAddObject()
  364. {
  365. if (!m_actor || !m_actor->GetSimulatedObjectSetup())
  366. {
  367. return;
  368. }
  369. const SimulatedObjectSetup* simulatedObjectSetup = m_actor->GetSimulatedObjectSetup().get();
  370. const int first = static_cast<int>(simulatedObjectSetup->GetNumSimulatedObjects());
  371. beginInsertRows(QModelIndex(), first, first);
  372. }
  373. void SimulatedObjectModel::PostAddObject()
  374. {
  375. if (!m_actor || !m_actor->GetSimulatedObjectSetup())
  376. {
  377. return;
  378. }
  379. endInsertRows();
  380. }
  381. void SimulatedObjectModel::PreRemoveObject(size_t objectIndex)
  382. {
  383. if (!m_actor || !m_actor->GetSimulatedObjectSetup())
  384. {
  385. return;
  386. }
  387. const int first = static_cast<int>(objectIndex);
  388. beginRemoveRows(QModelIndex(), first, first);
  389. }
  390. void SimulatedObjectModel::PostRemoveObject()
  391. {
  392. if (!m_actor || !m_actor->GetSimulatedObjectSetup())
  393. {
  394. return;
  395. }
  396. endRemoveRows();
  397. }
  398. }