aboutsummaryrefslogtreecommitdiffstats
path: root/src/ui/base.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/ui/base.c')
-rw-r--r--src/ui/base.c90
1 files changed, 78 insertions, 12 deletions
diff --git a/src/ui/base.c b/src/ui/base.c
index dd454ec..0db31b3 100644
--- a/src/ui/base.c
+++ b/src/ui/base.c
@@ -47,6 +47,7 @@ void ui__init_window_base(struct ui_window_base *base)
base->draw_proc = &ui__default_draw_proc;
base->layout_proc = NULL;
+ base->control_proc = NULL;
}
void ui__init_window_leaf(struct ui_window_leaf *leaf)
@@ -65,6 +66,7 @@ void ui__init_window_dock(struct ui_window_dock *dock)
dock->super.type = UI__WINDOW_TYPE_DOCK;
dock->super.draw_proc = &ui__dock_default_draw_proc;
dock->super.layout_proc = &ui__dock_default_layout_proc;
+ dock->super.control_proc = &ui__dock_default_control_proc;
for (unsigned i = 0; i < UI__WINDOW_DOCK_MAX; ++i)
{
@@ -81,14 +83,19 @@ void ui__init_window_root(struct ui_window_root *root, WINDOW *cwindow)
root->super.type = UI__WINDOW_TYPE_ROOT;
root->super.draw_proc = &ui__root_draw_proc;
root->super.layout_proc = &ui__root_layout_proc;
+ root->super.control_proc = &ui__root_control_proc;
root->cwindow = cwindow;
getmaxyx(cwindow, root->super.dims.maxy, root->super.dims.maxx);
getbegyx(cwindow, root->super.dims.begy, root->super.dims.begx);
+ root->menu_cwindow = newwin(1, root->super.dims.maxx, 0, 0);
+ root->menu_selected = NULL;
+
root->undersize_scr = false;
root->content = NULL;
root->floating = NULL;
+ root->modal = NULL;
root->menu_root = malloc(sizeof(struct uimenu_item_menu));
uimenu_item_menu_init(root->menu_root, NULL);
@@ -207,6 +214,55 @@ childfound:
}
}
+WINDOW *ui__find_focused_leaf(struct ui_window_base *start)
+{
+ switch (start->type) {
+ case UI__WINDOW_TYPE_LEAF:
+ return ui__cast(leaf, start)->cwindow;
+ case UI__WINDOW_TYPE_DOCK: {
+ struct ui_window_dock *dock = ui__cast(dock, start);
+
+ for (unsigned i = 0; i < UI__WINDOW_DOCK_MAX; ++i) {
+ if (dock->children[i]) {
+ WINDOW *focus = ui__find_focused_leaf(dock->children[i]);
+ if (focus) return focus;
+ }
+ }
+
+ return NULL;
+ }
+ case UI__WINDOW_TYPE_ROOT: {
+ struct ui_window_root *root = ui__cast(root, start);
+ WINDOW *focus;
+
+ if (root->undersize_scr)
+ return root->cwindow; /* gobble up focus if the screen is undersize */
+
+ if (root->modal) {
+ focus = ui__find_focused_leaf(root->modal);
+ if (focus) return focus;
+ }
+
+ if (root->floating) {
+ focus = ui__find_focused_leaf(root->modal);
+ if (focus) return focus;
+ }
+
+ if (root->menu_selected) {
+ return root->menu_cwindow;
+ }
+
+ if (root->content) {
+ return ui__find_focused_leaf(root->content);
+ }
+
+ return NULL;
+ }
+ default:
+ umps_trap;
+ }
+}
+
void ui__call_draw_proc(struct ui_window_base *base)
{
if (base->draw_proc)
@@ -223,6 +279,16 @@ void ui__call_layout_proc(struct ui_window_base *base)
}
}
+struct ui_window_base *ui__call_control_proc(struct ui_window_base *base, ui_control inp)
+{
+ if (base->control_proc)
+ {
+ return (*base->control_proc)(base, inp);
+ }
+
+ return NULL;
+}
+
void ui_init(void)
{
ui_root = malloc(sizeof(struct ui_window_root)); /* TODO: check */
@@ -267,17 +333,18 @@ void ui_handle(void)
{
while (true)
{
- struct ui_window_base *window = ui__find_focused();
+ WINDOW *cwindow = ui__find_focused_leaf(ui__cast(base, ui_root));
+
+ ui_control inp;
#ifdef NCURSES_WIDE
- wint_t inp;
- /* FIXME: find a better way of circumnavigating this annoying implied-wrefresh business */
- wget_wch(ui__cast(leaf, window)->cwindow, &inp);
+ keypad(cwindow, TRUE);
+ wget_wch(cwindow, &inp);
#else
- int inp = wgetch(window->cwindow);
+ inp = wgetch(window->cwindow);
#endif
- if (inp == NS('q'))
+ if (inp == NS('q')) /* TODO: make quitting flag in ui_root */
{
break;
}
@@ -287,12 +354,11 @@ void ui_handle(void)
getbegyx(ui_root->cwindow, ui_root->super.dims.begy, ui_root->super.dims.begx);
ui__call_layout_proc(ui__cast(base, ui_root));
ui__call_draw_proc(ui__cast(base, ui_root));
- } else if (inp == NS('h')) {
- ui__status_text = "Hello...";
- ui__call_draw_proc(ui__cast(base, ui_root));
- } else if (inp == NS('w')) {
- ui__status_text = "World\u0416!";
- ui__call_draw_proc(ui__cast(base, ui_root));
+ }
+
+ struct ui_window_base *target = ui__cast(base, ui_root);
+ while (target) {
+ target = ui__call_control_proc(target, inp);
}
}