diff --git a/src/core/core.odin b/src/core/core.odin index 5ec62a3..eefb3fa 100644 --- a/src/core/core.odin +++ b/src/core/core.odin @@ -50,6 +50,7 @@ State :: struct { command_args: [dynamic]EditorCommandArgument, current_panel: Maybe(int), + last_panel: Maybe(int), panels: util.StaticList(Panel), buffers: util.StaticList(FileBuffer), } @@ -150,6 +151,20 @@ current_buffer :: proc(state: ^State) -> ^FileBuffer { return nil } +switch_to_panel :: proc(state: ^State, panel_id: int) { + if panel, ok := util.get(&state.panels, panel_id).?; ok { + if current_panel, ok := state.current_panel.?; ok { + if current_panel, ok := util.get(&state.panels, current_panel).?; ok { + if !current_panel.is_floating { + state.last_panel = state.current_panel + } + } + } + + state.current_panel = panel_id + } +} + new_buffer_virtual :: proc(state: ^State) -> (id: int, buffer: ^FileBuffer, ok: bool) { return util.append(&state.buffers, new_virtual_file_buffer(context.allocator)) } @@ -178,19 +193,37 @@ new_buffer_file :: proc(state: ^State, file_path: string, line: int = 0, col: in new_buffer :: proc{new_buffer_file, new_buffer_virtual} open_buffer_file :: proc(state: ^State, file_path: string, line: int = 0, col: int = 0) { + attempt_switch_to_panel_buffer :: proc(state: ^State, panel: ^Panel, file_path: string, line: int, col: int) -> bool { + if type, ok := &panel.type.(FileBufferPanel); ok { + buffer_id, _, ok := new_buffer_file(state, file_path, line, col) + if ok { + type.buffer_id = buffer_id + switch_to_panel(state, panel.id) + + return true + } + } + + return false + } + + if last_panel, ok := state.last_panel.?; ok { + if panel, ok := util.get(&state.panels, last_panel).?; ok { + if attempt_switch_to_panel_buffer(state, panel, file_path, line, col) { + return + } + } + } + next_id := 0 for { if panel, ok := util.get(&state.panels, next_id).?; ok { - if type, ok := &panel.type.(FileBufferPanel); ok { - buffer_id, _, ok := new_buffer_file(state, file_path, line, col) - if ok { - type.buffer_id = buffer_id - state.current_panel = panel.id - } - + if attempt_switch_to_panel_buffer(state, panel, file_path, line, col) { break - } else { - next_id := util.get_next(&state.panels, next_id) + } + + if id, ok := util.get_next(&state.panels, next_id).?; ok { + next_id = id continue } } diff --git a/src/main.odin b/src/main.odin index 6742d42..3da828e 100644 --- a/src/main.odin +++ b/src/main.odin @@ -265,10 +265,6 @@ main :: proc() { panels.open(&state, panels.make_file_buffer_panel("")) } - - panels.open(&state, panels.make_debug_panel()) - panels.open(&state, panels.make_debug_panel()) - if sdl2.Init({.VIDEO}) < 0 { log.error("SDL failed to initialize:", sdl2.GetError()); return; diff --git a/src/panels/debug.odin b/src/panels/debug.odin index 5886179..1c474b2 100644 --- a/src/panels/debug.odin +++ b/src/panels/debug.odin @@ -85,7 +85,13 @@ render_buffer_list :: proc(state: ^core.State, s: ^ui.State) { for i in 0.. len(state.directory) { + buffer_label = fmt.tprintf("buf '%v' - %v", i, buffer.file_path[len(state.directory):]) + } else { + buffer_label = fmt.tprintf("buf '%v' - %v", i, buffer.file_path) + } + ui.open_element(s, buffer_label, {}) ui.close_element(s) } @@ -121,6 +127,13 @@ render_panel_list :: proc(state: ^core.State, s: ^ui.State) { }) ui.close_element(s) + + if state.last_panel != nil { + last_panel_label := fmt.tprintf("last panel id '%v'", state.last_panel.?) + ui.open_element(s, last_panel_label, {}) + ui.close_element(s) + } + for i in 0.. (panel_id: int, ok: bool) { if panel_id, panel, ok := util.append_static_list(&state.panels, panel); ok && make_active { panel.id = panel_id - state.current_panel = panel_id arena_bytes, err := make([]u8, 1024*1024*8) if err != nil { @@ -68,6 +83,7 @@ open :: proc(state: ^core.State, panel: core.Panel, make_active: bool = true) -> panel->create(state) + core.switch_to_panel(state, panel_id) core.reset_input_map(state) return panel_id, true @@ -86,9 +102,12 @@ close :: proc(state: ^core.State, panel_id: int) { util.delete(&state.panels, panel_id) - // TODO: keep track of the last active panel instead of focusing back to the first one - if first_active, ok := util.get_first_active_index(&state.panels).?; ok { + if last_panel, ok := state.last_panel.?; ok { + core.switch_to_panel(state, last_panel) + } else if first_active, ok := util.get_first_active_index(&state.panels).?; ok { state.current_panel = first_active + } else { + // TODO: open panel } core.reset_input_map(state)