fix size of .percent when box is shrunk due to strictness

This commit is contained in:
Rokas Puzonas 2025-02-07 00:40:22 +02:00
parent 785355509e
commit d744ab4b6b
2 changed files with 46 additions and 27 deletions

View File

@ -745,6 +745,22 @@ fn showToolbar(self: *App) void {
} }
} }
fn updateUI(self: *App) !void {
self.ui.begin();
defer self.ui.end();
const root_box = self.ui.getParent().?;
root_box.layout_axis = .Y;
self.showToolbar();
if (self.shown_window == .channels) {
try self.showChannelsWindow();
} else if (self.shown_window == .add_from_device) {
try self.showAddFromDeviceWindow();
}
}
pub fn tick(self: *App) !void { pub fn tick(self: *App) !void {
for (self.channel_views.slice()) |*_view| { for (self.channel_views.slice()) |*_view| {
const view: *ChannelView = _view; const view: *ChannelView = _view;
@ -769,21 +785,12 @@ pub fn tick(self: *App) !void {
Platform.toggleConsoleWindow(); Platform.toggleConsoleWindow();
} }
{ // On the first frame, render the UI twice.
self.ui.begin(); // So that on the second pass widgets that depend on sizes from other widgets have settled
defer self.ui.end(); if (self.ui.frame_index == 0) {
try self.updateUI();
const root_box = self.ui.getParent().?;
root_box.layout_axis = .Y;
self.showToolbar();
if (self.shown_window == .channels) {
try self.showChannelsWindow();
} else if (self.shown_window == .add_from_device) {
try self.showAddFromDeviceWindow();
}
} }
try self.updateUI();
self.ui.draw(); self.ui.draw();
} }

View File

@ -881,6 +881,8 @@ fn calcLayoutEnforceConstraints(self: *UI, box: *Box, axis: Axis) void {
{ {
var child_iter = self.iterChildrenByParent(box); var child_iter = self.iterChildrenByParent(box);
while (child_iter.next()) |child| { while (child_iter.next()) |child| {
if (child.isPositionFixed(axis)) continue;
const child_semantic_size_axis = child.size.getAxis(axis).*; const child_semantic_size_axis = child.size.getAxis(axis).*;
const child_size_axis = getVec2Axis(&child.persistent.size, axis).*; const child_size_axis = getVec2Axis(&child.persistent.size, axis).*;
@ -899,9 +901,17 @@ fn calcLayoutEnforceConstraints(self: *UI, box: *Box, axis: Axis) void {
var index: usize = 0; var index: usize = 0;
var child_iter = self.iterChildrenByParent(box); var child_iter = self.iterChildrenByParent(box);
while (child_iter.next()) |child| : (index += 1) { while (child_iter.next()) |child| : (index += 1) {
if (child.isPositionFixed(axis)) continue;
const child_size_axis = getVec2Axis(&child.persistent.size, axis); const child_size_axis = getVec2Axis(&child.persistent.size, axis);
child_size_axis.* -= children_fixups.buffer[index] * overflow_percent; child_size_axis.* -= children_fixups.buffer[index] * overflow_percent;
// Recalculate all upward depedent sizes, because the parent size changed
var child_child_iter = self.iterChildrenByParent(child);
while (child_child_iter.next()) |child_child| {
self.calcLayoutUpwardsSize(child_child, axis);
}
} }
} }
} }
@ -1136,18 +1146,18 @@ pub fn pushScrollbar(self: *UI, key: UI.Key) *Box {
}; };
self.pushParent(container); self.pushParent(container);
const scroll_area = self.newBoxFromString("Scroll area"); const content_area = self.newBoxFromString("Scroll area");
scroll_area.size = .{ content_area.size = .{
.x = UI.Size.percent(1, 0), .x = UI.Size.percent(1, 0),
.y = UI.Size.percent(1, 0), .y = UI.Size.percent(1, 0),
}; };
self.pushParent(scroll_area); self.pushParent(content_area);
return scroll_area; return content_area;
} }
pub fn popScrollbar(self: *UI) void { pub fn popScrollbar(self: *UI) void {
const scroll_area = self.getParent().?; const content_area = self.getParent().?;
self.popParent(); // pop scroll area self.popParent(); // pop scroll area
const scrollbar_area = self.newBoxFromString("Scrollbar area"); const scrollbar_area = self.newBoxFromString("Scrollbar area");
@ -1159,8 +1169,9 @@ pub fn popScrollbar(self: *UI) void {
self.pushParent(scrollbar_area); self.pushParent(scrollbar_area);
defer self.popParent(); defer self.popParent();
var scrollbar_size_percent = scroll_area.persistent.size.y / scroll_area.persistent.children_size.y; const visible_content_size = content_area.persistent.size.y;
scrollbar_size_percent = std.math.clamp(scrollbar_size_percent, 0, 1); const used_content_size = content_area.persistent.children_size.y;
const visible_percent = clamp(visible_content_size / used_content_size, 0, 1);
const draggable = self.newBoxFromString("Scrollbar button"); const draggable = self.newBoxFromString("Scrollbar button");
draggable.background = rl.Color.dark_brown; draggable.background = rl.Color.dark_brown;
@ -1168,21 +1179,22 @@ pub fn popScrollbar(self: *UI) void {
draggable.flags.insert(.draggable_y); draggable.flags.insert(.draggable_y);
draggable.size = .{ draggable.size = .{
.x = UI.Size.percent(1, 1), .x = UI.Size.percent(1, 1),
.y = UI.Size.percent(scrollbar_size_percent, 1), .y = UI.Size.percent(visible_percent, 1),
}; };
const scrollbar_area_height = scrollbar_area.persistent.size.y; const scrollbar_height = scrollbar_area.persistent.size.y;
const scrollbar_max_move = scrollbar_area_height * (1 - scrollbar_size_percent);
const max_offset = scrollbar_height * (1 - visible_percent);
const sroll_offset = &draggable.persistent.sroll_offset; const sroll_offset = &draggable.persistent.sroll_offset;
const signal = self.signalFromBox(draggable); const signal = self.signalFromBox(draggable);
if (signal.dragged()) { if (signal.dragged()) {
sroll_offset.* += signal.drag.y / scrollbar_max_move; sroll_offset.* += signal.drag.y / max_offset;
sroll_offset.* = clamp(sroll_offset.*, 0, 1); sroll_offset.* = clamp(sroll_offset.*, 0, 1);
} }
draggable.setFixedY(scrollbar_area.persistent.position.y + sroll_offset.* * scrollbar_max_move); draggable.setFixedY(scrollbar_area.persistent.position.y + sroll_offset.* * max_offset);
scroll_area.view_offset.y = sroll_offset.* * (1 - scrollbar_size_percent) * scroll_area.persistent.children_size.y; content_area.view_offset.y = sroll_offset.* * (1 - visible_percent) * used_content_size;
self.popParent(); // pop container self.popParent(); // pop container
} }