Progress on GUI scrolling

This commit is contained in:
Allen Webster 2018-07-16 20:21:22 -07:00
parent af5d6c8360
commit 468a7a33bc
11 changed files with 308 additions and 161 deletions

View File

@ -737,6 +737,8 @@ STRUCT UI_List{
STRUCT UI_Control{ STRUCT UI_Control{
UI_Item *items; UI_Item *items;
int32_t count; int32_t count;
i32_Rect bounding_box;
}; };
/* /*

View File

@ -1509,16 +1509,27 @@ CUSTOM_DOC("Interactively switch to an open buffer.")
int32_t line_height = (int32_t)view.line_height; int32_t line_height = (int32_t)view.line_height;
int32_t block_height = line_height*2; int32_t block_height = line_height*2;
int32_t hot_buffer_id = 0;
int32_t item_index = 0;
Temp_Memory temp = begin_temp_memory(scratch); Temp_Memory temp = begin_temp_memory(scratch);
String text_field = push_string(scratch, 256); String text_field = push_string(scratch, 256);
Temp_Memory list_restore_point = begin_temp_memory(scratch);
for(;;){ for(;;){
end_temp_memory(list_restore_point); Temp_Memory full_temp = begin_temp_memory(scratch);
refresh_view(app, &view);
Mouse_State mouse_state = get_mouse_state(app);
int32_t mx = mouse_state.x - view.file_region.x0 + (int32_t)view.scroll_vars.scroll_x;
int32_t my = mouse_state.y - view.file_region.y0 + (int32_t)view.scroll_vars.scroll_y;
int32_t y_pos = line_height; int32_t y_pos = line_height;
UI_List list = {0}; UI_List list = {0};
int32_t item_index_counter = 0;
UI_Item *highlighted_item = 0; UI_Item *highlighted_item = 0;
UI_Item *hot_item = 0;
UI_Item *hovered_item = 0;
int32_t option_item_count = 0;
for (Buffer_Summary buffer = get_buffer_first(app, AccessAll); for (Buffer_Summary buffer = get_buffer_first(app, AccessAll);
buffer.exists; buffer.exists;
get_buffer_next(app, &buffer, AccessAll)){ get_buffer_next(app, &buffer, AccessAll)){
@ -1543,17 +1554,39 @@ CUSTOM_DOC("Interactively switch to an open buffer.")
item.user_data = (void*)buffer.buffer_id; item.user_data = (void*)buffer.buffer_id;
item.activation_level = UIActivation_None; item.activation_level = UIActivation_None;
item.rectangle = item_rect; item.rectangle = item_rect;
if (highlighted_item == 0){
item.activation_level = UIActivation_Hover; UI_Item *item_ptr = ui_list_add_item(scratch, &list, item);
UI_Item *item_ptr = ui_list_add_item(scratch, &list, item); option_item_count += 1;
if (item_rect.x0 <= mx && mx < item_rect.x1 &&
item_rect.y0 <= my && my < item_rect.y1){
hovered_item = item_ptr;
}
if (item_index_counter == item_index){
highlighted_item = item_ptr; highlighted_item = item_ptr;
} }
else{ item_index_counter += 1;
ui_list_add_item(scratch, &list, item); if (buffer.buffer_id == hot_buffer_id){
hot_item = item_ptr;
} }
} }
} }
if (hovered_item != 0){
hovered_item->activation_level = UIActivation_Hover;
}
if (hot_item != 0){
if (hot_item == hovered_item){
hot_item->activation_level = UIActivation_Active;
}
else{
hot_item->activation_level = UIActivation_Hover;
}
}
if (highlighted_item != 0){
highlighted_item->activation_level = UIActivation_Active;
}
{ {
i32_Rect item_rect = {0}; i32_Rect item_rect = {0};
item_rect.x0 = x0; item_rect.x0 = x0;
@ -1566,6 +1599,7 @@ CUSTOM_DOC("Interactively switch to an open buffer.")
item.type = UIType_TextField; item.type = UIType_TextField;
item.query = push_string_copy(scratch, "Switch: "); item.query = push_string_copy(scratch, "Switch: ");
item.string = text_field; item.string = text_field;
item.activation_level = UIActivation_Active;
item.user_data = 0; item.user_data = 0;
item.rectangle = item_rect; item.rectangle = item_rect;
ui_list_add_item(scratch, &list, item); ui_list_add_item(scratch, &list, item);
@ -1574,45 +1608,94 @@ CUSTOM_DOC("Interactively switch to an open buffer.")
UI_Control control = ui_list_to_ui_control(scratch, &list); UI_Control control = ui_list_to_ui_control(scratch, &list);
view_set_ui(app, &view, &control); view_set_ui(app, &view, &control);
User_Input in = get_user_input(app, EventAll, EventOnEsc); for (;;){
if (in.abort){ bool32 needs_full_update = false;
goto done;
}
UI_Item *activated_item = 0;
switch (in.type){
case UserInputKey:
{
if (in.key.keycode == '\n' || in.key.keycode == '\t'){
activated_item = highlighted_item;
}
else if (in.key.keycode == key_back){
backspace_utf8(&text_field);
}
else{
uint8_t character[4];
uint32_t length = to_writable_character(in, character);
if (length > 0){
append(&text_field, make_string(character, length));
}
}
}break;
case UserInputMouse: User_Input in = get_user_input(app, EventAll, EventOnEsc);
{ if (in.abort){
if (in.mouse.press_l){ goto done;
int32_t mx = in.mouse.x - view.view_region.x0; }
int32_t my = in.mouse.y - view.view_region.y0;
activated_item = ui_control_get_mouse_hit(&control, mx, my); UI_Item *activated_item = 0;
} switch (in.type){
}break; case UserInputKey:
} {
if (in.key.keycode == '\n' || in.key.keycode == '\t'){
if (activated_item != 0){ activated_item = highlighted_item;
int32_t buffer_id = (int32_t)activated_item->user_data; }
view_set_buffer(app, &view, buffer_id, 0); else if (in.key.keycode == key_back){
goto done; backspace_utf8(&text_field);
needs_full_update = true;
item_index = 0;
}
else if (in.key.keycode == key_up || in.key.keycode == key_page_up){
item_index = item_index - 1;
if (item_index < 0){
item_index = 0;
}
needs_full_update = true;
}
else if (in.key.keycode == key_down || in.key.keycode == key_page_down){
item_index = item_index + 1;
if (item_index > option_item_count - 1){
item_index = option_item_count - 1;
}
needs_full_update = true;
}
else{
uint8_t character[4];
uint32_t length = to_writable_character(in, character);
if (length > 0){
append(&text_field, make_string(character, length));
needs_full_update = true;
item_index = 0;
}
}
}break;
case UserInputMouse:
{
if (in.mouse.wheel != 0){
GUI_Scroll_Vars scroll = view.scroll_vars;
scroll.target_y += in.mouse.wheel;
view_set_scroll(app, &view, scroll);
}
if (in.mouse.press_l || in.mouse.release_l){
int32_t mx = in.mouse.x - view.file_region.x0;
int32_t my = in.mouse.y - view.file_region.y0;
UI_Item *clicked = ui_control_get_mouse_hit(&control, mx, my);
if (in.mouse.press_l){
if (clicked != 0){
hot_buffer_id = (int32_t)clicked->user_data;
}
}
if (in.mouse.release_l){
if (clicked != 0){
if (hot_buffer_id == (int32_t)clicked->user_data){
activated_item = clicked;
}
}
hot_buffer_id = 0;
}
needs_full_update = true;
}
if (mx != in.mouse.x || my != in.mouse.y){
needs_full_update = true;
}
}break;
}
if (activated_item != 0){
int32_t buffer_id = (int32_t)activated_item->user_data;
view_set_buffer(app, &view, buffer_id, 0);
goto done;
}
if (needs_full_update){
goto full_update;
}
} }
full_update:;
end_temp_memory(full_temp);
} }
done:; done:;

View File

@ -307,7 +307,7 @@ static Command_Metadata fcoder_metacmd_table[185] = {
{ PROC_LINKS(open_all_code_recursive, 0), "open_all_code_recursive", 23, "Works as open_all_code but also runs in all subdirectories.", 59, "w:\\4ed\\code\\4coder_project_commands.cpp", 42, 1062 }, { PROC_LINKS(open_all_code_recursive, 0), "open_all_code_recursive", 23, "Works as open_all_code but also runs in all subdirectories.", 59, "w:\\4ed\\code\\4coder_project_commands.cpp", 42, 1062 },
{ PROC_LINKS(open_color_tweaker, 0), "open_color_tweaker", 18, "Opens the 4coder colors and fonts selector menu.", 48, "w:\\4ed\\code\\4coder_base_commands.cpp", 39, 1492 }, { PROC_LINKS(open_color_tweaker, 0), "open_color_tweaker", 18, "Opens the 4coder colors and fonts selector menu.", 48, "w:\\4ed\\code\\4coder_base_commands.cpp", 39, 1492 },
{ PROC_LINKS(open_file_in_quotes, 0), "open_file_in_quotes", 19, "Reads a filename from surrounding '\"' characters and attempts to open the corresponding file.", 94, "w:\\4ed\\code\\4coder_base_commands.cpp", 39, 1339 }, { PROC_LINKS(open_file_in_quotes, 0), "open_file_in_quotes", 19, "Reads a filename from surrounding '\"' characters and attempts to open the corresponding file.", 94, "w:\\4ed\\code\\4coder_base_commands.cpp", 39, 1339 },
{ PROC_LINKS(open_in_other, 0), "open_in_other", 13, "Interactively opens a file in the other panel.", 46, "w:\\4ed\\code\\4coder_base_commands.cpp", 39, 1625 }, { PROC_LINKS(open_in_other, 0), "open_in_other", 13, "Interactively opens a file in the other panel.", 46, "w:\\4ed\\code\\4coder_base_commands.cpp", 39, 1708 },
{ PROC_LINKS(open_long_braces, 0), "open_long_braces", 16, "At the cursor, insert a '{' and '}' separated by a blank line.", 62, "w:\\4ed\\code\\4coder_combined_write_commands.cpp", 49, 58 }, { PROC_LINKS(open_long_braces, 0), "open_long_braces", 16, "At the cursor, insert a '{' and '}' separated by a blank line.", 62, "w:\\4ed\\code\\4coder_combined_write_commands.cpp", 49, 58 },
{ PROC_LINKS(open_long_braces_break, 0), "open_long_braces_break", 22, "At the cursor, insert a '{' and '}break;' separated by a blank line.", 68, "w:\\4ed\\code\\4coder_combined_write_commands.cpp", 49, 74 }, { PROC_LINKS(open_long_braces_break, 0), "open_long_braces_break", 22, "At the cursor, insert a '{' and '}break;' separated by a blank line.", 68, "w:\\4ed\\code\\4coder_combined_write_commands.cpp", 49, 74 },
{ PROC_LINKS(open_long_braces_semicolon, 0), "open_long_braces_semicolon", 26, "At the cursor, insert a '{' and '};' separated by a blank line.", 63, "w:\\4ed\\code\\4coder_combined_write_commands.cpp", 49, 66 }, { PROC_LINKS(open_long_braces_semicolon, 0), "open_long_braces_semicolon", 26, "At the cursor, insert a '{' and '};' separated by a blank line.", 63, "w:\\4ed\\code\\4coder_combined_write_commands.cpp", 49, 66 },

View File

@ -17,22 +17,50 @@ static UI_Control
ui_list_to_ui_control(Partition *arena, UI_List *list){ ui_list_to_ui_control(Partition *arena, UI_List *list){
UI_Control control = {0}; UI_Control control = {0};
control.items = push_array(arena, UI_Item, list->count); control.items = push_array(arena, UI_Item, list->count);
if (list->count > 0){
control.bounding_box = list->first->fixed.rectangle;
}
for (UI_Item_Node *node = list->first; for (UI_Item_Node *node = list->first;
node != 0; node != 0;
node = node->next){ node = node->next){
control.items[control.count++] = node->fixed; control.items[control.count++] = node->fixed;
if (control.bounding_box.x0 > node->fixed.rectangle.x0){
control.bounding_box.x0 = node->fixed.rectangle.x0;
}
if (control.bounding_box.x1 < node->fixed.rectangle.x1){
control.bounding_box.x1 = node->fixed.rectangle.x1;
}
if (control.bounding_box.y0 > node->fixed.rectangle.y0){
control.bounding_box.y0 = node->fixed.rectangle.y0;
}
if (control.bounding_box.y1 < node->fixed.rectangle.y1){
control.bounding_box.y1 = node->fixed.rectangle.y1;
}
} }
return(control); return(control);
} }
static void
ui_control_set_top(UI_Control *control, int32_t top_y){
control->bounding_box.y0 = top_y;
}
static void
ui_control_set_bottom(UI_Control *control, int32_t bottom_y){
control->bounding_box.y1 = bottom_y;
}
static UI_Item* static UI_Item*
ui_control_get_mouse_hit(UI_Control *control, int32_t mx, int32_t my){ ui_control_get_mouse_hit(UI_Control *control, int32_t mx, int32_t my){
int32_t count = control->count; if (control->bounding_box.x0 <= mx && mx < control->bounding_box.x1 &&
UI_Item *item = control->items + count - 1; control->bounding_box.y0 <= my && my < control->bounding_box.y1){
for (int32_t i = 0; i < count; ++i, item -= 1){ int32_t count = control->count;
i32_Rect r = item->rectangle; UI_Item *item = control->items + count - 1;
if (r.x0 <= mx && mx < r.x1 && r.y0 <= my && my < r.y1){ for (int32_t i = 0; i < count; ++i, item -= 1){
return(item); i32_Rect r = item->rectangle;
if (r.x0 <= mx && mx < r.x1 && r.y0 <= my && my < r.y1){
return(item);
}
} }
} }
return(0); return(0);

75
4ed.cpp
View File

@ -1868,51 +1868,46 @@ App_Step_Sig(app_step){
b32 active = (panel == active_panel); b32 active = (panel == active_panel);
Input_Summary summary = (active)?(active_input):(dead_input); Input_Summary summary = (active)?(active_input):(dead_input);
view->transient.changed_context_in_step = 0; if (panel == mouse_panel && !input->mouse.out_of_window){
summary.mouse = mouse_state;
}
if (view->transient.changed_context_in_step == 0){ GUI_Scroll_Vars *scroll_vars = 0;
active = (panel == active_panel); i32 max_y = 0;
summary = (active)?(active_input):(dead_input); b32 file_scroll = false;
if (panel == mouse_panel && !input->mouse.out_of_window){ if (view->transient.ui_mode_counter == 0){
summary.mouse = mouse_state; scroll_vars = &view->transient.edit_pos->scroll;
} max_y = view_compute_max_target_y(view);
file_scroll = true;
b32 file_scroll = true; }
GUI_Scroll_Vars *scroll_vars = &view->transient.edit_pos->scroll; else{
scroll_vars = &view->transient.ui_scroll;
i32 max_y = 0; i32 bottom = view->transient.ui_control.bounding_box.y1;
if (view->transient.ui_mode_counter == 0){ max_y = view_compute_max_target_y_from_bottom_y(view, (f32)bottom);
max_y = view_compute_max_target_y(view); file_scroll = false;
}
Input_Process_Result ip_result = do_step_file_view(system, view, models, panel->inner, active, &summary, *scroll_vars, max_y);
if (ip_result.is_animating){
app_result.animating = true;
}
if (ip_result.consumed_l){
consume_input(&vars->available_input, Input_MouseLeftButton, "file view step");
}
if (ip_result.consumed_r){
consume_input(&vars->available_input, Input_MouseRightButton, "file view step");
}
if (memcmp(scroll_vars, &ip_result.scroll, sizeof(*scroll_vars)) != 0){
if (file_scroll){
view_set_scroll(system, view, ip_result.scroll);
} }
else{ else{
#if 0 *scroll_vars = ip_result.scroll;
max_y = view->transient.gui_max_y;
#endif
} }
Input_Process_Result ip_result = do_step_file_view(system, view, models, panel->inner, active, &summary, *scroll_vars, view->transient.scroll_region, max_y);
if (ip_result.is_animating){
app_result.animating = 1;
}
if (ip_result.consumed_l){
consume_input(&vars->available_input, Input_MouseLeftButton, "file view step");
}
if (ip_result.consumed_r){
consume_input(&vars->available_input, Input_MouseRightButton, "file view step");
}
if (memcmp(scroll_vars, &ip_result.vars, sizeof(*scroll_vars)) != 0){
if (file_scroll){
view_set_scroll(system, view, ip_result.vars);
}
else{
*scroll_vars = ip_result.vars;
}
}
view->transient.scroll_region = ip_result.region;
} }
} }
} }

View File

@ -86,7 +86,12 @@ fill_view_summary(System_Functions *system, View_Summary *view, View *vptr, Live
view->view_region = vptr->transient.panel->inner; view->view_region = vptr->transient.panel->inner;
view->file_region = vptr->transient.file_region; view->file_region = vptr->transient.file_region;
view->scroll_vars = vptr->transient.edit_pos->scroll; if (vptr->transient.ui_mode_counter == 0){
view->scroll_vars = vptr->transient.edit_pos->scroll;
}
else{
view->scroll_vars = vptr->transient.ui_scroll;
}
} }
} }
@ -2001,7 +2006,12 @@ DOC_SEE(GUI_Scroll_Vars)
Assert(file != 0); Assert(file != 0);
if (!file->is_loading){ if (!file->is_loading){
result = true; result = true;
view_set_scroll(system, vptr, scroll); if (vptr->transient.ui_mode_counter == 0){
view_set_scroll(system, vptr, scroll);
}
else{
vptr->transient.ui_scroll = scroll;
}
fill_view_summary(system, view, vptr, cmd); fill_view_summary(system, view, vptr, cmd);
} }
} }
@ -2228,7 +2238,7 @@ View_Set_UI(Application_Links *app, View_Summary *view, UI_Control *control){
if (vptr->transient.ui_control.items != 0){ if (vptr->transient.ui_control.items != 0){
general_memory_free(general, vptr->transient.ui_control.items); general_memory_free(general, vptr->transient.ui_control.items);
} }
vptr->transient.ui_control.count = 0; memset(&vptr->transient.ui_control, 0, sizeof(vptr->transient.ui_control));
if (control->count > 0){ if (control->count > 0){
i32 memory_size = sizeof(UI_Item)*control->count; i32 memory_size = sizeof(UI_Item)*control->count;
vptr->transient.ui_control.items = (UI_Item*)general_memory_allocate(general, memory_size); vptr->transient.ui_control.items = (UI_Item*)general_memory_allocate(general, memory_size);
@ -2240,9 +2250,7 @@ View_Set_UI(Application_Links *app, View_Summary *view, UI_Control *control){
return(false); return(false);
} }
} }
else{ vptr->transient.ui_control.bounding_box = control->bounding_box;
vptr->transient.ui_control.items = 0;
}
return(true); return(true);
} }
return(false); return(false);

View File

@ -657,5 +657,23 @@ fits_inside(i32_Rect rect, i32_Rect outer){
return(rect.x0 >= outer.x0 && rect.x1 <= outer.x1 && rect.y0 >= outer.y0 && rect.y1 <= outer.y1); return(rect.x0 >= outer.x0 && rect.x1 <= outer.x1 && rect.y0 >= outer.y0 && rect.y1 <= outer.y1);
} }
static int32_t
interval_overlap(float a0, float a1, float b0, float b1){
if (a0 <= b0 && b0 < a1 ||
b0 <= a0 && a0 < b1){
return(true);
}
return(false);
}
static int32_t
rect_opverlap(f32_Rect a, f32_Rect b){
if (interval_overlap(a.x0, a.x1, b.x0, b.x1) &&
interval_overlap(a.y0, a.y1, b.y0, b.y1)){
return(true);
}
return(false);
}
// BOTTOM // BOTTOM

View File

@ -74,6 +74,20 @@ draw_rectangle_outline(Render_Target *target, i32_Rect rect, u32 color){
draw_rectangle_outline(target, f32R(rect), color); draw_rectangle_outline(target, f32R(rect), color);
} }
internal void
draw_margin(Render_Target *target, f32_Rect outer, f32_Rect inner, u32 color){
draw_rectangle(target, f32R(outer.x0, outer.y0, outer.x1, inner.y0), color);
draw_rectangle(target, f32R(outer.x0, inner.y1, outer.x1, outer.y1), color);
draw_rectangle(target, f32R(outer.x0, inner.y0, inner.x0, inner.y1), color);
draw_rectangle(target, f32R(inner.x1, inner.y0, outer.x1, inner.y1), color);
}
inline void
draw_margin(Render_Target *target, f32_Rect outer, f32 width, u32 color){
f32_Rect inner = get_inner_rect(outer, width);
draw_margin(target, outer, inner, color);
}
internal void internal void
draw_margin(Render_Target *target, i32_Rect outer, i32_Rect inner, u32 color){ draw_margin(Render_Target *target, i32_Rect outer, i32_Rect inner, u32 color){
draw_rectangle(target, i32R(outer.x0, outer.y0, outer.x1, inner.y0), color); draw_rectangle(target, i32R(outer.x0, outer.y0, outer.x1, inner.y0), color);

View File

@ -138,6 +138,14 @@ view_cursor_limits(View *view){
return(limits); return(limits);
} }
inline i32
view_compute_max_target_y_from_bottom_y(View *view, f32 max_item_y){
i32 line_height = view->transient.line_height;
f32 height = clamp_bottom((f32)line_height, view_height(view));
f32 max_target_y = clamp_bottom(0.f, max_item_y - height*0.5f);
return(ceil32(max_target_y));
}
inline i32 inline i32
view_compute_max_target_y(View *view){ view_compute_max_target_y(View *view){
i32 line_height = view->transient.line_height; i32 line_height = view->transient.line_height;
@ -147,9 +155,7 @@ view_compute_max_target_y(View *view){
if (!file->settings.unwrapped_lines){ if (!file->settings.unwrapped_lines){
lowest_line = file->state.wrap_line_index[buffer->line_count]; lowest_line = file->state.wrap_line_index[buffer->line_count];
} }
f32 height = clamp_bottom((f32)line_height, view_height(view)); return(view_compute_max_target_y_from_bottom_y(view, (lowest_line + 0.5f)*(f32)line_height));
f32 max_target_y = clamp_bottom(0.f, ((lowest_line + 0.5f)*line_height) - height*0.5f);
return(ceil32(max_target_y));
} }
inline u32 inline u32

View File

@ -48,6 +48,7 @@ struct View_Transient{
i32 ui_mode_counter; i32 ui_mode_counter;
UI_Control ui_control; UI_Control ui_control;
GUI_Scroll_Vars ui_scroll;
b32 hide_scrollbar; b32 hide_scrollbar;
b32 hide_file_bar; b32 hide_file_bar;
@ -184,14 +185,10 @@ struct View_Step_Result{
}; };
struct Input_Process_Result{ struct Input_Process_Result{
GUI_Scroll_Vars vars; GUI_Scroll_Vars scroll;
i32_Rect region;
b32 is_animating; b32 is_animating;
b32 consumed_l; b32 consumed_l;
b32 consumed_r; b32 consumed_r;
b32 has_max_y_suggestion;
i32 max_y;
}; };
enum{ enum{

View File

@ -146,13 +146,11 @@ global_const Style_Color_Edit colors_to_edit[] = {
}; };
internal Input_Process_Result internal Input_Process_Result
do_step_file_view(System_Functions *system, View *view, Models *models, i32_Rect rect, b32 is_active, Input_Summary *user_input, GUI_Scroll_Vars vars, i32_Rect region, i32 max_y){ do_step_file_view(System_Functions *system, View *view, Models *models, i32_Rect rect, b32 is_active, Input_Summary *user_input, GUI_Scroll_Vars scroll, i32 max_y){
scroll.target_y = clamp(0, scroll.target_y, max_y);
Input_Process_Result result = {0}; Input_Process_Result result = {0};
result.scroll = scroll;
vars.target_y = clamp(0, vars.target_y, max_y);
result.vars = vars;
result.region = region;
i32 line_height = view->transient.line_height; i32 line_height = view->transient.line_height;
@ -166,8 +164,8 @@ do_step_file_view(System_Functions *system, View *view, Models *models, i32_Rect
} }
if (user_input->mouse.wheel != 0){ if (user_input->mouse.wheel != 0){
result.vars.target_y += user_input->mouse.wheel; result.scroll.target_y += user_input->mouse.wheel;
result.vars.target_y = clamp(0, result.vars.target_y, max_y); result.scroll.target_y = clamp(0, result.scroll.target_y, max_y);
result.is_animating = true; result.is_animating = true;
} }
@ -194,26 +192,23 @@ do_step_file_view(System_Functions *system, View *view, Models *models, i32_Rect
target_y = clamp_bottom(0, floor32(cursor.y - height*.5f)); target_y = clamp_bottom(0, floor32(cursor.y - height*.5f));
} }
result.vars.target_y = target_y; result.scroll.target_y = target_y;
result.vars.scroll_y = (f32)target_y; result.scroll.scroll_y = (f32)target_y;
result.vars.prev_target_y = -1000; result.scroll.prev_target_y = -1000;
result.vars.target_x = target_x; result.scroll.target_x = target_x;
result.vars.scroll_x = (f32)target_x; result.scroll.scroll_x = (f32)target_x;
result.vars.prev_target_x = -1000; result.scroll.prev_target_x = -1000;
} }
if (!file->is_loading && file->state.paste_effect.seconds_down > 0.f){ if (!file->is_loading && file->state.paste_effect.seconds_down > 0.f){
file->state.paste_effect.seconds_down -= user_input->dt; file->state.paste_effect.seconds_down -= user_input->dt;
result.is_animating = true; result.is_animating = true;
} }
result.has_max_y_suggestion = true;
result.max_y = view_compute_max_target_y(view);
} }
{ {
GUI_Scroll_Vars scroll_vars = result.vars; GUI_Scroll_Vars scroll_vars = result.scroll;
b32 is_new_target = (scroll_vars.target_x != scroll_vars.prev_target_x || b32 is_new_target = (scroll_vars.target_x != scroll_vars.prev_target_x ||
scroll_vars.target_y != scroll_vars.prev_target_y); scroll_vars.target_y != scroll_vars.prev_target_y);
@ -227,7 +222,7 @@ do_step_file_view(System_Functions *system, View *view, Models *models, i32_Rect
scroll_vars.prev_target_x = scroll_vars.target_x; scroll_vars.prev_target_x = scroll_vars.target_x;
scroll_vars.prev_target_y = scroll_vars.target_y; scroll_vars.prev_target_y = scroll_vars.target_y;
result.vars = scroll_vars; result.scroll = scroll_vars;
} }
return(result); return(result);
@ -398,46 +393,47 @@ do_render_file_view(System_Functions *system, View *view, Models *models, GUI_Sc
} }
} }
else{ else{
f32_Rect rect_f32 = f32R(rect);
i32 item_count = view->transient.ui_control.count; i32 item_count = view->transient.ui_control.count;
UI_Item *item = view->transient.ui_control.items; UI_Item *item = view->transient.ui_control.items;
GUI_Scroll_Vars scroll = view->transient.ui_scroll;
for (i32 i = 0; i < item_count; ++i, item += 1){ for (i32 i = 0; i < item_count; ++i, item += 1){
switch (item->type){ f32_Rect item_rect = f32R(item->rectangle);
case UIType_Option: item_rect.x0 += rect_f32.x0 - scroll.scroll_x;
{ item_rect.y0 += rect_f32.y0 - scroll.scroll_y;
u32 back = style->main.back_color; item_rect.x1 += rect_f32.x0 - scroll.scroll_x;
u32 margin = style_get_margin_color(item->activation_level, style); item_rect.y1 += rect_f32.y0 - scroll.scroll_y;
u32 text_color = style->main.default_color;
u32 pop_color = style->main.file_info_style.pop2_color; if (rect_opverlap(item_rect, rect_f32)){
i32_Rect item_rect = item->rectangle; switch (item->type){
item_rect.x0 += rect.x0; case UIType_Option:
item_rect.y0 += rect.y0; {
item_rect.x1 += rect.x0; u32 back = style->main.back_color;
item_rect.y1 += rect.y0; u32 margin_color = style_get_margin_color(item->activation_level, style);
i32_Rect inner = get_inner_rect(item_rect, 3); u32 text_color = style->main.default_color;
draw_rectangle(target, inner, back); u32 pop_color = style->main.file_info_style.pop2_color;
draw_margin(target, item_rect, inner, margin); f32_Rect inner = get_inner_rect(item_rect, 3);
i32 x = inner.x0 + 3; draw_rectangle(target, inner, back);
i32 y = inner.y0 + line_height/2 - 1; draw_margin(target, item_rect, inner, margin_color);
x = ceil32(draw_string(system, target, font_id, item->string, x, y, text_color)); i32 x = (i32)inner.x0 + 3;
draw_string(system, target, font_id, item->status, x, y, pop_color); i32 y = (i32)inner.y0 + line_height/2 - 1;
}break; x = ceil32(draw_string(system, target, font_id, item->string, x, y, text_color));
draw_string(system, target, font_id, item->status, x, y, pop_color);
case UIType_TextField: }break;
{
u32 back_color = style->main.margin_color; case UIType_TextField:
u32 text1_color = style->main.default_color; {
u32 text2_color = style->main.file_info_style.pop1_color; u32 back_color = style->main.margin_color;
i32_Rect item_rect = item->rectangle; u32 text1_color = style->main.default_color;
item_rect.x0 += rect.x0; u32 text2_color = style->main.file_info_style.pop1_color;
item_rect.y0 += rect.y0; draw_rectangle(target, item_rect, back_color);
item_rect.x1 += rect.x0; i32 x = (i32)item_rect.x0;
item_rect.y1 += rect.y0; i32 y = (i32)item_rect.y0 + 2;
draw_rectangle(target, item_rect, back_color); x = ceil32(draw_string(system, target, font_id, item->query, x, y, text2_color));
i32 x = item_rect.x0; draw_string(system, target, font_id, item->string, x, y, text1_color);
i32 y = item_rect.y0 + 2; }break;
x = ceil32(draw_string(system, target, font_id, item->query, x, y, text2_color)); }
draw_string(system, target, font_id, item->string, x, y, text1_color);
}break;
} }
} }
} }