Progress on window widget, minor refactor for layout directions structs
This commit is contained in:
parent
68b712acc6
commit
c2476ab854
@ -224,7 +224,6 @@ ui_graph_build_end :: proc( ui : ^UI_State )
|
||||
computed.content = computed.bounds
|
||||
}
|
||||
|
||||
|
||||
// Auto-layout and initial render_queue generation
|
||||
render_queue := array_to_slice(ui.render_queue)
|
||||
for current := root.first; current != nil; current = ui_box_tranverse_next_depth_first( current )
|
||||
|
@ -61,12 +61,19 @@ UI_Computed :: struct {
|
||||
fresh : b32, // If the auto-layout has been computed for the current frame
|
||||
}
|
||||
|
||||
UI_LayoutDirectionX :: enum(i32) {
|
||||
UI_LayoutDirection_XY :: enum(i32) {
|
||||
Left_To_Right,
|
||||
Right_to_Left,
|
||||
Top_To_Bottom,
|
||||
Bottom_To_Top,
|
||||
}
|
||||
|
||||
UI_LayoutDirection_X :: enum(i32) {
|
||||
Left_To_Right,
|
||||
Right_To_Left,
|
||||
}
|
||||
|
||||
UI_LayoutDirectionY :: enum(i32) {
|
||||
UI_LayoutDirection_Y :: enum(i32) {
|
||||
Top_To_Bottom,
|
||||
Bottom_To_Top,
|
||||
}
|
||||
@ -190,3 +197,24 @@ ui_layout_pop :: #force_inline proc() { pop( &
|
||||
@(deferred_none = ui_layout_pop) ui_layout_scope_via_combo :: #force_inline proc( combo : UI_LayoutCombo ) { ui_layout_push( combo) }
|
||||
|
||||
ui_set_layout :: #force_inline proc( layout : UI_Layout, preset : UI_StylePreset ) { stack_peek_ref( & get_state().ui_context.layout_combo_stack).array[preset] = layout }
|
||||
|
||||
ui_size_to_content_xy :: proc ( box : ^UI_Box) {
|
||||
using box
|
||||
children_bounds := ui_compute_children_overall_bounds(box)
|
||||
layout.size.min = size_range2(children_bounds)
|
||||
layout.flags |= { .Fixed_Width, .Fixed_Height }
|
||||
}
|
||||
|
||||
ui_size_to_content_x :: proc ( box : ^UI_Box) {
|
||||
using box
|
||||
children_bounds := ui_compute_children_overall_bounds(box)
|
||||
layout.size.min.x = size_range2(children_bounds).x
|
||||
layout.flags |= { .Fixed_Width }
|
||||
}
|
||||
|
||||
ui_size_to_content_y :: proc ( box : ^UI_Box) {
|
||||
using box
|
||||
children_bounds := ui_compute_children_overall_bounds(box)
|
||||
layout.size.min.y = size_range2(children_bounds).y
|
||||
layout.flags |= { .Fixed_Height }
|
||||
}
|
||||
|
@ -7,7 +7,7 @@ import lalg "core:math/linalg"
|
||||
Widget Layout Ops
|
||||
*/
|
||||
|
||||
ui_layout_children_horizontally :: proc( container : ^UI_Box, direction : UI_LayoutDirectionX, width_ref : ^f32 )
|
||||
ui_layout_children_horizontally :: proc( container : ^UI_Box, direction : UI_LayoutDirection_X, width_ref : ^f32 )
|
||||
{
|
||||
container_width : f32
|
||||
if width_ref != nil {
|
||||
@ -86,7 +86,7 @@ ui_layout_children_horizontally :: proc( container : ^UI_Box, direction : UI_Lay
|
||||
}
|
||||
}
|
||||
|
||||
ui_layout_children_vertically :: proc( container : ^UI_Box, direction : UI_LayoutDirectionY, height_ref : ^f32 )
|
||||
ui_layout_children_vertically :: proc( container : ^UI_Box, direction : UI_LayoutDirection_Y, height_ref : ^f32 )
|
||||
{
|
||||
container_height : f32
|
||||
if height_ref != nil {
|
||||
|
@ -173,8 +173,8 @@ theme_window_bar :: proc() -> UI_Theme
|
||||
app_color := app_color_theme()
|
||||
layout := UI_Layout {
|
||||
flags = {.Fixed_Height},
|
||||
anchor = range2({},{}),
|
||||
alignment = {0, 0},
|
||||
anchor = range2({0, 1},{0, 0}),
|
||||
alignment = {0, 1},
|
||||
text_alignment = {0.0, 0.0},
|
||||
font_size = 16,
|
||||
margins = {0, 0, 0, 0},
|
||||
|
@ -37,7 +37,7 @@ UI_DropDown :: struct {
|
||||
|
||||
@(deferred_out = ui_drop_down_end_auto)
|
||||
ui_drop_down :: proc( drop_down : ^UI_DropDown, label : string, title_text : StrRunesPair,
|
||||
direction := UI_LayoutDirectionY.Top_To_Bottom,
|
||||
direction := UI_LayoutDirection_Y.Top_To_Bottom,
|
||||
btn_flags := UI_BoxFlags{},
|
||||
vb_flags := UI_BoxFlags{},
|
||||
vb_compute_layout := true,
|
||||
@ -55,7 +55,7 @@ ui_drop_down :: proc( drop_down : ^UI_DropDown, label : string, title_text : Str
|
||||
|
||||
// Its assumed that the drop down has a vertical box parent already pushed
|
||||
ui_drop_down_begin :: proc( drop_down : ^UI_DropDown, label : string, title_text : StrRunesPair,
|
||||
direction := UI_LayoutDirectionY.Top_To_Bottom,
|
||||
direction := UI_LayoutDirection_Y.Top_To_Bottom,
|
||||
btn_flags := UI_BoxFlags{},
|
||||
vb_flags := UI_BoxFlags{},
|
||||
btn_theme : ^UI_Theme = nil,
|
||||
@ -91,7 +91,7 @@ ui_drop_down_begin :: proc( drop_down : ^UI_DropDown, label : string, title_text
|
||||
if vb_parent != nil {
|
||||
ui_parent_push(vb_parent)
|
||||
}
|
||||
vbox = ui_vbox_begin( direction, str_intern_fmt("%v : vbox", label).str, compute_layout = vb_compute_layout )
|
||||
vbox = ui_vbox_begin( direction, str_intern_fmt("%v.vbox", label).str, flags = {.Mouse_Clickable}, compute_layout = vb_compute_layout )
|
||||
vbox.layout.anchor.ratio.y = 1.0
|
||||
|
||||
if vb_parent != nil {
|
||||
@ -129,10 +129,10 @@ Keep in mind the stretch ratio is only respected if no size.min.x value is viola
|
||||
|
||||
UI_HBox :: struct {
|
||||
using widget : UI_Widget,
|
||||
direction : UI_LayoutDirectionX,
|
||||
direction : UI_LayoutDirection_X,
|
||||
}
|
||||
|
||||
ui_hbox_begin :: proc( direction : UI_LayoutDirectionX, label : string, flags : UI_BoxFlags = {} ) -> (hbox : UI_HBox) {
|
||||
ui_hbox_begin :: proc( direction : UI_LayoutDirection_X, label : string, flags : UI_BoxFlags = {} ) -> (hbox : UI_HBox) {
|
||||
// profile(#procedure)
|
||||
hbox.direction = direction
|
||||
hbox.box = ui_box_make( flags, label )
|
||||
@ -150,7 +150,7 @@ ui_hbox_end :: proc( hbox : UI_HBox, width_ref : ^f32 = nil, compute_layout := t
|
||||
}
|
||||
|
||||
@(deferred_out = ui_hbox_end_auto)
|
||||
ui_hbox :: #force_inline proc( direction : UI_LayoutDirectionX, label : string, flags : UI_BoxFlags = {} ) -> (hbox : UI_HBox) {
|
||||
ui_hbox :: #force_inline proc( direction : UI_LayoutDirection_X, label : string, flags : UI_BoxFlags = {} ) -> (hbox : UI_HBox) {
|
||||
hbox = ui_hbox_begin(direction, label, flags)
|
||||
ui_parent_push(hbox.box)
|
||||
return
|
||||
@ -755,10 +755,10 @@ Keep in mind the stretch ratio is only respected if no size.min.y value is viola
|
||||
|
||||
UI_VBox :: struct {
|
||||
using widget : UI_Widget,
|
||||
direction : UI_LayoutDirectionY,
|
||||
direction : UI_LayoutDirection_Y,
|
||||
}
|
||||
|
||||
ui_vbox_begin :: proc( direction : UI_LayoutDirectionY, label : string, flags : UI_BoxFlags = {}, compute_layout := false ) -> (vbox : UI_VBox) {
|
||||
ui_vbox_begin :: proc( direction : UI_LayoutDirection_Y, label : string, flags : UI_BoxFlags = {}, compute_layout := false ) -> (vbox : UI_VBox) {
|
||||
// profile(#procedure)
|
||||
vbox.direction = direction
|
||||
vbox.box = ui_box_make( flags, label )
|
||||
@ -781,7 +781,7 @@ ui_vbox_end_pop_parent :: proc( vbox : UI_VBox ) {
|
||||
}
|
||||
|
||||
@(deferred_out = ui_vbox_end_pop_parent)
|
||||
ui_vbox :: #force_inline proc( direction : UI_LayoutDirectionY, label : string, flags : UI_BoxFlags = {}, compute_layout := false ) -> (vbox : UI_VBox) {
|
||||
ui_vbox :: #force_inline proc( direction : UI_LayoutDirection_Y, label : string, flags : UI_BoxFlags = {}, compute_layout := false ) -> (vbox : UI_VBox) {
|
||||
vbox = ui_vbox_begin(direction, label, flags, compute_layout )
|
||||
ui_parent_push(vbox.widget)
|
||||
return
|
||||
|
@ -3,7 +3,12 @@ package sectr
|
||||
UI_Window :: struct
|
||||
{
|
||||
frame : UI_Widget,
|
||||
frame_bar : UI_HBox,
|
||||
bar : UI_HBox,
|
||||
children_box : struct #raw_union {
|
||||
box : UI_Widget,
|
||||
hbox : UI_HBox,
|
||||
vbox : UI_VBox,
|
||||
},
|
||||
tile_text : UI_Widget,
|
||||
maximize_btn : UI_Widget,
|
||||
close_btn : UI_Widget,
|
||||
@ -14,13 +19,38 @@ UI_Window :: struct
|
||||
is_maximized : b32,
|
||||
}
|
||||
|
||||
ui_window_begin :: proc( window : ^UI_Window, label : string,
|
||||
// Same as UI_LayoutDirection_XY but children may have the option to have their container just be a sub-box
|
||||
UI_Window_ChildLayout :: enum(i32) {
|
||||
None,
|
||||
Left_To_Right,
|
||||
Right_to_Left,
|
||||
Top_To_Bottom,
|
||||
Bottom_To_Top,
|
||||
}
|
||||
|
||||
@(deferred_in=ui_window_end_auto)
|
||||
ui_window :: proc (window : ^UI_Window, label : string,
|
||||
title : StrRunesPair = {},
|
||||
closable := true,
|
||||
maximizable := true,
|
||||
draggable := true,
|
||||
resizable := true
|
||||
) -> (dragged, resized, maximized : b32)
|
||||
resizable := true,
|
||||
child_layout : UI_Window_ChildLayout = .None
|
||||
) -> (dragged, resized, maximized, closed : b32)
|
||||
{
|
||||
dragged, resized, maximized, closed = ui_window_begin(window, label, title, closable, maximizable, draggable, resizable, child_layout)
|
||||
ui_parent_push(window.frame)
|
||||
return
|
||||
}
|
||||
|
||||
ui_window_begin :: proc( window : ^UI_Window, label : string,
|
||||
title : StrRunesPair = {},
|
||||
closable := true,
|
||||
maximizable := true,
|
||||
draggable := true,
|
||||
resizable := true,
|
||||
child_layout : UI_Window_ChildLayout = .None
|
||||
) -> (dragged, resized, maximized, closed : b32)
|
||||
{
|
||||
using window
|
||||
if ! is_open do return
|
||||
@ -34,9 +64,7 @@ ui_window_begin :: proc( window : ^UI_Window, label : string,
|
||||
if ! is_maximized
|
||||
{
|
||||
layout.flags = {
|
||||
// .Size_To_Content,
|
||||
.Fixed_Width, .Fixed_Height,
|
||||
// .Min_Size_To_Content_Y,
|
||||
.Fixed_Position_X, .Fixed_Position_Y,
|
||||
.Origin_At_Anchor_Center
|
||||
}
|
||||
@ -53,42 +81,85 @@ ui_window_begin :: proc( window : ^UI_Window, label : string,
|
||||
resized = ui_resizable_handles( & frame, & position, & size)
|
||||
}
|
||||
|
||||
if len(title.str) == 0 && ! closable && ! maximizable && ! draggable do return
|
||||
ui_parent(frame)
|
||||
if len(title.str) > 0 || closable || maximizable || draggable {
|
||||
dragged, maximized, closed = ui_window_bar(window, title, closable, maximizable, draggable)
|
||||
}
|
||||
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
ui_window_end :: proc (window : ^UI_Window)
|
||||
{
|
||||
}
|
||||
|
||||
ui_window_end_auto :: proc( window : ^UI_Window, label : string,
|
||||
title : StrRunesPair = {},
|
||||
closable := true,
|
||||
maximizable := true,
|
||||
draggable := true,
|
||||
resizable := true,
|
||||
child_layout : UI_Window_ChildLayout = .None
|
||||
)
|
||||
{
|
||||
ui_parent_pop()
|
||||
}
|
||||
|
||||
ui_window_bar :: proc( window : ^UI_Window,
|
||||
title : StrRunesPair = {},
|
||||
closable := true,
|
||||
maximizable := true,
|
||||
draggable := true,
|
||||
) -> (dragged, maximized, closed : b32)
|
||||
{
|
||||
using window
|
||||
ui_parent(frame)
|
||||
draggable_flag : UI_BoxFlags = draggable ? {.Mouse_Clickable} : {}
|
||||
|
||||
scope(theme_window_bar)
|
||||
frame_bar = ui_hbox(.Left_To_Right, str_intern_fmt("%v.frame_bar", label). str, draggable_flag);
|
||||
ui_parent(frame_bar)
|
||||
bar = ui_hbox(.Left_To_Right, str_intern_fmt("%v.bar", frame.label). str, draggable_flag);
|
||||
ui_parent(bar)
|
||||
|
||||
scope(theme_text)
|
||||
tile_text = ui_text( str_intern_fmt("%v.title_text", label).str, title, {.Disabled}); {
|
||||
using tile_text
|
||||
layout.anchor.ratio.x = 1.0
|
||||
layout.margins = { 0, 0, 15, 0}
|
||||
layout.font_size = 14
|
||||
if len(title.str) > 0
|
||||
{
|
||||
scope(theme_text)
|
||||
tile_text = ui_text( str_intern_fmt("%v.title_text", bar.label).str, title, {.Disabled}); {
|
||||
using tile_text
|
||||
layout.anchor.ratio.x = 1.0
|
||||
layout.margins = { 0, 0, 15, 0}
|
||||
layout.font_size = 14
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
scope(theme_window_bar_btn)
|
||||
maximize_btn = ui_button( str_intern_fmt("%v.maximize_btn", label).str ); {
|
||||
using maximize_btn
|
||||
if maximize_btn.pressed {
|
||||
is_maximized = ~is_maximized
|
||||
maximized = true
|
||||
if maximizable
|
||||
{
|
||||
maximize_btn = ui_button( str_intern_fmt("%v.maximize_btn", bar.label).str ); {
|
||||
using maximize_btn
|
||||
if maximize_btn.pressed {
|
||||
is_maximized = ~is_maximized
|
||||
maximized = true
|
||||
}
|
||||
if is_maximized do text = str_intern("min")
|
||||
else do text = str_intern("max")
|
||||
}
|
||||
if is_maximized do text = str_intern("min")
|
||||
else do text = str_intern("max")
|
||||
}
|
||||
close_btn = ui_button( str_intern_fmt("%v.close_btn", label).str ); {
|
||||
using close_btn
|
||||
text = str_intern("close")
|
||||
if close_btn.hot do style.bg_color = app_color_theme().window_btn_close_bg_hot
|
||||
if close_btn.pressed do is_open = false
|
||||
style.corner_radii = { 0, 0, 0, 0 }
|
||||
if closable
|
||||
{
|
||||
close_btn = ui_button( str_intern_fmt("%v.close_btn", bar.label).str ); {
|
||||
using close_btn
|
||||
text = str_intern("close")
|
||||
if close_btn.hot do style.bg_color = app_color_theme().window_btn_close_bg_hot
|
||||
if close_btn.pressed {
|
||||
is_open = false
|
||||
closed = true
|
||||
}
|
||||
style.corner_radii = { 0, 0, 0, 0 }
|
||||
}
|
||||
}
|
||||
|
||||
if frame_bar.active {
|
||||
|
||||
if bar.active {
|
||||
position += get_input_state().mouse.delta
|
||||
dragged = true
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user