aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/ui/render/border_render_object.cpp120
-rw-r--r--src/ui/render/border_render_object.hpp4
-rw-r--r--src/ui/render/render_object.cpp11
-rw-r--r--src/ui/render/render_object.hpp2
-rw-r--r--src/ui/render/text_render_object.cpp14
-rw-r--r--src/ui/render/text_render_object.hpp6
6 files changed, 83 insertions, 74 deletions
diff --git a/src/ui/render/border_render_object.cpp b/src/ui/render/border_render_object.cpp
index 49700869..72cea756 100644
--- a/src/ui/render/border_render_object.cpp
+++ b/src/ui/render/border_render_object.cpp
@@ -36,66 +36,6 @@ void BorderRenderObject::SetBrush(ID2D1Brush* new_brush) {
border_brush_ = new_brush;
}
-void BorderRenderObject::RecreateGeometry() {
- util::SafeRelease(geometry_);
- util::SafeRelease(border_outer_geometry_);
-
- const auto d2d_factory = graph::GraphManager::GetInstance()->GetD2D1Factory();
-
- Microsoft::WRL::ComPtr<ID2D1PathGeometry> geometry;
- ThrowIfFailed(d2d_factory->CreatePathGeometry(&geometry));
-
- Microsoft::WRL::ComPtr<ID2D1PathGeometry> border_outer_geometry;
- ThrowIfFailed(d2d_factory->CreatePathGeometry(&border_outer_geometry));
-
- Microsoft::WRL::ComPtr<ID2D1GeometrySink> sink;
- auto f = [&sink](const Rect& rect, const CornerRadius& corner) {
- sink->BeginFigure(D2D1::Point2F(rect.left + corner.left_top.x, rect.top),
- D2D1_FIGURE_BEGIN_FILLED);
- sink->AddLine(
- D2D1::Point2F(rect.GetRight() - corner.right_top.x, rect.top));
- sink->AddQuadraticBezier(D2D1::QuadraticBezierSegment(
- D2D1::Point2F(rect.GetRight(), rect.top),
- D2D1::Point2F(rect.GetRight(), rect.top + corner.right_top.y)));
- sink->AddLine(D2D1::Point2F(rect.GetRight(),
- rect.GetBottom() - corner.right_bottom.y));
- sink->AddQuadraticBezier(D2D1::QuadraticBezierSegment(
- D2D1::Point2F(rect.GetRight(), rect.GetBottom()),
- D2D1::Point2F(rect.GetRight() - corner.right_bottom.x,
- rect.GetBottom())));
- sink->AddLine(
- D2D1::Point2F(rect.left + corner.left_bottom.x, rect.GetBottom()));
- sink->AddQuadraticBezier(D2D1::QuadraticBezierSegment(
- D2D1::Point2F(rect.left, rect.GetBottom()),
- D2D1::Point2F(rect.left, rect.GetBottom() - corner.left_bottom.y)));
- sink->AddLine(D2D1::Point2F(rect.left, rect.top + corner.left_top.y));
- sink->AddQuadraticBezier(D2D1::QuadraticBezierSegment(
- D2D1::Point2F(rect.left, rect.top),
- D2D1::Point2F(rect.left + corner.left_top.x, rect.top)));
- sink->EndFigure(D2D1_FIGURE_END_CLOSED);
- };
-
- const auto size = GetSize();
- const auto margin = GetMargin();
- const Rect outer_rect{margin.left, margin.top,
- size.width - margin.GetHorizontalTotal(),
- size.height - margin.GetVerticalTotal()};
- ThrowIfFailed(border_outer_geometry->Open(&sink));
- f(outer_rect, corner_radius_);
- ThrowIfFailed(sink->Close());
- sink = nullptr;
-
- const Rect inner_rect = outer_rect.Shrink(border_thickness_);
- ThrowIfFailed(geometry->Open(&sink));
- f(outer_rect, corner_radius_);
- f(inner_rect, corner_radius_);
- ThrowIfFailed(sink->Close());
- sink = nullptr;
-
- geometry_ = geometry.Detach();
- border_outer_geometry_ = border_outer_geometry.Detach();
-}
-
void BorderRenderObject::Draw(ID2D1RenderTarget* render_target) {
render_target->FillGeometry(geometry_, border_brush_);
if (const auto child = GetChild()) {
@@ -231,4 +171,64 @@ void BorderRenderObject::OnLayoutContent(const Rect& content_rect) {
child->Layout(content_rect);
}
}
+
+void BorderRenderObject::RecreateGeometry() {
+ util::SafeRelease(geometry_);
+ util::SafeRelease(border_outer_geometry_);
+
+ const auto d2d_factory = graph::GraphManager::GetInstance()->GetD2D1Factory();
+
+ Microsoft::WRL::ComPtr<ID2D1PathGeometry> geometry;
+ ThrowIfFailed(d2d_factory->CreatePathGeometry(&geometry));
+
+ Microsoft::WRL::ComPtr<ID2D1PathGeometry> border_outer_geometry;
+ ThrowIfFailed(d2d_factory->CreatePathGeometry(&border_outer_geometry));
+
+ Microsoft::WRL::ComPtr<ID2D1GeometrySink> sink;
+ auto f = [&sink](const Rect& rect, const CornerRadius& corner) {
+ sink->BeginFigure(D2D1::Point2F(rect.left + corner.left_top.x, rect.top),
+ D2D1_FIGURE_BEGIN_FILLED);
+ sink->AddLine(
+ D2D1::Point2F(rect.GetRight() - corner.right_top.x, rect.top));
+ sink->AddQuadraticBezier(D2D1::QuadraticBezierSegment(
+ D2D1::Point2F(rect.GetRight(), rect.top),
+ D2D1::Point2F(rect.GetRight(), rect.top + corner.right_top.y)));
+ sink->AddLine(D2D1::Point2F(rect.GetRight(),
+ rect.GetBottom() - corner.right_bottom.y));
+ sink->AddQuadraticBezier(D2D1::QuadraticBezierSegment(
+ D2D1::Point2F(rect.GetRight(), rect.GetBottom()),
+ D2D1::Point2F(rect.GetRight() - corner.right_bottom.x,
+ rect.GetBottom())));
+ sink->AddLine(
+ D2D1::Point2F(rect.left + corner.left_bottom.x, rect.GetBottom()));
+ sink->AddQuadraticBezier(D2D1::QuadraticBezierSegment(
+ D2D1::Point2F(rect.left, rect.GetBottom()),
+ D2D1::Point2F(rect.left, rect.GetBottom() - corner.left_bottom.y)));
+ sink->AddLine(D2D1::Point2F(rect.left, rect.top + corner.left_top.y));
+ sink->AddQuadraticBezier(D2D1::QuadraticBezierSegment(
+ D2D1::Point2F(rect.left, rect.top),
+ D2D1::Point2F(rect.left + corner.left_top.x, rect.top)));
+ sink->EndFigure(D2D1_FIGURE_END_CLOSED);
+ };
+
+ const auto size = GetSize();
+ const auto margin = GetMargin();
+ const Rect outer_rect{margin.left, margin.top,
+ size.width - margin.GetHorizontalTotal(),
+ size.height - margin.GetVerticalTotal()};
+ ThrowIfFailed(border_outer_geometry->Open(&sink));
+ f(outer_rect, corner_radius_);
+ ThrowIfFailed(sink->Close());
+ sink = nullptr;
+
+ const Rect inner_rect = outer_rect.Shrink(border_thickness_);
+ ThrowIfFailed(geometry->Open(&sink));
+ f(outer_rect, corner_radius_);
+ f(inner_rect, corner_radius_);
+ ThrowIfFailed(sink->Close());
+ sink = nullptr;
+
+ geometry_ = geometry.Detach();
+ border_outer_geometry_ = border_outer_geometry.Detach();
+}
} // namespace cru::ui::render
diff --git a/src/ui/render/border_render_object.hpp b/src/ui/render/border_render_object.hpp
index 6f9a8c11..80db648a 100644
--- a/src/ui/render/border_render_object.hpp
+++ b/src/ui/render/border_render_object.hpp
@@ -56,7 +56,7 @@ class BorderRenderObject : public RenderObject {
corner_radius_ = new_corner_radius;
}
- void RecreateGeometry();
+ void Refresh() { RecreateGeometry(); }
void Draw(ID2D1RenderTarget* render_target) override;
@@ -77,6 +77,8 @@ class BorderRenderObject : public RenderObject {
return GetChildren().empty() ? nullptr : GetChildren()[0];
}
+ void RecreateGeometry();
+
private:
bool is_enabled_ = false;
diff --git a/src/ui/render/render_object.cpp b/src/ui/render/render_object.cpp
index 232eda41..5c6af580 100644
--- a/src/ui/render/render_object.cpp
+++ b/src/ui/render/render_object.cpp
@@ -1,5 +1,7 @@
#include "render_object.hpp"
+#include <algorithm>
+
#include "cru_debug.hpp"
namespace cru::ui::render {
@@ -96,6 +98,15 @@ void RenderObject::OnLayoutCore(const Rect& rect) {
coerced_content_available_size.height});
}
+Rect RenderObject::GetContentRect() const {
+ Rect rect{Point::Zero(), GetSize()};
+ rect = rect.Shrink(GetMargin());
+ rect = rect.Shrink(GetPadding());
+ rect.width = std::max(rect.width, 0.0f);
+ rect.height = std::max(rect.height, 0.0f);
+ return rect;
+}
+
void RenderObject::SetParent(RenderObject* new_parent) {
const auto old_parent = parent_;
parent_ = new_parent;
diff --git a/src/ui/render/render_object.hpp b/src/ui/render/render_object.hpp
index abdda605..824b88e6 100644
--- a/src/ui/render/render_object.hpp
+++ b/src/ui/render/render_object.hpp
@@ -75,6 +75,8 @@ class RenderObject : public Object {
virtual Size OnMeasureContent(const Size& available_size) = 0;
virtual void OnLayoutContent(const Rect& content_rect) = 0;
+ Rect GetContentRect() const;
+
private:
void SetParent(RenderObject* new_parent);
diff --git a/src/ui/render/text_render_object.cpp b/src/ui/render/text_render_object.cpp
index b66fffa3..69563ad7 100644
--- a/src/ui/render/text_render_object.cpp
+++ b/src/ui/render/text_render_object.cpp
@@ -114,15 +114,9 @@ RenderObject* TextRenderObject::HitTest(const Point& point) {
void TextRenderObject::OnSizeChanged(const Size& old_size,
const Size& new_size) {
- const auto margin = GetMargin();
- const auto padding = GetPadding();
- ThrowIfFailed(text_layout_->SetMaxWidth(
- std::max(new_size.width - margin.GetHorizontalTotal() -
- padding.GetHorizontalTotal(),
- 0.0f)));
- ThrowIfFailed(text_layout_->SetMaxHeight(std::max(
- new_size.height - margin.GetVerticalTotal() - padding.GetVerticalTotal(),
- 0.0f)));
+ const auto&& size = GetContentRect().GetSize();
+ ThrowIfFailed(text_layout_->SetMaxWidth(size.width));
+ ThrowIfFailed(text_layout_->SetMaxHeight(size.height));
}
Size TextRenderObject::OnMeasureContent(const Size& available_size) {
@@ -145,7 +139,7 @@ void TextRenderObject::RecreateTextLayout() {
const auto dwrite_factory =
graph::GraphManager::GetInstance()->GetDWriteFactory();
- const auto&& size = GetSize();
+ const auto&& size = GetContentRect().GetSize();
ThrowIfFailed(dwrite_factory->CreateTextLayout(
text_.c_str(), static_cast<UINT32>(text_.size()), text_format_,
diff --git a/src/ui/render/text_render_object.hpp b/src/ui/render/text_render_object.hpp
index db102b04..7827f994 100644
--- a/src/ui/render/text_render_object.hpp
+++ b/src/ui/render/text_render_object.hpp
@@ -38,11 +38,11 @@ class TextRenderObject : public RenderObject {
selection_range_ = std::move(new_range);
}
- ID2D1Brush* GetSelectionBrush() const {
- return selection_brush_;
- }
+ ID2D1Brush* GetSelectionBrush() const { return selection_brush_; }
void SetSelectionBrush(ID2D1Brush* new_brush);
+ void Refresh() { RecreateTextLayout(); }
+
void Draw(ID2D1RenderTarget* render_target) override;
RenderObject* HitTest(const Point& point) override;