ArticulationsUtilities.cpp 4.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394
  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 "ArticulationsUtilities.h"
  9. #include "Source/ArticulationLinkComponent.h"
  10. #include <AzFramework/Physics/PhysicsScene.h>
  11. namespace ROS2Controllers::Utils
  12. {
  13. AZ::EntityId GetRootOfArticulation(AZ::EntityId entityId)
  14. {
  15. AZ::EntityId parentEntityId{ AZ::EntityId::InvalidEntityId };
  16. AZ::Entity* parentEntity = nullptr;
  17. AZ::Entity* thisEntity = nullptr;
  18. AZ::TransformBus::EventResult(parentEntityId, entityId, &AZ::TransformBus::Events::GetParentId);
  19. AZ::ComponentApplicationBus::BroadcastResult(parentEntity, &AZ::ComponentApplicationRequests::FindEntity, parentEntityId);
  20. AZ::ComponentApplicationBus::BroadcastResult(thisEntity, &AZ::ComponentApplicationRequests::FindEntity, entityId);
  21. constexpr AZ::Uuid EditorArticulationLinkComponentUuid{ "{7D23169B-3214-4A32-ABFC-FCCE6E31F2CF}" };
  22. if (parentEntity == nullptr)
  23. {
  24. return AZ::EntityId(AZ::EntityId::InvalidEntityId);
  25. }
  26. if (thisEntity->FindComponent<PhysX::ArticulationLinkComponent>())
  27. {
  28. // Get articulation link component, if not found for parent, return current entity - game only
  29. PhysX::ArticulationLinkComponent* component = parentEntity->FindComponent<PhysX::ArticulationLinkComponent>();
  30. if (component == nullptr)
  31. {
  32. return entityId;
  33. }
  34. }
  35. else if (thisEntity->FindComponent(EditorArticulationLinkComponentUuid)) // EditorArticulationLinkComponent
  36. {
  37. // Get articulation link component, if not found for parent, return current entity - Editor only
  38. AZ::Component* component = parentEntity->FindComponent(EditorArticulationLinkComponentUuid);
  39. if (component == nullptr)
  40. {
  41. return entityId;
  42. }
  43. }
  44. else
  45. {
  46. return AZ::EntityId(AZ::EntityId::InvalidEntityId);
  47. }
  48. return GetRootOfArticulation(parentEntity->GetId());
  49. }
  50. AZStd::unordered_map<AZ::EntityId, AzPhysics::SimulatedBodyHandle> GetSimulatedBodyHandles(
  51. AzPhysics::SceneHandle sceneHandle, AZ::EntityId entityId)
  52. {
  53. AZ::EntityId rootArticulationEntity = GetRootOfArticulation(entityId);
  54. AZ::Entity* rootEntity = nullptr;
  55. AZ::ComponentApplicationBus::BroadcastResult(rootEntity, &AZ::ComponentApplicationRequests::FindEntity, rootArticulationEntity);
  56. const PhysX::ArticulationLinkComponent* component = rootEntity->FindComponent<PhysX::ArticulationLinkComponent>();
  57. const AZStd::vector<AzPhysics::SimulatedBodyHandle> articulationHandles = component->GetSimulatedBodyHandles();
  58. AZStd::unordered_map<AZ::EntityId, AzPhysics::SimulatedBodyHandle> result;
  59. for (const auto& articulationHandle : articulationHandles)
  60. {
  61. auto* sceneInterface = AZ::Interface<AzPhysics::SceneInterface>::Get();
  62. const auto* body = sceneInterface->GetSimulatedBodyFromHandle(sceneHandle, articulationHandle);
  63. result.insert({ body->GetEntityId(), articulationHandle });
  64. }
  65. return result;
  66. }
  67. AZStd::optional<PhysX::ArticulationJointAxis> TryGetFreeArticulationAxis(const AZ::EntityId& entityId)
  68. {
  69. PhysX::ArticulationJointAxis tempAxis;
  70. for (AZ::u8 i = 0; i <= static_cast<AZ::u8>(PhysX::ArticulationJointAxis::Z); i++)
  71. {
  72. PhysX::ArticulationJointMotionType type = PhysX::ArticulationJointMotionType::Locked;
  73. tempAxis = static_cast<PhysX::ArticulationJointAxis>(i);
  74. // Use bus to prevent compilation error without PhysX Articulation support.
  75. PhysX::ArticulationJointRequestBus::EventResult(type, entityId, &PhysX::ArticulationJointRequests::GetMotion, tempAxis);
  76. if (type != PhysX::ArticulationJointMotionType::Locked)
  77. {
  78. return tempAxis;
  79. }
  80. }
  81. return AZStd::nullopt;
  82. }
  83. } // namespace ROS2Controllers::Utils