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 CORE__ECS_HELPER__COMPONENT_TOOLS__BASE_MANAGER_H
16 #define CORE__ECS_HELPER__COMPONENT_TOOLS__BASE_MANAGER_H
17 
18 #include <atomic>
19 #include <cstddef>
20 #include <cstdint>
21 
22 #include <base/containers/array_view.h>
23 #include <base/containers/string_view.h>
24 #include <base/containers/unordered_map.h>
25 #include <base/containers/vector.h>
26 #include <base/namespace.h>
27 #include <base/util/uid.h>
28 #include <core/ecs/entity.h>
29 #include <core/ecs/intf_component_manager.h>
30 #include <core/namespace.h>
31 #include <core/property/intf_property_api.h>
32 #include <core/property/intf_property_handle.h>
33 #include <core/property/scoped_handle.h>
34 
35 CORE_BEGIN_NAMESPACE()
36 class IEcs;
37 struct Property;
38 
39 // BaseClass should inherit IComponentManager AND should follow the basic form of component managers
40 // (this will be enforced later)
41 template<typename ComponentType, typename BaseClass>
42 class BaseManager : public BaseClass, public IPropertyApi {
43     using ComponentId = IComponentManager::ComponentId;
44 
45 public:
46     // IPropertyApi
47     size_t PropertyCount() const override = 0;
48     const Property* MetaData(size_t index) const override = 0;
49     BASE_NS::array_view<const Property> MetaData() const override = 0;
50     IPropertyHandle* Create() const override;
51     IPropertyHandle* Clone(const IPropertyHandle*) const override;
52     void Release(IPropertyHandle*) const override;
53     uint64_t Type() const override;
54 
55     // IComponentManager
56     BASE_NS::string_view GetName() const override;
57     BASE_NS::Uid GetUid() const override;
58     size_t GetComponentCount() const override;
59     const IPropertyApi& GetPropertyApi() const override;
60     Entity GetEntity(ComponentId index) const override;
61     uint32_t GetComponentGeneration(ComponentId index) const override;
62     bool HasComponent(Entity entity) const override;
63     IComponentManager::ComponentId GetComponentId(Entity entity) const override;
64     void Create(Entity entity) override;
65     bool Destroy(Entity entity) override;
66     void Gc() override;
67     void Destroy(BASE_NS::array_view<const Entity> gcList) override;
68     BASE_NS::vector<Entity> GetAddedComponents() override;
69     BASE_NS::vector<Entity> GetRemovedComponents() override;
70     BASE_NS::vector<Entity> GetUpdatedComponents() override;
71     CORE_NS::ComponentManagerModifiedFlags GetModifiedFlags() const override;
72     void ClearModifiedFlags() override;
73     uint32_t GetGenerationCounter() const override;
74     void SetData(Entity entity, const IPropertyHandle& dataHandle) override;
75     const IPropertyHandle* GetData(Entity entity) const override;
76     IPropertyHandle* GetData(Entity entity) override;
77     void SetData(ComponentId index, const IPropertyHandle& dataHandle) override;
78     const IPropertyHandle* GetData(ComponentId index) const override;
79     IPropertyHandle* GetData(ComponentId index) override;
80     IEcs& GetEcs() const override;
81 
82     // "base class"
83     ComponentType Get(ComponentId index) const override;
84     ComponentType Get(Entity entity) const override;
85     void Set(ComponentId index, const ComponentType& aData) override;
86     void Set(Entity entity, const ComponentType& aData) override;
87     ScopedHandle<const ComponentType> Read(ComponentId index) const override;
88     ScopedHandle<const ComponentType> Read(Entity entity) const override;
89     ScopedHandle<ComponentType> Write(ComponentId index) override;
90     ScopedHandle<ComponentType> Write(Entity entity) override;
91 
92     // internal, non-public
93     void Updated(Entity entity);
94 
95     BaseManager(const BaseManager&) = delete;
96     BaseManager(BaseManager&&) = delete;
97     BaseManager& operator=(const BaseManager&) = delete;
98     BaseManager& operator=(BaseManager&&) = delete;
99 
100 protected:
101     BaseManager(IEcs& ecs, BASE_NS::string_view) noexcept;
102     virtual ~BaseManager();
103     IEcs& ecs_;
104     BASE_NS::string_view name_;
105 
106     bool IsMatchingHandle(const IPropertyHandle& handle);
107 
108     class BaseComponentHandle : public IPropertyHandle {
109     public:
110         BaseComponentHandle() = delete;
111         BaseComponentHandle(BaseManager* owner, Entity entity) noexcept;
112         BaseComponentHandle(BaseManager* owner, Entity entity, const ComponentType& data) noexcept;
113         ~BaseComponentHandle() override = default;
114         BaseComponentHandle(const BaseComponentHandle& other) = delete;
115         BaseComponentHandle(BaseComponentHandle&& other) noexcept;
116         BaseComponentHandle& operator=(const BaseComponentHandle& other) = delete;
117         BaseComponentHandle& operator=(BaseComponentHandle&& other) noexcept;
118         const IPropertyApi* Owner() const override;
119         size_t Size() const override;
120         const void* RLock() const override;
121         void RUnlock() const override;
122         void* WLock() override;
123         void WUnlock() override;
124 
125         mutable std::atomic_uint32_t rLocked_ { 0 };
126         mutable bool wLocked_ { false };
127         bool dirty_ { false };
128         BaseManager* manager_ { nullptr };
129         uint32_t generation_ { 0 };
130         Entity entity_;
131         ComponentType data_;
132     };
133     uint32_t generationCounter_ { 0 };
134     uint32_t modifiedFlags_ { 0 };
135     BASE_NS::unordered_map<Entity, ComponentId> entityComponent_;
136     BASE_NS::vector<BaseComponentHandle> components_;
137     BASE_NS::vector<Entity> added_;
138     BASE_NS::vector<Entity> removed_;
139     BASE_NS::vector<Entity> updated_;
140     uint64_t typeHash_;
141 };
142 CORE_END_NAMESPACE()
143 #endif
144