diff options
Diffstat (limited to 'src/ui/render/RenderObject.cpp')
-rw-r--r-- | src/ui/render/RenderObject.cpp | 206 |
1 files changed, 56 insertions, 150 deletions
diff --git a/src/ui/render/RenderObject.cpp b/src/ui/render/RenderObject.cpp index 00488425..67bbae12 100644 --- a/src/ui/render/RenderObject.cpp +++ b/src/ui/render/RenderObject.cpp @@ -1,66 +1,15 @@ #include "cru/ui/render/RenderObject.h" #include "cru/common/Logger.h" -#include "cru/platform/GraphicsBase.h" -#include "cru/platform/graphics/util/Painter.h" -#include "cru/ui/Base.h" #include "cru/ui/DebugFlags.h" +#include "cru/ui/controls/Control.h" #include "cru/ui/host/WindowHost.h" -#include <algorithm> -#include <string> -#include <string_view> -#include <vector> - namespace cru::ui::render { void RenderObject::SetAttachedControl(controls::Control* new_control) { + auto old_control = control_; control_ = new_control; - OnAttachedControlChanged(new_control); -} - -void RenderObject::AddChild(RenderObject* render_object, const Index position) { - Expects(child_mode_ != ChildMode::None); - Expects(!(child_mode_ == ChildMode::Single && children_.size() > 0)); - - Expects(render_object->GetParent() == - nullptr); // Render object already has a parent. - Expects(position >= 0); // Position index is less than 0. - Expects( - position <= - static_cast<Index>(children_.size())); // Position index is out of bound. - - children_.insert(children_.cbegin() + position, render_object); - render_object->SetParent(this); - render_object->SetWindowHostRecursive(GetWindowHost()); - OnAddChild(render_object, position); -} - -void RenderObject::RemoveChild(const Index position) { - Expects(position >= 0); // Position index is less than 0. - Expects(position < static_cast<Index>( - children_.size())); // Position index is out of bound. - - const auto i = children_.cbegin() + position; - const auto removed_child = *i; - children_.erase(i); - removed_child->SetParent(nullptr); - removed_child->SetWindowHostRecursive(nullptr); - OnRemoveChild(removed_child, position); -} - -RenderObject* RenderObject::GetFirstChild() const { - const auto& children = GetChildren(); - if (children.empty()) { - return nullptr; - } else { - return children.front(); - } -} - -void RenderObject::TraverseDescendants( - const std::function<void(RenderObject*)>& action) { - action(this); - for (auto child : children_) child->TraverseDescendants(action); + OnAttachedControlChanged(old_control, new_control); } Point RenderObject::GetTotalOffset() const { @@ -84,6 +33,31 @@ Point RenderObject::FromRootToContent(const Point& point) const { point.y - (offset.y + rect.top)}; } +void RenderObject::SetMargin(const Thickness& margin) { + margin_ = margin; + InvalidateLayout(); +} + +void RenderObject::SetPadding(const Thickness& padding) { + padding_ = padding; + InvalidateLayout(); +} + +void RenderObject::SetPreferredSize(const MeasureSize& preferred_size) { + preferred_size_ = preferred_size; + InvalidateLayout(); +} + +void RenderObject::SetMinSize(const MeasureSize& min_size) { + custom_measure_requirement_.min = min_size; + InvalidateLayout(); +} + +void RenderObject::SetMaxSize(const MeasureSize& max_size) { + custom_measure_requirement_.max = max_size; + InvalidateLayout(); +} + void RenderObject::Measure(const MeasureRequirement& requirement, const MeasureSize& preferred_size) { MeasureRequirement merged_requirement = @@ -98,23 +72,27 @@ void RenderObject::Measure(const MeasureRequirement& requirement, preferred_size.ToDebugString()); } - size_ = OnMeasureCore(merged_requirement, merged_preferred_size); + desired_size_ = OnMeasureCore(merged_requirement, merged_preferred_size); if constexpr (cru::ui::debug_flags::layout) { log::Debug(u"{} Measure ends :\nresult size: {}", - this->GetDebugPathInTree(), size_); + this->GetDebugPathInTree(), desired_size_); } - Ensures(size_.width >= 0); - Ensures(size_.height >= 0); + Ensures(desired_size_.width >= 0); + Ensures(desired_size_.height >= 0); } void RenderObject::Layout(const Point& offset) { if constexpr (cru::ui::debug_flags::layout) { log::Debug(u"{} Layout :\noffset: {} size: {}", this->GetDebugPathInTree(), - offset, GetSize()); + offset, desired_size_); } offset_ = offset; + size_ = desired_size_; + + OnResize(size_); + OnLayoutCore(); } @@ -122,67 +100,6 @@ Thickness RenderObject::GetOuterSpaceThickness() const { return margin_ + padding_; } -void RenderObject::Draw(platform::graphics::IPainter* painter) { - OnDrawCore(painter); -} - -RenderObject* RenderObject::GetSingleChild() const { - Expects(child_mode_ == ChildMode::Single); - const auto& children = GetChildren(); - if (children.empty()) - return nullptr; - else - return children.front(); -} - -void RenderObject::OnParentChanged(RenderObject* old_parent, - RenderObject* new_parent) { - CRU_UNUSED(old_parent) - CRU_UNUSED(new_parent) -} - -void RenderObject::OnAddChild(RenderObject* new_child, Index position) { - CRU_UNUSED(new_child) - CRU_UNUSED(position) - - InvalidateLayout(); - InvalidatePaint(); -} - -void RenderObject::OnRemoveChild(RenderObject* removed_child, Index position) { - CRU_UNUSED(removed_child) - CRU_UNUSED(position) - - InvalidateLayout(); - InvalidatePaint(); -} - -void RenderObject::DefaultDrawChildren(platform::graphics::IPainter* painter) { - for (const auto child : GetChildren()) { - auto offset = child->GetOffset(); - platform::graphics::util::WithTransform( - painter, platform::Matrix::Translation(offset.x, offset.y), - [child](auto p) { child->Draw(p); }); - } -} - -void RenderObject::DefaultDrawContent(platform::graphics::IPainter* painter) { - const auto content_rect = GetContentRect(); - - platform::graphics::util::WithTransform( - painter, Matrix::Translation(content_rect.left, content_rect.top), - [this](auto p) { this->OnDrawContent(p); }); -} - -void RenderObject::OnDrawCore(platform::graphics::IPainter* painter) { - DefaultDrawContent(painter); - DefaultDrawChildren(painter); -} - -void RenderObject::OnDrawContent(platform::graphics::IPainter* painter) { - CRU_UNUSED(painter); -} - Size RenderObject::OnMeasureCore(const MeasureRequirement& requirement, const MeasureSize& preferred_size) { const Thickness outer_space = GetOuterSpaceThickness(); @@ -204,7 +121,7 @@ Size RenderObject::OnMeasureCore(const MeasureRequirement& requirement, } void RenderObject::OnLayoutCore() { - Size total_size = GetSize(); + Size total_size = GetDesiredSize(); const Thickness outer_space = GetOuterSpaceThickness(); const Size space_size{outer_space.GetHorizontalTotal(), outer_space.GetVerticalTotal()}; @@ -231,10 +148,8 @@ void RenderObject::OnLayoutCore() { OnLayoutContent(content_rect); } -void RenderObject::OnAfterLayout() {} - Rect RenderObject::GetPaddingRect() const { - const auto size = GetSize(); + const auto size = GetDesiredSize(); Rect rect{Point{}, size}; rect = rect.Shrink(GetMargin()); rect.left = std::min(rect.left, size.width); @@ -245,7 +160,7 @@ Rect RenderObject::GetPaddingRect() const { } Rect RenderObject::GetContentRect() const { - const auto size = GetSize(); + const auto size = GetDesiredSize(); Rect rect{Point{}, size}; rect = rect.Shrink(GetMargin()); rect = rect.Shrink(GetPadding()); @@ -256,33 +171,37 @@ Rect RenderObject::GetContentRect() const { return rect; } -void RenderObject::SetParent(RenderObject* new_parent) { - const auto old_parent = parent_; - parent_ = new_parent; - OnParentChanged(old_parent, new_parent); +host::WindowHost* RenderObject::GetWindowHost() { + if (control_) { + return control_->GetWindowHost(); + } + return nullptr; } void RenderObject::InvalidateLayout() { - if (window_host_ != nullptr) window_host_->InvalidateLayout(); + if (auto window_host = GetWindowHost()) { + window_host->InvalidateLayout(); + } } void RenderObject::InvalidatePaint() { - if (window_host_ != nullptr) window_host_->InvalidatePaint(); + if (auto window_host = GetWindowHost()) { + window_host->InvalidatePaint(); + } } -constexpr std::u16string_view kUnamedName(u"UNNAMED"); - -std::u16string_view RenderObject::GetName() const { return kUnamedName; } +String kUnamedName(u"UNNAMED"); +String RenderObject::GetName() const { return kUnamedName; } -std::u16string RenderObject::GetDebugPathInTree() const { - std::vector<std::u16string_view> chain; +String RenderObject::GetDebugPathInTree() const { + std::vector<String> chain; const RenderObject* parent = this; while (parent != nullptr) { chain.push_back(parent->GetName()); parent = parent->GetParent(); } - std::u16string result(chain.back()); + String result(chain.back()); for (auto iter = chain.crbegin() + 1; iter != chain.crend(); ++iter) { result += u" -> "; result += *iter; @@ -290,17 +209,4 @@ std::u16string RenderObject::GetDebugPathInTree() const { return result; } - -void RenderObject::SetWindowHostRecursive(host::WindowHost* host) { - if (window_host_ != nullptr) { - detach_from_host_event_.Raise(nullptr); - } - window_host_ = host; - if (host != nullptr) { - attach_to_host_event_.Raise(nullptr); - } - for (const auto child : GetChildren()) { - child->SetWindowHostRecursive(host); - } -} } // namespace cru::ui::render |