1+ local uv = vim .uv or vim .loop
2+
3+ --- @class cheaty.Window
14local M = {}
25
3- local win_id = nil
4- local buf_id = nil
6+ local win_id , buf_id = nil , nil --- @type integer | nil , integer | nil
7+ local fd , stat = nil , nil --- @type integer | nil , uv.fs_stat.result | nil
8+
9+ --- @param cfg cheatyOpts
10+ --- @param flags ? uv.fs_open.flags
11+ local function open_file (cfg , flags )
12+ if not cfg .save_file or cfg .save_file == " " then
13+ error (" No valid path!" , vim .log .levels .ERROR )
14+ end
15+
16+ if vim .fn .filereadable (cfg .save_file ) ~= 1 then
17+ vim .fn .writefile (cfg .cheatsheet or {}, cfg .save_file )
18+ end
519
20+ stat = uv .fs_stat (cfg .save_file )
21+ fd = uv .fs_open (cfg .save_file , flags or " r" , tonumber (" 644" , 8 ))
22+ end
23+
24+ --- @param cfg cheatyOpts
625local function create_window (cfg )
726 buf_id = vim .api .nvim_create_buf (false , true )
827
9- vim . api . nvim_buf_set_lines ( buf_id , 0 , - 1 , false , cfg . cheatsheet )
28+ open_file ( cfg , " r " )
1029
11- -- Buffer options
12- local buffer = vim .bo [buf_id ]
30+ local contents = cfg .cheatsheet
31+ if fd and stat then
32+ contents = vim .split (uv .fs_read (fd , stat .size ), " \n " , { trimempty = false })
33+ uv .fs_close (fd )
34+ end
1335
14- buffer .buftype = " nofile"
15- buffer .bufhidden = " wipe"
16- buffer .modifiable = false
17- buffer .swapfile = false
18- buffer .filetype = " markdown"
36+ vim .api .nvim_buf_set_lines (buf_id , 0 , - 1 , false , contents )
1937
20- vim .api .nvim_buf_call (buf_id , function ()
21- vim .cmd (" doautocmd FileType markdown" )
22- end )
38+ -- Buffer options
39+ local opts = { buf = buf_id } --- @type vim.api.keyset.option
40+ vim .api .nvim_set_option_value (" buftype" , " nofile" , opts )
41+ -- vim.api.nvim_set_option_value("bufhidden", "wipe", opts)
42+ vim .api .nvim_set_option_value (" modified" , false , opts )
43+ vim .api .nvim_set_option_value (" modifiable" , true , opts )
44+ vim .api .nvim_set_option_value (" swapfile" , false , opts )
45+ vim .api .nvim_set_option_value (" filetype" , " markdown" , opts )
2346
2447 local width = math.floor (vim .o .columns * cfg .width )
2548 local height = math.floor (vim .o .lines * cfg .height )
@@ -29,30 +52,62 @@ local function create_window(cfg)
2952
3053 win_id = vim .api .nvim_open_win (buf_id , true , {
3154 relative = " editor" ,
55+ noautocmd = false ,
56+ title = " Cheaty" ,
57+ title_pos = " center" ,
3258 row = row ,
3359 col = col ,
3460 width = width ,
3561 height = height ,
3662 style = " minimal" ,
3763 border = " rounded" ,
3864 })
65+
66+ vim .keymap .set (" n" , " q" , M .close , { buffer = buf_id })
67+
68+ local augroup = vim .api .nvim_create_augroup (" cheaty" , { clear = true })
69+ vim .api .nvim_create_autocmd ({ " TextChanged" , " TextChangedI" }, {
70+ group = augroup ,
71+ buffer = buf_id ,
72+ callback = function ()
73+ if not (buf_id and vim .api .nvim_buf_is_valid (buf_id )) then
74+ return
75+ end
76+
77+ open_file (cfg , " w" )
78+ if not fd then
79+ return
80+ end
81+
82+ local content = vim .api .nvim_buf_get_lines (buf_id , 0 , - 1 , true )
83+ uv .fs_write (fd , table.concat (content , " \n " ))
84+ uv .fs_close (fd )
85+ end ,
86+ })
3987end
4088
4189function M .close ()
42- if win_id and vim . api . nvim_win_is_valid ( win_id ) then
43- vim . api . nvim_win_close ( win_id , true )
90+ if not ( buf_id or win_id ) then
91+ return
4492 end
4593
94+ pcall (vim .api .nvim_buf_delete , buf_id , { force = true })
95+ pcall (vim .api .nvim_win_close , win_id , true )
96+
97+ fd = nil
98+ stat = nil
4699 win_id = nil
47100 buf_id = nil
48101end
49102
103+ --- @param cfg cheatyOpts
50104function M .toggle (cfg )
51- if win_id and vim . api . nvim_win_is_valid ( win_id ) then
105+ if win_id and buf_id then
52106 M .close ()
53- else
54- create_window (cfg )
107+ return
55108 end
109+
110+ create_window (cfg )
56111end
57112
58113return M
0 commit comments