#include "base.h" const I32 LIST_TITLE_OFFSET = 15; const I32 LIST_ITEM_HEIGHT = 18; void gui_list_draw_fn( void* ptr ) { GUI_LIST* list = (GUI_LIST*)ptr; I32 x = gui_relx( list ); I32 y = gui_rely( list ); gui_draw_str( x, y, ALIGN_L, FNT_JPN12, ui_clr.txt, list->name ); I32 panel_y = y + LIST_TITLE_OFFSET; CLR col = gui_is_fg_window( list )? ui_clr.border : ui_clr.border_inactive; gui_draw_frect( x, panel_y, list->w, list->h, col ); gui_draw_frect( x + 1, panel_y + 1, list->w - 2, list->h - 2, ui_clr.bg_sec ); I32 txt_h = 12; gui_draw_get_str_bounds( 0, &txt_h, FNT_JPN12, "ag" ); I32 yoff = 0; list->plist->each( fn( GUI_LIST_ENTRY* e ) { U8 selected = e->val == *list->pval; I32 row_x = x + 1; I32 row_y = panel_y + 1 + yoff; I32 row_w = list->w - 2; if( row_w < 1 ) row_w = 1; I32 row_h = LIST_ITEM_HEIGHT; if( selected ) { CLR sel_bg = CLR::blend( ui_clr.border, ui_clr.bg, 0.70f ); gui_draw_frect( row_x, row_y, row_w, row_h, sel_bg ); } CLR col = selected ? ui_clr.txt : ui_clr.txt_inactive; I32 txt_y = row_y + ( row_h - txt_h ) / 2; gui_draw_str( row_x + 3, txt_y, ALIGN_L, FNT_JPN12, col, e->title ); yoff += LIST_ITEM_HEIGHT; } ); } void gui_list_input_fn( void* ptr ) { GUI_LIST* list = (GUI_LIST*)ptr; I32 x = gui_relx( list ); I32 y = gui_rely( list ); I32 panel_y = y + LIST_TITLE_OFFSET; I32 w = list->w; I32 h = list->h; U8 m1 = gui_mbutton_down( 0 ); I32 mx, my; gui_cursor_pos( &mx, &my ); U8 inbounds = mx >= x && mx <= x + w && my >= panel_y && my <= panel_y + h; if( !inbounds ) return; I32 diff = my - panel_y; I32 idx = diff / LIST_ITEM_HEIGHT; if( idx >= list->plist->size ) idx = list->plist->size - 1; if( idx < 0 ) idx = 0; if( m1 ) { if( !list->held ) { GUI_LIST_ENTRY* e = &list->plist->data[idx]; I32 prevval = *list->pval; *list->pval = e->val; if( list->cb && prevval != *list->pval ) list->cb( list ); } list->held = 1; } else { list->held = 0; } } GUI_LIST* gui_list( I32 x, I32 y, I32 w, I32 h, const char* title, LIST* plist, I32* pval ) { if( !gui_check_target() ) return 0; GUI_LIST* list = new GUI_LIST; list->x = x; list->y = y; list->w = w; list->h = h; list->xbound = w; list->ybound = h + LIST_TITLE_OFFSET; list->cb = 0; list->pval = pval; list->plist = plist; list->draw_fn = gui_list_draw_fn; list->input_fn = gui_list_input_fn; strcpy( list->name, title ); list->parent = gui_get_view(); gui_get_view()->children.push( list ); return list; } GUI_LIST_ENTRY* gui_list_get_selected( GUI_LIST* list ) { for( U32 i = 0; i < list->plist->size; ++i ) { GUI_LIST_ENTRY* e = &list->plist->data[i]; if( e->val == *list->pval ) return e; } return 0; }