aboutsummaryrefslogtreecommitdiff
path: root/include/cru/ui/render/RenderObject.hpp
diff options
context:
space:
mode:
authorcrupest <crupest@outlook.com>2022-02-08 16:53:51 +0800
committercrupest <crupest@outlook.com>2022-02-08 16:53:51 +0800
commit74bb9cd27242b9320f99ff4d2b50c3051576cc14 (patch)
tree744bac5799c593d1d6f81e7b09581bea626f2cde /include/cru/ui/render/RenderObject.hpp
parentb90c398de829d1ba5329651d75bae82f5e4085fe (diff)
downloadcru-74bb9cd27242b9320f99ff4d2b50c3051576cc14.tar.gz
cru-74bb9cd27242b9320f99ff4d2b50c3051576cc14.tar.bz2
cru-74bb9cd27242b9320f99ff4d2b50c3051576cc14.zip
...
Diffstat (limited to 'include/cru/ui/render/RenderObject.hpp')
-rw-r--r--include/cru/ui/render/RenderObject.hpp240
1 files changed, 0 insertions, 240 deletions
diff --git a/include/cru/ui/render/RenderObject.hpp b/include/cru/ui/render/RenderObject.hpp
deleted file mode 100644
index bac97640..00000000
--- a/include/cru/ui/render/RenderObject.hpp
+++ /dev/null
@@ -1,240 +0,0 @@
-#pragma once
-#include "Base.hpp"
-
-#include "MeasureRequirement.hpp"
-#include "cru/common/Base.hpp"
-#include "cru/common/Event.hpp"
-#include "cru/ui/Base.hpp"
-
-#include <cstddef>
-#include <string>
-#include <string_view>
-
-namespace cru::ui::render {
-// Render object will not destroy its children when destroyed. Control must
-// manage lifecycle of its render objects. Since control will destroy its
-// children when destroyed, render objects will be destroyed along with it.
-//
-// About layout:
-// Render object should be able to deal with arbitrary size as the result of
-// measure and layout.
-//
-// Parent may pass calculated preferred size down. But the preferred size set on
-// child itself takes precedence.
-//
-// Each render object should obey the measure requirement to set size and report
-// a warning when that requirement can't be satisfied with probably bigger size
-// of children than that of itself and optional visual effect to indicate that.
-//
-// If size of chilren are less than min size requirement, then render object
-// should try to fill the rest area. If size of children are more than max size
-// requirement, then render object should display a warning of the layout
-// problem and use the max size of itself with children exceeding its bound.
-// (Or better you could use some visual effect to indicate that.)
-//
-// To write a custom RenderObject, override following methods:
-// public:
-// void Draw(platform::graphics::IPainter* painter) override;
-// RenderObject* HitTest(const Point& point) override;
-// protected:
-// Size OnMeasureContent(const MeasureRequirement& requirement) override;
-// void OnLayoutContent(const Rect& content_rect) override;
-class CRU_UI_API RenderObject : public Object {
- friend host::WindowHost;
-
- CRU_DEFINE_CLASS_LOG_TAG(u"cru::ui::render::RenderObject")
-
- protected:
- enum class ChildMode {
- None,
- Single,
- Multiple,
- };
-
- RenderObject() = default;
- RenderObject(ChildMode child_mode) : RenderObject() {
- SetChildMode(child_mode);
- }
-
- public:
- RenderObject(const RenderObject& other) = delete;
- RenderObject(RenderObject&& other) = delete;
- RenderObject& operator=(const RenderObject& other) = delete;
- RenderObject& operator=(RenderObject&& other) = delete;
- ~RenderObject() override = default;
-
- controls::Control* GetAttachedControl() const { return control_; }
- void SetAttachedControl(controls::Control* new_control);
-
- host::WindowHost* GetWindowHost() const { return window_host_; }
-
- RenderObject* GetParent() const { return parent_; }
-
- const std::vector<RenderObject*>& GetChildren() const { return children_; }
- Index GetChildCount() const { return static_cast<Index>(children_.size()); }
- void AddChild(RenderObject* render_object, Index position);
- void RemoveChild(Index position);
-
- RenderObject* GetFirstChild() const;
- void TraverseDescendants(const std::function<void(RenderObject*)>& action);
-
- // Offset from parent's lefttop to lefttop of this render object. Margin is
- // accounted for.
- Point GetOffset() const { return offset_; }
- Size GetSize() const { return size_; }
- Point GetTotalOffset() const;
- Point FromRootToContent(const Point& point) const;
-
- Thickness GetMargin() const { return margin_; }
- void SetMargin(const Thickness& margin) {
- margin_ = margin;
- InvalidateLayout();
- }
-
- Thickness GetPadding() const { return padding_; }
- void SetPadding(const Thickness& padding) {
- padding_ = padding;
- InvalidateLayout();
- }
-
- MeasureSize GetPreferredSize() const { return preferred_size_; }
- void SetPreferredSize(const MeasureSize& preferred_size) {
- preferred_size_ = preferred_size;
- InvalidateLayout();
- }
-
- MeasureSize GetMinSize() const { return custom_measure_requirement_.min; }
- void SetMinSize(const MeasureSize& min_size) {
- custom_measure_requirement_.min = min_size;
- InvalidateLayout();
- }
-
- MeasureSize GetMaxSize() const { return custom_measure_requirement_.max; }
- void SetMaxSize(const MeasureSize& max_size) {
- custom_measure_requirement_.max = max_size;
- InvalidateLayout();
- }
-
- MeasureRequirement GetCustomMeasureRequirement() const {
- return custom_measure_requirement_;
- }
-
- // This method will merge requirement passed by argument and requirement of
- // the render object using MeasureRequirement::Merge and then call
- // MeasureRequirement::Normalize on it. And it will use preferred size of the
- // render object to override the one passed by argument. Then pass the two to
- // OnMeasureCore and use the return value of it to set the size of this render
- // object. This can be called multiple times on children during measure to
- // adjust for better size.
- void Measure(const MeasureRequirement& requirement,
- const MeasureSize& preferred_size);
- // This will set offset of this render object and call OnLayoutCore.
- void Layout(const Point& offset);
-
- virtual Thickness GetOuterSpaceThickness() const;
- virtual Rect GetPaddingRect() const;
- virtual Rect GetContentRect() const;
-
- void Draw(platform::graphics::IPainter* painter);
-
- // Param point must be relative the lefttop of render object including margin.
- // Add offset before pass point to children.
- virtual RenderObject* HitTest(const Point& point) = 0;
-
- IEvent<host::WindowHost*>* AttachToHostEvent() {
- return &attach_to_host_event_;
- }
- IEvent<std::nullptr_t>* DetachFromHostEvent() {
- return &detach_from_host_event_;
- }
-
- public:
- void InvalidateLayout();
- void InvalidatePaint();
-
- public:
- virtual std::u16string_view GetName() const;
- std::u16string GetDebugPathInTree() const;
-
- protected:
- void SetChildMode(ChildMode mode) { child_mode_ = mode; }
-
- protected:
- RenderObject* GetSingleChild() const;
-
- virtual void OnParentChanged(RenderObject* old_parent,
- RenderObject* new_parent);
-
- // default is to invalidate both layout and paint
- virtual void OnAddChild(RenderObject* new_child, Index position);
- // default is to invalidate both layout and paint
- virtual void OnRemoveChild(RenderObject* removed_child, Index position);
-
- // Draw all children with offset.
- void DefaultDrawChildren(platform::graphics::IPainter* painter);
-
- // Draw all children with translation of content rect lefttop.
- void DefaultDrawContent(platform::graphics::IPainter* painter);
-
- // Call DefaultDrawContent. Then call DefaultDrawChildren.
- virtual void OnDrawCore(platform::graphics::IPainter* painter);
-
- virtual void OnDrawContent(platform::graphics::IPainter* painter);
-
- // Size measure including margin and padding. Please reduce margin and padding
- // or other custom things and pass the result content measure requirement and
- // preferred size to OnMeasureContent. Return value must not be negative and
- // must obey requirement.
- // Note: Implementation should coerce the preferred size into the requirement
- // when pass them to OnMeasureContent.
- virtual Size OnMeasureCore(const MeasureRequirement& requirement,
- const MeasureSize& preferred_size);
-
- // Please reduce margin and padding or other custom things and pass the result
- // content rect to OnLayoutContent.
- virtual void OnLayoutCore();
-
- // Override this function to measure content and children(Call Measure on
- // them). Do not consider margin or padding in this method because they are
- // already considered in OnMeasureCore. Returned size must obey requirement.
- // Caller should guarantee preferred_size is corerced into required range.
- virtual Size OnMeasureContent(const MeasureRequirement& requirement,
- const MeasureSize& preferred_size) = 0;
-
- // Layout all content and children(Call Layout on them).
- // Lefttop of content_rect should be added when calculated children's offset.
- virtual void OnLayoutContent(const Rect& content_rect) = 0;
-
- virtual void OnAttachedControlChanged(controls::Control* control) {
- CRU_UNUSED(control)
- }
-
- virtual void OnAfterLayout();
-
- private:
- void SetParent(RenderObject* new_parent);
-
- void SetWindowHostRecursive(host::WindowHost* host);
-
- private:
- controls::Control* control_ = nullptr;
- host::WindowHost* window_host_ = nullptr;
-
- RenderObject* parent_ = nullptr;
- std::vector<RenderObject*> children_{};
-
- ChildMode child_mode_ = ChildMode::None;
-
- Point offset_{};
- Size size_{};
-
- MeasureSize preferred_size_;
- MeasureRequirement custom_measure_requirement_;
-
- Thickness margin_{};
- Thickness padding_{};
-
- Event<host::WindowHost*> attach_to_host_event_;
- Event<std::nullptr_t> detach_from_host_event_;
-};
-} // namespace cru::ui::render