fixed auto indent cursor weirdness - adjustments to API

This commit is contained in:
Allen Webster 2016-06-23 22:21:11 -04:00
parent 7f05551216
commit ab4d5bbe02
5 changed files with 171 additions and 50 deletions

View File

@ -275,6 +275,16 @@ enum Buffer_Setting_ID{
BufferSetting_MapID, BufferSetting_MapID,
}; };
enum Buffer_Kill_Flag{
BufferKill_Background = 0x1,
BufferKill_AlwaysKill = 0x2,
};
enum Buffer_Create_Flag{
BufferCreate_Background = 0x1,
BufferCreate_AlwaysNew = 0x2,
};
enum Access_Flag{ enum Access_Flag{
AccessOpen = 0x0, AccessOpen = 0x0,
AccessProtected = 0x1, AccessProtected = 0x1,

View File

@ -17,12 +17,12 @@
#define BUFFER_READ_RANGE_SIG(n) int n(Application_Links *app, Buffer_Summary *buffer, int start, int end, char *out) #define BUFFER_READ_RANGE_SIG(n) int n(Application_Links *app, Buffer_Summary *buffer, int start, int end, char *out)
#define BUFFER_REPLACE_RANGE_SIG(n) int n(Application_Links *app, Buffer_Summary *buffer, int start, int end, char *str, int len) #define BUFFER_REPLACE_RANGE_SIG(n) int n(Application_Links *app, Buffer_Summary *buffer, int start, int end, char *str, int len)
#define BUFFER_SET_SETTING_SIG(n) int n(Application_Links *app, Buffer_Summary *buffer, int setting, int value) #define BUFFER_SET_SETTING_SIG(n) int n(Application_Links *app, Buffer_Summary *buffer, int setting, int value)
#define CREATE_BUFFER_SIG(n) Buffer_Summary n(Application_Links *app, char *filename, int filename_len, int do_in_background) #define CREATE_BUFFER_SIG(n) Buffer_Summary n(Application_Links *app, char *filename, int filename_len, unsigned int flags)
#define SAVE_BUFFER_SIG(n) int n(Application_Links *app, Buffer_Summary *buffer, char *filename, int filename_len) #define SAVE_BUFFER_SIG(n) int n(Application_Links *app, Buffer_Summary *buffer, char *filename, int filename_len, unsigned int flags)
#define KILL_BUFFER_SIG(n) int n(Application_Links *app, Buffer_Identifier buffer, int always_kill, int view_id) #define KILL_BUFFER_SIG(n) int n(Application_Links *app, Buffer_Identifier buffer, int view_id, unsigned int flags)
#define GET_VIEW_FIRST_SIG(n) View_Summary n(Application_Links *app, unsigned int access) #define GET_VIEW_FIRST_SIG(n) View_Summary n(Application_Links *app, unsigned int access)
#define GET_VIEW_NEXT_SIG(n) void n(Application_Links *app, View_Summary *view, unsigned int access) #define GET_VIEW_NEXT_SIG(n) void n(Application_Links *app, View_Summary *view, unsigned int access)
#define GET_VIEW_SIG(n) View_Summary n(Application_Links *app, int index, unsigned int access) #define GET_VIEW_SIG(n) View_Summary n(Application_Links *app, int view_id, unsigned int access)
#define GET_ACTIVE_VIEW_SIG(n) View_Summary n(Application_Links *app, unsigned int access) #define GET_ACTIVE_VIEW_SIG(n) View_Summary n(Application_Links *app, unsigned int access)
#define VIEW_AUTO_TAB_SIG(n) int n(Application_Links *app, View_Summary *view, int start, int end, int tab_width, unsigned int flags) #define VIEW_AUTO_TAB_SIG(n) int n(Application_Links *app, View_Summary *view, int start, int end, int tab_width, unsigned int flags)
#define VIEW_COMPUTE_CURSOR_SIG(n) Full_Cursor n(Application_Links *app, View_Summary *view, Buffer_Seek seek) #define VIEW_COMPUTE_CURSOR_SIG(n) Full_Cursor n(Application_Links *app, View_Summary *view, Buffer_Seek seek)

View File

@ -169,14 +169,14 @@ identifier can either name a new buffer that does not exist, name a buffer that
id of a buffer that does exist. If the buffer already exists the command will fail, unless id of a buffer that does exist. If the buffer already exists the command will fail, unless
CLI_OverlapWithConflict is set in the flags. CLI_OverlapWithConflict is set in the flags.
If the buffer is not already in an active view, and the view parameter is no NULL, then the provided view If the buffer is not already in an open view, and the view parameter is no NULL, then the provided view
will display the output buffer. If the view parameter is NULL, no view will display the output. will display the output buffer. If the view parameter is NULL, no view will display the output.
If CLI_OverlapWithConflict is set in the flags, the command will always be executed even if another command If CLI_OverlapWithConflict is set in the flags, the command will always be executed even if another command
was outputting to the same buffer still. was outputting to the same buffer still.
If CLI_AlwaysBindToView is set and the view parameter is not NULL, then the specified view will always If CLI_AlwaysBindToView is set and the view parameter is not NULL, then the specified view will always
begin displaying the output buffer, even if another active view already displays that buffer. begin displaying the output buffer, even if another open view already displays that buffer.
If CLI_CursorAtEnd is set the cursor in the output buffer will be placed at the end of the buffer instead If CLI_CursorAtEnd is set the cursor in the output buffer will be placed at the end of the buffer instead
of at the beginning. of at the beginning.
@ -721,7 +721,12 @@ deleteing the range from start to end.
return(result); return(result);
} }
BUFFER_SET_SETTING_SIG(external_buffer_set_setting){ BUFFER_SET_SETTING_SIG(external_buffer_set_setting)/*
DOC_PARAM(buffer, the buffer to set a setting on)
DOC_PARAM(setting, one of the Buffer_Setting_ID enum values that identifies the setting to set)
DOC_PARAM(value, the value to set the specified setting to)
DOC_SEE(Buffer_Setting_ID)
*/{
Command_Data *cmd = (Command_Data*)app->cmd_context; Command_Data *cmd = (Command_Data*)app->cmd_context;
System_Functions *system = cmd->system; System_Functions *system = cmd->system;
Models *models = cmd->models; Models *models = cmd->models;
@ -787,23 +792,21 @@ BUFFER_SET_SETTING_SIG(external_buffer_set_setting){
return(result); return(result);
} }
SAVE_BUFFER_SIG(external_save_buffer){ CREATE_BUFFER_SIG(external_create_buffer)/*
Command_Data *cmd = (Command_Data*)app->cmd_context; DOC_PARAM(filename, the name of the file to be opened or created)
System_Functions *system = cmd->system; DOC_PARAM(filename_len, the length of the filename string)
Models *models = cmd->models; DOC_PARAM(flags, flags for buffer creation behavior)
int result = false; DOC_RETURN(returns the summary of the created buffer on success or a NULL buffer otherwise)
DOC
Editing_File *file = imp_get_file(cmd, buffer); (
if (file){ Tries to create a new buffer and associate it to the given filename. If such a buffer already
result = true; exists the existing buffer is returned in the buffer summary and no new buffer is created.
String name = make_string(filename, filename_len); If the buffer does not exist a new buffer is created and named after the given filename. If
view_save_file(system, models, file, 0, name, false); the filename corresponds to a file on the disk that file is loaded and put into buffer, if
} the filename does not correspond to a file on disk the buffer is created empty.
)
return(result); DOC_SEE(Buffer_Create_Flag)
} */{
CREATE_BUFFER_SIG(external_create_buffer){
Command_Data *cmd = (Command_Data*)app->cmd_context; Command_Data *cmd = (Command_Data*)app->cmd_context;
System_Functions *system = cmd->system; System_Functions *system = cmd->system;
Models *models = cmd->models; Models *models = cmd->models;
@ -818,8 +821,21 @@ CREATE_BUFFER_SIG(external_create_buffer){
String filename_string = make_string_terminated(part, filename, filename_len); String filename_string = make_string_terminated(part, filename, filename_len);
Editing_File *file = working_set_contains(system, working_set, filename_string); Editing_File *file = working_set_contains(system, working_set, filename_string);
if (file == 0){ if (file == 0){
File_Loading loading = system->file_load_begin(filename_string.str); File_Loading loading = {0};
if (loading.exists){
b32 do_new_file = false;
if (flags & BufferCreate_AlwaysNew){
do_new_file = true;
}
else{
loading = system->file_load_begin(filename_string.str);
if (!loading.exists){
do_new_file = true;
}
}
if (do_new_file){
b32 in_general_mem = false; b32 in_general_mem = false;
char *buffer = push_array(part, char, loading.size); char *buffer = push_array(part, char, loading.size);
@ -867,7 +883,41 @@ CREATE_BUFFER_SIG(external_create_buffer){
return(result); return(result);
} }
KILL_BUFFER_SIG(external_kill_buffer){ SAVE_BUFFER_SIG(external_save_buffer)/*
DOC_PARAM(buffer, the buffer to save to a file)
DOC_PARAM(filename, the name of the file to save the buffer into)
DOC_PARAM(filename_len, length of the filename string)
DOC_PARAM(flags, not currently used)
DOC_RETURN(returns non-zero if the save succeeds)
*/{
Command_Data *cmd = (Command_Data*)app->cmd_context;
System_Functions *system = cmd->system;
Models *models = cmd->models;
int result = false;
Editing_File *file = imp_get_file(cmd, buffer);
if (file){
result = true;
String name = make_string(filename, filename_len);
view_save_file(system, models, file, 0, name, false);
}
return(result);
}
KILL_BUFFER_SIG(external_kill_buffer)/*
DOC_PARAM(buffer, a buffer identifier specifying the buffer to try to kill)
DOC_PARAM(view_id, the id of view that will contain the "are you sure" dialogue)
DOC_PARAM(flags, flags for buffer kill behavior)
DOC_RETURN(returns non-zero if the kill succeeds)
DOC
(
Tries to kill the idenfied buffer. If the buffer is dirty and the "are you sure"
dialogue needs to be displayed the provided view is used to show the dialogue.
If the view is not open the kill fails.
)
DOC_SEE(Buffer_Kill_Flags)
*/{
Command_Data *cmd = (Command_Data*)app->cmd_context; Command_Data *cmd = (Command_Data*)app->cmd_context;
System_Functions *system = cmd->system; System_Functions *system = cmd->system;
Models *models = cmd->models; Models *models = cmd->models;
@ -877,12 +927,18 @@ KILL_BUFFER_SIG(external_kill_buffer){
int result = false; int result = false;
if (file){ if (file){
result = true; if (flags & BufferKill_AlwaysKill){
if (always_kill){ result = true;
kill_file(system, models, file, string_zero()); kill_file(system, models, file, string_zero());
} }
else{ else{
try_kill_file(system, models, file, vptr, string_zero()); if (vptr == 0){
result = true;
try_kill_file(system, models, file, vptr, string_zero());
}
else{
// TODO(allen): message
}
} }
} }
@ -924,7 +980,19 @@ internal_get_view_next(Command_Data *cmd, View_Summary *view){
} }
} }
GET_VIEW_FIRST_SIG(external_get_view_first){ GET_VIEW_FIRST_SIG(external_get_view_first)/*
DOC_PARAM(access, the access flags for the access)
DOC_RETURN(returns the summary of the first view in a view loop)
DOC
(
Begins a loop across all the open views.
If the view summary returned is NULL, the loop is finished.
Views should not be closed or opened durring a view loop.
)
DOC_SEE(Access_Flag)
DOC_SEE(get_view_next)
*/{
Command_Data *cmd = (Command_Data*)app->cmd_context; Command_Data *cmd = (Command_Data*)app->cmd_context;
View_Summary view = {}; View_Summary view = {};
@ -936,7 +1004,21 @@ GET_VIEW_FIRST_SIG(external_get_view_first){
return(view); return(view);
} }
GET_VIEW_NEXT_SIG(external_get_view_next){ GET_VIEW_NEXT_SIG(external_get_view_next)/*
DOC_PARAM(view, pointer to the loop view originally returned by get_view_first)
DOC_PARAM(access, the access flags for the access)
DOC
(
Writes the next view into the view struct. To get predictable results every
call to get_view_first and get_view_next in the loop should have the same
access flags.
If the view summary returned is NULL, the loop is finished.
Views should not be closed or opened durring a view loop.
)
DOC_SEE(Access_Flag)
DOC_SEE(get_view_first)
*/{
Command_Data *cmd = (Command_Data*)app->cmd_context; Command_Data *cmd = (Command_Data*)app->cmd_context;
internal_get_view_next(cmd, view); internal_get_view_next(cmd, view);
@ -945,16 +1027,20 @@ GET_VIEW_NEXT_SIG(external_get_view_next){
} }
} }
GET_VIEW_SIG(external_get_view){ GET_VIEW_SIG(external_get_view)/*
DOC_PARAM(view_id, the id of the view to get)
DOC_PARAM(access, the access flags for the access)
DOC_RETURN(returns a summary that describes the indicated view if it is open and is accessible)
*/{
Command_Data *cmd = (Command_Data*)app->cmd_context; Command_Data *cmd = (Command_Data*)app->cmd_context;
View_Summary view = {}; View_Summary view = {0};
Live_Views *live_set = cmd->live_set; Live_Views *live_set = cmd->live_set;
int max = live_set->max; int max = live_set->max;
View *vptr = 0; View *vptr = 0;
index -= 1; view_id -= 1;
if (index >= 0 && index < max){ if (view_id >= 0 && view_id < max){
vptr = live_set->views + index; vptr = live_set->views + view_id;
fill_view_summary(&view, vptr, live_set, &cmd->models->working_set); fill_view_summary(&view, vptr, live_set, &cmd->models->working_set);
if (!access_test(view.lock_flags, access)){ if (!access_test(view.lock_flags, access)){
view = view_summary_zero(); view = view_summary_zero();
@ -964,7 +1050,10 @@ GET_VIEW_SIG(external_get_view){
return(view); return(view);
} }
GET_ACTIVE_VIEW_SIG(external_get_active_view){ GET_ACTIVE_VIEW_SIG(external_get_active_view)/*
DOC_PARAM(access, the access flags for the access)
DOC_RETURN(returns a summary that describes the active view)
*/{
Command_Data *cmd = (Command_Data*)app->cmd_context; Command_Data *cmd = (Command_Data*)app->cmd_context;
View_Summary view = {}; View_Summary view = {};
fill_view_summary(&view, cmd->view, &cmd->vars->live_set, &cmd->models->working_set); fill_view_summary(&view, cmd->view, &cmd->vars->live_set, &cmd->models->working_set);
@ -974,7 +1063,12 @@ GET_ACTIVE_VIEW_SIG(external_get_active_view){
return(view); return(view);
} }
VIEW_AUTO_TAB_SIG(external_view_auto_tab){ VIEW_AUTO_TAB_SIG(external_view_auto_tab)/*
DOC_PARAM(start, )
DOC_PARAM(end, )
DOC_PARAM(tab_width, )
DOC_PARAM(flags, )
*/{
Command_Data *cmd = (Command_Data*)app->cmd_context; Command_Data *cmd = (Command_Data*)app->cmd_context;
System_Functions *system = cmd->system; System_Functions *system = cmd->system;
Models *models = cmd->models; Models *models = cmd->models;

View File

@ -2968,10 +2968,9 @@ make_batch_from_indent_marks(Partition *part, Buffer *buffer, i32 line_start, i3
} }
internal void internal void
view_auto_tab_tokens(System_Functions *system, Models *models, file_auto_tab_tokens(System_Functions *system, Models *models,
View *view, i32 start, i32 end, Indent_Options opts){ Editing_File *file, i32 pos, i32 start, i32 end, Indent_Options opts){
#if BUFFER_EXPERIMENT_SCALPEL <= 0 #if BUFFER_EXPERIMENT_SCALPEL <= 0
Editing_File *file = view->file_data.file;
Mem_Options *mem = &models->mem; Mem_Options *mem = &models->mem;
Partition *part = &mem->part; Partition *part = &mem->part;
Buffer *buffer = &file->state.buffer; Buffer *buffer = &file->state.buffer;
@ -3000,19 +2999,37 @@ view_auto_tab_tokens(System_Functions *system, Models *models,
char *inv_str = (char*)part->base + part->pos; char *inv_str = (char*)part->base + part->pos;
Edit_Spec spec = Edit_Spec spec =
file_compute_whitespace_edit(mem, file, view->recent->cursor.pos, file_compute_whitespace_edit(mem, file, pos,
batch.edits, batch.str_base, batch.str_size, batch.edits, batch.str_base, batch.str_size,
inverse_array, inv_str, part->max - part->pos, batch.edit_count); inverse_array, inv_str, part->max - part->pos, batch.edit_count);
file_do_white_batch_edit(system, models, view->file_data.file, spec, hist_normal); file_do_white_batch_edit(system, models, file, spec, hist_normal);
} }
end_temp_memory(temp); end_temp_memory(temp);
#endif
}
internal void
view_auto_tab_tokens(System_Functions *system, Models *models,
View *view, i32 start, i32 end, Indent_Options opts){
#if BUFFER_EXPERIMENT_SCALPEL <= 0
Editing_File *file = view->file_data.file;
i32 pos = view->recent->cursor.pos;
file_auto_tab_tokens(system, models, file, pos, start, end, opts);
// TODO(allen): This is the bug dummy
{ {
i32 start = view->recent->cursor.pos; Buffer_Type *buffer = &file->state.buffer;
i32 line = buffer_get_line_index(buffer, pos);
i32 start = buffer->line_starts[line];
Hard_Start_Result hard_start = buffer_find_hard_start(buffer, start, 4); Hard_Start_Result hard_start = buffer_find_hard_start(buffer, start, 4);
view_cursor_move(view, hard_start.char_pos); if (hard_start.char_pos > pos){
view_cursor_move(view, hard_start.char_pos);
}
} }
#endif #endif
} }

View File

@ -31,15 +31,15 @@ int Buffer_Read_Range(Application_Links *app, Buffer_Summary *buffer, int start,
int Buffer_Replace_Range(Application_Links *app, Buffer_Summary *buffer, int start, int end, char *str, int len); int Buffer_Replace_Range(Application_Links *app, Buffer_Summary *buffer, int start, int end, char *str, int len);
int Buffer_Set_Setting(Application_Links *app, Buffer_Summary *buffer, int setting, int value); int Buffer_Set_Setting(Application_Links *app, Buffer_Summary *buffer, int setting, int value);
Buffer_Summary Create_Buffer(Application_Links *app, char *filename, int filename_len, int do_in_background); Buffer_Summary Create_Buffer(Application_Links *app, char *filename, int filename_len, unsigned int flags);
int Save_Buffer(Application_Links *app, Buffer_Summary *buffer, char *filename, int filename_len); int Save_Buffer(Application_Links *app, Buffer_Summary *buffer, char *filename, int filename_len, unsigned int flags);
int Kill_Buffer(Application_Links *app, Buffer_Identifier buffer, int always_kill, int view_id); int Kill_Buffer(Application_Links *app, Buffer_Identifier buffer, int view_id, unsigned int flags);
// View manipulation // View manipulation
View_Summary Get_View_First(Application_Links *app, unsigned int access); View_Summary Get_View_First(Application_Links *app, unsigned int access);
void Get_View_Next(Application_Links *app, View_Summary *view, unsigned int access); void Get_View_Next(Application_Links *app, View_Summary *view, unsigned int access);
View_Summary Get_View(Application_Links *app, int index, unsigned int access); View_Summary Get_View(Application_Links *app, int view_id, unsigned int access);
View_Summary Get_Active_View(Application_Links *app, unsigned int access); View_Summary Get_Active_View(Application_Links *app, unsigned int access);
int View_Auto_Tab (Application_Links *app, View_Summary *view, int start, int end, int tab_width, unsigned int flags); int View_Auto_Tab (Application_Links *app, View_Summary *view, int start, int end, int tab_width, unsigned int flags);