From 615c8c5f64e2dd3de75444027665c08bbc6b73dc Mon Sep 17 00:00:00 2001 From: vurtun Date: Wed, 13 May 2015 14:47:11 +0200 Subject: [PATCH] added option group + demo clean up --- demo/demo.c | 440 +++++++++++++++++++++++++++----------------------- demo/opengl.c | 26 +-- demo/win32.c | 25 +-- demo/xlib.c | 29 ++-- gui.c | 14 ++ gui.h | 7 + 6 files changed, 287 insertions(+), 254 deletions(-) diff --git a/demo/demo.c b/demo/demo.c index 42d0875..ae94f0b 100644 --- a/demo/demo.c +++ b/demo/demo.c @@ -3,227 +3,247 @@ struct show_window { struct gui_panel_hook hook; - - /* widget data */ - gui_char in_buf[MAX_BUFFER]; - gui_size in_len; - gui_bool in_act; - gui_char cmd_buf[MAX_BUFFER]; - gui_size cmd_len; - gui_bool cmd_act; - gui_bool check; + /* input buffer */ + gui_char input_buffer[MAX_BUFFER]; + gui_size input_length; + gui_bool input_active; + /* command buffer */ + gui_char command_buffer[MAX_BUFFER]; + gui_size command_length; + gui_bool command_active; + /* widgets state */ + gui_bool checkbox; gui_float slider; - gui_size prog; + gui_size progressbar; gui_int spinner; - gui_bool spin_act; - gui_size item_cur; - gui_size cur; - gui_int combo_sel; + gui_bool spinner_active; + gui_size item_current; + gui_size shelf_selection; + gui_int combo_selection; gui_bool toggle; gui_int option; - /* tabs */ - gui_bool diff_min; - gui_bool wid_min; - gui_bool tbl_min; - + gui_bool combobox_tab; + gui_bool widget_tab; + gui_bool table_tab; /* scrollbars */ - gui_float shelf_off; - gui_float tbl_off; + gui_float shelf_scrollbar; + gui_float table_scrollbar; }; struct control_window { struct gui_panel_hook hook; gui_flags show_flags; - /* tabs */ - gui_bool flag_min; - gui_bool style_min; - gui_bool color_min; - + gui_bool flag_tab; + gui_bool style_tab; + gui_bool color_tab; /* color picker */ - gui_bool picker_act; - gui_bool col_r_act; - gui_bool col_g_act; - gui_bool col_b_act; - gui_bool col_a_act; - gui_size current; + gui_bool picker_active; + gui_bool spinner_r_active; + gui_bool spinner_g_active; + gui_bool spinner_b_active; + gui_bool spinner_a_active; + gui_size current_color; struct gui_color color; }; -static void -table_panel(struct gui_panel_layout *panel, struct show_window *demo) -{ +struct demo_gui { + struct show_window show; + struct control_window control; + struct gui_memory memory; + struct gui_command_buffer buffer; + struct gui_panel_stack stack; struct gui_panel_layout tab; - static const struct gui_color header = {178, 122, 1, 255}; - gui_panel_row(panel, 250, 1); - gui_panel_group_begin(panel, &tab, "Table", demo->tbl_off); - gui_panel_table_begin(&tab, GUI_TABLE_HHEADER, 30, 2); - gui_panel_label_colored(&tab, "MOVEMENT", GUI_TEXT_CENTERED, header); - gui_panel_label_colored(&tab, "KEY/BUTTON", GUI_TEXT_CENTERED, header); - gui_panel_table_row(&tab); - gui_panel_label(&tab, "Move foward", GUI_TEXT_LEFT); - gui_panel_label(&tab, "w", GUI_TEXT_CENTERED); - gui_panel_table_row(&tab); - gui_panel_label(&tab, "Move back", GUI_TEXT_LEFT); - gui_panel_label(&tab, "s", GUI_TEXT_CENTERED); - gui_panel_table_row(&tab); - gui_panel_label(&tab, "Move left", GUI_TEXT_LEFT); - gui_panel_label(&tab, "a", GUI_TEXT_CENTERED); - gui_panel_table_row(&tab); - gui_panel_label(&tab, "Move right", GUI_TEXT_LEFT); - gui_panel_label(&tab, "d", GUI_TEXT_CENTERED); - gui_panel_table_row(&tab); - gui_panel_label(&tab, "Jump", GUI_TEXT_LEFT); - gui_panel_label(&tab, "SPACE", GUI_TEXT_CENTERED); - gui_panel_table_row(&tab); - gui_panel_label(&tab, "Duck", GUI_TEXT_LEFT); - gui_panel_label(&tab, "CTRL", GUI_TEXT_CENTERED); - gui_panel_table_end(&tab); - demo->tbl_off = gui_panel_group_end(panel, &tab); -} - -static void -graph_panel(struct gui_panel_layout *panel, struct show_window *demo) -{ - enum {HISTO, PLOT}; - struct gui_panel_layout tab; - static const char *shelfs[] = {"Histogram", "Lines"}; - static const gui_float values[] = {8.0f,15.0f,20.0f,12.0f,30.0f,12.0f,35.0f,40.0f,20.0f}; - gui_panel_row(panel, 180, 1); - demo->cur = gui_panel_shelf_begin(panel,&tab,shelfs,LEN(shelfs),demo->cur,demo->shelf_off); - gui_panel_row(&tab, 100, 1); - if (demo->cur == HISTO) { - gui_panel_graph(&tab, GUI_GRAPH_HISTO, values, LEN(values)); - } else { - gui_panel_graph(&tab, GUI_GRAPH_LINES, values, LEN(values)); - } - demo->shelf_off = gui_panel_shelf_end(panel, &tab); -} + struct gui_config config; + struct gui_font font; + gui_size width, height; +}; static void combobox_panel(struct gui_panel_layout *panel, struct show_window *demo) { gui_int i = 0; static const char *options[] = {"easy", "normal", "hard", "hell", "doom", "godlike"}; - struct gui_panel_layout tab; - demo->diff_min = gui_panel_tab_begin(panel, &tab, "Comobox", demo->diff_min); - gui_panel_row(&tab, 30, 3); + gui_panel_row(panel, 30, 3); for (i = 0; i < (gui_int)LEN(options); i++) { - if (gui_panel_option(&tab, options[i], demo->combo_sel == i)) - demo->combo_sel = i; + if (gui_panel_option(panel, options[i], demo->combo_selection == i)) + demo->combo_selection = i; } - gui_panel_tab_end(panel, &tab); } static void widget_panel(struct gui_panel_layout *panel, struct show_window *demo) { - struct gui_panel_layout tab; char buffer[MAX_BUFFER]; const char *items[] = {"Fist", "Pistol", "Shotgun", "Railgun", "BFG"}; - demo->wid_min = gui_panel_tab_begin(panel, &tab, "Widgets", demo->wid_min); - gui_panel_row(&tab, 30, 1); - gui_panel_label(&tab, "text left", GUI_TEXT_LEFT); - gui_panel_label(&tab, "text center", GUI_TEXT_CENTERED); - gui_panel_label(&tab, "text right", GUI_TEXT_RIGHT); - if (gui_panel_button_text(&tab, "button", GUI_BUTTON_DEFAULT)) + gui_panel_row(panel, 30, 1); + gui_panel_label(panel, "text left", GUI_TEXT_LEFT); + gui_panel_label(panel, "text center", GUI_TEXT_CENTERED); + gui_panel_label(panel, "text right", GUI_TEXT_RIGHT); + if (gui_panel_button_text(panel, "button", GUI_BUTTON_DEFAULT)) fprintf(stdout, "button pressed!\n"); - demo->toggle = gui_panel_button_toggle(&tab, "toggle", demo->toggle); - demo->check = gui_panel_check(&tab, "checkbox", demo->check); + demo->toggle = gui_panel_button_toggle(panel, "toggle", demo->toggle); + demo->checkbox = gui_panel_check(panel, "checkbox", demo->checkbox); - gui_panel_row(&tab, 30, 2); - if (gui_panel_option(&tab, "option 0", demo->option == 0)) demo->option = 0; - if (gui_panel_option(&tab, "option 1", demo->option == 1)) demo->option = 1; - demo->slider = gui_panel_slider(&tab, 0, demo->slider, 10, 1.0f); + gui_panel_row(panel, 30, 2); + if (gui_panel_option(panel, "option 0", demo->option == 0)) demo->option = 0; + if (gui_panel_option(panel, "option 1", demo->option == 1)) demo->option = 1; + demo->slider = gui_panel_slider(panel, 0, demo->slider, 10, 1.0f); sprintf(buffer, "%.2f", demo->slider); - gui_panel_label(&tab, buffer, GUI_TEXT_LEFT); - demo->prog = gui_panel_progress(&tab, demo->prog, 100, gui_true); - sprintf(buffer, "%lu", demo->prog); - gui_panel_label(&tab, buffer, GUI_TEXT_LEFT); + gui_panel_label(panel, buffer, GUI_TEXT_LEFT); + demo->progressbar = gui_panel_progress(panel, demo->progressbar, 100, gui_true); + sprintf(buffer, "%lu", demo->progressbar); + gui_panel_label(panel, buffer, GUI_TEXT_LEFT); - gui_panel_row(&tab, 30, 1); - demo->item_cur = gui_panel_selector(&tab, items, LEN(items), demo->item_cur); - demo->spinner = gui_panel_spinner(&tab, 0, demo->spinner, 250, 10, &demo->spin_act); - if (gui_panel_shell(&tab, demo->cmd_buf, &demo->cmd_len, MAX_BUFFER, &demo->cmd_act)) - demo->cmd_len = 0; - demo->in_len = gui_panel_edit(&tab, demo->in_buf, demo->in_len, - MAX_BUFFER, &demo->in_act, GUI_INPUT_DEFAULT); - gui_panel_tab_end(panel, &tab); + gui_panel_row(panel, 30, 1); + demo->item_current = gui_panel_selector(panel, items, LEN(items), demo->item_current); + demo->spinner = gui_panel_spinner(panel, 0, demo->spinner, 250, 10, &demo->spinner_active); + if (gui_panel_shell(panel, demo->command_buffer, &demo->command_length, MAX_BUFFER, &demo->command_active)) + demo->command_length = 0; + demo->input_length = gui_panel_edit(panel, demo->input_buffer, demo->input_length, + MAX_BUFFER, &demo->input_active, GUI_INPUT_DEFAULT); } static void -show_panel(struct show_window *show, struct gui_panel_stack *stack, +graph_panel(struct gui_panel_layout *panel, gui_size current) +{ + enum {HISTO, PLOT}; + static const gui_float values[] = {8.0f,15.0f,20.0f,12.0f,30.0f,12.0f,35.0f,40.0f,20.0f}; + gui_panel_row(panel, 100, 1); + if (current == HISTO) { + gui_panel_graph(panel, GUI_GRAPH_HISTO, values, LEN(values)); + } else { + gui_panel_graph(panel, GUI_GRAPH_LINES, values, LEN(values)); + } +} + +static void +table_panel(struct gui_panel_layout *panel) +{ + static const struct gui_color header = {178, 122, 1, 255}; + gui_panel_table_begin(panel, GUI_TABLE_HHEADER, 30, 2); + gui_panel_label_colored(panel, "MOVEMENT", GUI_TEXT_CENTERED, header); + gui_panel_label_colored(panel, "KEY/BUTTON", GUI_TEXT_CENTERED, header); + gui_panel_table_row(panel); + gui_panel_label(panel, "Move foward", GUI_TEXT_LEFT); + gui_panel_label(panel, "w", GUI_TEXT_CENTERED); + gui_panel_table_row(panel); + gui_panel_label(panel, "Move back", GUI_TEXT_LEFT); + gui_panel_label(panel, "s", GUI_TEXT_CENTERED); + gui_panel_table_row(panel); + gui_panel_label(panel, "Move left", GUI_TEXT_LEFT); + gui_panel_label(panel, "a", GUI_TEXT_CENTERED); + gui_panel_table_row(panel); + gui_panel_label(panel, "Move right", GUI_TEXT_LEFT); + gui_panel_label(panel, "d", GUI_TEXT_CENTERED); + gui_panel_table_row(panel); + gui_panel_label(panel, "Jump", GUI_TEXT_LEFT); + gui_panel_label(panel, "SPACE", GUI_TEXT_CENTERED); + gui_panel_table_row(panel); + gui_panel_label(panel, "Duck", GUI_TEXT_LEFT); + gui_panel_label(panel, "CTRL", GUI_TEXT_CENTERED); + gui_panel_table_end(panel); +} + +static void +init_show(struct show_window *win, struct gui_config *config, struct gui_font *font, + struct gui_panel_stack *stack) +{ + gui_panel_hook_init(&win->hook, 50, 50, 300, 500, + GUI_PANEL_BORDER|GUI_PANEL_MOVEABLE| + GUI_PANEL_CLOSEABLE|GUI_PANEL_SCALEABLE| + GUI_PANEL_MINIMIZABLE, config, font); + gui_stack_push(stack, &win->hook); + + win->widget_tab = GUI_MINIMIZED; + win->combobox_tab = GUI_MINIMIZED; + win->slider = 5.0f; + win->progressbar = 50; + win->spinner = 100; +} + +static void +update_show(struct show_window *show, struct gui_panel_stack *stack, struct gui_input *in, struct gui_canvas *canvas) { struct gui_panel_layout layout; + struct gui_panel_layout tab; + static const char *shelfs[] = {"Histogram", "Lines"}; gui_panel_hook_begin(&layout, &show->hook, stack, "Show", canvas, in); - combobox_panel(&layout, show); - widget_panel(&layout, show); - graph_panel(&layout, show); - table_panel(&layout, show); + + show->combobox_tab = gui_panel_tab_begin(&layout, &tab, "Combobox", show->combobox_tab); + combobox_panel(&tab, show); + gui_panel_tab_end(&layout, &tab); + + show->widget_tab = gui_panel_tab_begin(&layout, &tab, "Widgets", show->widget_tab); + widget_panel(&tab, show); + gui_panel_tab_end(&layout, &tab); + + gui_panel_row(&layout, 180, 1); + show->shelf_selection = gui_panel_shelf_begin(&layout, &tab, shelfs, + LEN(shelfs), show->shelf_selection, show->shelf_scrollbar); + graph_panel(&tab, show->shelf_selection); + show->shelf_scrollbar = gui_panel_shelf_end(&layout, &tab); + + gui_panel_row(&layout, 180, 1); + gui_panel_group_begin(&layout, &tab, "Table", show->table_scrollbar); + table_panel(&tab); + show->table_scrollbar = gui_panel_group_end(&layout, &tab); + gui_panel_hook_end(&layout, &show->hook); } static void -flags_tab(struct gui_panel_layout *panel, struct control_window *control) +update_flags(struct gui_panel_layout *panel, struct control_window *control) { gui_flags i = 0x01; gui_size n = 0; gui_flags res = 0; - struct gui_panel_layout tab; - - const char *options[] = {"Hidden", "Border", "Minimizable", - "Closeable", "Moveable", "Scaleable"}; - control->flag_min = gui_panel_tab_begin(panel, &tab, "Options", control->flag_min); - gui_panel_row(&tab, 30, 2); + const char *options[] = {"Hidden", "Border", "Minimizable", "Closeable", "Moveable", "Scaleable"}; + gui_panel_row(panel, 30, 2); do { - if (gui_panel_check(&tab, options[n++], (control->show_flags & i) ? gui_true : gui_false)) + if (gui_panel_check(panel, options[n++], (control->show_flags & i) ? gui_true : gui_false)) res |= i; i = i << 1; } while (i <= GUI_PANEL_SCALEABLE); control->show_flags = res; - gui_panel_tab_end(panel, &tab); } static void -style_tab(struct gui_panel_layout *panel, struct control_window *control, struct gui_config *config) +style_tab(struct gui_panel_layout *panel, struct gui_config *config) { gui_int tx, ty; - struct gui_panel_layout tab; - control->style_min = gui_panel_tab_begin(panel, &tab, "Style", control->style_min); - gui_panel_row(&tab, 30, 2); - gui_panel_label(&tab, "scrollbar width:", GUI_TEXT_LEFT); - tx = gui_panel_spinner(&tab, 0, (gui_int)config->scrollbar_width, 20, 1, NULL); + gui_panel_label(panel, "scrollbar width:", GUI_TEXT_LEFT); + tx = gui_panel_spinner(panel, 0, (gui_int)config->scrollbar_width, 20, 1, NULL); config->scrollbar_width = (float)tx; - gui_panel_row(&tab, 30, 3); - gui_panel_label(&tab, "padding:", GUI_TEXT_LEFT); - tx = gui_panel_spinner(&tab, 0, (gui_int)config->panel_padding.x, 20, 1, NULL); - ty = gui_panel_spinner(&tab, 0, (gui_int)config->panel_padding.y, 20, 1, NULL); + gui_panel_row(panel, 30, 3); + gui_panel_label(panel, "padding:", GUI_TEXT_LEFT); + tx = gui_panel_spinner(panel, 0, (gui_int)config->panel_padding.x, 20, 1, NULL); + ty = gui_panel_spinner(panel, 0, (gui_int)config->panel_padding.y, 20, 1, NULL); config->panel_padding.x = (float)tx; config->panel_padding.y = (float)ty; - gui_panel_label(&tab, "item spacing:", GUI_TEXT_LEFT); - tx = gui_panel_spinner(&tab, 0, (gui_int)config->item_spacing.x, 20, 1, NULL); - ty = gui_panel_spinner(&tab, 0, (gui_int)config->item_spacing.y, 20, 1, NULL); + gui_panel_label(panel, "item spacing:", GUI_TEXT_LEFT); + tx = gui_panel_spinner(panel, 0, (gui_int)config->item_spacing.x, 20, 1, NULL); + ty = gui_panel_spinner(panel, 0, (gui_int)config->item_spacing.y, 20, 1, NULL); config->item_spacing.x = (float)tx; config->item_spacing.y = (float)ty; - gui_panel_label(&tab, "item padding:", GUI_TEXT_LEFT); - tx = gui_panel_spinner(&tab, 0, (gui_int)config->item_padding.x, 20, 1, NULL); - ty = gui_panel_spinner(&tab, 0, (gui_int)config->item_padding.y, 20, 1, NULL); + gui_panel_label(panel, "item padding:", GUI_TEXT_LEFT); + tx = gui_panel_spinner(panel, 0, (gui_int)config->item_padding.x, 20, 1, NULL); + ty = gui_panel_spinner(panel, 0, (gui_int)config->item_padding.y, 20, 1, NULL); config->item_padding.x = (float)tx; config->item_padding.y = (float)ty; - gui_panel_label(&tab, "scaler size:", GUI_TEXT_LEFT); - tx = gui_panel_spinner(&tab, 0, (gui_int)config->scaler_size.x, 20, 1, NULL); - ty = gui_panel_spinner(&tab, 0, (gui_int)config->scaler_size.y, 20, 1, NULL); + gui_panel_label(panel, "scaler size:", GUI_TEXT_LEFT); + tx = gui_panel_spinner(panel, 0, (gui_int)config->scaler_size.x, 20, 1, NULL); + ty = gui_panel_spinner(panel, 0, (gui_int)config->scaler_size.y, 20, 1, NULL); config->scaler_size.x = (float)tx; config->scaler_size.y = (float)ty; - gui_panel_tab_end(panel, &tab); } static struct gui_color @@ -236,18 +256,22 @@ color_picker(struct gui_panel_layout *panel, struct control_window *control, gui_panel_button_color(panel, color, GUI_BUTTON_DEFAULT); gui_panel_row(panel, 30, 2); r = color.r; g = color.g; b = color.b; a = color.a; + r = gui_panel_slider(panel, 0, r, 255, 10); color.r = (gui_byte)r; - color.r = (gui_byte)gui_panel_spinner(panel, 0, color.r, 255, 1, &control->col_r_act); + color.r = (gui_byte)gui_panel_spinner(panel, 0, color.r, 255, 1, &control->spinner_r_active); + g = gui_panel_slider(panel, 0, g, 255, 10); color.g = (gui_byte)g; - color.g = (gui_byte)gui_panel_spinner(panel, 0, color.g, 255, 1, &control->col_g_act); + color.g = (gui_byte)gui_panel_spinner(panel, 0, color.g, 255, 1, &control->spinner_g_active); + b = gui_panel_slider(panel, 0, b, 255, 10); color.b = (gui_byte)b; - color.b = (gui_byte)gui_panel_spinner(panel, 0, (gui_int)color.b, 255, 1, &control->col_b_act); + color.b = (gui_byte)gui_panel_spinner(panel, 0, (gui_int)color.b, 255, 1, &control->spinner_b_active); + a = gui_panel_slider(panel, 0, a, 255, 10); color.a = (gui_byte)a; - color.a = (gui_byte)gui_panel_spinner(panel, 0, (gui_int)color.a, 255, 1, &control->col_a_act); + color.a = (gui_byte)gui_panel_spinner(panel, 0, (gui_int)color.a, 255, 1, &control->spinner_a_active); return color; } @@ -255,7 +279,6 @@ static void color_tab(struct gui_panel_layout *panel, struct control_window *control, struct gui_config *config) { gui_size i = 0; - struct gui_panel_layout tab; static const char *labels[] = {"Text:", "Panel:", "Header:", "Border:", "Button:", "Button Border:", "Button Hovering:", "Button Toggle:", "Button Hovering Text:", "Check:", "Check BG:", "Check Active:", "Option:", "Option BG:", "Option Active:", @@ -265,94 +288,113 @@ color_tab(struct gui_panel_layout *panel, struct control_window *control, struct "Plot Hightlight:", "Scrollbar:", "Scrollbar Cursor:", "Scrollbar Border:", "Table lines:", "Scaler:" }; - control->color_min = gui_panel_tab_begin(panel, &tab, "Color", control->color_min); - if (control->picker_act) { - control->color = color_picker(&tab, control, labels[control->current], control->color); - gui_panel_row(&tab, 30, 3); - gui_panel_seperator(&tab, 1); - if (gui_panel_button_text(&tab, "ok", GUI_BUTTON_DEFAULT)) { - config->colors[control->current] = control->color; - control->picker_act = gui_false; + if (control->picker_active) { + control->color = color_picker(panel, control, labels[control->current_color], control->color); + gui_panel_row(panel, 30, 3); + gui_panel_seperator(panel, 1); + if (gui_panel_button_text(panel, "ok", GUI_BUTTON_DEFAULT)) { + config->colors[control->current_color] = control->color; + control->picker_active = gui_false; } - if (gui_panel_button_text(&tab, "cancel", GUI_BUTTON_DEFAULT)) - control->picker_act = gui_false; + if (gui_panel_button_text(panel, "cancel", GUI_BUTTON_DEFAULT)) + control->picker_active = gui_false; } else { - gui_panel_row(&tab, 30, 2); + gui_panel_row(panel, 30, 2); for (i = 0; i < GUI_COLOR_COUNT; ++i) { struct gui_panel_layout layout; - gui_panel_label(&tab, labels[i], GUI_TEXT_LEFT); - if (gui_panel_button_color(&tab, config->colors[i], GUI_BUTTON_DEFAULT)) { - if (!control->picker_act) { - control->picker_act = gui_true; + gui_panel_label(panel, labels[i], GUI_TEXT_LEFT); + if (gui_panel_button_color(panel, config->colors[i], GUI_BUTTON_DEFAULT)) { + if (!control->picker_active) { + control->picker_active = gui_true; control->color = config->colors[i]; - control->current = i; + control->current_color = i; } else continue; } } } - gui_panel_tab_end(panel, &tab); +} + +static void +init_control(struct control_window *win, struct gui_config *config, struct gui_font *font, + struct gui_panel_stack *stack) +{ + gui_panel_hook_init(&win->hook, 380, 50, 400, 350, + GUI_PANEL_BORDER|GUI_PANEL_MOVEABLE|GUI_PANEL_CLOSEABLE|GUI_PANEL_SCALEABLE, config, font); + gui_stack_push(stack, &win->hook); + win->show_flags = gui_hook_panel(&win->hook)->flags; + win->style_tab = GUI_MINIMIZED; + win->color_tab = GUI_MINIMIZED; } static gui_bool -control_panel(struct control_window *control, struct gui_panel_stack *stack, +update_control(struct control_window *control, struct gui_panel_stack *stack, struct gui_input *in, struct gui_canvas *canvas, struct gui_config *config) { gui_bool running; struct gui_panel_layout layout; + struct gui_panel_layout tab; + running = gui_panel_hook_begin(&layout, &control->hook, stack, "Control", canvas, in); - flags_tab(&layout, control); - style_tab(&layout, control, config); - color_tab(&layout, control, config); + control->flag_tab = gui_panel_tab_begin(&layout, &tab, "Options", control->flag_tab); + update_flags(&tab, control); + gui_panel_tab_end(&layout, &tab); + + control->style_tab = gui_panel_tab_begin(&layout, &tab, "Style", control->style_tab); + style_tab(&tab, config); + gui_panel_tab_end(&layout, &tab); + + control->color_tab = gui_panel_tab_begin(&layout, &tab, "Color", control->color_tab); + color_tab(&tab, control, config); + gui_panel_tab_end(&layout, &tab); + gui_panel_hook_end(&layout, &control->hook); return running; } static void -init_demo(struct show_window *show, struct control_window *control, - struct gui_panel_stack *stack, struct gui_config *config, struct gui_font *font) +init_demo(struct demo_gui *gui, struct gui_font *font) { - memset(show, 0, sizeof(*show)); - gui_panel_hook_init(&show->hook, 50, 50, 300, 500, - GUI_PANEL_BORDER|GUI_PANEL_MOVEABLE| - GUI_PANEL_CLOSEABLE|GUI_PANEL_SCALEABLE| - GUI_PANEL_MINIMIZABLE, config, font); - gui_stack_push(stack, &show->hook); + struct gui_command_buffer *buffer = &gui->buffer; + struct gui_memory *memory = &gui->memory; + struct gui_config *config = &gui->config; + struct gui_panel_stack *stack = &gui->stack; - show->wid_min = gui_true; - show->diff_min = gui_true; - show->slider = 5.0f; - show->prog = 50; - show->spinner = 100; + gui->font = *font; + memory->memory = calloc(MAX_MEMORY, 1); + memory->size = MAX_MEMORY; + gui_buffer_init_fixed(buffer, memory, GUI_BUFFER_CLIPPING); - memset(control, 0, sizeof(*control)); - gui_panel_hook_init(&control->hook, 380, 50, 400, 350, - GUI_PANEL_BORDER|GUI_PANEL_MOVEABLE|GUI_PANEL_CLOSEABLE|GUI_PANEL_SCALEABLE, config, font); - gui_stack_push(stack, &control->hook); - control->show_flags = gui_hook_panel(&show->hook)->flags; - control->style_min = gui_true; - control->color_min = gui_true; + gui_default_config(config); + gui_stack_clear(stack); + init_show(&gui->show, config, font, stack); + init_control(&gui->control, config, font, stack); } static gui_bool -run_demo(struct show_window *show, struct control_window *control, struct gui_panel_stack *stack, - struct gui_config *config, struct gui_input *in, struct gui_command_buffer *buffer, - gui_size width, gui_size height) +run_demo(struct demo_gui *gui, struct gui_input *input) { gui_bool running; + struct show_window *show = &gui->show; + struct control_window *control = &gui->control; + struct gui_command_buffer *buffer = &gui->buffer; struct gui_command_buffer sub; struct gui_canvas canvas; - gui_buffer_begin(NULL, buffer, width, height); - gui_buffer_lock(&canvas, buffer, &sub, 0, width, height); - running = control_panel(control, stack, in, &canvas, config); + gui_buffer_begin(NULL, buffer, gui->width, gui->height); + + /* Show window */ + gui_buffer_lock(&canvas, buffer, &sub, 0, gui->width, gui->height); + running = update_control(control, &gui->stack, input, &canvas, &gui->config); gui_buffer_unlock(gui_hook_output(&control->hook), buffer, &sub, &canvas, NULL); + /* control window */ gui_hook_panel(&show->hook)->flags = control->show_flags; - gui_buffer_lock(&canvas, buffer, &sub, 0, width, height); - show_panel(show, stack, in, &canvas); + gui_buffer_lock(&canvas, buffer, &sub, 0, gui->width, gui->height); + update_show(show, &gui->stack, input, &canvas); if (gui_hook_panel(&show->hook)->flags & GUI_PANEL_HIDDEN) control->show_flags |= GUI_PANEL_HIDDEN; gui_buffer_unlock(gui_hook_output(&show->hook), buffer, &sub, &canvas, NULL); + gui_buffer_end(NULL, buffer, NULL, NULL); return running; } diff --git a/demo/opengl.c b/demo/opengl.c index 52e914b..2c25854 100644 --- a/demo/opengl.c +++ b/demo/opengl.c @@ -551,17 +551,11 @@ main(int argc, char *argv[]) unsigned int started; unsigned int dt; int width = 0, height = 0; - struct demo demo; /* GUI */ struct gui_input in; struct gui_font font; - struct gui_memory memory; - struct gui_config config; - struct gui_command_buffer buffer; - struct gui_panel_stack stack; - struct show_window show; - struct control_window control; + struct demo_gui gui; font_path = argv[1]; if (argc < 2) { @@ -582,16 +576,11 @@ main(int argc, char *argv[]) /* GUI */ memset(&in, 0, sizeof in); - memory.memory = calloc(MAX_MEMORY, 1); - memory.size = MAX_MEMORY; - gui_buffer_init_fixed(&buffer, &memory, GUI_BUFFER_CLIPPING); - + memset(&gui, 0, sizeof gui); font.userdata = glfont; font.height = glfont->height; font.width = font_get_text_width; - gui_default_config(&config); - gui_stack_clear(&stack); - init_demo(&show, &control, &stack, &config, &font); + init_demo(&gui, &font); while (running) { /* Input */ @@ -612,13 +601,14 @@ main(int argc, char *argv[]) /* GUI */ SDL_GetWindowSize(win, &width, &height); - running = run_demo(&show, &control, &stack, &config, &in, &buffer, - (gui_size)width, (gui_size)height); + gui.width = (gui_size)width; + gui.height = (gui_size)height; + running = run_demo(&gui, &in); /* Draw */ glClearColor(0.4f, 0.4f, 0.4f, 1.0f); glClear(GL_COLOR_BUFFER_BIT); - draw(&stack, width, height); + draw(&gui.stack, width, height); SDL_GL_SwapWindow(win); /* Timing */ @@ -629,7 +619,7 @@ main(int argc, char *argv[]) cleanup: /* Cleanup */ - free(memory.memory); + free(gui.memory.memory); font_del(glfont); SDL_GL_DeleteContext(glContext); SDL_DestroyWindow(win); diff --git a/demo/win32.c b/demo/win32.c index b9ee0f5..41e6e35 100644 --- a/demo/win32.c +++ b/demo/win32.c @@ -415,12 +415,7 @@ WinMain(HINSTANCE hInstance, HINSTANCE prev, LPSTR lpCmdLine, int shown) /* GUI */ struct gui_input in; struct gui_font font; - struct gui_memory memory; - struct gui_config config; - struct gui_command_buffer buffer; - struct gui_panel_stack stack; - struct show_window show; - struct control_window control; + struct demo_gui gui; /* Window */ QueryPerformanceFrequency(&freq); @@ -445,16 +440,11 @@ WinMain(HINSTANCE hInstance, HINSTANCE prev, LPSTR lpCmdLine, int shown) /* GUI */ memset(&in, 0, sizeof in); - memory.memory = calloc(MAX_MEMORY, 1); - memory.size = MAX_MEMORY; - gui_buffer_init_fixed(&buffer, &memory, GUI_BUFFER_CLIPPING); - + memset(&gui, 0, sizeof gui); font.userdata = &xw; font.height = (gui_float)xw.font->height; font.width = font_get_text_width; - gui_default_config(&config); - gui_stack_clear(&stack); - init_demo(&show, &control, &stack, &config, &font); + init_demo(&gui, &font); while (running && !quit) { /* Input */ @@ -474,13 +464,14 @@ WinMain(HINSTANCE hInstance, HINSTANCE prev, LPSTR lpCmdLine, int shown) gui_input_end(&in); /* GUI */ - running = run_demo(&show, &control, &stack, &config, &in, &buffer, - xw.width, xw.height); + gui.width = xw.width; + gui.height = xw.height; + running = run_demo(&gui, &in); /* Draw */ surface_begin(xw.backbuffer); surface_clear(xw.backbuffer, 255, 255, 255); - draw(xw.backbuffer, &stack); + draw(xw.backbuffer, &gui.stack); surface_end(xw.backbuffer, xw.hdc); /* Timing */ @@ -488,7 +479,7 @@ WinMain(HINSTANCE hInstance, HINSTANCE prev, LPSTR lpCmdLine, int shown) if (dt < DTIME) Sleep(DTIME - dt); } - free(memory.memory); + free(gui.memory.memory); font_del(xw.font); surface_del(xw.backbuffer); ReleaseDC(xw.hWnd, xw.hdc); diff --git a/demo/xlib.c b/demo/xlib.c index d6f2eb1..ebd6854 100644 --- a/demo/xlib.c +++ b/demo/xlib.c @@ -407,23 +407,16 @@ resize(struct XWindow *xw, XSurface *surf) int main(int argc, char *argv[]) { - /* Platform */ long dt; long started; XWindow xw; gui_bool running = gui_true; - /* GUI */ struct gui_input in; struct gui_font font; - struct gui_memory memory; - struct gui_config config; - struct gui_command_buffer buffer; - struct gui_panel_stack stack; - struct show_window show; - struct control_window control; + struct demo_gui gui; - /* Window */ + /* Platform */ UNUSED(argc); UNUSED(argv); memset(&xw, 0, sizeof xw); xw.dpy = XOpenDisplay(NULL); @@ -448,16 +441,11 @@ main(int argc, char *argv[]) /* GUI */ memset(&in, 0, sizeof in); - memory.memory = calloc(MAX_MEMORY, 1); - memory.size = MAX_MEMORY; - gui_buffer_init_fixed(&buffer, &memory, GUI_BUFFER_CLIPPING); - + memset(&gui, 0, sizeof gui); font.userdata = xw.font; font.height = (gui_float)xw.font->height; font.width = font_get_text_width; - gui_default_config(&config); - gui_stack_clear(&stack); - init_demo(&show, &control, &stack, &config, &font); + init_demo(&gui, &font); while (running) { /* Input */ @@ -476,13 +464,14 @@ main(int argc, char *argv[]) gui_input_end(&in); /* GUI */ - running = run_demo(&show, &control, &stack, &config, &in, &buffer, - xw.width, xw.height); + gui.width = xw.width; + gui.height = xw.height; + running = run_demo(&gui, &in); /* Draw */ XClearWindow(xw.dpy, xw.win); surface_clear(xw.surf, 0x00646464); - draw(xw.surf, &stack); + draw(xw.surf, &gui.stack); surface_blit(xw.win, xw.surf, xw.width, xw.height); XFlush(xw.dpy); @@ -493,7 +482,7 @@ main(int argc, char *argv[]) } cleanup: - free(memory.memory); + free(gui.memory.memory); font_del(xw.dpy, xw.font); surface_del(xw.surf); XUnmapWindow(xw.dpy, xw.win); diff --git a/gui.c b/gui.c index 05d14eb..61a1b60 100644 --- a/gui.c +++ b/gui.c @@ -1880,6 +1880,20 @@ gui_panel_option(struct gui_panel_layout *layout, const char *text, gui_bool is_ is_active, text, GUI_TOGGLE_OPTION, &toggle, layout->input, &layout->font); } +gui_size +gui_panel_option_group(struct gui_panel_layout *layout, const char **options, + gui_size count, gui_size current) +{ + gui_size i; + ASSERT(layout && options && count); + if (!layout || !options || !count) return current; + for (i = 0; i < count; ++i) { + if (gui_panel_option(layout, options[i], i == current)) + current = i; + } + return current; +} + gui_float gui_panel_slider(struct gui_panel_layout *layout, gui_float min_value, gui_float value, gui_float max_value, gui_float value_step) diff --git a/gui.h b/gui.h index 269c9f5..f26fa15 100644 --- a/gui.h +++ b/gui.h @@ -393,6 +393,11 @@ struct gui_config { struct gui_color colors[GUI_COLOR_COUNT]; }; +enum gui_panel_tab { + GUI_MAXIMIZED = gui_false, + GUI_MINIMIZED = gui_true +}; + enum gui_panel_flags { GUI_PANEL_HIDDEN = 0x01, GUI_PANEL_BORDER = 0x02, @@ -450,6 +455,7 @@ struct gui_panel_stack { struct gui_panel_hook *end; }; + /* Input */ gui_size gui_utf_decode(const gui_char*, gui_long*, gui_size); gui_size gui_utf_encode(gui_long, gui_char*, gui_size); @@ -557,6 +563,7 @@ void gui_panel_label_colored(struct gui_panel_layout*, const char*, enum gui_tex struct gui_color color); gui_bool gui_panel_check(struct gui_panel_layout*, const char*, gui_bool active); gui_bool gui_panel_option(struct gui_panel_layout*, const char*, gui_bool active); +gui_size gui_panel_option_group(struct gui_panel_layout*, const char**, gui_size cnt, gui_size cur); gui_bool gui_panel_button_text(struct gui_panel_layout*, const char*, enum gui_button_behavior); gui_bool gui_panel_button_color(struct gui_panel_layout*, const struct gui_color, enum gui_button_behavior);