GPU-accelerated UI toolkit (Vulkan)
git clone https://git.lucas.co/cce-ui.git
feat: implement CPU bounds clipping for Window descendants
src/widget/container/paginator.rs | 19 +++++++++++++-
src/widget/container/window.rs | 55 ++++++++++++++++++++++++++++++++++-----
2 files changed, 67 insertions(+), 7 deletions(-)
diff --git a/src/widget/container/paginator.rs b/src/widget/container/paginator.rs
index 23c1435..f377771 100644
--- a/src/widget/container/paginator.rs
+++ b/src/widget/container/paginator.rs
@@ -21,9 +21,26 @@ pub struct Paginator {
}
impl Paginator {
- pub fn new(sidebar_w: f32, pages: Vec<String>) -> Self {
+ pub fn new(pages: Vec<String>) -> Self {
let num_pages = pages.len();
+ let temp_paginator = Self {
+ x: 0.0,
+ y: 0.0,
+ w: 0.0,
+ h: 0.0,
+ sidebar_menu: ButtonStrip::new(0.0, 0.0, 0.0, 0.0),
+ plates: Vec::new(),
+ selected_page: 0,
+ page_hidden: false,
+ sidebar_w: 0.0,
+ pages: pages.clone(),
+ parent: None,
+ on_page_changed_cb: None,
+ just_clicked: None,
+ };
+ let sidebar_w = temp_paginator.sidebar_w();
+
let mut sidebar_menu = ButtonStrip::new(0.0, 0.0, sidebar_w, 0.0)
.with_vertical(true)
.with_buttons(pages.clone());
diff --git a/src/widget/container/window.rs b/src/widget/container/window.rs
index 1183f3d..0d66fc7 100644
--- a/src/widget/container/window.rs
+++ b/src/widget/container/window.rs
@@ -154,18 +154,29 @@ impl Element for Window {
}
let mut quads = Vec::new();
let bg_color = self.color();
+ let (wx, wy, ww, wh) = self.rect();
if bg_color[3] != 0.0 {
- let (wx, wy, ww, wh) = self.rect();
quads.push((wx, wy, ww, wh, bg_color));
}
for &child_ptr in &self.children {
let widget = unsafe { &*child_ptr };
+ let mut child_quads = Vec::new();
let cc = widget.color();
if cc[3] > 0.0 {
- let (wx, wy, ww, wh) = widget.rect();
- quads.push((wx, wy, ww, wh, cc));
+ let (cx, cy, cw, ch) = widget.rect();
+ child_quads.push((cx, cy, cw, ch, cc));
+ }
+ child_quads.extend(widget.all_quads(ctx));
+
+ for (qx, qy, qw, qh, qc) in child_quads {
+ let x0 = qx.max(wx);
+ let y0 = qy.max(wy);
+ let x1 = (qx + qw).min(wx + ww);
+ let y1 = (qy + qh).min(wy + wh);
+ if x1 > x0 && y1 > y0 {
+ quads.push((x0, y0, x1 - x0, y1 - y0, qc));
+ }
}
- quads.extend(widget.all_quads(ctx));
}
quads
}
@@ -187,9 +198,25 @@ impl Element for Window {
return Vec::new();
}
let mut result = Vec::new();
+ let (wx, wy, ww, wh) = self.rect();
for &child_ptr in &self.children {
let widget = unsafe { &*child_ptr };
- result.extend(widget.text_labels_with_bounds(ctx));
+ for (label, bounds) in widget.text_labels_with_bounds(ctx) {
+ let cb = if let Some(b) = bounds {
+ let cx0 = b[0].max(wx);
+ let cy0 = b[1].max(wy);
+ let cx1 = b[2].min(wx + ww);
+ let cy1 = b[3].min(wy + wh);
+ if cx1 > cx0 && cy1 > cy0 {
+ Some([cx0, cy0, cx1, cy1])
+ } else {
+ continue;
+ }
+ } else {
+ Some([wx, wy, wx + ww, wy + wh])
+ };
+ result.push((label, cb));
+ }
}
result
}
@@ -199,9 +226,25 @@ impl Element for Window {
return Vec::new();
}
let mut result = Vec::new();
+ let (wx, wy, ww, wh) = self.rect();
for &child_ptr in &self.children {
let widget = unsafe { &*child_ptr };
- result.extend(widget.text_labels_with_font_and_bounds(ctx));
+ for (label, font, bounds) in widget.text_labels_with_font_and_bounds(ctx) {
+ let cb = if let Some(b) = bounds {
+ let cx0 = b[0].max(wx);
+ let cy0 = b[1].max(wy);
+ let cx1 = b[2].min(wx + ww);
+ let cy1 = b[3].min(wy + wh);
+ if cx1 > cx0 && cy1 > cy0 {
+ Some([cx0, cy0, cx1, cy1])
+ } else {
+ continue;
+ }
+ } else {
+ Some([wx, wy, wx + ww, wy + wh])
+ };
+ result.push((label, font, cb));
+ }
}
result
}