get_elem now also pushes into the tree and check the correct type
This commit is contained in:
parent
849b267f91
commit
c49a689304
2
TODO
2
TODO
@ -64,6 +64,8 @@ to maintain focus until mouse release (fix scroll bars)
|
|||||||
- border radius
|
- border radius
|
||||||
[x] add a command to update an atlas
|
[x] add a command to update an atlas
|
||||||
[ ] New window command, useful for popups
|
[ ] New window command, useful for popups
|
||||||
|
[ ] Text command returns the text bounds, this way we can avoid the pattern
|
||||||
|
draw_text(a, pos) -> off = compute_bounds(a) -> draw_text(b, pos+off) -> ...
|
||||||
|
|
||||||
## Atlas
|
## Atlas
|
||||||
|
|
||||||
|
@ -16,15 +16,7 @@ fn ElemEvents? Ctx.button_id(&ctx, Id id, Rect size, bool active)
|
|||||||
id = ctx.gen_id(id)!;
|
id = ctx.gen_id(id)!;
|
||||||
|
|
||||||
Elem *parent = ctx.get_parent()!;
|
Elem *parent = ctx.get_parent()!;
|
||||||
Elem *elem = ctx.get_elem(id)!;
|
Elem *elem = ctx.get_elem(id, ETYPE_BUTTON)!;
|
||||||
// add it to the tree
|
|
||||||
ctx.tree.add(id, ctx.active_div)!;
|
|
||||||
|
|
||||||
if (elem.flags.is_new) {
|
|
||||||
elem.type = ETYPE_BUTTON;
|
|
||||||
} else if (elem.type != ETYPE_BUTTON) {
|
|
||||||
return WRONG_ELEMENT_TYPE?;
|
|
||||||
}
|
|
||||||
|
|
||||||
elem.bounds = ctx.position_element(parent, size, true);
|
elem.bounds = ctx.position_element(parent, size, true);
|
||||||
|
|
||||||
@ -53,13 +45,7 @@ fn ElemEvents? Ctx.button_label_id(&ctx, Id id, String label, Rect size, bool ac
|
|||||||
id = ctx.gen_id(id)!;
|
id = ctx.gen_id(id)!;
|
||||||
|
|
||||||
Elem *parent = ctx.get_parent()!;
|
Elem *parent = ctx.get_parent()!;
|
||||||
Elem *elem = ctx.get_elem(id)!;
|
Elem *elem = ctx.get_elem(id, ETYPE_BUTTON)!;
|
||||||
// add it to the tree
|
|
||||||
ctx.tree.add(id, ctx.active_div)!;
|
|
||||||
|
|
||||||
// 1. Fill the element fields
|
|
||||||
// this resets the flags
|
|
||||||
elem.type = ETYPE_BUTTON;
|
|
||||||
|
|
||||||
short line_height = (short)ctx.font.ascender - (short)ctx.font.descender;
|
short line_height = (short)ctx.font.ascender - (short)ctx.font.descender;
|
||||||
Rect text_size = ctx.get_text_bounds(label)!;
|
Rect text_size = ctx.get_text_bounds(label)!;
|
||||||
@ -96,15 +82,7 @@ fn ElemEvents? Ctx.button_icon_id(&ctx, Id id, String icon, String on_icon, bool
|
|||||||
id = ctx.gen_id(id)!;
|
id = ctx.gen_id(id)!;
|
||||||
|
|
||||||
Elem *parent = ctx.get_parent()!;
|
Elem *parent = ctx.get_parent()!;
|
||||||
Elem *elem = ctx.get_elem(id)!;
|
Elem *elem = ctx.get_elem(id, ETYPE_BUTTON)!;
|
||||||
// add it to the tree
|
|
||||||
ctx.tree.add(id, ctx.active_div)!;
|
|
||||||
|
|
||||||
if (elem.flags.is_new) {
|
|
||||||
elem.type = ETYPE_BUTTON;
|
|
||||||
} else if (elem.type != ETYPE_BUTTON) {
|
|
||||||
return WRONG_ELEMENT_TYPE?;
|
|
||||||
}
|
|
||||||
|
|
||||||
Sprite* def_sprite = ctx.sprite_atlas.get(icon)!;
|
Sprite* def_sprite = ctx.sprite_atlas.get(icon)!;
|
||||||
Sprite* on_sprite = ctx.sprite_atlas.get(on_icon) ?? &&(Sprite){};
|
Sprite* on_sprite = ctx.sprite_atlas.get(on_icon) ?? &&(Sprite){};
|
||||||
@ -141,15 +119,7 @@ fn void? Ctx.checkbox_id(&ctx, Id id, String description, Point off, bool* activ
|
|||||||
id = ctx.gen_id(id)!;
|
id = ctx.gen_id(id)!;
|
||||||
|
|
||||||
Elem *parent = ctx.get_parent()!;
|
Elem *parent = ctx.get_parent()!;
|
||||||
Elem *elem = ctx.get_elem(id)!;
|
Elem *elem = ctx.get_elem(id, ETYPE_BUTTON)!;
|
||||||
// add it to the tree
|
|
||||||
ctx.tree.add(id, ctx.active_div)!;
|
|
||||||
|
|
||||||
if (elem.flags.is_new) {
|
|
||||||
elem.type = ETYPE_BUTTON;
|
|
||||||
} else if (elem.type != ETYPE_BUTTON) {
|
|
||||||
return WRONG_ELEMENT_TYPE?;
|
|
||||||
}
|
|
||||||
|
|
||||||
Rect size = {off.x, off.y, DEFAULT_CHECKBOX_SIZE, DEFAULT_CHECKBOX_SIZE};
|
Rect size = {off.x, off.y, DEFAULT_CHECKBOX_SIZE, DEFAULT_CHECKBOX_SIZE};
|
||||||
elem.bounds = ctx.position_element(parent, size, true);
|
elem.bounds = ctx.position_element(parent, size, true);
|
||||||
@ -186,17 +156,7 @@ fn void? Ctx.toggle_id(&ctx, Id id, String description, Point off, bool* active)
|
|||||||
id = ctx.gen_id(id)!;
|
id = ctx.gen_id(id)!;
|
||||||
|
|
||||||
Elem *parent = ctx.get_parent()!;
|
Elem *parent = ctx.get_parent()!;
|
||||||
Elem *elem = ctx.get_elem(id)!;
|
Elem *elem = ctx.get_elem(id, ETYPE_BUTTON)!;
|
||||||
// add it to the tree
|
|
||||||
ctx.tree.add(id, ctx.active_div)!;
|
|
||||||
|
|
||||||
// FIXME: for now switches and buttons have no members so the element types
|
|
||||||
// can be the same
|
|
||||||
if (elem.flags.is_new) {
|
|
||||||
elem.type = ETYPE_BUTTON;
|
|
||||||
} else if (elem.type != ETYPE_BUTTON) {
|
|
||||||
return WRONG_ELEMENT_TYPE?;
|
|
||||||
}
|
|
||||||
|
|
||||||
Rect size = {off.x, off.y, DEFAULT_SWITCH_SIZE*2, DEFAULT_SWITCH_SIZE};
|
Rect size = {off.x, off.y, DEFAULT_SWITCH_SIZE*2, DEFAULT_SWITCH_SIZE};
|
||||||
elem.bounds = ctx.position_element(parent, size, true);
|
elem.bounds = ctx.position_element(parent, size, true);
|
||||||
|
@ -40,6 +40,7 @@ bitstruct ElemEvents : uint {
|
|||||||
// element structure
|
// element structure
|
||||||
struct Elem {
|
struct Elem {
|
||||||
Id id;
|
Id id;
|
||||||
|
isz tree_idx;
|
||||||
ElemFlags flags;
|
ElemFlags flags;
|
||||||
ElemEvents events;
|
ElemEvents events;
|
||||||
Rect bounds;
|
Rect bounds;
|
||||||
@ -158,7 +159,7 @@ macro Id @compute_id(...)
|
|||||||
|
|
||||||
// get or push an element from the cache, return a pointer to it
|
// get or push an element from the cache, return a pointer to it
|
||||||
// resets all flags except is_new which is set accordingly
|
// resets all flags except is_new which is set accordingly
|
||||||
fn Elem*? Ctx.get_elem(&ctx, Id id)
|
fn Elem*? Ctx.get_elem(&ctx, Id id, ElemType type)
|
||||||
{
|
{
|
||||||
Elem empty_elem;
|
Elem empty_elem;
|
||||||
bool is_new;
|
bool is_new;
|
||||||
@ -166,8 +167,13 @@ fn Elem*? Ctx.get_elem(&ctx, Id id)
|
|||||||
elem = ctx.cache.get_or_insert(&empty_elem, id, &is_new)!;
|
elem = ctx.cache.get_or_insert(&empty_elem, id, &is_new)!;
|
||||||
elem.flags = (ElemFlags)0;
|
elem.flags = (ElemFlags)0;
|
||||||
elem.flags.is_new = is_new;
|
elem.flags.is_new = is_new;
|
||||||
// FIXME: should this be here? or is it better to have the elements set the id?
|
|
||||||
elem.id = id;
|
elem.id = id;
|
||||||
|
if (is_new == false && elem.type != type) {
|
||||||
|
return WRONG_ELEMENT_TYPE?;
|
||||||
|
} else {
|
||||||
|
elem.type = type;
|
||||||
|
}
|
||||||
|
elem.tree_idx = ctx.tree.add(id, ctx.active_div)!;
|
||||||
return elem;
|
return elem;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -223,11 +229,13 @@ fn void Ctx.free(&ctx)
|
|||||||
|
|
||||||
fn void? Ctx.frame_begin(&ctx)
|
fn void? Ctx.frame_begin(&ctx)
|
||||||
{
|
{
|
||||||
|
// 1. Reset the active div
|
||||||
// 2. Get the root element from the cache and update it
|
// 2. Get the root element from the cache and update it
|
||||||
Elem* elem = ctx.get_elem(ROOT_ID)!;
|
ctx.active_div = 0;
|
||||||
|
Elem* elem = ctx.get_elem(ROOT_ID, ETYPE_DIV)!;
|
||||||
|
ctx.active_div = elem.tree_idx;
|
||||||
// The root should have the updated flag only if the size of the window
|
// The root should have the updated flag only if the size of the window
|
||||||
// was changed between frames, this propagates an element size recalculation
|
// was changed between frasmes, this propagates an element size recalculation
|
||||||
// down the element tree
|
// down the element tree
|
||||||
elem.flags.updated = ctx.input.events.resize;
|
elem.flags.updated = ctx.input.events.resize;
|
||||||
// if the window has focus then the root element also has focus, no other
|
// if the window has focus then the root element also has focus, no other
|
||||||
@ -235,28 +243,15 @@ fn void? Ctx.frame_begin(&ctx)
|
|||||||
// other stuff
|
// other stuff
|
||||||
//elem.flags.has_focus = ctx.has_focus;
|
//elem.flags.has_focus = ctx.has_focus;
|
||||||
|
|
||||||
Elem def_root = {
|
elem.bounds = {0, 0, ctx.width, ctx.height};
|
||||||
.id = ROOT_ID,
|
elem.div.layout = LAYOUT_ROW;
|
||||||
.type = ETYPE_DIV,
|
elem.div.z_index = 0;
|
||||||
.bounds = {
|
elem.div.children_bounds = elem.bounds;
|
||||||
.w = ctx.width,
|
elem.div.scroll_x.enabled = false;
|
||||||
.h = ctx.height,
|
elem.div.scroll_y.enabled = false;
|
||||||
},
|
elem.div.pcb = {};
|
||||||
.div = {
|
elem.div.origin_c = {};
|
||||||
.layout = LAYOUT_ROW,
|
elem.div.origin_r = {};
|
||||||
.z_index = 0,
|
|
||||||
.children_bounds = {
|
|
||||||
.w = ctx.width,
|
|
||||||
.h = ctx.height,
|
|
||||||
}
|
|
||||||
},
|
|
||||||
.flags = elem.flags,
|
|
||||||
};
|
|
||||||
|
|
||||||
*elem = def_root;
|
|
||||||
|
|
||||||
// 3. Push the root element into the element tree
|
|
||||||
ctx.active_div = ctx.tree.add(ROOT_ID, 0)!;
|
|
||||||
|
|
||||||
ctx.div_scissor = {0, 0, ctx.width, ctx.height};
|
ctx.div_scissor = {0, 0, ctx.width, ctx.height};
|
||||||
|
|
||||||
|
@ -36,17 +36,9 @@ fn void? Ctx.div_begin_id(&ctx, Id id, Rect size, bool scroll_x, bool scroll_y)
|
|||||||
id = ctx.gen_id(id)!;
|
id = ctx.gen_id(id)!;
|
||||||
|
|
||||||
Elem* parent = ctx.get_parent()!;
|
Elem* parent = ctx.get_parent()!;
|
||||||
Elem* elem = ctx.get_elem(id)!;
|
Elem* elem = ctx.get_elem(id, ETYPE_DIV)!;
|
||||||
isz div_node = ctx.tree.add(id, ctx.active_div)!;
|
ctx.active_div = elem.tree_idx;
|
||||||
ctx.active_div = div_node;
|
|
||||||
|
|
||||||
bool is_new = elem.flags.is_new;
|
|
||||||
|
|
||||||
if (elem.flags.is_new) {
|
|
||||||
elem.type = ETYPE_DIV;
|
|
||||||
} else if (elem.type != ETYPE_DIV) {
|
|
||||||
return WRONG_ELEMENT_TYPE?;
|
|
||||||
}
|
|
||||||
elem.div.scroll_x.enabled = scroll_x;
|
elem.div.scroll_x.enabled = scroll_x;
|
||||||
elem.div.scroll_y.enabled = scroll_y;
|
elem.div.scroll_y.enabled = scroll_y;
|
||||||
elem.div.z_index = parent.div.z_index + 1;
|
elem.div.z_index = parent.div.z_index + 1;
|
||||||
|
@ -35,16 +35,7 @@ fn ElemEvents? Ctx.slider_hor_id(&ctx,
|
|||||||
id = ctx.gen_id(id)!;
|
id = ctx.gen_id(id)!;
|
||||||
|
|
||||||
Elem *parent = ctx.get_parent()!;
|
Elem *parent = ctx.get_parent()!;
|
||||||
Elem *elem = ctx.get_elem(id)!;
|
Elem *elem = ctx.get_elem(id, ETYPE_SLIDER)!;
|
||||||
// add it to the tree
|
|
||||||
ctx.tree.add(id, ctx.active_div)!;
|
|
||||||
|
|
||||||
// 1. Fill the element fields
|
|
||||||
if (elem.flags.is_new) {
|
|
||||||
elem.type = ETYPE_SLIDER;
|
|
||||||
} else if (elem.type != ETYPE_SLIDER) {
|
|
||||||
return WRONG_ELEMENT_TYPE?;
|
|
||||||
}
|
|
||||||
|
|
||||||
// 2. Layout
|
// 2. Layout
|
||||||
elem.bounds = ctx.position_element(parent, size, true);
|
elem.bounds = ctx.position_element(parent, size, true);
|
||||||
@ -106,9 +97,7 @@ fn ElemEvents? Ctx.slider_ver_id(&ctx,
|
|||||||
id = ctx.gen_id(id)!;
|
id = ctx.gen_id(id)!;
|
||||||
|
|
||||||
Elem *parent = ctx.get_parent()!;
|
Elem *parent = ctx.get_parent()!;
|
||||||
Elem *elem = ctx.get_elem(id)!;
|
Elem *elem = ctx.get_elem(id, ETYPE_SLIDER)!;
|
||||||
// add it to the tree
|
|
||||||
ctx.tree.add(id, ctx.active_div)!;
|
|
||||||
|
|
||||||
// 1. Fill the element fields
|
// 1. Fill the element fields
|
||||||
if (elem.flags.is_new) {
|
if (elem.flags.is_new) {
|
||||||
|
@ -111,22 +111,14 @@ fn void? Ctx.import_sprite_file_qoi(&ctx, String name, String path, SpriteType t
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
macro Ctx.draw_sprite(&ctx, String name, Point off = {0,0}, ...)
|
macro Ctx.sprite(&ctx, String name, Point off = {0,0}, ...)
|
||||||
=> ctx.draw_sprite_id(@compute_id($vasplat), name, off);
|
=> ctx.sprite_id(@compute_id($vasplat), name, off);
|
||||||
fn void? Ctx.draw_sprite_id(&ctx, Id id, String name, Point off)
|
fn void? Ctx.sprite_id(&ctx, Id id, String name, Point off)
|
||||||
{
|
{
|
||||||
id = ctx.gen_id(id)!;
|
id = ctx.gen_id(id)!;
|
||||||
|
|
||||||
Elem *parent = ctx.get_parent()!;
|
Elem *parent = ctx.get_parent()!;
|
||||||
Elem *elem = ctx.get_elem(id)!;
|
Elem *elem = ctx.get_elem(id, ETYPE_SPRITE)!;
|
||||||
// add it to the tree
|
|
||||||
ctx.tree.add(id, ctx.active_div)!;
|
|
||||||
|
|
||||||
if (elem.flags.is_new) {
|
|
||||||
elem.type = ETYPE_SPRITE;
|
|
||||||
} else if (elem.type != ETYPE_SPRITE) {
|
|
||||||
return WRONG_ELEMENT_TYPE?;
|
|
||||||
}
|
|
||||||
|
|
||||||
Sprite* sprite = ctx.sprite_atlas.get(name)!;
|
Sprite* sprite = ctx.sprite_atlas.get(name)!;
|
||||||
|
|
||||||
|
@ -14,13 +14,8 @@ fn void? Ctx.text_unbounded_id(&ctx, Id id, String text)
|
|||||||
id = ctx.gen_id(id)!;
|
id = ctx.gen_id(id)!;
|
||||||
|
|
||||||
Elem *parent = ctx.get_parent()!;
|
Elem *parent = ctx.get_parent()!;
|
||||||
Elem *elem = ctx.get_elem(id)!;
|
Elem *elem = ctx.get_elem(id, ETYPE_TEXT)!;
|
||||||
// add it to the tree
|
|
||||||
ctx.tree.add(id, ctx.active_div)!;
|
|
||||||
|
|
||||||
// 1. Fill the element fields
|
|
||||||
// this resets the flags
|
|
||||||
elem.type = ETYPE_TEXT;
|
|
||||||
elem.text.str = text;
|
elem.text.str = text;
|
||||||
|
|
||||||
// if the element is new or the parent was updated then redo layout
|
// if the element is new or the parent was updated then redo layout
|
||||||
@ -39,13 +34,8 @@ fn ElemEvents? Ctx.text_box_id(&ctx, Id id, Rect size, char[] text, usz* text_le
|
|||||||
id = ctx.gen_id(id)!;
|
id = ctx.gen_id(id)!;
|
||||||
|
|
||||||
Elem *parent = ctx.get_parent()!;
|
Elem *parent = ctx.get_parent()!;
|
||||||
Elem *elem = ctx.get_elem(id)!;
|
Elem *elem = ctx.get_elem(id, ETYPE_TEXT)!;
|
||||||
// add it to the tree
|
|
||||||
ctx.tree.add(id, ctx.active_div)!;
|
|
||||||
|
|
||||||
// 1. Fill the element fields
|
|
||||||
// this resets the flags
|
|
||||||
elem.type = ETYPE_TEXT;
|
|
||||||
elem.text.str = text;
|
elem.text.str = text;
|
||||||
|
|
||||||
// layout the text box
|
// layout the text box
|
||||||
|
@ -231,7 +231,7 @@ fn int main(String[] args)
|
|||||||
ui.checkbox("", {}, &check)!!;
|
ui.checkbox("", {}, &check)!!;
|
||||||
ui.toggle("", {}, &toggle)!!;
|
ui.toggle("", {}, &toggle)!!;
|
||||||
};
|
};
|
||||||
ui.draw_sprite("tux")!!;
|
ui.sprite("tux")!!;
|
||||||
|
|
||||||
static char[128] text_box = "ciao mamma";
|
static char[128] text_box = "ciao mamma";
|
||||||
static usz text_len = "ciao mamma".len;
|
static usz text_len = "ciao mamma".len;
|
||||||
|
Loading…
Reference in New Issue
Block a user