1 /*
2  * Copyright (c) 2024 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 #ifndef SCENEPLUGIN_INTF_ECS_SCENE_H
16 #define SCENEPLUGIN_INTF_ECS_SCENE_H
17 
18 #include <scene_plugin/interface/intf_ecs_object.h>
19 #include <scene_plugin/interface/intf_node.h>
20 #include <scene_plugin/namespace.h>
21 
22 #include <core/ecs/intf_ecs.h>
23 
24 #include <meta/base/interface_macros.h>
25 #include <meta/base/types.h>
26 #include <meta/interface/intf_task_queue.h>
27 
28 SCENE_BEGIN_NAMESPACE()
29 
30 class IAssetManager;
31 
32 // Implemented by SCENE_NS::ClassId::Scene, not intended to direct application use
33 REGISTER_INTERFACE(IEcsScene, "d2b4295b-d06d-401e-a82d-b167a3c51a92")
34 class IEcsScene : public CORE_NS::IInterface {
35     META_INTERFACE(CORE_NS::IInterface, IEcsScene, InterfaceId::IEcsScene)
36 public:
37     /**
38      * Mode that controls how the engine will be used to render a frame. This can be used to skip rendering altogether
39      * when the scene contents have not changed, lowering the GPU and CPU load and saving battery life.
40      */
41     enum RenderMode {
42         /**
43          * In addition to render requests also re-render when the scene is detected to be dirty. The scene is
44          * considered dirty if any component in an entity has been changed, added or removed or rendering is
45          * explicitly requestedthrough RequestRender().
46          */
47         RENDER_IF_DIRTY,
48 
49         /**
50          * Render every frame regardless of calls to RequestRender(). This mode will still take v-sync count into
51          * account.
52          */
53         RENDER_ALWAYS,
54     };
55     META_PROPERTY(uint8_t, RenderMode)
56 
57     /**
58      * @brief Get Ecs instance. Raw access to ECS. This should be used in the tasks from UI_NS::JobQueues::ENGINE_THREAD
59      * @return Strong pointer to ECS. Can be null.
60      */
61     virtual CORE_NS::IEcs::Ptr GetEcs() = 0;
62 
63     class IPrepareSceneForInitialization : public META_NS::ICallable {
64     public:
65         constexpr static BASE_NS::Uid UID { "d4000af2-3dc2-455e-86f4-3b5124cc026c" };
66         using Ptr = BASE_NS::shared_ptr<IPrepareSceneForInitialization>;
67         using WeakPtr = BASE_NS::weak_ptr<IPrepareSceneForInitialization>;
68         virtual bool Invoke(CORE_NS::IEcs::Ptr ecs) = 0;
69         using FunctionType = bool(CORE_NS::IEcs::Ptr ecs);
70 
71     protected:
72         friend Ptr;
73         META_NO_COPY_MOVE_INTERFACE(IPrepareSceneForInitialization)
74     };
75 
76     /**
77      * @brief Set Ecs instance. Raw access to ECS. Previous instance is destroyed and the existing scene
78      * will be reset. Runs ecs initialization with the given instance.
79      * @param ecs The instance to (re)set.
80      */
81     virtual void SetEcsInitializationCallback(IPrepareSceneForInitialization::WeakPtr callback) = 0;
82 
83     /**
84      * @brief Create new node or get existing object from the scene cache.
85      * @param path to Ecs object on engine scene
86      * @return Always returns object, if the object does not exist on scene yet, the assumption is that it will be
87      * created by someone else.
88      */
89     virtual IEcsObject::Ptr GetEcsObject(const BASE_NS::string_view& path) = 0;
90 
91     /**
92      * @brief Update EcsObject on existing node
93      * @param node Node instance
94      * @param name including the full path on esc
95      * @param createEngineObject boolean value to define if the object should be created by function or someone else
96      */
97     virtual void BindNodeToEcs(
98         SCENE_NS::INode::Ptr& node, const BASE_NS::string_view name, bool createEngineObject) = 0;
99 
100     /**
101      * @brief Queue task in Engine job queue. This may use other thread to run the task.
102      * @param task TaskQueue-item
103      * @return a token that can be used to cancel the task before it runs (again)
104      */
105     virtual META_NS::ITaskQueue::Token AddEngineTask(
106         const META_NS::ITaskQueue::CallableType::Ptr& task, bool runDeferred) = 0;
107 
108     /**
109      * @brief Queue task in Application job queue. This may use other thread to run the task.
110      * @param task TaskQueue-item
111      * @return a token that can be used to cancel the task before it runs (again)
112      */
113     virtual META_NS::ITaskQueue::Token AddApplicationTask(
114         const META_NS::ITaskQueue::CallableType::Ptr& task, bool runDeferred) = 0;
115 
116     /**
117      * @brief Cancel Engine Task
118      * @param token that was received when task was added
119      */
120     virtual void CancelEngineTask(META_NS::ITaskQueue::Token token) = 0;
121 
122     /**
123      * @brief Cancel App Task
124      * @param token that was received when task was added
125      */
126     virtual void CancelAppTask(META_NS::ITaskQueue::Token token) = 0;
127 
128     /**
129      * @brief Retrieve root entity collection with scene contents.
130      */
131     virtual IEntityCollection* GetEntityCollection() = 0;
132 
133     /**
134      * @brief Retrieve asset manager for the scene.
135      */
136     virtual IAssetManager* GetAssetManager() = 0;
137 };
138 SCENE_END_NAMESPACE()
139 
140 META_TYPE(SCENE_NS::IEcsScene::WeakPtr);
141 META_TYPE(SCENE_NS::IEcsScene::Ptr);
142 
143 #endif // SCENEPLUGIN_INTF_ECS_SCENE_H
144