1 #ifndef DALI_INTERNAL_RELAYOUT_CONTROLLER_IMPL_H
2 #define DALI_INTERNAL_RELAYOUT_CONTROLLER_IMPL_H
5 * Copyright (c) 2024 Samsung Electronics Co., Ltd.
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
11 * http://www.apache.org/licenses/LICENSE-2.0
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
23 #include <memory> // for unique_ptr
26 #include <dali/integration-api/ordered-set.h>
27 #include <dali/internal/common/memory-pool-object-allocator.h>
28 #include <dali/internal/event/size-negotiation/memory-pool-relayout-container.h>
29 #include <dali/public-api/common/vector-wrapper.h>
30 #include <dali/public-api/object/base-object.h>
31 #include <dali/public-api/size-negotiation/relayout-container.h>
37 class RenderController;
43 * @brief The relayout controller is responsible for taking request from actors to relayout their sizes.
44 * The requests are actioned on at the end of the frame where all actors that have made a request are
47 class RelayoutController : public Dali::BaseObject
52 * We should only create a unique instance.
53 * @param[in] controller to request a render from the RenderController if core is not processing events.
55 RelayoutController(Integration::RenderController& controller);
60 ~RelayoutController() override;
63 * @brief Get the singleton of RelayoutController object.
65 * @return A handle to the RelayoutController control.
67 static RelayoutController* Get();
70 * @brief Request to relayout the given actor and all sub-actors of it.
72 * This flags the actor and all actors dependent on it for relayout. The actual
73 * relayout is performed at the end of the frame. This means that multiple calls to relayout
74 * will not cause multiple relayouts to occur.
76 * @param[in] actor The actor to request relayout on
77 * @param[in] dimension The dimension(s) to request the relayout on. Defaults to all dimensions
79 void RequestRelayout(Dali::Actor& actor, Dimension::Type dimension = Dimension::ALL_DIMENSIONS);
82 * @brief Request to relayout of all actors in the sub-tree below the given actor.
84 * This flags the actor and all actors below it for relayout. The actual
85 * relayout is performed at the end of the frame. This means that multiple calls to relayout
86 * will not cause multiple relayouts to occur.
88 * @param[in] actor The actor to request relayout on
90 void RequestRelayoutTree(Dali::Actor& actor);
93 * @brief Force propagate relayout flags through the tree. This is similiar to Request Relayout
94 * except all dependencies have their flags reset in spite of whether they are all ready set.
96 * This is useful for resetting layout flags during the layout process.
98 * @param[in] actor The actor to propagate from
99 * @param[in] dimension The dimension to propagate on
101 void PropagateFlags(Dali::Actor& actor, Dimension::Type dimension = Dimension::ALL_DIMENSIONS);
104 * @brief Relayouts all actors that have been marked as dirty
109 * @brief Enable/disable the controller
111 * @param[in] enabled Flag to indicate whether the controller should be enabled or disabled
113 void SetEnabled(bool enabled);
116 * @brief Return true if the relayout controller is currently performing a relayout
118 * @return Return true if the relayout controller is currently performing a relayout
120 bool IsPerformingRelayout() const;
123 * @brief Sets whether core is processing events.
125 * @param[in] processingEvents whether core is processing events.
127 void SetProcessingCoreEvents(bool processingEvents);
130 * Get the capacity of the memory pool containing relayout info
131 * (It Should be regularly purged!)
133 uint32_t GetMemoryPoolCapacity();
137 * @brief Callback raised after the application creates the scene
139 void OnApplicationSceneCreated();
142 * @brief Callback for when an object is destroyed
144 * @param[in] object The object being destroyed
146 void OnObjectDestroyed(const Dali::RefObject* object);
149 using RawActorList = Dali::Integration::OrderedSet<Dali::Internal::Actor, false>;
152 * @brief Request for relayout. Relays out whole scene.
157 * @brief Add actor to request list
159 * @param[in] actor The root of the sub tree to add
161 void AddRequest(Dali::Actor& actor);
164 * @brief Remove actor from request list
166 * @param[in] actor The root of the sub tree to remove
168 void RemoveRequest(Dali::Actor& actor);
171 * @brief Disconnect the Relayout() method from the Stage::EventProcessingFinishedSignal().
176 * @brief Propagate dirty layout flags to actor and all sub-actors. This will stop propagating when a dirty actor
179 * @param[in] actor The actor to propagate on
180 * @param[in] dimension The dimension to propagate on
181 * @param[in] topOfSubTreeStack The top of the sub tree that this actor is in
182 * @param[in] potentialRedundantSubRoots Actors collected as potentially already being included in relayout
184 void PropagateAll(Dali::Actor& actor, Dimension::Type dimension, std::vector<Dali::Actor>& topOfSubTreeStack, std::vector<Dali::Actor>& potentialRedundantSubRoots);
187 * Queue an actor on the relayout container
189 * @param[in] actor The actor to be queued
190 * @param[in] actors The container to add the actor to
191 * @param[in] size The size that this actor should be
193 void QueueActor(Internal::Actor* actor, RelayoutContainer& actors, Vector2 size);
196 RelayoutController(const RelayoutController&) = delete;
197 RelayoutController& operator=(const RelayoutController&) = delete;
200 Integration::RenderController& mRenderController;
201 MemoryPoolObjectAllocator<MemoryPoolRelayoutContainer::RelayoutInfo> mRelayoutInfoAllocator;
203 SlotDelegate<RelayoutController> mSlotDelegate;
205 RawActorList mDirtyLayoutSubTrees; ///< List of roots of sub trees that are dirty
207 std::unique_ptr<MemoryPoolRelayoutContainer> mRelayoutStack; ///< Stack for relayouting
209 std::vector<Dali::Actor> mPotentialRedundantSubRoots; ///< Stack of Actor when RequestLayout comes. Keep it as member to avoid vector size reserving.
210 std::vector<Dali::Actor> mTopOfSubTreeStack;
212 bool mRelayoutConnection : 1; ///< Whether EventProcessingFinishedSignal signal is connected.
213 bool mRelayoutFlag : 1; ///< Relayout flag to avoid unnecessary calls
214 bool mEnabled : 1; ///< Initially disabled. Must be enabled at some point.
215 bool mPerformingRelayout : 1; ///< The relayout controller is currently performing a relayout
216 bool mProcessingCoreEvents : 1; ///< Whether core is processing events.
219 } // namespace Internal
223 #endif // DALI_INTERNAL_RELAYOUT_CONTROLLER_IMPL_H