flashcards.nvim

Flashcards neovim plugin
git clone git://git.laack.co/flashcards.nvim.git
Log | Files | Refs | README | LICENSE

init.lua (4002B)


      1 local state = {
      2     buf = nil,
      3     win = nil,
      4     cards = {},
      5     index = 1,
      6     showing_back = false,
      7 }
      8 
      9 local function shuffle(t)
     10     for i = #t, 2, -1 do
     11         local j = math.random(i)
     12         t[i], t[j] = t[j], t[i]
     13     end
     14     return t
     15 end
     16 
     17 local function formatCard(strArr)
     18 
     19     local result = {}
     20     local firstNonBlank = false
     21 
     22     for i = 2, #strArr do
     23         if strArr[i] == "" and firstNonBlank == false then
     24             goto continue
     25         end
     26 
     27         firstNonBlank = true
     28         table.insert(result, strArr[i])
     29 
     30         ::continue::
     31     end
     32 
     33     return result
     34 end
     35 
     36 local function formatH1(str)
     37     if not str then
     38         return ""
     39     end
     40 
     41     if #str >= 3 then
     42         return str:sub(3)
     43     end
     44 
     45     return ""
     46 end
     47 
     48 local function load_cards()
     49 
     50     -- clear state
     51     state.cards = {}
     52     state.index = 1
     53     state.showing_back = false
     54 
     55     local cwd = vim.fs.dirname(vim.api.nvim_buf_get_name(0))
     56     local files = vim.split(vim.fn.glob(cwd .. "/*.md"), "\n")
     57     files = shuffle(files)
     58 
     59     for index, _ in ipairs(files) do
     60         if files[index] ~= "" then
     61             local file = vim.fn.readfile(files[index])
     62             -- add card to state
     63             table.insert(state.cards, {
     64                 formatH1(file[1]), formatCard(file)
     65             })
     66         end
     67     end
     68 end
     69 
     70 local function render()
     71 
     72     if state.cards[state.index] == nil then
     73         print("Unable to find card.")
     74         return
     75     end
     76 
     77     vim.bo[state.buf].modifiable = true
     78     vim.api.nvim_buf_set_lines(state.buf, 0, -1, false, {})
     79     if state.showing_back then
     80         vim.api.nvim_buf_set_lines(state.buf, 0, 10, false, state.cards[state.index][2])
     81     else
     82         vim.api.nvim_buf_set_lines(state.buf, 0, 10, false, {state.cards[state.index][1]})
     83     end
     84     vim.bo[state.buf].modifiable = false
     85 end
     86 
     87 
     88 local function previous_card()
     89     state.index = state.index - 1
     90     state.showing_back = false
     91 
     92     if state.index < 1 then
     93         state.index = #state.cards
     94     end
     95 
     96     render()
     97 end
     98 
     99 local function next_card()
    100     state.index = state.index + 1
    101     state.showing_back = false
    102 
    103     if state.index > #state.cards then
    104         state.index = 1
    105     end
    106 
    107     render()
    108 end
    109 
    110 local function flip_card()
    111     state.showing_back = not state.showing_back
    112     render()
    113 end
    114 
    115 local function flash()
    116 
    117     load_cards()
    118 
    119     if state.cards[1] == nil then
    120         print("No cards found in the cwd.")
    121         return
    122     end
    123 
    124     if state.buf ~= nil then
    125         vim.api.nvim_buf_delete(state.buf, { force = true })
    126         state.buf = nil
    127         state.win = nil
    128     end
    129 
    130     state.win = vim.api.nvim_get_current_win()
    131     state.buf = vim.api.nvim_create_buf(false, true)
    132 
    133     vim.api.nvim_buf_set_keymap(state.buf, "n", "<Left>", "<Cmd>PreviousCard<CR>", {})
    134     vim.api.nvim_buf_set_keymap(state.buf, "n", "<Right>", "<Cmd>NextCard<CR>", {})
    135     vim.api.nvim_buf_set_keymap(state.buf, "n", "<Up>", "<Cmd>Flip<CR>", {})
    136     vim.api.nvim_buf_set_keymap(state.buf, "n", "<Down>", "<Cmd>Flip<CR>", {})
    137 
    138     vim.api.nvim_buf_set_keymap(state.buf, "n", "h", "<Cmd>PreviousCard<CR>", {})
    139     vim.api.nvim_buf_set_keymap(state.buf, "n", "l", "<Cmd>NextCard<CR>", {})
    140     vim.api.nvim_buf_set_keymap(state.buf, "n", "k", "<Cmd>Flip<CR>", {})
    141     vim.api.nvim_buf_set_keymap(state.buf, "n", "j", "<Cmd>Flip<CR>", {})
    142 
    143     local row = 0
    144     local col = 0
    145 
    146     local width = vim.fn.winwidth(state.win)
    147     local height = vim.fn.winheight(state.win)
    148 
    149     local opts = {
    150       width = width,
    151       height = height,
    152       row = row,
    153       col = col,
    154       border = "rounded",
    155       relative = "win",
    156       title = "Flashcards",
    157       title_pos = "center"
    158     }
    159 
    160     local _ = vim.api.nvim_open_win(state.buf, true, opts)
    161 
    162     render()
    163 
    164 
    165 end
    166 
    167 vim.api.nvim_create_user_command('Flash', flash, {})
    168 vim.api.nvim_create_user_command('Flip', flip_card, {})
    169 vim.api.nvim_create_user_command('NextCard', next_card, {}) -- defaults first side
    170 vim.api.nvim_create_user_command('PreviousCard', previous_card, {}) -- defaults first side