@@ -9,6 +9,7 @@ local Config = require("chatgpt.config")
99local Utils = require (" chatgpt.utils" )
1010local Spinner = require (" chatgpt.spinner" )
1111local Settings = require (" chatgpt.settings" )
12+ local Help = require (" chatgpt.help" )
1213
1314EDIT_FUNCTION_ARGUMENTS = {
1415 function_call = {
@@ -140,6 +141,9 @@ M.edit_with_instructions = function(output_lines, bufnr, selection, ...)
140141 local openai_params = Config .options .openai_edit_params
141142 local use_functions_for_edits = Config .options .use_openai_functions_for_edits
142143 local settings_panel = Settings .get_settings_panel (" edits" , openai_params )
144+ local help_panel = Help .get_help_panel (" edit" ) -- I like the highlighting for Lua.
145+ local open_extra_panels = {} -- tracks which extra panels are open
146+ local active_panel = instructions_input -- for cycling windows
143147 input_window = Popup (Config .options .popup_window )
144148 output_window = Popup (Config .options .popup_window )
145149 instructions_input = ChatInput (Config .options .popup_input , {
@@ -226,56 +230,119 @@ M.edit_with_instructions = function(output_lines, bufnr, selection, ...)
226230 end , { noremap = true })
227231 end
228232
233+ local function inTable (tbl , item )
234+ for key , value in pairs (tbl ) do
235+ if value == item then
236+ return key
237+ end
238+ end
239+ return false
240+ end
241+
242+ -- toggle extra panels
243+ local function toggle_extra_panel (extra_panel , modifiable_panel )
244+ local extra_open = inTable (open_extra_panels , extra_panel )
245+ if not extra_open then
246+ table.insert (open_extra_panels , extra_panel )
247+ local extra_boxes = function ()
248+ local box_size = (100 / # open_extra_panels ) .. " %"
249+ local boxes = {}
250+ for i , panel in ipairs (open_extra_panels ) do
251+ -- for the last panel, make it grow to fill the remaining space
252+ if i == # open_extra_panels then
253+ table.insert (boxes , Layout .Box (panel , { grow = 1 }))
254+ else
255+ table.insert (boxes , Layout .Box (panel , { size = box_size }))
256+ end
257+ end
258+ return Layout .Box (boxes , { dir = " col" , size = 40 })
259+ end
260+ layout :update (Layout .Box ({
261+ Layout .Box ({
262+ Layout .Box (input_window , { grow = 1 }),
263+ Layout .Box (instructions_input , { size = 3 }),
264+ }, { dir = " col" , grow = 1 }),
265+ Layout .Box (output_window , { grow = 1 }),
266+ extra_boxes (),
267+ }, { dir = " row" }))
268+ extra_panel :show ()
269+ extra_panel :mount ()
270+
271+ vim .api .nvim_set_current_win (extra_panel .winid )
272+ active_panel = extra_panel
273+ vim .api .nvim_buf_set_option (extra_panel .bufnr , " modifiable" , modifiable_panel )
274+ vim .api .nvim_win_set_option (extra_panel .winid , " cursorline" , true )
275+ else
276+ table.remove (open_extra_panels , extra_open )
277+ if # open_extra_panels == 0 then
278+ layout :update (Layout .Box ({
279+ Layout .Box ({
280+ Layout .Box (input_window , { grow = 1 }),
281+ Layout .Box (instructions_input , { size = 3 }),
282+ }, { dir = " col" , size = " 50%" }),
283+ Layout .Box (output_window , { size = " 50%" }),
284+ }, { dir = " row" }))
285+ extra_panel :hide ()
286+ vim .api .nvim_set_current_win (instructions_input .winid )
287+ active_panel = instructions_input
288+ else
289+ local box_size = (100 / # open_extra_panels ) .. " %"
290+ local extra_boxes = function ()
291+ local boxes = {}
292+ for _ , panel in ipairs (open_extra_panels ) do
293+ table.insert (boxes , Layout .Box (panel , { size = box_size }))
294+ end
295+ return Layout .Box (boxes , { dir = " col" , size = 40 })
296+ end
297+ layout :update (Layout .Box ({
298+ Layout .Box ({
299+ Layout .Box (input_window , { grow = 1 }),
300+ Layout .Box (instructions_input , { size = 3 }),
301+ }, { dir = " col" , grow = 1 }),
302+ Layout .Box (output_window , { grow = 1 }),
303+ extra_boxes (),
304+ }, { dir = " row" }))
305+ extra_panel :hide ()
306+ vim .api .nvim_set_current_win (open_extra_panels [# open_extra_panels ].winid )
307+ active_panel = open_extra_panels [# open_extra_panels ]
308+ end
309+ end
310+ for _ , window in ipairs ({ input_window , output_window }) do
311+ vim .api .nvim_buf_set_option (window .bufnr , " filetype" , filetype )
312+ vim .api .nvim_win_set_option (window .winid , " number" , true )
313+ end
314+ end
315+
229316 -- toggle settings
230- local settings_open = false
231- for _ , popup in ipairs ({ settings_panel , instructions_input }) do
317+ for _ , popup in ipairs ({ instructions_input , settings_panel , help_panel }) do
232318 for _ , mode in ipairs ({ " n" , " i" }) do
233319 popup :map (mode , Config .options .edit_with_instructions .keymaps .toggle_settings , function ()
234- if settings_open then
235- layout :update (Layout .Box ({
236- Layout .Box ({
237- Layout .Box (input_window , { grow = 1 }),
238- Layout .Box (instructions_input , { size = 3 }),
239- }, { dir = " col" , size = " 50%" }),
240- Layout .Box (output_window , { size = " 50%" }),
241- }, { dir = " row" }))
242- settings_panel :hide ()
243- vim .api .nvim_set_current_win (instructions_input .winid )
244- else
245- layout :update (Layout .Box ({
246- Layout .Box ({
247- Layout .Box (input_window , { grow = 1 }),
248- Layout .Box (instructions_input , { size = 3 }),
249- }, { dir = " col" , grow = 1 }),
250- Layout .Box (output_window , { grow = 1 }),
251- Layout .Box (settings_panel , { size = 40 }),
252- }, { dir = " row" }))
253- settings_panel :show ()
254- settings_panel :mount ()
255-
256- vim .api .nvim_set_current_win (settings_panel .winid )
257- vim .api .nvim_buf_set_option (settings_panel .bufnr , " modifiable" , false )
258- vim .api .nvim_win_set_option (settings_panel .winid , " cursorline" , true )
259- end
260- settings_open = not settings_open
320+ toggle_extra_panel (settings_panel , false )
321+ -- set input and output settings
322+ -- TODO
323+ end , {})
324+ end
325+ end
326+
327+ -- toggle help
328+ for _ , popup in ipairs ({ instructions_input , settings_panel , help_panel }) do
329+ for _ , mode in ipairs ({ " n" , " i" }) do
330+ popup :map (mode , Config .options .edit_with_instructions .keymaps .toggle_help , function ()
331+ toggle_extra_panel (help_panel , false )
261332 -- set input and output settings
262333 -- TODO
263- for _ , window in ipairs ({ input_window , output_window }) do
264- vim .api .nvim_buf_set_option (window .bufnr , " filetype" , filetype )
265- vim .api .nvim_win_set_option (window .winid , " number" , true )
266- end
267334 end , {})
268335 end
269336 end
270337
271338 -- cycle windows
272- local active_panel = instructions_input
273- for _ , popup in ipairs ({ input_window , output_window , settings_panel , instructions_input }) do
339+ for _ , popup in ipairs ({ input_window , output_window , settings_panel , help_panel , instructions_input }) do
274340 for _ , mode in ipairs ({ " n" , " i" }) do
275341 if mode == " i" and (popup == input_window or popup == output_window ) then
276342 goto continue
277343 end
278344 popup :map (mode , Config .options .edit_with_instructions .keymaps .cycle_windows , function ()
345+ local in_table = inTable (open_extra_panels , active_panel )
279346 if active_panel == instructions_input then
280347 vim .api .nvim_set_current_win (input_window .winid )
281348 active_panel = input_window
@@ -285,16 +352,23 @@ M.edit_with_instructions = function(output_lines, bufnr, selection, ...)
285352 active_panel = output_window
286353 vim .api .nvim_command (" stopinsert" )
287354 elseif active_panel == output_window and mode ~= " i" then
288- if settings_open then
289- vim .api .nvim_set_current_win (settings_panel .winid )
290- active_panel = settings_panel
355+ if # open_extra_panels == 0 then
356+ vim .api .nvim_set_current_win (instructions_input .winid )
357+ active_panel = instructions_input
291358 else
359+ vim .api .nvim_set_current_win (open_extra_panels [1 ].winid )
360+ active_panel = open_extra_panels [1 ]
361+ end
362+ elseif in_table then
363+ -- next index with wrap around and 0 for instructions_input
364+ local next_index = (in_table + 1 ) % (# open_extra_panels + 1 )
365+ if next_index == 0 then
292366 vim .api .nvim_set_current_win (instructions_input .winid )
293367 active_panel = instructions_input
368+ else
369+ vim .api .nvim_set_current_win (open_extra_panels [next_index ].winid )
370+ active_panel = open_extra_panels [next_index ]
294371 end
295- elseif active_panel == settings_panel then
296- vim .api .nvim_set_current_win (instructions_input .winid )
297- active_panel = instructions_input
298372 end
299373 end , {})
300374 :: continue::
@@ -303,7 +377,7 @@ M.edit_with_instructions = function(output_lines, bufnr, selection, ...)
303377
304378 -- toggle diff mode
305379 local diff_mode = Config .options .edit_with_instructions .diff
306- for _ , popup in ipairs ({ settings_panel , instructions_input }) do
380+ for _ , popup in ipairs ({ help_panel , settings_panel , instructions_input }) do
307381 for _ , mode in ipairs ({ " n" , " i" }) do
308382 popup :map (mode , Config .options .edit_with_instructions .keymaps .toggle_diff , function ()
309383 diff_mode = not diff_mode
0 commit comments