18bf80f4bSopenharmony_ci/* 28bf80f4bSopenharmony_ci * Copyright (c) 2024 Huawei Device Co., Ltd. 38bf80f4bSopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License"); 48bf80f4bSopenharmony_ci * you may not use this file except in compliance with the License. 58bf80f4bSopenharmony_ci * You may obtain a copy of the License at 68bf80f4bSopenharmony_ci * 78bf80f4bSopenharmony_ci * http://www.apache.org/licenses/LICENSE-2.0 88bf80f4bSopenharmony_ci * 98bf80f4bSopenharmony_ci * Unless required by applicable law or agreed to in writing, software 108bf80f4bSopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS, 118bf80f4bSopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 128bf80f4bSopenharmony_ci * See the License for the specific language governing permissions and 138bf80f4bSopenharmony_ci * limitations under the License. 148bf80f4bSopenharmony_ci */ 158bf80f4bSopenharmony_ci#include <scene_plugin/api/mesh_uid.h> 168bf80f4bSopenharmony_ci#include <scene_plugin/interface/intf_material.h> 178bf80f4bSopenharmony_ci 188bf80f4bSopenharmony_ci#include <3d/ecs/components/mesh_component.h> 198bf80f4bSopenharmony_ci 208bf80f4bSopenharmony_ci#include <meta/ext/object.h> 218bf80f4bSopenharmony_ci 228bf80f4bSopenharmony_ci#include "intf_node_private.h" 238bf80f4bSopenharmony_ci#include "intf_submesh_bridge.h" 248bf80f4bSopenharmony_ci#include "submesh_handler_uid.h" 258bf80f4bSopenharmony_ci#include "task_utils.h" 268bf80f4bSopenharmony_ci 278bf80f4bSopenharmony_ciusing SCENE_NS::MakeTask; 288bf80f4bSopenharmony_ci 298bf80f4bSopenharmony_cinamespace { 308bf80f4bSopenharmony_ciclass SubMeshHandler : public META_NS::ObjectFwd<SubMeshHandler, SCENE_NS::ClassId::SubMeshHandler, 318bf80f4bSopenharmony_ci META_NS::ClassId::Object, SCENE_NS::IEcsProxyObject, SCENE_NS::ISubMeshBridge> { 328bf80f4bSopenharmony_cipublic: 338bf80f4bSopenharmony_ci void Initialize(CORE3D_NS::IMeshComponentManager* componentManager, CORE_NS::Entity entity, 348bf80f4bSopenharmony_ci META_NS::IProperty::Ptr submeshes, INodeEcsInterfacePrivate::Ptr node) override 358bf80f4bSopenharmony_ci { 368bf80f4bSopenharmony_ci node_ = node; 378bf80f4bSopenharmony_ci if (node) { 388bf80f4bSopenharmony_ci componentManager_ = componentManager; 398bf80f4bSopenharmony_ci entity_ = entity; 408bf80f4bSopenharmony_ci submeshes_ = META_NS::ArrayProperty<SCENE_NS::ISubMesh::Ptr>(submeshes); 418bf80f4bSopenharmony_ci SetCommonListener(node->SceneHolder()->GetCommonEcsListener()); 428bf80f4bSopenharmony_ci if (auto scene = node->EcsScene()) { 438bf80f4bSopenharmony_ci scene->AddEngineTask(MakeTask( 448bf80f4bSopenharmony_ci [](auto obj) { 458bf80f4bSopenharmony_ci if (auto self = static_cast<SubMeshHandler*>(obj.get())) { 468bf80f4bSopenharmony_ci self->DoComponentEvent( 478bf80f4bSopenharmony_ci CORE_NS::IEcs::ComponentListener::EventType::MODIFIED, 488bf80f4bSopenharmony_ci *self->componentManager_, self->entity_); 498bf80f4bSopenharmony_ci } 508bf80f4bSopenharmony_ci return false; 518bf80f4bSopenharmony_ci }, 528bf80f4bSopenharmony_ci GetSelf()), 538bf80f4bSopenharmony_ci false); 548bf80f4bSopenharmony_ci } 558bf80f4bSopenharmony_ci } 568bf80f4bSopenharmony_ci } 578bf80f4bSopenharmony_ci 588bf80f4bSopenharmony_ci void Destroy() override 598bf80f4bSopenharmony_ci { 608bf80f4bSopenharmony_ci if (listener_) { 618bf80f4bSopenharmony_ci listener_->RemoveEntity(entity_, GetSelf<SCENE_NS::IEcsProxyObject>(), 628bf80f4bSopenharmony_ci *static_cast<CORE_NS::IComponentManager*>(componentManager_)); 638bf80f4bSopenharmony_ci } 648bf80f4bSopenharmony_ci } 658bf80f4bSopenharmony_ci 668bf80f4bSopenharmony_ci // IEcsProxyObject 678bf80f4bSopenharmony_ci 688bf80f4bSopenharmony_ci void SetCommonListener(BASE_NS::shared_ptr<SCENE_NS::EcsListener> listener) override 698bf80f4bSopenharmony_ci { 708bf80f4bSopenharmony_ci if (listener_) { 718bf80f4bSopenharmony_ci listener_->RemoveEntity(entity_, GetSelf<SCENE_NS::IEcsProxyObject>(), 728bf80f4bSopenharmony_ci *static_cast<CORE_NS::IComponentManager*>(componentManager_)); 738bf80f4bSopenharmony_ci } 748bf80f4bSopenharmony_ci listener_ = listener; 758bf80f4bSopenharmony_ci if (listener_) { 768bf80f4bSopenharmony_ci listener_->AddEntity(entity_, GetSelf<SCENE_NS::IEcsProxyObject>(), 778bf80f4bSopenharmony_ci *static_cast<CORE_NS::IComponentManager*>(componentManager_)); 788bf80f4bSopenharmony_ci } 798bf80f4bSopenharmony_ci } 808bf80f4bSopenharmony_ci 818bf80f4bSopenharmony_ci void DoEntityEvent(CORE_NS::IEcs::EntityListener::EventType, const CORE_NS::Entity&) override {} 828bf80f4bSopenharmony_ci 838bf80f4bSopenharmony_ci SCENE_NS::IMaterial::Ptr GetMaterialFromEntity( 848bf80f4bSopenharmony_ci SCENE_NS::IScene::Ptr scene, SceneHolder::Ptr sceneHolder, CORE_NS::Entity entity) 858bf80f4bSopenharmony_ci { 868bf80f4bSopenharmony_ci // First see if we have this material already. 878bf80f4bSopenharmony_ci auto materials = scene->GetMaterials(); 888bf80f4bSopenharmony_ci for (auto material : materials) { 898bf80f4bSopenharmony_ci auto ecsObject = interface_pointer_cast<SCENE_NS::IEcsObject>(material); 908bf80f4bSopenharmony_ci if (ecsObject && ecsObject->GetEntity() == entity) { 918bf80f4bSopenharmony_ci return material; 928bf80f4bSopenharmony_ci } 938bf80f4bSopenharmony_ci } 948bf80f4bSopenharmony_ci 958bf80f4bSopenharmony_ci // Then try to resolve from uri. 968bf80f4bSopenharmony_ci BASE_NS::string uri; 978bf80f4bSopenharmony_ci if (sceneHolder->GetEntityUri(entity, uri)) { 988bf80f4bSopenharmony_ci return scene->GetMaterial(uri); 998bf80f4bSopenharmony_ci } 1008bf80f4bSopenharmony_ci 1018bf80f4bSopenharmony_ci BASE_NS::string name; 1028bf80f4bSopenharmony_ci if (sceneHolder->GetEntityName(entity, name)) { 1038bf80f4bSopenharmony_ci return scene->GetMaterial(name); 1048bf80f4bSopenharmony_ci } 1058bf80f4bSopenharmony_ci 1068bf80f4bSopenharmony_ci return {}; 1078bf80f4bSopenharmony_ci } 1088bf80f4bSopenharmony_ci 1098bf80f4bSopenharmony_ci // ToDo: This runs on "engine queue", someday the property operations could be decoupled 1108bf80f4bSopenharmony_ci // Another todo, this should presumably be closer to SceneHolder instead interleaved into the node impl 1118bf80f4bSopenharmony_ci void DoComponentEvent(CORE_NS::IEcs::ComponentListener::EventType type, 1128bf80f4bSopenharmony_ci const CORE_NS::IComponentManager& componentManager, const CORE_NS::Entity& entity) override 1138bf80f4bSopenharmony_ci { 1148bf80f4bSopenharmony_ci if (entity != entity_) { 1158bf80f4bSopenharmony_ci CORE_LOG_W("DoComponentEvent called for wrong entity."); 1168bf80f4bSopenharmony_ci return; 1178bf80f4bSopenharmony_ci } 1188bf80f4bSopenharmony_ci 1198bf80f4bSopenharmony_ci if (type == CORE_NS::IEcs::ComponentListener::EventType::MODIFIED) { 1208bf80f4bSopenharmony_ci // Read data here, we don't want to keep read lock when we update materials below 1218bf80f4bSopenharmony_ci // as it can cause changes to material components further down the pipeline. 1228bf80f4bSopenharmony_ci auto componentData = componentManager_->Get(entity); 1238bf80f4bSopenharmony_ci 1248bf80f4bSopenharmony_ci // This may be nasty from the application point of view, but lessens a risk 1258bf80f4bSopenharmony_ci // that index changes would be propagated incorrectly to client app 1268bf80f4bSopenharmony_ci if (submeshes_->GetSize() > componentData.submeshes.size()) { 1278bf80f4bSopenharmony_ci submeshes_->Reset(); 1288bf80f4bSopenharmony_ci } 1298bf80f4bSopenharmony_ci 1308bf80f4bSopenharmony_ci while (submeshes_->GetSize() < componentData.submeshes.size()) { 1318bf80f4bSopenharmony_ci auto submesh = GetObjectRegistry().Create<SCENE_NS::ISubMesh>(SCENE_NS::ClassId::SubMesh); 1328bf80f4bSopenharmony_ci submeshes_->AddValue(submesh); 1338bf80f4bSopenharmony_ci } 1348bf80f4bSopenharmony_ci 1358bf80f4bSopenharmony_ci for (auto i = 0; i < componentData.submeshes.size(); ++i) { 1368bf80f4bSopenharmony_ci const auto& submesh = componentData.submeshes.at(i); 1378bf80f4bSopenharmony_ci auto ptr = submeshes_->GetValueAt(i); 1388bf80f4bSopenharmony_ci // TODO: These could be initialized only once. 1398bf80f4bSopenharmony_ci ptr->Name()->SetValue(BASE_NS::string("Submesh ") + BASE_NS::to_string(i)); 1408bf80f4bSopenharmony_ci 1418bf80f4bSopenharmony_ci META_NS::SetValue(ptr->AABBMin(), submesh.aabbMin); 1428bf80f4bSopenharmony_ci META_NS::SetValue(ptr->AABBMax(), submesh.aabbMax); 1438bf80f4bSopenharmony_ci META_NS::SetValue(ptr->RenderSortLayerOrder(), submesh.renderSortLayerOrder); 1448bf80f4bSopenharmony_ci META_NS::SetValue(ptr->Handle(), i); 1458bf80f4bSopenharmony_ci 1468bf80f4bSopenharmony_ci auto priv = interface_pointer_cast<SCENE_NS::ISubMeshPrivate>(ptr); 1478bf80f4bSopenharmony_ci if (CORE_NS::EntityUtil::IsValid(submesh.material)) { 1488bf80f4bSopenharmony_ci if (auto node = node_.lock()) { 1498bf80f4bSopenharmony_ci // This would appreciate more async approach 1508bf80f4bSopenharmony_ci auto sceneHolder = node->SceneHolder(); 1518bf80f4bSopenharmony_ci auto scene = interface_pointer_cast<SCENE_NS::IScene>(node->EcsScene()); 1528bf80f4bSopenharmony_ci 1538bf80f4bSopenharmony_ci if (scene && sceneHolder) { 1548bf80f4bSopenharmony_ci auto material = GetMaterialFromEntity(scene, sceneHolder, submesh.material); 1558bf80f4bSopenharmony_ci priv->SetDefaultMaterial(material); 1568bf80f4bSopenharmony_ci } 1578bf80f4bSopenharmony_ci } 1588bf80f4bSopenharmony_ci } else { 1598bf80f4bSopenharmony_ci priv->SetDefaultMaterial({}); 1608bf80f4bSopenharmony_ci } 1618bf80f4bSopenharmony_ci priv->AddSubmeshBrigde(GetSelf<ISubMeshBridge>()); 1628bf80f4bSopenharmony_ci } 1638bf80f4bSopenharmony_ci } 1648bf80f4bSopenharmony_ci } 1658bf80f4bSopenharmony_ci 1668bf80f4bSopenharmony_cipublic: // ISubMeshBridge 1678bf80f4bSopenharmony_ci void SetRenderSortLayerOrder(size_t index, uint8_t value) override 1688bf80f4bSopenharmony_ci { 1698bf80f4bSopenharmony_ci#ifdef SYNC_ACCESS_ECS 1708bf80f4bSopenharmony_ci if (auto handle = componentManager_->Write(entity_)) { 1718bf80f4bSopenharmony_ci if (index >= 0 && index < handle->submeshes.size()) { 1728bf80f4bSopenharmony_ci handle->submeshes[index].renderSortOrder = value; 1738bf80f4bSopenharmony_ci } 1748bf80f4bSopenharmony_ci } 1758bf80f4bSopenharmony_ci#else 1768bf80f4bSopenharmony_ci if (auto node = node_.lock()) { 1778bf80f4bSopenharmony_ci if (auto scene = node->EcsScene()) { 1788bf80f4bSopenharmony_ci scene->AddEngineTask(MakeTask( 1798bf80f4bSopenharmony_ci [index, value](auto selfNode) { 1808bf80f4bSopenharmony_ci if (auto self = interface_pointer_cast<SCENE_NS::IEcsObject>(selfNode)) { 1818bf80f4bSopenharmony_ci if (auto node = interface_cast<INodeEcsInterfacePrivate>(selfNode)) { 1828bf80f4bSopenharmony_ci if (auto sceneHolder = node->SceneHolder()) { 1838bf80f4bSopenharmony_ci sceneHolder->SetSubmeshRenderSortOrder( 1848bf80f4bSopenharmony_ci self->GetEntity(), index, value); 1858bf80f4bSopenharmony_ci } 1868bf80f4bSopenharmony_ci } 1878bf80f4bSopenharmony_ci } 1888bf80f4bSopenharmony_ci return false; 1898bf80f4bSopenharmony_ci }, 1908bf80f4bSopenharmony_ci node), 1918bf80f4bSopenharmony_ci false); 1928bf80f4bSopenharmony_ci } 1938bf80f4bSopenharmony_ci } 1948bf80f4bSopenharmony_ci#endif 1958bf80f4bSopenharmony_ci if (index < submeshes_->GetSize()) { 1968bf80f4bSopenharmony_ci META_NS::SetValue(submeshes_->GetValueAt(index)->RenderSortLayerOrder(), value); 1978bf80f4bSopenharmony_ci } 1988bf80f4bSopenharmony_ci } 1998bf80f4bSopenharmony_ci 2008bf80f4bSopenharmony_ci void SetMaterialToEcs(size_t index, SCENE_NS::IMaterial::Ptr& material) override 2018bf80f4bSopenharmony_ci { 2028bf80f4bSopenharmony_ci if (auto node = node_.lock()) { 2038bf80f4bSopenharmony_ci if (auto scene = node->EcsScene()) { 2048bf80f4bSopenharmony_ci scene->AddEngineTask( 2058bf80f4bSopenharmony_ci MakeTask( 2068bf80f4bSopenharmony_ci [mat = SCENE_NS::IMaterial::WeakPtr(material), index](auto node) { 2078bf80f4bSopenharmony_ci if (auto self = interface_pointer_cast<SCENE_NS::IEcsObject>(node)) { 2088bf80f4bSopenharmony_ci CORE_NS::Entity entity {}; 2098bf80f4bSopenharmony_ci if (auto ecsObject = interface_pointer_cast<SCENE_NS::IEcsObject>(mat.lock())) { 2108bf80f4bSopenharmony_ci entity = ecsObject->GetEntity(); 2118bf80f4bSopenharmony_ci } 2128bf80f4bSopenharmony_ci auto sceneHolder = node->SceneHolder(); 2138bf80f4bSopenharmony_ci if (sceneHolder) { 2148bf80f4bSopenharmony_ci sceneHolder->SetMaterial(self->GetEntity(), entity, index); 2158bf80f4bSopenharmony_ci } 2168bf80f4bSopenharmony_ci } 2178bf80f4bSopenharmony_ci return false; 2188bf80f4bSopenharmony_ci }, 2198bf80f4bSopenharmony_ci node_), 2208bf80f4bSopenharmony_ci false); 2218bf80f4bSopenharmony_ci } 2228bf80f4bSopenharmony_ci } 2238bf80f4bSopenharmony_ci } 2248bf80f4bSopenharmony_ci 2258bf80f4bSopenharmony_ci void SetAABBMin(size_t index, BASE_NS::Math::Vec3 vec) override 2268bf80f4bSopenharmony_ci { 2278bf80f4bSopenharmony_ci#ifdef SYNC_ACCESS_ECS 2288bf80f4bSopenharmony_ci if (auto handle = componentManager_->Write(entity_)) { 2298bf80f4bSopenharmony_ci if (index >= 0 && index < handle->submeshes.size()) { 2308bf80f4bSopenharmony_ci handle->submeshes[index].aabbMin = vec; 2318bf80f4bSopenharmony_ci handle->aabbMin = BASE_NS::Math::min(handle->aabbMin, vec); 2328bf80f4bSopenharmony_ci } 2338bf80f4bSopenharmony_ci } 2348bf80f4bSopenharmony_ci#else 2358bf80f4bSopenharmony_ci if (auto node = node_.lock()) { 2368bf80f4bSopenharmony_ci if (auto scene = node->EcsScene()) { 2378bf80f4bSopenharmony_ci scene->AddEngineTask(MakeTask( 2388bf80f4bSopenharmony_ci [index, vec](auto selfNode) { 2398bf80f4bSopenharmony_ci if (auto self = interface_pointer_cast<SCENE_NS::IEcsObject>(selfNode)) { 2408bf80f4bSopenharmony_ci if (auto node = interface_cast<INodeEcsInterfacePrivate>(selfNode)) { 2418bf80f4bSopenharmony_ci if (auto sceneHolder = node->SceneHolder()) { 2428bf80f4bSopenharmony_ci sceneHolder->SetSubmeshAABBMin(self->GetEntity(), index, vec); 2438bf80f4bSopenharmony_ci } 2448bf80f4bSopenharmony_ci } 2458bf80f4bSopenharmony_ci } 2468bf80f4bSopenharmony_ci return false; 2478bf80f4bSopenharmony_ci }, 2488bf80f4bSopenharmony_ci node), 2498bf80f4bSopenharmony_ci false); 2508bf80f4bSopenharmony_ci } 2518bf80f4bSopenharmony_ci } 2528bf80f4bSopenharmony_ci#endif 2538bf80f4bSopenharmony_ci if (index < submeshes_->GetSize()) { 2548bf80f4bSopenharmony_ci META_NS::SetValue(submeshes_->GetValueAt(index)->AABBMin(), vec); 2558bf80f4bSopenharmony_ci } 2568bf80f4bSopenharmony_ci } 2578bf80f4bSopenharmony_ci 2588bf80f4bSopenharmony_ci void SetAABBMax(size_t index, BASE_NS::Math::Vec3 vec) override 2598bf80f4bSopenharmony_ci { 2608bf80f4bSopenharmony_ci#ifdef SYNC_ACCESS_ECS 2618bf80f4bSopenharmony_ci if (auto handle = componentManager_->Write(entity_)) { 2628bf80f4bSopenharmony_ci if (index >= 0 && index < handle->submeshes.size()) { 2638bf80f4bSopenharmony_ci handle->submeshes[index].aabbMax = vec; 2648bf80f4bSopenharmony_ci handle->aabbMax = BASE_NS::Math::max(handle->aabbMax, vec); 2658bf80f4bSopenharmony_ci } 2668bf80f4bSopenharmony_ci } 2678bf80f4bSopenharmony_ci#else 2688bf80f4bSopenharmony_ci if (auto node = node_.lock()) { 2698bf80f4bSopenharmony_ci if (auto scene = node->EcsScene()) { 2708bf80f4bSopenharmony_ci scene->AddEngineTask(MakeTask( 2718bf80f4bSopenharmony_ci [index, vec](auto selfNode) { 2728bf80f4bSopenharmony_ci if (auto self = interface_pointer_cast<SCENE_NS::IEcsObject>(selfNode)) { 2738bf80f4bSopenharmony_ci if (auto node = interface_cast<INodeEcsInterfacePrivate>(selfNode)) { 2748bf80f4bSopenharmony_ci if (auto sceneHolder = node->SceneHolder()) { 2758bf80f4bSopenharmony_ci sceneHolder->SetSubmeshAABBMax(self->GetEntity(), index, vec); 2768bf80f4bSopenharmony_ci } 2778bf80f4bSopenharmony_ci } 2788bf80f4bSopenharmony_ci } 2798bf80f4bSopenharmony_ci return false; 2808bf80f4bSopenharmony_ci }, 2818bf80f4bSopenharmony_ci node), 2828bf80f4bSopenharmony_ci false); 2838bf80f4bSopenharmony_ci } 2848bf80f4bSopenharmony_ci } 2858bf80f4bSopenharmony_ci#endif 2868bf80f4bSopenharmony_ci if (index < submeshes_->GetSize()) { 2878bf80f4bSopenharmony_ci META_NS::SetValue(submeshes_->GetValueAt(index)->AABBMax(), vec); 2888bf80f4bSopenharmony_ci } 2898bf80f4bSopenharmony_ci } 2908bf80f4bSopenharmony_ci 2918bf80f4bSopenharmony_ci void RemoveSubmesh(int32_t index) override 2928bf80f4bSopenharmony_ci { 2938bf80f4bSopenharmony_ci#ifdef SYNC_ACCESS_ECS 2948bf80f4bSopenharmony_ci if (auto handle = componentManager_->Write(entity_)) { 2958bf80f4bSopenharmony_ci if (index < 0) { 2968bf80f4bSopenharmony_ci handle->submeshes.clear(); 2978bf80f4bSopenharmony_ci handle->aabbMin = { 0.f, 0.f, 0.f }; 2988bf80f4bSopenharmony_ci handle->aabbMax = { 0.f, 0.f, 0.f }; 2998bf80f4bSopenharmony_ci } else if (index < handle->submeshes.size()) { 3008bf80f4bSopenharmony_ci handle->submeshes.erase(handle->submeshes.begin() + index); 3018bf80f4bSopenharmony_ci for (const auto& submesh : handle->submeshes) { 3028bf80f4bSopenharmony_ci handle->aabbMin = BASE_NS::Math::min(handle->aabbMin, submesh.aabbMin); 3038bf80f4bSopenharmony_ci handle->aabbMax = BASE_NS::Math::max(handle->aabbMax, submesh.aabbMax); 3048bf80f4bSopenharmony_ci } 3058bf80f4bSopenharmony_ci } 3068bf80f4bSopenharmony_ci } 3078bf80f4bSopenharmony_ci#else 3088bf80f4bSopenharmony_ci if (auto node = node_.lock()) { 3098bf80f4bSopenharmony_ci if (auto scene = node->EcsScene()) { 3108bf80f4bSopenharmony_ci scene->AddEngineTask(MakeTask( 3118bf80f4bSopenharmony_ci [index](auto selfNode) { 3128bf80f4bSopenharmony_ci if (auto self = interface_pointer_cast<SCENE_NS::IEcsObject>(selfNode)) { 3138bf80f4bSopenharmony_ci if (auto node = interface_cast<INodeEcsInterfacePrivate>(selfNode)) { 3148bf80f4bSopenharmony_ci if (auto sceneHolder = node->SceneHolder()) { 3158bf80f4bSopenharmony_ci sceneHolder->RemoveSubmesh(self->GetEntity(), index); 3168bf80f4bSopenharmony_ci } 3178bf80f4bSopenharmony_ci } 3188bf80f4bSopenharmony_ci } 3198bf80f4bSopenharmony_ci return false; 3208bf80f4bSopenharmony_ci }, 3218bf80f4bSopenharmony_ci node_), 3228bf80f4bSopenharmony_ci false); 3238bf80f4bSopenharmony_ci } 3248bf80f4bSopenharmony_ci } 3258bf80f4bSopenharmony_ci#endif 3268bf80f4bSopenharmony_ci } 3278bf80f4bSopenharmony_ci 3288bf80f4bSopenharmony_ci CORE_NS::Entity GetEntity() const override 3298bf80f4bSopenharmony_ci { 3308bf80f4bSopenharmony_ci return entity_; 3318bf80f4bSopenharmony_ci } 3328bf80f4bSopenharmony_ci 3338bf80f4bSopenharmony_ci BASE_NS::shared_ptr<SCENE_NS::EcsListener> listener_ {}; 3348bf80f4bSopenharmony_ci CORE3D_NS::IMeshComponentManager* componentManager_ {}; 3358bf80f4bSopenharmony_ci CORE_NS::Entity entity_ {}; 3368bf80f4bSopenharmony_ci META_NS::ArrayProperty<SCENE_NS::ISubMesh::Ptr> submeshes_ {}; 3378bf80f4bSopenharmony_ci INodeEcsInterfacePrivate::WeakPtr node_ {}; 3388bf80f4bSopenharmony_ci}; 3398bf80f4bSopenharmony_ci} // namespace 3408bf80f4bSopenharmony_ciSCENE_BEGIN_NAMESPACE() 3418bf80f4bSopenharmony_ci 3428bf80f4bSopenharmony_civoid RegisterSubMeshHandler() 3438bf80f4bSopenharmony_ci{ 3448bf80f4bSopenharmony_ci META_NS::GetObjectRegistry().RegisterObjectType<SubMeshHandler>(); 3458bf80f4bSopenharmony_ci} 3468bf80f4bSopenharmony_civoid UnregisterSubMeshHandler() 3478bf80f4bSopenharmony_ci{ 3488bf80f4bSopenharmony_ci META_NS::GetObjectRegistry().UnregisterObjectType<SubMeshHandler>(); 3498bf80f4bSopenharmony_ci} 3508bf80f4bSopenharmony_ciSCENE_END_NAMESPACE()