From 40b5e61e917c363ab0ccc6e87a8ac8585ab17ece Mon Sep 17 00:00:00 2001 From: Allen Webster Date: Sat, 24 Mar 2018 23:43:56 -0700 Subject: [PATCH] Cut down 4ed_view.cpp a lot more, cut the old debug view --- 4coder_API/types.h | 2 - 4coder_base_commands.cpp | 6 - 4coder_generated/command_metadata.h | 181 ++- 4coder_generated/remapping.h | 12 +- 4ed.cpp | 46 +- 4ed_api_implementation.cpp | 80 +- 4ed_app_target.cpp | 4 +- 4ed_file.cpp | 34 + 4ed_font.h | 2 +- 4ed_view.cpp | 1709 +++++++-------------------- 4ed_view.h | 53 +- 4ed_working_set.cpp | 270 ++++- meta/4ed_metagen.cpp | 2 - 13 files changed, 902 insertions(+), 1499 deletions(-) diff --git a/4coder_API/types.h b/4coder_API/types.h index 45d2b37a..7201799b 100644 --- a/4coder_API/types.h +++ b/4coder_API/types.h @@ -87,8 +87,6 @@ ENUM(uint64_t, Command_ID){ /* DOC(cmdid_open_color_tweaker opens the theme editing GUI.) */ cmdid_open_color_tweaker, - /* DOC(cmdid_open_debug opens the debug information viewer mode.) */ - cmdid_open_debug, // count cmdid_count diff --git a/4coder_base_commands.cpp b/4coder_base_commands.cpp index cf456813..2824b687 100644 --- a/4coder_base_commands.cpp +++ b/4coder_base_commands.cpp @@ -1282,12 +1282,6 @@ CUSTOM_DOC("Opens the 4coder colors and fonts selector menu.") exec_command(app, cmdid_open_color_tweaker); } -CUSTOM_COMMAND_SIG(open_debug) -CUSTOM_DOC("Opens a debug view for internal use.") -{ - exec_command(app, cmdid_open_debug); -} - #endif // BOTTOM diff --git a/4coder_generated/command_metadata.h b/4coder_generated/command_metadata.h index 0ac65252..9e4c9932 100644 --- a/4coder_generated/command_metadata.h +++ b/4coder_generated/command_metadata.h @@ -1,7 +1,7 @@ #define command_id(c) (fcoder_metacmd_ID_##c) #define command_metadata(c) (&fcoder_metacmd_table[command_id(c)]) #define command_metadata_by_id(id) (&fcoder_metacmd_table[id]) -#define command_one_past_last_id 195 +#define command_one_past_last_id 194 #if defined(CUSTOM_COMMAND_SIG) #define PROC_LINKS(x,y) x #else @@ -115,7 +115,6 @@ CUSTOM_COMMAND_SIG(newline_or_goto_position_sticky); CUSTOM_COMMAND_SIG(open_all_code); CUSTOM_COMMAND_SIG(open_all_code_recursive); CUSTOM_COMMAND_SIG(open_color_tweaker); -CUSTOM_COMMAND_SIG(open_debug); CUSTOM_COMMAND_SIG(open_file_in_quotes); CUSTOM_COMMAND_SIG(open_in_other); CUSTOM_COMMAND_SIG(open_long_braces); @@ -214,7 +213,7 @@ char *source_name; int32_t source_name_len; int32_t line_number; }; -static Command_Metadata fcoder_metacmd_table[195] = { +static Command_Metadata fcoder_metacmd_table[194] = { { PROC_LINKS(allow_mouse, 0), "allow_mouse", 11, "Shows the mouse and causes all mouse input to be processed normally.", 68, "C:\\work\\4ed\\code\\4coder_default_framework.h", 47, 232 }, { PROC_LINKS(auto_tab_line_at_cursor, 0), "auto_tab_line_at_cursor", 23, "Auto-indents the line on which the cursor sits.", 47, "C:\\work\\4ed\\code\\4coder_auto_indent.cpp", 43, 667 }, { PROC_LINKS(auto_tab_range, 0), "auto_tab_range", 14, "Auto-indents the range between the cursor and the mark.", 55, "C:\\work\\4ed\\code\\4coder_auto_indent.cpp", 43, 678 }, @@ -322,7 +321,6 @@ static Command_Metadata fcoder_metacmd_table[195] = { { PROC_LINKS(open_all_code, 0), "open_all_code", 13, "Open all code in the current directory. File types are determined by extensions. An extension is considered code based on the extensions specified in 4coder.config.", 164, "C:\\work\\4ed\\code\\4coder_project_commands.cpp", 48, 165 }, { PROC_LINKS(open_all_code_recursive, 0), "open_all_code_recursive", 23, "Works as open_all_code but also runs in all subdirectories.", 59, "C:\\work\\4ed\\code\\4coder_project_commands.cpp", 48, 180 }, { PROC_LINKS(open_color_tweaker, 0), "open_color_tweaker", 18, "Opens the 4coder colors and fonts selector menu.", 48, "C:\\work\\4ed\\code\\4coder_base_commands.cpp", 45, 1279 }, -{ PROC_LINKS(open_debug, 0), "open_debug", 10, "Opens a debug view for internal use.", 36, "C:\\work\\4ed\\code\\4coder_base_commands.cpp", 45, 1285 }, { 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, "C:\\work\\4ed\\code\\4coder_default_include.cpp", 47, 634 }, { PROC_LINKS(open_in_other, 0), "open_in_other", 13, "Reads a filename from surrounding '\"' characters and attempts to open the corresponding file, displaying it in the other view.", 127, "C:\\work\\4ed\\code\\4coder_default_include.cpp", 47, 651 }, { PROC_LINKS(open_long_braces, 0), "open_long_braces", 16, "At the cursor, insert a '{' and '}' separated by a blank line.", 62, "C:\\work\\4ed\\code\\4coder_default_include.cpp", 47, 513 }, @@ -518,91 +516,90 @@ static int32_t fcoder_metacmd_ID_newline_or_goto_position_sticky = 103; static int32_t fcoder_metacmd_ID_open_all_code = 104; static int32_t fcoder_metacmd_ID_open_all_code_recursive = 105; static int32_t fcoder_metacmd_ID_open_color_tweaker = 106; -static int32_t fcoder_metacmd_ID_open_debug = 107; -static int32_t fcoder_metacmd_ID_open_file_in_quotes = 108; -static int32_t fcoder_metacmd_ID_open_in_other = 109; -static int32_t fcoder_metacmd_ID_open_long_braces = 110; -static int32_t fcoder_metacmd_ID_open_long_braces_break = 111; -static int32_t fcoder_metacmd_ID_open_long_braces_semicolon = 112; -static int32_t fcoder_metacmd_ID_open_matching_file_cpp = 113; -static int32_t fcoder_metacmd_ID_open_panel_hsplit = 114; -static int32_t fcoder_metacmd_ID_open_panel_vsplit = 115; -static int32_t fcoder_metacmd_ID_page_down = 116; -static int32_t fcoder_metacmd_ID_page_up = 117; -static int32_t fcoder_metacmd_ID_paste = 118; -static int32_t fcoder_metacmd_ID_paste_and_indent = 119; -static int32_t fcoder_metacmd_ID_paste_next = 120; -static int32_t fcoder_metacmd_ID_paste_next_and_indent = 121; -static int32_t fcoder_metacmd_ID_place_in_scope = 122; -static int32_t fcoder_metacmd_ID_project_fkey_command = 123; -static int32_t fcoder_metacmd_ID_project_go_to_root_directory = 124; -static int32_t fcoder_metacmd_ID_query_replace = 125; -static int32_t fcoder_metacmd_ID_query_replace_identifier = 126; -static int32_t fcoder_metacmd_ID_query_replace_selection = 127; -static int32_t fcoder_metacmd_ID_redo = 128; -static int32_t fcoder_metacmd_ID_reload_current_project = 129; -static int32_t fcoder_metacmd_ID_remap_interactive = 130; -static int32_t fcoder_metacmd_ID_rename_file_query = 131; -static int32_t fcoder_metacmd_ID_rename_parameter = 132; -static int32_t fcoder_metacmd_ID_reopen = 133; -static int32_t fcoder_metacmd_ID_replace_all_occurrences = 134; -static int32_t fcoder_metacmd_ID_replace_in_range = 135; -static int32_t fcoder_metacmd_ID_reverse_search = 136; -static int32_t fcoder_metacmd_ID_reverse_search_identifier = 137; -static int32_t fcoder_metacmd_ID_save = 138; -static int32_t fcoder_metacmd_ID_save_all_dirty_buffers = 139; -static int32_t fcoder_metacmd_ID_save_to_query = 140; -static int32_t fcoder_metacmd_ID_scope_absorb_down = 141; -static int32_t fcoder_metacmd_ID_search = 142; -static int32_t fcoder_metacmd_ID_search_identifier = 143; -static int32_t fcoder_metacmd_ID_seek_alphanumeric_left = 144; -static int32_t fcoder_metacmd_ID_seek_alphanumeric_or_camel_left = 145; -static int32_t fcoder_metacmd_ID_seek_alphanumeric_or_camel_right = 146; -static int32_t fcoder_metacmd_ID_seek_alphanumeric_right = 147; -static int32_t fcoder_metacmd_ID_seek_beginning_of_line = 148; -static int32_t fcoder_metacmd_ID_seek_beginning_of_textual_line = 149; -static int32_t fcoder_metacmd_ID_seek_end_of_line = 150; -static int32_t fcoder_metacmd_ID_seek_end_of_textual_line = 151; -static int32_t fcoder_metacmd_ID_seek_token_left = 152; -static int32_t fcoder_metacmd_ID_seek_token_right = 153; -static int32_t fcoder_metacmd_ID_seek_white_or_token_left = 154; -static int32_t fcoder_metacmd_ID_seek_white_or_token_right = 155; -static int32_t fcoder_metacmd_ID_seek_whitespace_down = 156; -static int32_t fcoder_metacmd_ID_seek_whitespace_down_end_line = 157; -static int32_t fcoder_metacmd_ID_seek_whitespace_left = 158; -static int32_t fcoder_metacmd_ID_seek_whitespace_right = 159; -static int32_t fcoder_metacmd_ID_seek_whitespace_up = 160; -static int32_t fcoder_metacmd_ID_seek_whitespace_up_end_line = 161; -static int32_t fcoder_metacmd_ID_select_all = 162; -static int32_t fcoder_metacmd_ID_set_bindings_choose = 163; -static int32_t fcoder_metacmd_ID_set_bindings_default = 164; -static int32_t fcoder_metacmd_ID_set_bindings_mac_default = 165; -static int32_t fcoder_metacmd_ID_set_mark = 166; -static int32_t fcoder_metacmd_ID_setup_new_project = 167; -static int32_t fcoder_metacmd_ID_show_filebar = 168; -static int32_t fcoder_metacmd_ID_show_scrollbar = 169; -static int32_t fcoder_metacmd_ID_snipe_token_or_word = 170; -static int32_t fcoder_metacmd_ID_snipe_token_or_word_right = 171; -static int32_t fcoder_metacmd_ID_suppress_mouse = 172; -static int32_t fcoder_metacmd_ID_swap_buffers_between_panels = 173; -static int32_t fcoder_metacmd_ID_to_lowercase = 174; -static int32_t fcoder_metacmd_ID_to_uppercase = 175; -static int32_t fcoder_metacmd_ID_toggle_filebar = 176; -static int32_t fcoder_metacmd_ID_toggle_fullscreen = 177; -static int32_t fcoder_metacmd_ID_toggle_line_wrap = 178; -static int32_t fcoder_metacmd_ID_toggle_mouse = 179; -static int32_t fcoder_metacmd_ID_toggle_show_whitespace = 180; -static int32_t fcoder_metacmd_ID_toggle_virtual_whitespace = 181; -static int32_t fcoder_metacmd_ID_undo = 182; -static int32_t fcoder_metacmd_ID_view_buffer_other_panel = 183; -static int32_t fcoder_metacmd_ID_word_complete = 184; -static int32_t fcoder_metacmd_ID_write_and_auto_tab = 185; -static int32_t fcoder_metacmd_ID_write_block = 186; -static int32_t fcoder_metacmd_ID_write_character = 187; -static int32_t fcoder_metacmd_ID_write_explicit_enum_flags = 188; -static int32_t fcoder_metacmd_ID_write_explicit_enum_values = 189; -static int32_t fcoder_metacmd_ID_write_hack = 190; -static int32_t fcoder_metacmd_ID_write_note = 191; -static int32_t fcoder_metacmd_ID_write_todo = 192; -static int32_t fcoder_metacmd_ID_write_underscore = 193; -static int32_t fcoder_metacmd_ID_write_zero_struct = 194; +static int32_t fcoder_metacmd_ID_open_file_in_quotes = 107; +static int32_t fcoder_metacmd_ID_open_in_other = 108; +static int32_t fcoder_metacmd_ID_open_long_braces = 109; +static int32_t fcoder_metacmd_ID_open_long_braces_break = 110; +static int32_t fcoder_metacmd_ID_open_long_braces_semicolon = 111; +static int32_t fcoder_metacmd_ID_open_matching_file_cpp = 112; +static int32_t fcoder_metacmd_ID_open_panel_hsplit = 113; +static int32_t fcoder_metacmd_ID_open_panel_vsplit = 114; +static int32_t fcoder_metacmd_ID_page_down = 115; +static int32_t fcoder_metacmd_ID_page_up = 116; +static int32_t fcoder_metacmd_ID_paste = 117; +static int32_t fcoder_metacmd_ID_paste_and_indent = 118; +static int32_t fcoder_metacmd_ID_paste_next = 119; +static int32_t fcoder_metacmd_ID_paste_next_and_indent = 120; +static int32_t fcoder_metacmd_ID_place_in_scope = 121; +static int32_t fcoder_metacmd_ID_project_fkey_command = 122; +static int32_t fcoder_metacmd_ID_project_go_to_root_directory = 123; +static int32_t fcoder_metacmd_ID_query_replace = 124; +static int32_t fcoder_metacmd_ID_query_replace_identifier = 125; +static int32_t fcoder_metacmd_ID_query_replace_selection = 126; +static int32_t fcoder_metacmd_ID_redo = 127; +static int32_t fcoder_metacmd_ID_reload_current_project = 128; +static int32_t fcoder_metacmd_ID_remap_interactive = 129; +static int32_t fcoder_metacmd_ID_rename_file_query = 130; +static int32_t fcoder_metacmd_ID_rename_parameter = 131; +static int32_t fcoder_metacmd_ID_reopen = 132; +static int32_t fcoder_metacmd_ID_replace_all_occurrences = 133; +static int32_t fcoder_metacmd_ID_replace_in_range = 134; +static int32_t fcoder_metacmd_ID_reverse_search = 135; +static int32_t fcoder_metacmd_ID_reverse_search_identifier = 136; +static int32_t fcoder_metacmd_ID_save = 137; +static int32_t fcoder_metacmd_ID_save_all_dirty_buffers = 138; +static int32_t fcoder_metacmd_ID_save_to_query = 139; +static int32_t fcoder_metacmd_ID_scope_absorb_down = 140; +static int32_t fcoder_metacmd_ID_search = 141; +static int32_t fcoder_metacmd_ID_search_identifier = 142; +static int32_t fcoder_metacmd_ID_seek_alphanumeric_left = 143; +static int32_t fcoder_metacmd_ID_seek_alphanumeric_or_camel_left = 144; +static int32_t fcoder_metacmd_ID_seek_alphanumeric_or_camel_right = 145; +static int32_t fcoder_metacmd_ID_seek_alphanumeric_right = 146; +static int32_t fcoder_metacmd_ID_seek_beginning_of_line = 147; +static int32_t fcoder_metacmd_ID_seek_beginning_of_textual_line = 148; +static int32_t fcoder_metacmd_ID_seek_end_of_line = 149; +static int32_t fcoder_metacmd_ID_seek_end_of_textual_line = 150; +static int32_t fcoder_metacmd_ID_seek_token_left = 151; +static int32_t fcoder_metacmd_ID_seek_token_right = 152; +static int32_t fcoder_metacmd_ID_seek_white_or_token_left = 153; +static int32_t fcoder_metacmd_ID_seek_white_or_token_right = 154; +static int32_t fcoder_metacmd_ID_seek_whitespace_down = 155; +static int32_t fcoder_metacmd_ID_seek_whitespace_down_end_line = 156; +static int32_t fcoder_metacmd_ID_seek_whitespace_left = 157; +static int32_t fcoder_metacmd_ID_seek_whitespace_right = 158; +static int32_t fcoder_metacmd_ID_seek_whitespace_up = 159; +static int32_t fcoder_metacmd_ID_seek_whitespace_up_end_line = 160; +static int32_t fcoder_metacmd_ID_select_all = 161; +static int32_t fcoder_metacmd_ID_set_bindings_choose = 162; +static int32_t fcoder_metacmd_ID_set_bindings_default = 163; +static int32_t fcoder_metacmd_ID_set_bindings_mac_default = 164; +static int32_t fcoder_metacmd_ID_set_mark = 165; +static int32_t fcoder_metacmd_ID_setup_new_project = 166; +static int32_t fcoder_metacmd_ID_show_filebar = 167; +static int32_t fcoder_metacmd_ID_show_scrollbar = 168; +static int32_t fcoder_metacmd_ID_snipe_token_or_word = 169; +static int32_t fcoder_metacmd_ID_snipe_token_or_word_right = 170; +static int32_t fcoder_metacmd_ID_suppress_mouse = 171; +static int32_t fcoder_metacmd_ID_swap_buffers_between_panels = 172; +static int32_t fcoder_metacmd_ID_to_lowercase = 173; +static int32_t fcoder_metacmd_ID_to_uppercase = 174; +static int32_t fcoder_metacmd_ID_toggle_filebar = 175; +static int32_t fcoder_metacmd_ID_toggle_fullscreen = 176; +static int32_t fcoder_metacmd_ID_toggle_line_wrap = 177; +static int32_t fcoder_metacmd_ID_toggle_mouse = 178; +static int32_t fcoder_metacmd_ID_toggle_show_whitespace = 179; +static int32_t fcoder_metacmd_ID_toggle_virtual_whitespace = 180; +static int32_t fcoder_metacmd_ID_undo = 181; +static int32_t fcoder_metacmd_ID_view_buffer_other_panel = 182; +static int32_t fcoder_metacmd_ID_word_complete = 183; +static int32_t fcoder_metacmd_ID_write_and_auto_tab = 184; +static int32_t fcoder_metacmd_ID_write_block = 185; +static int32_t fcoder_metacmd_ID_write_character = 186; +static int32_t fcoder_metacmd_ID_write_explicit_enum_flags = 187; +static int32_t fcoder_metacmd_ID_write_explicit_enum_values = 188; +static int32_t fcoder_metacmd_ID_write_hack = 189; +static int32_t fcoder_metacmd_ID_write_note = 190; +static int32_t fcoder_metacmd_ID_write_todo = 191; +static int32_t fcoder_metacmd_ID_write_underscore = 192; +static int32_t fcoder_metacmd_ID_write_zero_struct = 193; diff --git a/4coder_generated/remapping.h b/4coder_generated/remapping.h index c2ce2d77..07f40c19 100644 --- a/4coder_generated/remapping.h +++ b/4coder_generated/remapping.h @@ -15,7 +15,6 @@ bind(context, 'h', MDFR_CTRL, project_go_to_root_directory); bind(context, 'H', MDFR_CTRL, reload_current_project); bind(context, 'S', MDFR_CTRL, save_all_dirty_buffers); bind(context, 'c', MDFR_ALT, open_color_tweaker); -bind(context, 'd', MDFR_ALT, open_debug); bind(context, '.', MDFR_ALT, change_to_build_panel); bind(context, ',', MDFR_ALT, close_build_panel); bind(context, 'n', MDFR_ALT, goto_next_jump_no_skips_sticky); @@ -172,7 +171,6 @@ bind(context, 'h', MDFR_CMND, project_go_to_root_directory); bind(context, 'H', MDFR_CMND, reload_current_project); bind(context, 'S', MDFR_CMND, save_all_dirty_buffers); bind(context, 'c', MDFR_CTRL, open_color_tweaker); -bind(context, 'd', MDFR_CTRL, open_debug); bind(context, '.', MDFR_CTRL, change_to_build_panel); bind(context, ',', MDFR_CTRL, close_build_panel); bind(context, 'n', MDFR_CTRL, goto_next_jump_sticky); @@ -344,7 +342,7 @@ Meta_Sub_Map *sub_maps; int32_t sub_map_count; LINK_PROCS(void (*fill_keys_proc)(Bind_Helper *context);) }; -static Meta_Key_Bind fcoder_binds_for_default_mapid_global[48] = { +static Meta_Key_Bind fcoder_binds_for_default_mapid_global[47] = { {0, 112, 1, "open_panel_vsplit", 17, LINK_PROCS(open_panel_vsplit)}, {0, 95, 1, "open_panel_hsplit", 17, LINK_PROCS(open_panel_hsplit)}, {0, 80, 1, "close_panel", 11, LINK_PROCS(close_panel)}, @@ -359,7 +357,6 @@ static Meta_Key_Bind fcoder_binds_for_default_mapid_global[48] = { {0, 72, 1, "reload_current_project", 22, LINK_PROCS(reload_current_project)}, {0, 83, 1, "save_all_dirty_buffers", 22, LINK_PROCS(save_all_dirty_buffers)}, {0, 99, 2, "open_color_tweaker", 18, LINK_PROCS(open_color_tweaker)}, -{0, 100, 2, "open_debug", 10, LINK_PROCS(open_debug)}, {0, 46, 2, "change_to_build_panel", 21, LINK_PROCS(change_to_build_panel)}, {0, 44, 2, "close_build_panel", 17, LINK_PROCS(close_build_panel)}, {0, 110, 2, "goto_next_jump_no_skips_sticky", 30, LINK_PROCS(goto_next_jump_no_skips_sticky)}, @@ -499,11 +496,11 @@ static Meta_Key_Bind fcoder_binds_for_default_default_code_map[32] = { {0, 73, 1, "list_all_functions_current_buffer", 33, LINK_PROCS(list_all_functions_current_buffer)}, }; static Meta_Sub_Map fcoder_submaps_for_default[3] = { -{"mapid_global", 12, "The following bindings apply in all situations.", 47, 0, 0, fcoder_binds_for_default_mapid_global, 48}, +{"mapid_global", 12, "The following bindings apply in all situations.", 47, 0, 0, fcoder_binds_for_default_mapid_global, 47}, {"mapid_file", 10, "The following bindings apply in general text files and most apply in code files, but some are overriden by other commands specific to code files.", 145, 0, 0, fcoder_binds_for_default_mapid_file, 68}, {"default_code_map", 16, "The following commands only apply in files where the lexer (syntax highlighting) is turned on.", 94, "mapid_file", 10, fcoder_binds_for_default_default_code_map, 32}, }; -static Meta_Key_Bind fcoder_binds_for_mac_default_mapid_global[48] = { +static Meta_Key_Bind fcoder_binds_for_mac_default_mapid_global[47] = { {0, 112, 4, "open_panel_vsplit", 17, LINK_PROCS(open_panel_vsplit)}, {0, 95, 4, "open_panel_hsplit", 17, LINK_PROCS(open_panel_hsplit)}, {0, 80, 4, "close_panel", 11, LINK_PROCS(close_panel)}, @@ -518,7 +515,6 @@ static Meta_Key_Bind fcoder_binds_for_mac_default_mapid_global[48] = { {0, 72, 4, "reload_current_project", 22, LINK_PROCS(reload_current_project)}, {0, 83, 4, "save_all_dirty_buffers", 22, LINK_PROCS(save_all_dirty_buffers)}, {0, 99, 1, "open_color_tweaker", 18, LINK_PROCS(open_color_tweaker)}, -{0, 100, 1, "open_debug", 10, LINK_PROCS(open_debug)}, {0, 46, 1, "change_to_build_panel", 21, LINK_PROCS(change_to_build_panel)}, {0, 44, 1, "close_build_panel", 17, LINK_PROCS(close_build_panel)}, {0, 110, 1, "goto_next_jump_sticky", 21, LINK_PROCS(goto_next_jump_sticky)}, @@ -656,7 +652,7 @@ static Meta_Key_Bind fcoder_binds_for_mac_default_default_code_map[32] = { {0, 73, 4, "list_all_functions_current_buffer", 33, LINK_PROCS(list_all_functions_current_buffer)}, }; static Meta_Sub_Map fcoder_submaps_for_mac_default[3] = { -{"mapid_global", 12, "The following bindings apply in all situations.", 47, 0, 0, fcoder_binds_for_mac_default_mapid_global, 48}, +{"mapid_global", 12, "The following bindings apply in all situations.", 47, 0, 0, fcoder_binds_for_mac_default_mapid_global, 47}, {"mapid_file", 10, "The following bindings apply in general text files and most apply in code files, but some are overriden by other commands specific to code files.", 145, 0, 0, fcoder_binds_for_mac_default_mapid_file, 66}, {"default_code_map", 16, "The following commands only apply in files where the lexer (syntax highlighting) is turned on.", 94, "mapid_file", 10, fcoder_binds_for_mac_default_default_code_map, 32}, }; diff --git a/4ed.cpp b/4ed.cpp index 62603859..ae3525ab 100644 --- a/4ed.cpp +++ b/4ed.cpp @@ -371,7 +371,7 @@ internal View* panel_make_empty(System_Functions *system, Models *models, Panel *panel){ Assert(panel->view == 0); View_And_ID new_view = live_set_alloc_view(&models->live_set, panel, models); - view_set_file(system, new_view.view, models->scratch_buffer, models); + view_set_file(system, models, new_view.view, models->scratch_buffer); new_view.view->transient.map = models->scratch_buffer->settings.base_map_id; return(new_view.view); } @@ -475,10 +475,10 @@ COMMAND_DECL(reopen){ } file_free(system, general, file); - init_normal_file(system, models, file, buffer, size); + init_normal_file(system, models, buffer, size, file); for (i32 i = 0; i < vptr_count; ++i){ - view_set_file(system, vptrs[i], file, models); + view_set_file(system, models, vptrs[i], file); int32_t line = line_number[i]; int32_t character = column_number[i]; @@ -515,14 +515,12 @@ COMMAND_DECL(save){ COMMAND_DECL(interactive_switch_buffer){ USE_MODELS(models); USE_VIEW(view); - view_show_interactive(system, view, models, IAct_Switch, IInt_Live_File_List, make_lit_string("Switch Buffer: ")); } COMMAND_DECL(interactive_kill_buffer){ USE_MODELS(models); USE_VIEW(view); - view_show_interactive(system, view, models, IAct_Kill, IInt_Live_File_List, make_lit_string("Kill Buffer: ")); } @@ -530,8 +528,9 @@ COMMAND_DECL(kill_buffer){ USE_MODELS(models); USE_VIEW(view); REQ_FILE(file, view); - - interactive_try_kill_file(system, models, view, file); + if (interactive_try_kill_file(system, models, file) == TryKill_NeedDialogue){ + interactive_begin_sure_to_kill(system, view, models, file); + } } internal void @@ -567,20 +566,19 @@ case_change_range(System_Functions *system, Models *models, View *view, Editing_ COMMAND_DECL(open_color_tweaker){ USE_VIEW(view); - USE_MODELS(models); - view_show_theme(view, models); -} - -COMMAND_DECL(open_debug){ - USE_VIEW(view); - USE_MODELS(models); - view_show_GUI(view, models, VUI_Debug); - view->transient.debug_vars = null_debug_vars; + view->transient.map = mapid_ui; + view->transient.showing_ui = VUI_Theme; + view->transient.color_mode = CV_Mode_Library; + view->transient.color = super_color_create(0xFF000000); + view->transient.current_color_editing = 0; + view->transient.changed_context_in_step = true; } COMMAND_DECL(user_callback){ USE_MODELS(models); - if (binding.custom) binding.custom(&models->app_links); + if (binding.custom != 0){ + binding.custom(&models->app_links); + } } global Command_Function *command_table[cmdid_count]; @@ -981,7 +979,6 @@ setup_command_table(){ SET(kill_buffer); SET(open_color_tweaker); - SET(open_debug); #undef SET } @@ -1403,13 +1400,12 @@ App_Init_Sig(app_init){ cmd->key = null_key_event_data; - General_Memory *general = &models->mem.general; - File_Init init_files[] = { { make_lit_string("*messages*"), &models->message_buffer, true , }, - { make_lit_string("*scratch*"), &models->scratch_buffer, false, } + { make_lit_string("*scratch*"), &models->scratch_buffer, false, }, }; + General_Memory *general = &models->mem.general; for (i32 i = 0; i < ArrayCount(init_files); ++i){ Editing_File *file = working_set_alloc_always(&models->working_set, general); buffer_bind_name(models, general, partition, &models->working_set, file, init_files[i].name); @@ -1418,7 +1414,7 @@ App_Init_Sig(app_init){ init_read_only_file(system, models, file); } else{ - init_normal_file(system, models, file, 0, 0); + init_normal_file(system, models, 0, 0, file); } file->settings.never_kill = true; @@ -1583,7 +1579,8 @@ App_Step_Sig(app_step){ for (;system->get_file_change(buffer, buffer_size, &mem_too_small, &size);){ Assert(!mem_too_small); Editing_File_Name canon = {0}; - if (get_canon_name(system, &canon, make_string(buffer, size))){ + if (get_canon_name(system, make_string(buffer, size), + &canon)){ Editing_File *file = working_set_contains_canon(working_set, canon.name); if (file != 0){ if (file->state.ignore_behind_os == 0){ @@ -1799,7 +1796,8 @@ App_Step_Sig(app_step){ String filename = {0}; Editing_File_Name canon_name = {0}; - if (get_canon_name(system, &canon_name, make_string_slowly(models->settings.init_files[i]))){ + if (get_canon_name(system, make_string_slowly(models->settings.init_files[i]), + &canon_name)){ filename = canon_name.name; } else{ diff --git a/4ed_api_implementation.cpp b/4ed_api_implementation.cpp index 8eef5ca6..4c6f9cb6 100644 --- a/4ed_api_implementation.cpp +++ b/4ed_api_implementation.cpp @@ -282,15 +282,19 @@ DOC_SEE(Command_Line_Interface_Flag) } // NOTE(allen): If the buffer is specified by name but does not already exist, then create it. - if (file == 0 && buffer_id.name){ + if (file == 0 && buffer_id.name != 0){ file = working_set_alloc_always(working_set, general); + Assert(file != 0); + +#if 0 if (file == 0){ append(&feedback_str, make_lit_string("ERROR: unable to allocate a new buffer\n")); result = false; goto done; } +#endif - String name = make_string_terminated(part, buffer_id.name, buffer_id.name_len); + String name = push_string(part, buffer_id.name, buffer_id.name_len); buffer_bind_name(models, general, part, working_set, file, name); init_read_only_file(system, models, file); } @@ -336,7 +340,7 @@ DOC_SEE(Command_Line_Interface_Flag) if (bind_to_new_view){ View *vptr = imp_get_view(cmd, view); if (vptr != 0){ - view_set_file(system, vptr, file, models); + view_set_file(system, models, vptr, file); view_show_file(vptr); } } @@ -349,7 +353,7 @@ DOC_SEE(Command_Line_Interface_Flag) path_string = models->hot_directory.string; } else{ - path_string = make_string_terminated(part, path, path_len); + path_string = push_string(part, path, path_len); } // NOTE(allen): Figure out the command string. @@ -358,7 +362,7 @@ DOC_SEE(Command_Line_Interface_Flag) command_string = make_lit_string(" echo no script specified"); } else{ - command_string = make_string_terminated(part, command, command_len); + command_string = push_string(part, command, command_len); } // NOTE(allen): Attept to execute the command. @@ -619,7 +623,8 @@ DOC_SEE(Access_Flag) String fname = make_string(name, len); Editing_File_Name canon = {0}; - if (get_canon_name(system, &canon, fname)){ + if (get_canon_name(system, fname, + &canon)){ Editing_File *file = working_set_contains_canon(working_set, canon.name); fill_buffer_summary(&buffer, file, working_set); if (!access_test(buffer.lock_flags, access)){ @@ -770,7 +775,10 @@ DOC_SEE(Buffer_Batch_Edit_Type) char *inv_str = (char*)part->base + part->pos; int32_t inv_str_max = part->max - part->pos; - Edit_Spec spec = file_compute_edit(mem, file, edits, str, str_len, inverse_edits, inv_str, inv_str_max, edit_count, type); + Edit_Spec spec = edit_compute_batch_spec(&mem->general, + file, + edits, str, str_len, + inverse_edits, inv_str, inv_str_max, edit_count, type); edit_batch(system, models, file, spec, hist_normal, type); @@ -1063,7 +1071,7 @@ DOC_SEE(Buffer_Setting_ID) Font_Pointers font = system->font.get_pointers_by_id(file->settings.font_id); file->settings.display_width = new_value; file_measure_wraps(system, &models->mem, file, font); - adjust_views_looking_at_files_to_new_cursor(system, models, file); + adjust_views_looking_at_file_to_new_cursor(system, models, file); } }break; @@ -1077,7 +1085,7 @@ DOC_SEE(Buffer_Setting_ID) Font_Pointers font = system->font.get_pointers_by_id(file->settings.font_id); file->settings.minimum_base_display_width = new_value; file_measure_wraps(system, &models->mem, file, font); - adjust_views_looking_at_files_to_new_cursor(system, models, file); + adjust_views_looking_at_file_to_new_cursor(system, models, file); } }break; @@ -1167,7 +1175,7 @@ DOC_SEE(Buffer_Setting_ID) file_allocate_character_starts_as_needed(&models->mem.general, file); buffer_measure_character_starts(system, font, &file->state.buffer, file->state.character_starts, 0, file->settings.virtual_white); file_measure_wraps(system, &models->mem, file, font); - adjust_views_looking_at_files_to_new_cursor(system, models, file); + adjust_views_looking_at_file_to_new_cursor(system, models, file); } }break; @@ -1303,7 +1311,7 @@ DOC_SEE(Buffer_Create_Flag) Editing_File *file = 0; b32 do_new_file = false; Editing_File_Name canon = {0}; - if (get_canon_name(system, &canon, fname)){ + if (get_canon_name(system, fname, &canon)){ file = working_set_contains_canon(working_set, canon.name); } else{ @@ -1321,7 +1329,7 @@ DOC_SEE(Buffer_Create_Flag) // NOTE(allen): Figure out whether this is a new file, or an existing file. if (!do_new_file){ - if (flags & BufferCreate_AlwaysNew){ + if ((flags & BufferCreate_AlwaysNew) != 0){ do_new_file = true; } else{ @@ -1332,11 +1340,11 @@ DOC_SEE(Buffer_Create_Flag) } if (do_new_file){ - if (!(flags & BufferCreate_NeverNew)){ + if ((flags & BufferCreate_NeverNew) == 0){ file = working_set_alloc_always(working_set, general); if (file != 0){ - buffer_bind_name(models, general, part, working_set, file, fname); - init_normal_file(system, models, file, 0, 0); + buffer_bind_name(models, general, part, working_set, file, front_of_directory(fname)); + init_normal_file(system, models, 0, 0, file); fill_buffer_summary(&result, file, cmd); } } @@ -1359,8 +1367,8 @@ DOC_SEE(Buffer_Create_Flag) file = working_set_alloc_always(working_set, general); if (file != 0){ buffer_bind_file(system, general, working_set, file, canon.name); - buffer_bind_name(models, general, part, working_set, file, fname); - init_normal_file(system, models, file, buffer, size); + buffer_bind_name(models, general, part, working_set, file, front_of_directory(fname)); + init_normal_file(system, models, buffer, size, file); fill_buffer_summary(&result, file, cmd); } } @@ -1417,7 +1425,7 @@ DOC_SEE(Buffer_Save_Flag) Partition *part = &models->mem.part; Temp_Memory temp = begin_temp_memory(part); - String name = make_string_terminated(part, file_name, file_name_len); + String name = push_string(part, file_name, file_name_len); save_file_to_name(system, models, file, name.str); end_temp_memory(temp); } @@ -1444,26 +1452,25 @@ DOC_SEE(Buffer_Identifier) Command_Data *cmd = (Command_Data*)app->cmd_context; System_Functions *system = cmd->system; Models *models = cmd->models; - Working_Set *working_set = &models->working_set; - View *vptr = imp_get_view(cmd, view_id); - Editing_File *file = get_file_from_identifier(system, working_set, buffer); - int32_t result = false; - if (file){ - if (flags & BufferKill_AlwaysKill){ + bool32 result = false; + Working_Set *working_set = &models->working_set; + Editing_File *file = get_file_from_identifier(system, working_set, buffer); + if (file != 0){ + if ((flags & BufferKill_AlwaysKill) != 0){ result = true; - kill_file(system, models, file); + kill_file_and_update_views(system, models, file); } else{ Try_Kill_Result kill_result = interactive_try_kill_file(system, models, file); if (kill_result == TryKill_NeedDialogue){ - if (vptr){ + View *vptr = imp_get_view(cmd, view_id); + if (vptr != 0){ interactive_begin_sure_to_kill(system, vptr, models, file); } else{ -#define MESSAGE "CUSTOM WARNING: the buffer is dirty and no view was specified for a dialogue.\n" - print_message(app, literal(MESSAGE)); -#undef MESSAGE + char m[] = "WARNING: the buffer is dirty and no view was specified for a dialogue.\n"; + print_message(app, m, sizeof(m) - 1); } } else{ @@ -2079,7 +2086,7 @@ DOC_SEE(Set_Buffer_Flag) if (file != 0){ result = true; if (file != vptr->transient.file_data.file){ - view_set_file(system, vptr, file, models); + view_set_file(system, models, vptr, file); if (!(flags & SetBuffer_KeepOriginalGUI)){ view_show_file(vptr); } @@ -2341,7 +2348,7 @@ DOC_RETURN(Returns true if the given id was a valid face and the change was made Models *models = cmd->models; if (apply_to_all_buffers){ - global_set_font(system, models, id); + global_set_font_and_update_files(system, models, id); } else{ models->global_font_id = id; @@ -2543,7 +2550,7 @@ DOC_SEE(try_create_new_face) Font_Settings settings; if (face_description_to_settings(system, *description, &settings)){ Models *models = cmd->models; - if (alter_font(system, models, id, &settings)){ + if (alter_font_and_update_files(system, models, id, &settings)){ success = true; } } @@ -2567,12 +2574,7 @@ DOC_RETURN(Returns true on success and zero on failure.) Command_Data *cmd = (Command_Data*)app->cmd_context; System_Functions *system = cmd->system; Models *models = cmd->models; - - bool32 success = false; - if (release_font(system, models, id, replacement_id)){ - success = true; - } - + bool32 success = release_font_and_update_files(system, models, id, replacement_id); return(success); } @@ -2707,7 +2709,7 @@ DOC_SEE(File_List) Partition *part = &cmd->models->mem.part; File_List result = {}; Temp_Memory temp = begin_temp_memory(part); - String str = make_string_terminated(part, dir, len); + String str = push_string(part, dir, len); system->set_file_list(&result, str.str, 0, 0, 0); end_temp_memory(temp); return(result); diff --git a/4ed_app_target.cpp b/4ed_app_target.cpp index 392664c7..89f52185 100644 --- a/4ed_app_target.cpp +++ b/4ed_app_target.cpp @@ -63,6 +63,7 @@ #include "4ed_view.h" #include "4ed_app_models.h" +#include "4ed_parse_context.cpp" #include "4ed_font.cpp" #include "4ed_translation.cpp" #include "4ed_render_target.cpp" @@ -70,12 +71,11 @@ #include "4ed_command.cpp" #include "4ed_buffer.cpp" #include "4ed_undo.cpp" +#include "4ed_file_lex.cpp" #include "4ed_file.cpp" #include "4ed_code_wrap.cpp" #include "4ed_working_set.cpp" #include "4ed_hot_directory.cpp" -#include "4ed_parse_context.cpp" -#include "4ed_file_lex.cpp" #include "4ed_cli.cpp" #include "4ed_gui.cpp" #include "4ed_layout.cpp" diff --git a/4ed_file.cpp b/4ed_file.cpp index 6404d042..3afdec3b 100644 --- a/4ed_file.cpp +++ b/4ed_file.cpp @@ -681,5 +681,39 @@ file_free(System_Functions *system, General_Memory *general, Editing_File *file) } } +internal void +init_normal_file(System_Functions *system, Models *models, + char *buffer, i32 size, + Editing_File *file){ + PRFL_FUNC_GROUP(); + + String val = make_string(buffer, size); + file_create_from_string(system, models, file, val, 0); + + if (file->settings.tokens_exist && file->state.token_array.tokens == 0){ + if (!file->settings.virtual_white){ + file_first_lex_parallel(system, models, file); + } + else{ + file_first_lex_serial(models, file); + } + } +} + +internal void +init_read_only_file(System_Functions *system, Models *models, Editing_File *file){ + String val = null_string; + file_create_from_string(system, models, file, val, FileCreateFlag_ReadOnly); + + if (file->settings.tokens_exist && file->state.token_array.tokens == 0){ + if (!file->settings.virtual_white){ + file_first_lex_parallel(system, models, file); + } + else{ + file_first_lex_serial(models, file); + } + } +} + // BOTTOM diff --git a/4ed_font.h b/4ed_font.h index ec1f863e..e4ad6d0c 100644 --- a/4ed_font.h +++ b/4ed_font.h @@ -41,7 +41,7 @@ struct Font_Settings{ Font_Parameters parameters; }; -// NOTE(allen): Results about the font true for the entire font as a whole. +// NOTE(allen): Data about the font true for the entire font as a whole. struct Font_Metrics{ i32 name_len; char name[256]; diff --git a/4ed_view.cpp b/4ed_view.cpp index 3ce9f580..0f83cd4d 100644 --- a/4ed_view.cpp +++ b/4ed_view.cpp @@ -87,6 +87,22 @@ view_compute_max_target_y(View *view){ return(ceil32(max_target_y)); } +inline u32 +view_lock_flags(View *view){ + u32 result = AccessOpen; + File_Viewing_Data *data = &view->transient.file_data; + if (view->transient.showing_ui != VUI_None){ + result |= AccessHidden; + } + if (data->file_locked || + (data->file && data->file->settings.read_only)){ + result |= AccessProtected; + } + return(result); +} + +//////////////////////////////// + internal b32 view_move_view_to_cursor(View *view, GUI_Scroll_Vars *scroll, b32 center_view){ b32 result = 0; @@ -219,20 +235,27 @@ view_set_temp_highlight(System_Functions *system, View *view, i32 pos, i32 end_p view_set_cursor(view, view->transient.file_data.temp_highlight, 0, file->settings.unwrapped_lines); } -inline u32 -view_lock_flags(View *view){ - u32 result = AccessOpen; - File_Viewing_Data *data = &view->transient.file_data; - if (view->transient.showing_ui != VUI_None){ - result |= AccessHidden; - } - if (data->file_locked || - (data->file && data->file->settings.read_only)){ - result |= AccessProtected; - } - return(result); +inline void +view_cursor_move(System_Functions *system, View *view, i32 pos){ + Editing_File *file = view->transient.file_data.file; + Assert(file != 0); + Full_Cursor cursor = file_compute_cursor(system, file, seek_pos(pos), 0); + view_set_cursor(view, cursor, true, file->settings.unwrapped_lines); + view->transient.file_data.show_temp_highlight = false; } +inline void +view_post_paste_effect(View *view, f32 seconds, i32 start, i32 size, u32 color){ + Editing_File *file = view->transient.file_data.file; + file->state.paste_effect.start = start; + file->state.paste_effect.end = start + size; + file->state.paste_effect.color = color; + file->state.paste_effect.seconds_down = seconds; + file->state.paste_effect.seconds_max = seconds; +} + +//////////////////////////////// + internal b32 file_is_viewed(Editing_Layout *layout, Editing_File *file){ b32 is_viewed = false; @@ -248,10 +271,8 @@ file_is_viewed(Editing_Layout *layout, Editing_File *file){ return(is_viewed); } -//////////////////////////////// - internal void -adjust_views_looking_at_files_to_new_cursor(System_Functions *system, Models *models, Editing_File *file){ +adjust_views_looking_at_file_to_new_cursor(System_Functions *system, Models *models, Editing_File *file){ Editing_Layout *layout = &models->layout; for (Panel *panel = layout->used_sentinel.next; @@ -274,24 +295,89 @@ adjust_views_looking_at_files_to_new_cursor(System_Functions *system, Models *mo } } -//////////////////////////////// +internal void +file_full_remeasure(System_Functions *system, Models *models, Editing_File *file){ + Face_ID font_id = file->settings.font_id; + Font_Pointers font = system->font.get_pointers_by_id(font_id); + file_measure_wraps(system, &models->mem, file, font); + adjust_views_looking_at_file_to_new_cursor(system, models, file); + + Editing_Layout *layout = &models->layout; + + for (Panel *panel = layout->used_sentinel.next; + panel != &layout->used_sentinel; + panel = panel->next){ + View *view = panel->view; + if (view->transient.file_data.file == file){ + view->transient.line_height = font.metrics->height; + } + } +} internal void -update_view_line_height(System_Functions *system, Models *models, View *view, Face_ID font_id){ - Font_Pointers font = system->font.get_pointers_by_id(font_id); - Assert(font.valid); - view->transient.line_height = font.metrics->height; +file_set_font(System_Functions *system, Models *models, Editing_File *file, Face_ID font_id){ + file->settings.font_id = font_id; + file_full_remeasure(system, models, file); } -inline void -view_cursor_move(System_Functions *system, View *view, i32 pos){ - Editing_File *file = view->transient.file_data.file; - Assert(file != 0); - Full_Cursor cursor = file_compute_cursor(system, file, seek_pos(pos), 0); - view_set_cursor(view, cursor, true, file->settings.unwrapped_lines); - view->transient.file_data.show_temp_highlight = false; +internal void +global_set_font_and_update_files(System_Functions *system, Models *models, Face_ID font_id){ + for (File_Node *node = models->working_set.used_sentinel.next; + node != &models->working_set.used_sentinel; + node = node->next){ + Editing_File *file = (Editing_File*)node; + file_set_font(system, models, file, font_id); + } + models->global_font_id = font_id; } +internal b32 +alter_font_and_update_files(System_Functions *system, Models *models, Face_ID font_id, Font_Settings *new_settings){ + b32 success = false; + if (system->font.face_change_settings(font_id, new_settings)){ + success = true; + for (File_Node *node = models->working_set.used_sentinel.next; + node != &models->working_set.used_sentinel; + node = node->next){ + Editing_File *file = (Editing_File*)node; + if (file->settings.font_id == font_id){ + file_full_remeasure(system, models, file); + } + } + } + return(success); +} + +internal b32 +release_font_and_update_files(System_Functions *system, Models *models, Face_ID font_id, Face_ID replacement_id){ + b32 success = false; + if (system->font.face_release(font_id)){ + Font_Pointers font = system->font.get_pointers_by_id(replacement_id); + if (!font.valid){ + Face_ID largest_id = system->font.get_largest_id(); + for (replacement_id = 1; replacement_id <= largest_id && replacement_id > 0; ++replacement_id){ + font = system->font.get_pointers_by_id(replacement_id); + if (font.valid){ + break; + } + } + Assert(replacement_id <= largest_id && replacement_id > 0); + } + success = true; + for (File_Node *node = models->working_set.used_sentinel.next; + node != &models->working_set.used_sentinel; + node = node->next){ + Editing_File *file = (Editing_File*)node; + if (file->settings.font_id == font_id){ + file_set_font(system, models, file, replacement_id); + } + } + } + return(success); +} + +//////////////////////////////// + inline void view_show_file(View *view){ Editing_File *file = view->transient.file_data.file; @@ -303,8 +389,23 @@ view_show_file(View *view){ } } +inline void +view_show_interactive(System_Functions *system, View *view, Models *models, Interactive_Action action, Interactive_Interaction interaction, String query){ + view->transient.showing_ui = VUI_Interactive; + view->transient.action = action; + view->transient.interaction = interaction; + view->transient.dest = make_fixed_width_string(view->transient.dest_); + view->transient.list_i = 0; + + view->transient.map = mapid_ui; + + hot_directory_clean_end(&models->hot_directory); + hot_directory_reload(system, &models->hot_directory); + view->transient.changed_context_in_step = true; +} + internal void -view_set_file(System_Functions *system, View *view, Editing_File *file, Models *models){ +view_set_file(System_Functions *system, Models *models, View *view, Editing_File *file){ Assert(file != 0); if (view->transient.file_data.file != 0){ @@ -324,7 +425,8 @@ view_set_file(System_Functions *system, View *view, Editing_File *file, Models * edit_pos = edit_pos_get_new(file, view->persistent.id); view->transient.edit_pos = edit_pos; - update_view_line_height(system, models, view, file->settings.font_id); + Font_Pointers font = system->font.get_pointers_by_id(file->settings.font_id); + view->transient.line_height = font.metrics->height; if (edit_pos->cursor.line == 0){ view_cursor_move(system, view, 0); @@ -355,24 +457,7 @@ view_set_relative_scrolling(View *view, Relative_Scrolling scrolling){ } } -inline i32_Rect -view_widget_rect(View *view, i32 line_height){ - Assert(view->transient.file_data.file); - Panel *panel = view->transient.panel; - i32_Rect result = panel->inner; - result.y0 = result.y0 + line_height + 2; - return(result); -} - -inline void -view_post_paste_effect(View *view, f32 seconds, i32 start, i32 size, u32 color){ - Editing_File *file = view->transient.file_data.file; - file->state.paste_effect.start = start; - file->state.paste_effect.end = start + size; - file->state.paste_effect.color = color; - file->state.paste_effect.seconds_down = seconds; - file->state.paste_effect.seconds_max = seconds; -} +//////////////////////////////// inline void edit_pre_maintenance(System_Functions *system, General_Memory *general, Editing_File *file){ @@ -573,8 +658,48 @@ edit_single__inner(System_Functions *system, Models *models, Editing_File *file, edit_fix_marks(system, models, file, layout, desc); } +inline void +edit_single(System_Functions *system, Models *models, Editing_File *file, + i32 start, i32 end, char *str, i32 len){ + Edit_Spec spec = {}; + spec.step.type = ED_NORMAL; + spec.step.edit.start = start; + spec.step.edit.end = end; + spec.step.edit.len = len; + spec.str = (u8*)str; + edit_single__inner(system, models, file, spec, + hist_normal); +} + +internal Edit_Spec +edit_compute_batch_spec(General_Memory *general, + Editing_File *file, + Buffer_Edit *edits, char *str_base, i32 str_size, + Buffer_Edit *inverse_array, char *inv_str, i32 inv_max, i32 edit_count, i32 batch_type){ + + i32 inv_str_pos = 0; + Buffer_Invert_Batch state = {}; + if (buffer_invert_batch(&state, &file->state.buffer, edits, edit_count, + inverse_array, inv_str, &inv_str_pos, inv_max)){ + InvalidCodePath; + } + + i32 first_child = undo_children_push(general, &file->state.undo.children, edits, edit_count, (u8*)(str_base), str_size); + i32 inverse_first_child = undo_children_push(general, &file->state.undo.children, inverse_array, edit_count, (u8*)(inv_str), inv_str_pos); + + Edit_Spec spec = {}; + spec.step.type = ED_NORMAL; + spec.step.first_child = first_child; + spec.step.inverse_first_child = inverse_first_child; + spec.step.special_type = batch_type; + spec.step.child_count = edit_count; + spec.step.inverse_child_count = edit_count; + return(spec); +} + internal void -edit_batch(System_Functions *system, Models *models, Editing_File *file, Edit_Spec spec, History_Mode history_mode, i32 batch_type){ +edit_batch(System_Functions *system, Models *models, Editing_File *file, + Edit_Spec spec, History_Mode history_mode, Buffer_Batch_Edit_Type batch_type){ Mem_Options *mem = &models->mem; General_Memory *general = &mem->general; @@ -687,19 +812,6 @@ edit_batch(System_Functions *system, Models *models, Editing_File *file, Edit_Sp edit_fix_marks(system, models, file, layout, desc); } -inline void -edit_single(System_Functions *system, Models *models, Editing_File *file, - i32 start, i32 end, char *str, i32 len){ - Edit_Spec spec = {}; - spec.step.type = ED_NORMAL; - spec.step.edit.start = start; - spec.step.edit.end = end; - spec.step.edit.len = len; - spec.str = (u8*)str; - edit_single__inner(system, models, file, spec, - hist_normal); -} - inline void edit_clear(System_Functions *system, Models *models, Editing_File *file){ if (models->hook_end_file != 0){ @@ -735,498 +847,10 @@ edit_historical(System_Functions *system, Models *models, Editing_File *file, Vi } } -internal String* -working_set_next_clipboard_string(General_Memory *general, Working_Set *working, i32 str_size){ - String *result = 0; - i32 clipboard_current = working->clipboard_current; - if (working->clipboard_size == 0){ - clipboard_current = 0; - working->clipboard_size = 1; - } - else{ - ++clipboard_current; - if (clipboard_current >= working->clipboard_max_size){ - clipboard_current = 0; - } - else if (working->clipboard_size <= clipboard_current){ - working->clipboard_size = clipboard_current+1; - } - } - result = &working->clipboards[clipboard_current]; - working->clipboard_current = clipboard_current; - working->clipboard_rolling = clipboard_current; - char *new_str; - if (result->str){ - new_str = (char*)general_memory_reallocate(general, result->str, result->size, str_size); - } - else{ - new_str = (char*)general_memory_allocate(general, str_size+1); - } - // TODO(allen): What if new_str == 0? - *result = make_string_cap(new_str, 0, str_size); - return result; -} - -internal String* -working_set_clipboard_index(Working_Set *working, i32 index){ - String *result = 0; - i32 size = working->clipboard_size; - i32 current = working->clipboard_current; - if (index >= 0 && size > 0){ - index = index % size; - index = current + size - index; - index = index % size; - result = &working->clipboards[index]; - } - return(result); -} - -internal String* -working_set_clipboard_head(Working_Set *working){ - String *result = 0; - if (working->clipboard_size > 0){ - working->clipboard_rolling = 0; - result = working_set_clipboard_index(working, working->clipboard_rolling); - } - return(result); -} - -internal String* -working_set_clipboard_roll_down(Working_Set *working){ - String *result = 0; - if (working->clipboard_size > 0){ - i32 clipboard_index = working->clipboard_rolling; - ++clipboard_index; - working->clipboard_rolling = clipboard_index; - result = working_set_clipboard_index(working, working->clipboard_rolling); - } - return(result); -} - -internal Edit_Spec -file_compute_edit(Mem_Options *mem, Editing_File *file, Buffer_Edit *edits, char *str_base, i32 str_size, Buffer_Edit *inverse_array, char *inv_str, i32 inv_max, i32 edit_count, i32 batch_type){ - General_Memory *general = &mem->general; - - i32 inv_str_pos = 0; - Buffer_Invert_Batch state = {}; - if (buffer_invert_batch(&state, &file->state.buffer, edits, edit_count, - inverse_array, inv_str, &inv_str_pos, inv_max)){ - Assert(0); - } - - i32 first_child = undo_children_push(general, &file->state.undo.children, edits, edit_count, (u8*)(str_base), str_size); - i32 inverse_first_child = undo_children_push(general, &file->state.undo.children, inverse_array, edit_count, (u8*)(inv_str), inv_str_pos); - - Edit_Spec spec = {}; - spec.step.type = ED_NORMAL; - spec.step.first_child = first_child; - spec.step.inverse_first_child = inverse_first_child; - spec.step.special_type = batch_type; - spec.step.child_count = edit_count; - spec.step.inverse_child_count = edit_count; - - return(spec); -} - -internal u32* -style_get_color(Style *style, Cpp_Token token){ - u32 *result; - if (token.flags & CPP_TFLAG_IS_KEYWORD){ - if (token.type == CPP_TOKEN_BOOLEAN_CONSTANT){ - result = &style->main.bool_constant_color; - } - else{ - result = &style->main.keyword_color; - } - } - else if(token.flags & CPP_TFLAG_PP_DIRECTIVE){ - result = &style->main.preproc_color; - } - else{ - switch (token.type){ - case CPP_TOKEN_COMMENT: - result = &style->main.comment_color; - break; - - case CPP_TOKEN_STRING_CONSTANT: - result = &style->main.str_constant_color; - break; - - case CPP_TOKEN_CHARACTER_CONSTANT: - result = &style->main.char_constant_color; - break; - - case CPP_TOKEN_INTEGER_CONSTANT: - result = &style->main.int_constant_color; - break; - - case CPP_TOKEN_FLOATING_CONSTANT: - result = &style->main.float_constant_color; - break; - - case CPP_PP_INCLUDE_FILE: - result = &style->main.include_color; - break; - - default: - result = &style->main.default_color; - break; - } - } - return result; -} +//////////////////////////////// internal void -file_full_remeasure(System_Functions *system, Models *models, Editing_File *file){ - Face_ID font_id = file->settings.font_id; - Font_Pointers font = system->font.get_pointers_by_id(font_id); - file_measure_wraps(system, &models->mem, file, font); - adjust_views_looking_at_files_to_new_cursor(system, models, file); - - Editing_Layout *layout = &models->layout; - - for (Panel *panel = layout->used_sentinel.next; - panel != &layout->used_sentinel; - panel = panel->next){ - View *view = panel->view; - if (view->transient.file_data.file == file){ - update_view_line_height(system, models, view, font_id); - } - } -} - -internal void -file_set_font(System_Functions *system, Models *models, Editing_File *file, Face_ID font_id){ - file->settings.font_id = font_id; - file_full_remeasure(system, models, file); -} - -internal void -global_set_font(System_Functions *system, Models *models, Face_ID font_id){ - for (File_Node *node = models->working_set.used_sentinel.next; - node != &models->working_set.used_sentinel; - node = node->next){ - Editing_File *file = (Editing_File*)node; - file_set_font(system, models, file, font_id); - } - models->global_font_id = font_id; -} - -internal b32 -alter_font(System_Functions *system, Models *models, Face_ID font_id, Font_Settings *new_settings){ - b32 success = false; - - if (system->font.face_change_settings(font_id, new_settings)){ - success = true; - - for (File_Node *node = models->working_set.used_sentinel.next; - node != &models->working_set.used_sentinel; - node = node->next){ - Editing_File *file = (Editing_File*)node; - if (file->settings.font_id == font_id){ - file_full_remeasure(system, models, file); - } - } - } - - return(success); -} - -internal b32 -release_font(System_Functions *system, Models *models, Face_ID font_id, Face_ID replacement_id){ - b32 success = false; - - if (system->font.face_release(font_id)){ - Font_Pointers font = system->font.get_pointers_by_id(replacement_id); - if (!font.valid){ - Face_ID largest_id = system->font.get_largest_id(); - for (replacement_id = 1; replacement_id <= largest_id && replacement_id > 0; ++replacement_id){ - font = system->font.get_pointers_by_id(replacement_id); - if (font.valid){ - break; - } - } - Assert(replacement_id <= largest_id && replacement_id > 0); - } - - success = true; - for (File_Node *node = models->working_set.used_sentinel.next; - node != &models->working_set.used_sentinel; - node = node->next){ - Editing_File *file = (Editing_File*)node; - if (file->settings.font_id == font_id){ - file_set_font(system, models, file, replacement_id); - } - } - } - - return(success); -} - -inline void -view_show_GUI(View *view, Models *models, View_UI ui){ - view->transient.map = mapid_ui; - view->transient.showing_ui = ui; - view->transient.changed_context_in_step = true; -} - -inline void -view_show_interactive(System_Functions *system, View *view, Models *models, Interactive_Action action, Interactive_Interaction interaction, String query){ - view->transient.showing_ui = VUI_Interactive; - view->transient.action = action; - view->transient.interaction = interaction; - view->transient.dest = make_fixed_width_string(view->transient.dest_); - view->transient.list_i = 0; - - view->transient.map = mapid_ui; - - hot_directory_clean_end(&models->hot_directory); - hot_directory_reload(system, &models->hot_directory); - view->transient.changed_context_in_step = true; -} - -inline void -view_show_theme(View *view, Models *models){ - view->transient.map = mapid_ui; - view->transient.showing_ui = VUI_Theme; - view->transient.color_mode = CV_Mode_Library; - view->transient.color = super_color_create(0xFF000000); - view->transient.current_color_editing = 0; - view->transient.changed_context_in_step = true; -} - -internal String -make_string_terminated(Partition *part, char *str, i32 len){ - char *space = (char*)push_array(part, char, len + 1); - String string = make_string_cap(str, len, len+1); - copy_fast_unsafe_cs(space, string); - string.str = space; - terminate_with_null(&string); - return(string); -} - -internal void -init_normal_file(System_Functions *system, Models *models, Editing_File *file, char *buffer, i32 size){ - PRFL_FUNC_GROUP(); - - String val = make_string(buffer, size); - file_create_from_string(system, models, file, val, 0); - - if (file->settings.tokens_exist && file->state.token_array.tokens == 0){ - if (!file->settings.virtual_white){ - file_first_lex_parallel(system, models, file); - } - else{ - file_first_lex_serial(models, file); - } - } -} - -internal void -init_read_only_file(System_Functions *system, Models *models, Editing_File *file){ - String val = null_string; - file_create_from_string(system, models, file, val, FileCreateFlag_ReadOnly); - - if (file->settings.tokens_exist && file->state.token_array.tokens == 0){ - if (!file->settings.virtual_white){ - file_first_lex_parallel(system, models, file); - } - else{ - file_first_lex_serial(models, file); - } - } -} - -internal char* -make_string_part(Partition *scratch, String src, int32_t *size_out){ - char *r = {0}; - if (src.size > 0){ - r = push_array(scratch, char, src.size); - *size_out = src.size; - memcpy(r, src.str, *size_out); - } - return(r); -} - -internal char* -make_string_part(Partition *scratch, String src, int32_t cap, int32_t *size_out, int32_t *cap_out){ - cap = clamp_bottom(src.size, cap); - char *r = 0; - if (src.size > 0){ - r = push_array(scratch, char, cap); - *size_out = src.size; - *cap_out = cap; - memcpy(r, src.str, *size_out); - } - return(r); -} - -internal void -buffer_bind_name(Models *models, General_Memory *general, Partition *scratch, Working_Set *working_set, Editing_File *file, String file_name){ - String base_name = front_of_directory(file_name); - - Temp_Memory temp = begin_temp_memory(scratch); - - // List of conflict files. - Editing_File **conflict_file_ptrs = push_array(scratch, Editing_File*, 0); - int32_t conflict_count = 0; - - { - ++conflict_count; - Editing_File **new_file_ptr = push_array(scratch, Editing_File*, 1); - *new_file_ptr = file; - } - - File_Node *used_nodes = &working_set->used_sentinel; - for (File_Node *node = used_nodes->next; node != used_nodes; node = node->next){ - Editing_File *file_ptr = (Editing_File*)node; - if (file_is_ready(file_ptr) && match(base_name, file_ptr->base_name.name)){ - ++conflict_count; - Editing_File **new_file_ptr = push_array(scratch, Editing_File*, 1); - *new_file_ptr = file_ptr; - } - } - - // Fill conflict array. - Buffer_Name_Conflict_Entry *conflicts = push_array(scratch, Buffer_Name_Conflict_Entry, conflict_count); - - for (int32_t i = 0; i < conflict_count; ++i){ - Editing_File *file_ptr = conflict_file_ptrs[i]; - Buffer_Name_Conflict_Entry *entry = &conflicts[i]; - entry->buffer_id = file_ptr->id.id; - entry->file_name = make_string_part(scratch, file_ptr->canon.name, &entry->file_name_len); - entry->base_name = make_string_part(scratch, base_name, &entry->base_name_len); - - String b = base_name; - if (i > 0){ - b = file_ptr->unique_name.name; - } - entry->unique_name_in_out = make_string_part(scratch, b, 256, &entry->unique_name_len_in_out, &entry->unique_name_capacity); - } - - // Get user's resolution data. - if (models->buffer_name_resolver != 0){ - models->buffer_name_resolver(&models->app_links, conflicts, conflict_count); - } - - // Re-bind all of the files - for (int32_t i = 0; i < conflict_count; ++i){ - Editing_File *file_ptr = conflict_file_ptrs[i]; - if (file_ptr->unique_name.name.str != 0){ - buffer_unbind_name_low_level(working_set, file_ptr); - } - } - for (int32_t i = 0; i < conflict_count; ++i){ - Editing_File *file_ptr = conflict_file_ptrs[i]; - Buffer_Name_Conflict_Entry *entry = &conflicts[i]; - - String unique_name = make_string(entry->unique_name_in_out, entry->unique_name_len_in_out); - - buffer_bind_name_low_level(general, working_set, file_ptr, base_name, unique_name); - } - - end_temp_memory(temp); -} - -internal Editing_File* -open_file(System_Functions *system, Models *models, String filename){ - Working_Set *working_set = &models->working_set; - Editing_File *file = 0; - - if (terminate_with_null(&filename)){ - Editing_File_Name canon_name = {0}; - if (get_canon_name(system, &canon_name, filename)){ - file = working_set_contains_canon(working_set, canon_name.name); - - if (file == 0){ - Plat_Handle handle; - if (system->load_handle(canon_name.name.str, &handle)){ - Mem_Options *mem = &models->mem; - General_Memory *general = &mem->general; - Partition *part = &mem->part; - - file = working_set_alloc_always(working_set, general); - - buffer_bind_file(system, general, working_set, file, canon_name.name); - buffer_bind_name(models, general, part, working_set, file, filename); - - i32 size = system->load_size(handle); - char *buffer = 0; - b32 gen_buffer = 0; - - Temp_Memory temp = begin_temp_memory(part); - - buffer = push_array(part, char, size); - if (buffer == 0){ - buffer = (char*)general_memory_allocate(general, size); - Assert(buffer); - gen_buffer = 1; - } - - if (system->load_file(handle, buffer, size)){ - system->load_close(handle); - init_normal_file(system, models, file, buffer, size); - } - else{ - system->load_close(handle); - } - - if (gen_buffer){ - general_memory_free(general, buffer); - } - - end_temp_memory(temp); - } - } - } - } - - return(file); -} - -internal void -view_open_file(System_Functions *system, Models *models, View *view, String filename){ - Editing_File *file = open_file(system, models, filename); - if (file){ - view_set_file(system, view, file, models); - } -} - -internal void -view_interactive_new_file(System_Functions *system, Models *models, View *view, String filename){ - Working_Set *working_set = &models->working_set; - Editing_File *file = 0; - - if (terminate_with_null(&filename)){ - Editing_File_Name canon_name = {0}; - if (get_canon_name(system, &canon_name, filename)){ - file = working_set_contains_canon(working_set, canon_name.name); - - if (file != 0){ - edit_clear(system, models, file); - } - else{ - Mem_Options *mem = &models->mem; - General_Memory *general = &mem->general; - Partition *part = &mem->part; - - file = working_set_alloc_always(working_set, general); - - buffer_bind_file(system, general, working_set, file, canon_name.name); - buffer_bind_name(models, general, part, working_set, file, filename); - - init_normal_file(system, models, file, 0, 0); - } - } - } - - if (file){ - view_set_file(system, view, file, models); - } -} - -internal void -kill_file(System_Functions *system, Models *models, Editing_File *file){ +kill_file_and_update_views(System_Functions *system, Models *models, Editing_File *file){ Working_Set *working_set = &models->working_set; if (file != 0 && !file->settings.never_kill){ @@ -1241,87 +865,47 @@ kill_file(System_Functions *system, Models *models, Editing_File *file){ file_free(system, &models->mem.general, file); working_set_free_file(&models->mem.general, working_set, file); - File_Node *used = &models->working_set.used_sentinel; + File_Node *used = &working_set->used_sentinel; File_Node *node = used->next; - - for (Panel *panel = models->layout.used_sentinel.next; panel != &models->layout.used_sentinel; panel = panel->next){ View *view = panel->view; - if (view->transient.file_data.file != file){ - continue; - } - if (node != used){ + if (view->transient.file_data.file == file){ + Assert(node != used); view->transient.file_data.file = 0; - view_set_file(system, view, (Editing_File*)node, models); - node = node->next; - } - else{ - view->transient.file_data.file = 0; - view_set_file(system, view, 0, models); + view_set_file(system, models, view, (Editing_File*)node); + if (node->next != used){ + node = node->next; + } + else{ + node = node->next->next; + Assert(node != used); + } } } } } -internal void -kill_file_by_name(System_Functions *system, Models *models, String name){ - Editing_File *file = working_set_contains_name(&models->working_set, name); - kill_file(system, models, file); -} - -internal void -save_file_by_name(System_Functions *system, Models *models, String name){ - Editing_File *file = working_set_contains_name(&models->working_set, name); - if (file != 0){ - save_file(system, models, file); - } -} - -internal void -interactive_begin_sure_to_kill(System_Functions *system, View *view, Models *models, Editing_File *file){ - view_show_interactive(system, view, models, IAct_Sure_To_Kill, IInt_Sure_To_Kill, make_lit_string("Are you sure?")); - copy_ss(&view->transient.dest, file->unique_name.name); -} - internal Try_Kill_Result interactive_try_kill_file(System_Functions *system, Models *models, Editing_File *file){ Try_Kill_Result result = TryKill_CannotKill; - if (!file->settings.never_kill){ if (buffer_needs_save(file)){ result = TryKill_NeedDialogue; } else{ - kill_file(system, models, file); + kill_file_and_update_views(system, models, file); result = TryKill_Success; } } - return(result); } -internal b32 -interactive_try_kill_file(System_Functions *system, Models *models, View *view, Editing_File *file){ - Try_Kill_Result kill_result = interactive_try_kill_file(system, models, file); - b32 result = (kill_result == TryKill_NeedDialogue); - if (result){ - interactive_begin_sure_to_kill(system, view, models, file); - } - return(result); -} - -internal b32 -interactive_try_kill_file_by_name(System_Functions *system, Models *models, View *view, String name){ - b32 kill_dialogue = 0; - - Editing_File *file = working_set_contains_name(&models->working_set, name); - if (file){ - kill_dialogue = interactive_try_kill_file(system, models, view, file); - } - - return(kill_dialogue); +internal void +interactive_begin_sure_to_kill(System_Functions *system, View *view, Models *models, Editing_File *file){ + view_show_interactive(system, view, models, IAct_Sure_To_Kill, IInt_Sure_To_Kill, make_lit_string("Are you sure?")); + copy(&view->transient.dest, file->unique_name.name); } internal void @@ -1329,152 +913,127 @@ interactive_view_complete(System_Functions *system, View *view, Models *models, switch (view->transient.action){ case IAct_Open: { - view_open_file(system, models, view, dest); + Editing_File *file = open_file(system, models, dest); + if (file != 0){ + view_set_file(system, models, view, file); + } view_show_file(view); }break; case IAct_New: - if (dest.size > 0 && !char_is_slash(dest.str[dest.size-1])){ - view_interactive_new_file(system, models, view, dest); - view_show_file(view); - if (models->hook_new_file != 0){ - Editing_File *file = view->transient.file_data.file; - models->hook_new_file(&models->app_links, file->id.id); - } - }break; - - case IAct_OpenOrNew: { - InvalidCodePath; + if (dest.size > 0 && !char_is_slash(dest.str[dest.size-1])){ + Editing_File *file = 0; + Editing_File_Name canon_name = {0}; + + if (terminate_with_null(&dest) && + get_canon_name(system, dest, &canon_name)){ + Working_Set *working_set = &models->working_set; + file = working_set_contains_canon(working_set, canon_name.name); + if (file == 0){ + Mem_Options *mem = &models->mem; + General_Memory *general = &mem->general; + Partition *part = &mem->part; + + file = working_set_alloc_always(working_set, general); + buffer_bind_file(system, general, working_set, file, canon_name.name); + buffer_bind_name(models, general, part, working_set, file, front_of_directory(dest)); + + init_normal_file(system, models, 0, 0, file); + } + else{ + edit_clear(system, models, file); + } + } + if (file != 0){ + view_set_file(system, models, view, file); + } + view_show_file(view); + if (file != 0 && models->hook_new_file != 0){ + models->hook_new_file(&models->app_links, file->id.id); + } + } }break; case IAct_Switch: { Editing_File *file = working_set_contains_name(&models->working_set, dest); if (file){ - view_set_file(system, view, file, models); + view_set_file(system, models, view, file); } view_show_file(view); }break; case IAct_Kill: - if (!interactive_try_kill_file_by_name(system, models, view, dest)){ - view_show_file(view); + { + b32 kill_dialogue = false; + Editing_File *file = working_set_contains_name(&models->working_set, dest); + if (file != 0){ + kill_dialogue = (interactive_try_kill_file(system, models, file) == TryKill_NeedDialogue); + if (kill_dialogue){ + interactive_begin_sure_to_kill(system, view, models, file); + } + } + if (!kill_dialogue){ + view_show_file(view); + } }break; case IAct_Sure_To_Close: - switch (user_action){ - case 0: - { - models->keep_playing = 0; - }break; - - case 1: - { - view_show_file(view); - }break; - - case 2: // TODO(allen): Save all and close. - break; + { + switch (user_action){ + case UnsavedChangesUserResponse_ContinueAnyway: + { + models->keep_playing = false; + }break; + + case UnsavedChangesUserResponse_Cancel: + { + view_show_file(view); + }break; + + // TODO(allen): Save all and close. + case UnsavedChangesUserResponse_SaveAndContinue: InvalidCodePath; + default: InvalidCodePath; + } }break; case IAct_Sure_To_Kill: - switch (user_action){ - case 0: - { - kill_file_by_name(system, models, dest); - view_show_file(view); - }break; - - case 1: - { - view_show_file(view); - }break; - - case 2: - { - save_file_by_name(system, models, dest); - kill_file_by_name(system, models, dest); - view_show_file(view); - }break; + { + switch (user_action){ + case UnsavedChangesUserResponse_ContinueAnyway: + { + Editing_File *file = working_set_contains_name(&models->working_set, dest); + if (file != 0){ + kill_file_and_update_views(system, models, file); + } + view_show_file(view); + }break; + + case UnsavedChangesUserResponse_Cancel: + { + view_show_file(view); + }break; + + case UnsavedChangesUserResponse_SaveAndContinue: + { + Editing_File *file = working_set_contains_name(&models->working_set, dest); + if (file != 0){ + save_file(system, models, file); + kill_file_and_update_views(system, models, file); + } + view_show_file(view); + }break; + + default: InvalidCodePath; + } }break; - } -} - -internal void -intbar_draw_string(System_Functions *system, Render_Target *target, File_Bar *bar, String str, u32 char_color){ - draw_string(system, target, bar->font_id, str, (i32)(bar->pos_x + bar->text_shift_x), (i32)(bar->pos_y + bar->text_shift_y), char_color); - bar->pos_x += font_string_width(system, target, bar->font_id, str); -} - -internal GUI_Scroll_Vars -view_reinit_scrolling(View *view){ - - view->transient.reinit_scrolling = false; - - i32 target_x = 0; - i32 target_y = 0; - Editing_File *file = view->transient.file_data.file; - Assert(file != 0); - if (file_is_ready(file)){ - Vec2 cursor = view_get_cursor_xy(view); - f32 w = view_width(view); - f32 h = view_height(view); - - if (cursor.x >= target_x + w){ - target_x = round32(cursor.x - w*.35f); - } - - target_y = clamp_bottom(0, floor32(cursor.y - h*.5f)); + case IAct_OpenOrNew: InvalidCodePath; } - - GUI_Scroll_Vars scroll = {0}; - - scroll.target_y = target_y; - scroll.scroll_y = (f32)target_y; - scroll.prev_target_y = -1000; - - scroll.target_x = target_x; - scroll.scroll_x = (f32)target_x; - scroll.prev_target_x = -1000; - - return(scroll); } -internal b32 -file_step(View *view, i32_Rect region, Input_Summary *user_input, b32 is_active, b32 *consumed_l){ - b32 is_animating = false; - Editing_File *file = view->transient.file_data.file; - Assert(file != 0); - if (!file->is_loading){ - if (file->state.paste_effect.seconds_down > 0.f){ - file->state.paste_effect.seconds_down -= user_input->dt; - is_animating = true; - } - } - return(is_animating); -} - -internal void -do_widget(View *view, GUI_Target *target){ - Query_Slot *slot; - Query_Bar *bar; - - // NOTE(allen): A temporary measure... although in - // general we maybe want the user to be able to ask - // how large a particular section of the GUI turns - // out to be after layout? - f32 height = 0.f; - - for (slot = view->transient.query_set.used_slot; slot != 0; slot = slot->next){ - bar = slot->query_bar; - gui_do_text_field(target, bar->prompt, bar->string); - height += view->transient.line_height + 2; - } - - view->transient.widget_height = height; -} +//////////////////////////////// internal void begin_exhaustive_loop(Exhaustive_File_Loop *loop, Hot_Directory *hdir){ @@ -1559,7 +1118,7 @@ static Style_Color_Edit colors_to_edit[] = { }; internal Single_Line_Input_Step -app_single_line_input_core(System_Functions *system, Working_Set *working_set, Key_Event_Data key, Single_Line_Mode mode){ +app_single_line_input__inner(System_Functions *system, Working_Set *working_set, Key_Event_Data key, Single_Line_Mode mode){ Single_Line_Input_Step result = {0}; b8 ctrl = key.modifiers[MDFR_CONTROL_INDEX]; @@ -1626,7 +1185,7 @@ app_single_line_input_core(System_Functions *system, Working_Set *working_set, K } } - return result; + return(result); } inline Single_Line_Input_Step @@ -1634,7 +1193,7 @@ app_single_line_input_step(System_Functions *system, Key_Event_Data key, String Single_Line_Mode mode = {}; mode.type = SINGLE_LINE_STRING; mode.string = string; - return app_single_line_input_core(system, 0, key, mode); + return(app_single_line_input__inner(system, 0, key, mode)); } inline Single_Line_Input_Step @@ -1648,151 +1207,7 @@ app_single_file_input_step(System_Functions *system, mode.hot_directory = hot_directory; mode.try_to_match = try_to_match; mode.case_sensitive = case_sensitive; - return app_single_line_input_core(system, working_set, key, mode); -} - -inline Single_Line_Input_Step -app_single_number_input_step(System_Functions *system, Key_Event_Data key, String *string){ - Single_Line_Input_Step result = {}; - Single_Line_Mode mode = {}; - mode.type = SINGLE_LINE_STRING; - mode.string = string; - - char c = (char)key.character; - if (c == 0 || c == '\n' || char_is_numeric(c)) - result = app_single_line_input_core(system, 0, key, mode); - return result; -} - -internal void -append_label(String *string, i32 indent_level, char *message){ - i32 r = 0; - for (r = 0; r < indent_level; ++r){ - append_s_char(string, '>'); - } - append_sc(string, message); -} - -internal void -show_gui_line(GUI_Target *target, String *string, i32 indent_level, i32 h_align, char *message, char *follow_up){ - string->size = 0; - append_label(string, indent_level, message); - if (follow_up){ - append_padding(string, '-', h_align); - append_s_char(string, ' '); - append_sc(string, follow_up); - } - gui_do_text_field(target, *string, null_string); -} - -internal void -show_gui_int(GUI_Target *target, String *string, - i32 indent_level, i32 h_align, char *message, i32 x){ - string->size = 0; - append_label(string, indent_level, message); - append_padding(string, '-', h_align); - append_s_char(string, ' '); - append_int_to_str(string, x); - gui_do_text_field(target, *string, null_string); -} - -internal void -show_gui_u64(GUI_Target *target, String *string, - i32 indent_level, i32 h_align, char *message, u64 x){ - string->size = 0; - append_label(string, indent_level, message); - append_padding(string, '-', h_align); - append_s_char(string, ' '); - append_u64_to_str(string, x); - gui_do_text_field(target, *string, null_string); -} - -internal void -show_gui_int_int(GUI_Target *target, String *string, - i32 indent_level, i32 h_align, char *message, i32 x, i32 m){ - string->size = 0; - append_label(string, indent_level, message); - append_padding(string, '-', h_align); - append_s_char(string, ' '); - append_int_to_str(string, x); - append_s_char(string, '/'); - append_int_to_str(string, m); - gui_do_text_field(target, *string, null_string); -} - -internal void -show_gui_id(GUI_Target *target, String *string, - i32 indent_level, i32 h_align, char *message, GUI_id id){ - string->size = 0; - append_label(string, indent_level, message); - append_padding(string, '-', h_align); - append_ss(string, make_lit_string(" [0]: ")); - append_u64_to_str(string, id.id[0]); - append_padding(string, ' ', h_align + 26); - append_ss(string, make_lit_string(" [1]: ")); - append_u64_to_str(string, id.id[1]); - gui_do_text_field(target, *string, null_string); -} - -internal void -show_gui_float(GUI_Target *target, String *string, - i32 indent_level, i32 h_align, char *message, float x){ - string->size = 0; - append_label(string, indent_level, message); - append_padding(string, '-', h_align); - append_s_char(string, ' '); - append_float_to_str(string, x); - gui_do_text_field(target, *string, null_string); -} - -internal void -show_gui_scroll(GUI_Target *target, String *string, - i32 indent_level, i32 h_align, char *message, - GUI_Scroll_Vars scroll){ - show_gui_line (target, string, indent_level, 0, message, 0); - show_gui_float(target, string, indent_level+1, h_align, " scroll_y ", scroll.scroll_y); - show_gui_int (target, string, indent_level+1, h_align, " target_y ", scroll.target_y); - show_gui_int (target, string, indent_level+1, h_align, " prev_target_y ", scroll.prev_target_y); - show_gui_float(target, string, indent_level+1, h_align, " scroll_x ", scroll.scroll_x); - show_gui_int (target, string, indent_level+1, h_align, " target_x ", scroll.target_x); - show_gui_int (target, string, indent_level+1, h_align, " prev_target_x ", scroll.prev_target_x); -} - -internal void -show_gui_cursor(GUI_Target *target, String *string, - i32 indent_level, i32 h_align, char *message, - Full_Cursor cursor){ - show_gui_line (target, string, indent_level, 0, message, 0); - show_gui_int (target, string, indent_level+1, h_align, " pos ", cursor.pos); - show_gui_int (target, string, indent_level+1, h_align, " line ", cursor.line); - show_gui_int (target, string, indent_level+1, h_align, " column ", cursor.character); - show_gui_float(target, string, indent_level+1, h_align, " unwrapped_x ", cursor.unwrapped_x); - show_gui_float(target, string, indent_level+1, h_align, " unwrapped_y ", cursor.unwrapped_y); - show_gui_float(target, string, indent_level+1, h_align, " wrapped_x ", cursor.wrapped_x); - show_gui_float(target, string, indent_level+1, h_align, " wrapped_y ", cursor.wrapped_y); -} - -internal void -show_gui_region(GUI_Target *target, String *string, - i32 indent_level, i32 h_align, char *message, - i32_Rect region){ - show_gui_line(target, string, indent_level, 0, message, 0); - show_gui_int (target, string, indent_level+1, h_align, " x0 ", region.x0); - show_gui_int (target, string, indent_level+1, h_align, " y0 ", region.y0); - show_gui_int (target, string, indent_level+1, h_align, " x1 ", region.x1); - show_gui_int (target, string, indent_level+1, h_align, " y1 ", region.y1); -} - -inline void -gui_show_mouse(GUI_Target *target, String *string, i32 mx, i32 my){ - string->size = 0; - append_ss(string, make_lit_string("mouse: (")); - append_int_to_str(string, mx); - append_s_char(string, ','); - append_int_to_str(string, my); - append_s_char(string, ')'); - - gui_do_text_field(target, *string, null_string); + return(app_single_line_input__inner(system, working_set, key, mode)); } internal View_Step_Result @@ -1821,30 +1236,41 @@ step_file_view(System_Functions *system, View *view, Models *models, View *activ gui_begin_top_level(target, input); { - if (view->transient.showing_ui != VUI_Debug && !view->transient.hide_file_bar){ + if (!view->transient.hide_file_bar){ gui_do_top_bar(target); } - do_widget(view, target); + + // NOTE(allen): A temporary measure... although in + // general we maybe want the user to be able to ask + // how large a particular section of the GUI turns + // out to be after layout? + i32 bar_count = 0; + for (Query_Slot *slot = view->transient.query_set.used_slot; + slot != 0; + slot = slot->next, ++bar_count){ + Query_Bar *bar = slot->query_bar; + gui_do_text_field(target, bar->prompt, bar->string); + } + view->transient.widget_height = (f32)bar_count*(view->transient.line_height + 2); if (view->transient.showing_ui == VUI_None){ - gui_begin_serial_section(target); - { - i32 delta = 9*view->transient.line_height; - GUI_id scroll_context = {0}; - scroll_context.id[1] = view->transient.showing_ui; - scroll_context.id[0] = (u64)(view->transient.file_data.file); - - Assert(view->transient.file_data.file != 0); - Assert(view->transient.edit_pos != 0); - - GUI_Scroll_Vars *scroll = &view->transient.edit_pos->scroll; - gui_begin_scrollable(target, scroll_context, *scroll, - delta, show_scrollbar); - - gui_do_file(target); - gui_end_scrollable(target); - } + + i32 delta = 9*view->transient.line_height; + GUI_id scroll_context = {0}; + scroll_context.id[1] = view->transient.showing_ui; + scroll_context.id[0] = (u64)(view->transient.file_data.file); + + Assert(view->transient.file_data.file != 0); + Assert(view->transient.edit_pos != 0); + + GUI_Scroll_Vars *scroll = &view->transient.edit_pos->scroll; + gui_begin_scrollable(target, scroll_context, *scroll, + delta, show_scrollbar); + + gui_do_file(target); + gui_end_scrollable(target); + gui_end_serial_section(target); } else{ @@ -1995,7 +1421,7 @@ step_file_view(System_Functions *system, View *view, Models *models, View *activ file_set_font(system, models, file, new_font_id); } else if (new_font_id != font_id || new_font_id != models->global_font_id){ - global_set_font(system, models, new_font_id); + global_set_font_and_update_files(system, models, new_font_id); } } @@ -2117,7 +1543,7 @@ step_file_view(System_Functions *system, View *view, Models *models, View *activ gui_end_scrollable(target); if (has_new_settings){ - alter_font(system, models, font_edit_id, &new_settings); + alter_font_and_update_files(system, models, font_edit_id, &new_settings); } }break; @@ -2550,355 +1976,6 @@ step_file_view(System_Functions *system, View *view, Models *models, View *activ interactive_view_complete(system, view, models, comp_dest, comp_action); } }break; - - case VUI_Debug: - { - GUI_id scroll_context = {0}; - scroll_context.id[1] = VUI_Debug + ((u64)view->transient.debug_vars.mode << 32); - - GUI_id id = {0}; - id.id[1] = VUI_Debug + ((u64)view->transient.debug_vars.mode << 32); - - // TODO(allen): - // + Incoming input - // + Memory info - // + Thread info - // + View inspection - // - auto generate? - // - expand/collapse sections - // - Buffer inspection - // - Command maps inspection - // - Clipboard inspection - - String empty_str = null_string; - - char space1[512]; - String string = make_fixed_width_string(space1); - - // Time Watcher - { - string.size = 0; - u64 time = system->now_time(); - - append_ss(&string, make_lit_string("last redraw: ")); - append_u64_to_str(&string, time); - - gui_do_text_field(target, string, empty_str); - } - - { - i32 prev_mode = view->transient.debug_vars.mode; - for (i32 i = 0; i < keys.count; ++i){ - Key_Event_Data key = keys.keys[i]; - if (key.modifiers[MDFR_CONTROL_INDEX] == 0 && - key.modifiers[MDFR_ALT_INDEX] == 0){ - if (key.keycode == 'i'){ - view->transient.debug_vars.mode = DBG_Input; - } - if (key.keycode == 'm'){ - view->transient.debug_vars.mode = DBG_Threads_And_Memory; - } - if (key.keycode == 'v'){ - view->transient.debug_vars.mode = DBG_View_Inspection; - } - } - } - if (prev_mode != view->transient.debug_vars.mode){ - result.consume_keys = 1; - } - } - - gui_begin_scrollable(target, scroll_context, view->transient.gui_scroll, - 9*view->transient.line_height, show_scrollbar); - - switch (view->transient.debug_vars.mode){ - case DBG_Input: - { - Debug_Data *debug = &models->debug; - - gui_show_mouse(target, &string, input.mouse.x, input.mouse.y); - - Debug_Input_Event *input_event = debug->input_events; - for (i32 i = 0; - i < ArrayCount(debug->input_events); - ++i, ++input_event){ - string.size = 0; - - if (input_event->is_hold){ - append_ss(&string, make_lit_string("hold: ")); - } - else{ - append_ss(&string, make_lit_string("press: ")); - } - - if (input_event->is_ctrl){ - append_ss(&string, make_lit_string("ctrl-")); - } - else{ - append_ss(&string, make_lit_string(" -")); - } - - if (input_event->is_alt){ - append_ss(&string, make_lit_string("alt-")); - } - else{ - append_ss(&string, make_lit_string(" -")); - } - - if (input_event->is_shift){ - append_ss(&string, make_lit_string("shift ")); - } - else{ - append_ss(&string, make_lit_string(" ")); - } - - if (input_event->key > ' ' && input_event->key <= '~'){ - append_ss(&string, make_string(&input_event->key, 1)); - } - else if (input_event->key == ' '){ - append_ss(&string, make_lit_string("space")); - } - else if (input_event->key == '\n'){ - append_ss(&string, make_lit_string("\\n")); - } - else if (input_event->key == '\t'){ - append_ss(&string, make_lit_string("\\t")); - } - else{ - String str; - str.str = global_key_name(input_event->key, &str.size); - if (str.str){ - str.memory_size = str.size + 1; - append_ss(&string, str); - } - else{ - append_ss(&string, make_lit_string("unrecognized!")); - } - } - - if (input_event->consumer[0] != 0){ - append_padding(&string, ' ', 40); - append_sc(&string, input_event->consumer); - } - - gui_do_text_field(target, string, empty_str); - } - }break; - - case DBG_Threads_And_Memory: - { - b8 threads[4]; - i32 pending = 0; - - if (system->internal_get_thread_states){ - system->internal_get_thread_states(BACKGROUND_THREADS, - threads, &pending); - - string.size = 0; - append_ss(&string, make_lit_string("pending jobs: ")); - append_int_to_str(&string, pending); - gui_do_text_field(target, string, empty_str); - - for (i32 i = 0; i < 4; ++i){ - string.size = 0; - append_ss(&string, make_lit_string("thread ")); - append_int_to_str(&string, i); - append_ss(&string, make_lit_string(": ")); - - if (threads[i]){ - append_ss(&string, make_lit_string("running")); - } - else{ - append_ss(&string, make_lit_string("waiting")); - } - - gui_do_text_field(target, string, empty_str); - } - } - - Partition *part = &models->mem.part; - - string.size = 0; - append_ss(&string, make_lit_string("part memory: ")); - append_int_to_str(&string, part->pos); - append_s_char(&string, '/'); - append_int_to_str(&string, part->max); - gui_do_text_field(target, string, empty_str); - -#if !defined(FED_DEBUG_MEM_H) - General_Memory *general = &models->mem.general; - Bubble *bubble = 0, *sentinel = &general->sentinel; - for (dll_items(bubble, sentinel)){ - string.size = 0; - if (bubble->flags & MEM_BUBBLE_USED){ - append_ss(&string, make_lit_string(" used: ")); - } - else{ - append_ss(&string, make_lit_string(" free: ")); - } - - append_int_to_str(&string, bubble->size); - append_padding(&string, ' ', 40); - gui_do_text_field(target, string, empty_str); - } -#endif - }break; - - case DBG_View_Inspection: - { - i32 inspecting_id = view->transient.debug_vars.inspecting_view_id; - View *views_to_inspect[16]; - i32 view_count = 0; - b32 low_detail = true; - - if (inspecting_id == 0){ - Editing_Layout *layout = &models->layout; - - for (Panel *panel = layout->used_sentinel.next; - panel != &layout->used_sentinel; - panel = panel->next){ - View *view_ptr = panel->view; - views_to_inspect[view_count++] = view_ptr; - } - } - else if (inspecting_id >= 1 && inspecting_id <= 16){ - Live_Views *live_set = &models->live_set; - View *view_ptr = live_set->views + inspecting_id - 1; - views_to_inspect[view_count++] = view_ptr; - low_detail = false; - } - - for (i32 i = 0; i < view_count; ++i){ - View *view_ptr = views_to_inspect[i]; - - string.size = 0; - append_ss(&string, make_lit_string("view: ")); - append_int_to_str(&string, view_ptr->persistent.id + 1); - gui_do_text_field(target, string, empty_str); - - string.size = 0; - Editing_File *file = view_ptr->transient.file_data.file; - Assert(file != 0); - append_ss(&string, make_lit_string(" > buffer: ")); - append_ss(&string, file->unique_name.name); - gui_do_text_field(target, string, empty_str); - string.size = 0; - append_ss(&string, make_lit_string(" >> buffer-slot-id: ")); - append_int_to_str(&string, file->id.id); - - if (low_detail){ - string.size = 0; - append_ss(&string, make_lit_string("inspect this")); - - id.id[0] = (u64)(view_ptr->persistent.id); - if (gui_do_button(target, id, string)){ - view->transient.debug_vars.inspecting_view_id = view_ptr->persistent.id + 1; - } - } - else{ - - gui_show_mouse(target, &string, input.mouse.x, input.mouse.y); - -#define SHOW_GUI_BLANK(n) show_gui_line(target, &string, n, 0, "", 0) -#define SHOW_GUI_LINE(n, str) show_gui_line(target, &string, n, 0, " " str, 0) -#define SHOW_GUI_STRING(n, h, str, mes) show_gui_line(target, &string, n, h, " " str " ", mes) -#define SHOW_GUI_INT(n, h, str, v) show_gui_int(target, &string, n, h, " " str " ", v) -#define SHOW_GUI_INT_INT(n, h, str, v, m) show_gui_int_int(target, &string, n, h, " " str " ", v, m) -#define SHOW_GUI_U64(n, h, str, v) show_gui_u64(target, &string, n, h, " " str " ", v) -#define SHOW_GUI_ID(n, h, str, v) show_gui_id(target, &string, n, h, " " str, v) -#define SHOW_GUI_FLOAT(n, h, str, v) show_gui_float(target, &string, n, h, " " str " ", v) -#define SHOW_GUI_BOOL(n, h, str, v) do { if (v) { show_gui_line(target, &string, n, h, " " str " ", "true"); }\ - else { show_gui_line(target, &string, n, h, " " str " ", "false"); } } while(0) - -#define SHOW_GUI_SCROLL(n, h, str, v) show_gui_scroll(target, &string, n, h, " " str, v) -#define SHOW_GUI_CURSOR(n, h, str, v) show_gui_cursor(target, &string, n, h, " " str, v) -#define SHOW_GUI_REGION(n, h, str, v) show_gui_region(target, &string, n, h, " " str, v) - - i32 h_align = 31; - - SHOW_GUI_BLANK(0); - { - i32 map = view_ptr->transient.map; -#define MAP_LABEL "command map" - if (map == mapid_global){ - SHOW_GUI_STRING(1, h_align, MAP_LABEL, "global"); - } - else if (map == mapid_file){ - SHOW_GUI_STRING(1, h_align, MAP_LABEL, "file"); - } - else if (map == mapid_ui){ - SHOW_GUI_STRING(1, h_align, MAP_LABEL, "gui"); - } - else if (map == mapid_nomap){ - SHOW_GUI_STRING(1, h_align, MAP_LABEL, "nomap"); - } - else{ - SHOW_GUI_STRING(1, h_align, MAP_LABEL, "user"); - SHOW_GUI_INT(2, h_align, "custom map id", map); - } - } - - SHOW_GUI_BLANK(0); - SHOW_GUI_LINE(1, "file data:"); - SHOW_GUI_BOOL(2, h_align, "has file", view_ptr->transient.file_data.file); - SHOW_GUI_BOOL(2, h_align, "show temp highlight", view_ptr->transient.file_data.show_temp_highlight); - SHOW_GUI_INT (2, h_align, "start temp highlight", view_ptr->transient.file_data.temp_highlight.pos); - SHOW_GUI_INT (2, h_align, "end temp highlight", view_ptr->transient.file_data.temp_highlight_end_pos); - - SHOW_GUI_BOOL(2, h_align, "show whitespace", view_ptr->transient.file_data.show_whitespace); - SHOW_GUI_BOOL(2, h_align, "locked", view_ptr->transient.file_data.file_locked); - - SHOW_GUI_BLANK(0); - SHOW_GUI_REGION(1, h_align, "scroll region", view_ptr->transient.scroll_region); - - SHOW_GUI_BLANK(0); - SHOW_GUI_LINE(1, "file editing positions"); - { - File_Edit_Positions *edit_pos = view_ptr->transient.edit_pos; - - Assert(edit_pos != 0); - SHOW_GUI_SCROLL(2, h_align, "scroll:", edit_pos->scroll); - SHOW_GUI_BLANK (2); - SHOW_GUI_CURSOR(2, h_align, "cursor:", edit_pos->cursor); - SHOW_GUI_BLANK (2); - SHOW_GUI_INT (2, h_align, "mark", edit_pos->mark); - SHOW_GUI_FLOAT (2, h_align, "preferred_x", edit_pos->preferred_x); - SHOW_GUI_INT (2, h_align, "scroll_i", edit_pos->scroll_i); - } - - SHOW_GUI_BLANK (0); - SHOW_GUI_SCROLL(1, h_align, "gui scroll:", view_ptr->transient.gui_scroll); - - SHOW_GUI_BLANK (0); - SHOW_GUI_LINE (1, "gui target"); - SHOW_GUI_INT_INT(2, h_align, "gui partition", - view_ptr->transient.gui_target.push.pos, - view_ptr->transient.gui_target.push.max); - - SHOW_GUI_BLANK (2); - SHOW_GUI_ID (2, h_align, "active", view_ptr->transient.gui_target.active); - SHOW_GUI_ID (2, h_align, "mouse_hot", view_ptr->transient.gui_target.mouse_hot); - SHOW_GUI_ID (2, h_align, "auto_hot", view_ptr->transient.gui_target.auto_hot); - SHOW_GUI_ID (2, h_align, "hover", view_ptr->transient.gui_target.hover); - SHOW_GUI_ID (2, h_align, "scroll_id", view_ptr->transient.gui_target.scroll_id); - - SHOW_GUI_BLANK (2); - SHOW_GUI_SCROLL (2, h_align, "scroll_original", view_ptr->transient.gui_target.scroll_original); - SHOW_GUI_REGION (2, h_align, "region_original", view_ptr->transient.gui_target.region_original); - - SHOW_GUI_BLANK (2); - SHOW_GUI_REGION (2, h_align, "region_updated", view_ptr->transient.gui_target.region_updated); - - - SHOW_GUI_BLANK (1); - SHOW_GUI_SCROLL (1, h_align, "gui scroll", view_ptr->transient.gui_scroll); - } - } - }break; - } - - gui_end_scrollable(target); - }break; } } } @@ -3053,15 +2130,43 @@ do_step_file_view(System_Functions *system, View *view, Models *models, i32_Rect // computation of view_compute_max_target_y depends on it. view->transient.file_region = gui_session.rect; + Editing_File *file = view->transient.file_data.file; + Assert(file != 0); + if (view->transient.reinit_scrolling){ - result.vars = view_reinit_scrolling(view); - result.is_animating = 1; + view->transient.reinit_scrolling = false; + result.is_animating = true; + + i32 target_x = 0; + i32 target_y = 0; + if (file_is_ready(file)){ + Vec2 cursor = view_get_cursor_xy(view); + + f32 w = view_width(view); + f32 h = view_height(view); + + if (cursor.x >= target_x + w){ + target_x = round32(cursor.x - w*.35f); + } + + target_y = clamp_bottom(0, floor32(cursor.y - h*.5f)); + } + + result.vars.target_y = target_y; + result.vars.scroll_y = (f32)target_y; + result.vars.prev_target_y = -1000; + + result.vars.target_x = target_x; + result.vars.scroll_x = (f32)target_x; + result.vars.prev_target_x = -1000; } - if (file_step(view, gui_session.rect, user_input, is_active, &result.consumed_l)){ - result.is_animating = 1; + if (!file->is_loading && file->state.paste_effect.seconds_down > 0.f){ + file->state.paste_effect.seconds_down -= user_input->dt; + result.is_animating = true; } - is_file_scroll = 1; + + is_file_scroll = true; }break; case guicom_color_button: @@ -3088,29 +2193,27 @@ do_step_file_view(System_Functions *system, View *view, Models *models, i32_Rect result.consumed_l = true; } - { - Key_Input_Data *keys = &user_input->keys; - - void *ptr = (b + 1); - String string = gui_read_string(&ptr); - AllowLocal(string); - - char activation_key = *(char*)ptr; - activation_key = char_to_upper(activation_key); - - if (activation_key != 0){ - i32 count = keys->count; - for (i32 i = 0; i < count; ++i){ - Key_Event_Data key = keys->keys[i]; - - u8 character[4]; - u32 length = to_writable_character(key.character, character); - if (length == 1){ - if (char_to_upper(character[0]) == activation_key){ - target->active = b->id; - result.is_animating = 1; - break; - } + Key_Input_Data *keys = &user_input->keys; + + void *ptr = (b + 1); + String string = gui_read_string(&ptr); + AllowLocal(string); + + char activation_key = *(char*)ptr; + activation_key = char_to_upper(activation_key); + + if (activation_key != 0){ + i32 count = keys->count; + for (i32 i = 0; i < count; ++i){ + Key_Event_Data key = keys->keys[i]; + + u8 character[4]; + u32 length = to_writable_character(key.character, character); + if (length == 1){ + if (char_to_upper(character[0]) == activation_key){ + target->active = b->id; + result.is_animating = 1; + break; } } } @@ -3235,6 +2338,62 @@ do_step_file_view(System_Functions *system, View *view, Models *models, i32_Rect return(result); } +internal u32* +style_get_color(Style *style, Cpp_Token token){ + u32 *result = 0; + if ((token.flags & CPP_TFLAG_IS_KEYWORD) != 0){ + if (token.type == CPP_TOKEN_BOOLEAN_CONSTANT){ + result = &style->main.bool_constant_color; + } + else{ + result = &style->main.keyword_color; + } + } + else if ((token.flags & CPP_TFLAG_PP_DIRECTIVE) != 0){ + result = &style->main.preproc_color; + } + else{ + switch (token.type){ + case CPP_TOKEN_COMMENT: + { + result = &style->main.comment_color; + }break; + + case CPP_TOKEN_STRING_CONSTANT: + { + result = &style->main.str_constant_color; + }break; + + case CPP_TOKEN_CHARACTER_CONSTANT: + { + result = &style->main.char_constant_color; + }break; + + case CPP_TOKEN_INTEGER_CONSTANT: + { + result = &style->main.int_constant_color; + }break; + + case CPP_TOKEN_FLOATING_CONSTANT: + { + result = &style->main.float_constant_color; + }break; + + case CPP_PP_INCLUDE_FILE: + { + result = &style->main.include_color; + }break; + + default: + { + result = &style->main.default_color; + }break; + } + } + Assert(result != 0); + return(result); +} + internal i32 draw_file_loaded(System_Functions *system, View *view, Models *models, i32_Rect rect, b32 is_active, Render_Target *target){ Editing_File *file = view->transient.file_data.file; @@ -3531,6 +2690,12 @@ draw_text_with_cursor(System_Functions *system, Render_Target *target, View *vie } } +internal void +intbar_draw_string(System_Functions *system, Render_Target *target, File_Bar *bar, String str, u32 char_color){ + draw_string(system, target, bar->font_id, str, (i32)(bar->pos_x + bar->text_shift_x), (i32)(bar->pos_y + bar->text_shift_y), char_color); + bar->pos_x += font_string_width(system, target, bar->font_id, str); +} + internal void draw_file_bar(System_Functions *system, Render_Target *target, View *view, Models *models, Editing_File *file, i32_Rect rect){ File_Bar bar; diff --git a/4ed_view.h b/4ed_view.h index 5aea6056..5fa8b475 100644 --- a/4ed_view.h +++ b/4ed_view.h @@ -40,33 +40,36 @@ enum Interactive_Action{ IAct_Sure_To_Close }; -enum Interactive_Interaction{ - IInt_Sys_File_List, - IInt_Live_File_List, - IInt_Sure_To_Kill, - IInt_Sure_To_Close +typedef i32 Unsaved_Changes_User_Response; +enum{ + UnsavedChangesUserResponse_ContinueAnyway = 0, + UnsavedChangesUserResponse_Cancel = 1, + UnsavedChangesUserResponse_SaveAndContinue = 2, }; -enum View_UI{ - VUI_None, - VUI_Theme, - VUI_Interactive, - VUI_Debug +typedef i32 Interactive_Interaction; +enum{ + IInt_Sys_File_List = 0, + IInt_Live_File_List = 1, + IInt_Sure_To_Kill = 2, + IInt_Sure_To_Close = 3 }; -enum Debug_Mode{ - DBG_Input, - DBG_Threads_And_Memory, - DBG_View_Inspection +typedef i32 View_UI; +enum{ + VUI_None = 0, + VUI_Theme = 1, + VUI_Interactive = 2, }; -enum Color_View_Mode{ - CV_Mode_Library, - CV_Mode_Font, - CV_Mode_Global_Font, - CV_Mode_Font_Editing, - CV_Mode_Global_Font_Editing, - CV_Mode_Adjusting, +typedef i32 Color_View_Mode; +enum{ + CV_Mode_Library = 0, + CV_Mode_Font = 1, + CV_Mode_Global_Font = 2, + CV_Mode_Font_Editing = 3, + CV_Mode_Global_Font_Editing = 4, + CV_Mode_Adjusting = 5, }; struct Scroll_Context{ @@ -75,12 +78,6 @@ struct Scroll_Context{ View_UI mode; }; -struct Debug_Vars{ - i32 mode; - i32 inspecting_view_id; -}; -global_const Debug_Vars null_debug_vars = {0}; - struct View_Transient{ struct View *next; struct View *prev; @@ -139,8 +136,6 @@ struct View_Transient{ f32 widget_height; b32 reinit_scrolling; - - Debug_Vars debug_vars; }; struct View{ diff --git a/4ed_working_set.cpp b/4ed_working_set.cpp index e4658de4..9da5758e 100644 --- a/4ed_working_set.cpp +++ b/4ed_working_set.cpp @@ -9,9 +9,39 @@ // TOP -// -// Working_Set of files -// +// TODO(allen): Find a real home for this... string library needs a makeover. +internal String +push_string(Partition *part, char *str, i32 len){ + char *space = (char*)push_array(part, char, len + 1); + memcpy(space, str, len); + space[len] = 0; + String string = make_string_cap(space, len, len + 1); + return(string); +} + +internal String +push_string(Partition *part, String str){ + String res = push_string(part, str.str, str.size); + return(res); +} + +internal String +push_string(Partition *part, char *str, i32 len, i32 cap){ + cap = clamp_bottom(len + 1, cap); + char *space = (char*)push_array(part, char, cap); + memcpy(space, str, len); + space[len] = 0; + String string = make_string_cap(space, len, cap); + return(string); +} + +internal String +push_string(Partition *part, String str, i32 cap){ + String res = push_string(part, str.str, str.size, cap); + return(res); +} + +//////////////////////////////// internal void working_set_extend_memory(Working_Set *working_set, Editing_File *new_space, i16 number_of_files){ @@ -279,25 +309,87 @@ working_set_lookup_file(Working_Set *working_set, String string){ internal void touch_file(Working_Set *working_set, Editing_File *file){ - TentativeAssert(file != 0); + Assert(file != 0); Assert(!file->is_dummy); dll_remove(&file->node); dll_insert(&working_set->used_sentinel, &file->node); - } +//////////////////////////////// -// -// Name Binding -// - -internal void -editing_file_name_init(Editing_File_Name *name){ - name->name = make_fixed_width_string(name->name_); +// TODO(allen): Bring the clipboard fully to the custom side. +internal String* +working_set_next_clipboard_string(General_Memory *general, Working_Set *working, i32 str_size){ + i32 clipboard_current = working->clipboard_current; + if (working->clipboard_size == 0){ + clipboard_current = 0; + working->clipboard_size = 1; + } + else{ + ++clipboard_current; + if (clipboard_current >= working->clipboard_max_size){ + clipboard_current = 0; + } + else if (working->clipboard_size <= clipboard_current){ + working->clipboard_size = clipboard_current + 1; + } + } + String *result = &working->clipboards[clipboard_current]; + working->clipboard_current = clipboard_current; + working->clipboard_rolling = clipboard_current; + char *new_str; + if (result->str != 0){ + new_str = (char*)general_memory_reallocate(general, result->str, result->size, str_size); + } + else{ + new_str = (char*)general_memory_allocate(general, str_size+1); + } + // TODO(allen): What if new_str == 0? + *result = make_string_cap(new_str, 0, str_size); + return(result); } +internal String* +working_set_clipboard_index(Working_Set *working, i32 index){ + String *result = 0; + i32 size = working->clipboard_size; + i32 current = working->clipboard_current; + if (index >= 0 && size > 0){ + index = index % size; + index = current + size - index; + index = index % size; + result = &working->clipboards[index]; + } + return(result); +} + +internal String* +working_set_clipboard_head(Working_Set *working){ + String *result = 0; + if (working->clipboard_size > 0){ + working->clipboard_rolling = 0; + result = working_set_clipboard_index(working, working->clipboard_rolling); + } + return(result); +} + +internal String* +working_set_clipboard_roll_down(Working_Set *working){ + String *result = 0; + if (working->clipboard_size > 0){ + i32 clipboard_index = working->clipboard_rolling; + ++clipboard_index; + working->clipboard_rolling = clipboard_index; + result = working_set_clipboard_index(working, working->clipboard_rolling); + } + return(result); +} + +//////////////////////////////// + internal b32 -get_canon_name(System_Functions *system, Editing_File_Name *canon_name, String filename){ +get_canon_name(System_Functions *system, String filename, + Editing_File_Name *canon_name){ canon_name->name = make_fixed_width_string(canon_name->name_); canon_name->name.size = system->get_canonical(filename.str, filename.size, canon_name->name.str, canon_name->name.memory_size); @@ -308,16 +400,19 @@ get_canon_name(System_Functions *system, Editing_File_Name *canon_name, String f } internal void -buffer_bind_file(System_Functions *system, General_Memory *general, Working_Set *working_set, Editing_File *file, String canon_filename){ +buffer_bind_file(System_Functions *system, General_Memory *general, + Working_Set *working_set, + Editing_File *file, String canon_filename){ Assert(file->unique_name.name.size == 0); Assert(file->canon.name.size == 0); file->canon.name = make_fixed_width_string(file->canon.name_); - copy_ss(&file->canon.name, canon_filename); + copy(&file->canon.name, canon_filename); terminate_with_null(&file->canon.name); system->add_listener(file->canon.name.str); - b32 result = working_set_canon_add(general, working_set, file, file->canon.name); - Assert(result); AllowLocal(result); + if (!working_set_canon_add(general, working_set, file, file->canon.name)){ + InvalidCodePath; + } } internal void @@ -371,17 +466,18 @@ buffer_bind_name_low_level(General_Memory *general, Working_Set *working_set, Ed Assert(file->unique_name.name.size == 0); Editing_File_Name new_name = {0}; - editing_file_name_init(&new_name); + new_name.name = make_fixed_width_string(new_name.name_); buffer_resolve_name_low_level(working_set, &new_name, name); - editing_file_name_init(&file->base_name); + file->base_name.name = make_fixed_width_string(file->base_name.name_); copy(&file->base_name.name, base_name); - editing_file_name_init(&file->unique_name); + file->unique_name.name = make_fixed_width_string(file->unique_name.name_); copy(&file->unique_name.name, new_name.name); - b32 result = working_set_add_name(general, working_set, file, file->unique_name.name); - Assert(result); AllowLocal(result); + if (!working_set_add_name(general, working_set, file, file->unique_name.name)){ + InvalidCodePath; + } } internal void @@ -393,5 +489,135 @@ buffer_unbind_name_low_level(Working_Set *working_set, Editing_File *file){ file->unique_name.name.size = 0; } +internal void +buffer_bind_name(Models *models, General_Memory *general, Partition *scratch, + Working_Set *working_set, + Editing_File *file, String base_name){ + Temp_Memory temp = begin_temp_memory(scratch); + + // List of conflict files. + Editing_File **conflict_file_ptrs = push_array(scratch, Editing_File*, 0); + int32_t conflict_count = 0; + + { + Editing_File **new_file_ptr = push_array(scratch, Editing_File*, 1); + *new_file_ptr = file; + ++conflict_count; + } + + File_Node *used_nodes = &working_set->used_sentinel; + for (File_Node *node = used_nodes->next; node != used_nodes; node = node->next){ + Editing_File *file_ptr = (Editing_File*)node; + if (file_is_ready(file_ptr) && match(base_name, file_ptr->base_name.name)){ + Editing_File **new_file_ptr = push_array(scratch, Editing_File*, 1); + *new_file_ptr = file_ptr; + ++conflict_count; + } + } + + // Fill conflict array. + Buffer_Name_Conflict_Entry *conflicts = push_array(scratch, Buffer_Name_Conflict_Entry, conflict_count); + + for (int32_t i = 0; i < conflict_count; ++i){ + Editing_File *file_ptr = conflict_file_ptrs[i]; + Buffer_Name_Conflict_Entry *entry = &conflicts[i]; + entry->buffer_id = file_ptr->id.id; + + String file_name = push_string(scratch, file_ptr->canon.name); + entry->file_name = file_name.str; + entry->file_name_len = file_name.size; + + String term_base_name = push_string(scratch, base_name); + entry->base_name = term_base_name.str; + entry->base_name_len = term_base_name.size; + + String b = base_name; + if (i > 0){ + b = file_ptr->unique_name.name; + } + i32 unique_name_capacity = 256; + String unique_name = push_string(scratch, b, unique_name_capacity); + entry->unique_name_in_out = unique_name.str; + entry->unique_name_len_in_out = unique_name.size; + entry->unique_name_capacity = unique_name_capacity; + } + + // Get user's resolution data. + if (models->buffer_name_resolver != 0){ + models->buffer_name_resolver(&models->app_links, conflicts, conflict_count); + } + + // Re-bind all of the files + for (int32_t i = 0; i < conflict_count; ++i){ + Editing_File *file_ptr = conflict_file_ptrs[i]; + if (file_ptr->unique_name.name.str != 0){ + buffer_unbind_name_low_level(working_set, file_ptr); + } + } + for (int32_t i = 0; i < conflict_count; ++i){ + Editing_File *file_ptr = conflict_file_ptrs[i]; + Buffer_Name_Conflict_Entry *entry = &conflicts[i]; + String unique_name = make_string(entry->unique_name_in_out, entry->unique_name_len_in_out); + buffer_bind_name_low_level(general, working_set, file_ptr, base_name, unique_name); + } + + end_temp_memory(temp); +} + +//////////////////////////////// + +internal Editing_File* +open_file(System_Functions *system, Models *models, String filename){ + Editing_File *file = 0; + Editing_File_Name canon_name = {0}; + + if (terminate_with_null(&filename) && + get_canon_name(system, filename, &canon_name)){ + Working_Set *working_set = &models->working_set; + file = working_set_contains_canon(working_set, canon_name.name); + if (file == 0){ + Plat_Handle handle; + if (system->load_handle(canon_name.name.str, &handle)){ + Mem_Options *mem = &models->mem; + General_Memory *general = &mem->general; + Partition *part = &mem->part; + + file = working_set_alloc_always(working_set, general); + buffer_bind_file(system, general, working_set, file, canon_name.name); + buffer_bind_name(models, general, part, working_set, file, front_of_directory(filename)); + + i32 size = system->load_size(handle); + char *buffer = 0; + b32 gen_buffer = 0; + + Temp_Memory temp = begin_temp_memory(part); + + buffer = push_array(part, char, size); + if (buffer == 0){ + buffer = (char*)general_memory_allocate(general, size); + Assert(buffer); + gen_buffer = 1; + } + + if (system->load_file(handle, buffer, size)){ + system->load_close(handle); + init_normal_file(system, models, buffer, size, file); + } + else{ + system->load_close(handle); + } + + if (gen_buffer){ + general_memory_free(general, buffer); + } + + end_temp_memory(temp); + } + } + } + + return(file); +} + // BOTTOM diff --git a/meta/4ed_metagen.cpp b/meta/4ed_metagen.cpp index 95c55444..8990e1c3 100644 --- a/meta/4ed_metagen.cpp +++ b/meta/4ed_metagen.cpp @@ -688,7 +688,6 @@ generate_remapping_code_and_data(){ bind(mappings, 'S', MDFR_CTRL, save_all_dirty_buffers); bind(mappings, 'c', MDFR_ALT, open_color_tweaker); - bind(mappings, 'd', MDFR_ALT, open_debug); bind(mappings, '.', MDFR_ALT, change_to_build_panel); bind(mappings, ',', MDFR_ALT, close_build_panel); @@ -888,7 +887,6 @@ generate_remapping_code_and_data(){ bind(mappings, 'S', MDFR_CMND, save_all_dirty_buffers); bind(mappings, 'c', MDFR_CTRL, open_color_tweaker); - bind(mappings, 'd', MDFR_CTRL, open_debug); bind(mappings, '.', MDFR_CTRL, change_to_build_panel); bind(mappings, ',', MDFR_CTRL, close_build_panel);