aboutsummaryrefslogtreecommitdiff
path: root/lua/simple-denote.lua
blob: 98c6ded8ab6019525e74e5e67b8692dd7db5ef5e (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
local M = {}

local config = require("simple-denote.config")
local api = require("simple-denote.api")

function M.load_cmd(options)
  vim.api.nvim_create_user_command("Denote", function(opts)
    if opts.fargs[1] == "note" then
      api.note(options)
    elseif opts.fargs[1] == "title" then
      api.title(options)
    elseif opts.fargs[1] == "keywords" then
      api.keywords()
    elseif opts.fargs[1] == "signature" then
      api.signature()
    elseif opts.fargs[1] == "extension" then
      api.extension()
    elseif opts.fargs[1] == "dir" then
      M.switch_dir()
    else
      error("Unsupported operation " .. opts.fargs[1])
    end
  end, {
    nargs = 1,
    complete = function()
      return { "note", "title", "keywords", "signature", "extension", "dir" }
    end,
  })
end

---Add / to directory if necessary and set the heading_char based on the ext
function M.fix_options()
  if config.options.dir:sub(-1) ~= "/" then
    config.options.dir = config.options.dir .. "/"
  end
  for i, d in ipairs(config.options.directories) do
    if d:sub(-1) ~= "/" then
      config.options.directories[i] = d .. "/"
    end
  end
  if #config.options.directories > 0 then
    vim.g.denote_dir = config.options.dir
  end
  if config.options.ext == "md" then
    config.options.heading_char = "#"
  elseif config.options.ext == "org" or config.options.ext == "norg" then
    config.options.heading_char = "*"
  end
end

function M.switch_dir()
  local dirs = config.options.directories
  if #dirs == 0 then
    vim.notify("No directories configured. Add directories = { ... } to your setup.", vim.log.levels.WARN)
    return
  end

  local current = config.options.dir
  local cursor_line = 1
  for i, d in ipairs(dirs) do
    if d == current then
      cursor_line = i
      break
    end
  end

  local max_width = 0
  for _, d in ipairs(dirs) do
    max_width = math.max(max_width, #d)
  end

  local buf = vim.api.nvim_create_buf(false, true)
  vim.api.nvim_buf_set_lines(buf, 0, -1, false, dirs)
  vim.api.nvim_buf_set_option(buf, "modifiable", false)
  vim.api.nvim_buf_set_option(buf, "bufhidden", "wipe")

  local width = max_width + 2
  local height = #dirs
  local row = math.floor((vim.o.lines - height) / 2)
  local col = math.floor((vim.o.columns - width) / 2)

  local win = vim.api.nvim_open_win(buf, true, {
    relative = "editor",
    width = width,
    height = height,
    row = row,
    col = col,
    style = "minimal",
    border = "single",
  })

  vim.wo[win].cursorline = true
  vim.api.nvim_win_set_cursor(win, { cursor_line, 0 })

  local function select()
    local line = vim.api.nvim_win_get_cursor(win)[1]
    local choice = dirs[line]
    if choice then
      config.options.dir = choice
      vim.g.denote_dir = choice
      vim.notify("Notes directory: " .. choice, vim.log.levels.INFO)
    end
    vim.api.nvim_win_close(win, true)
  end

  local function cancel()
    vim.api.nvim_win_close(win, true)
  end

  vim.keymap.set("n", "<CR>", select, { buffer = buf, nowait = true })
  vim.keymap.set("n", "<Esc>", cancel, { buffer = buf, nowait = true })
  vim.keymap.set("n", "<C-c>", cancel, { buffer = buf, nowait = true })
  vim.keymap.set("n", "j", function()
    local line = math.min(vim.api.nvim_win_get_cursor(win)[1] + 1, #dirs)
    vim.api.nvim_win_set_cursor(win, { line, 0 })
  end, { buffer = buf, nowait = true })
  vim.keymap.set("n", "k", function()
    local line = math.max(vim.api.nvim_win_get_cursor(win)[1] - 1, 1)
    vim.api.nvim_win_set_cursor(win, { line, 0 })
  end, { buffer = buf, nowait = true })
  vim.keymap.set("n", "<Down>", function()
    local line = math.min(vim.api.nvim_win_get_cursor(win)[1] + 1, #dirs)
    vim.api.nvim_win_set_cursor(win, { line, 0 })
  end, { buffer = buf, nowait = true })
  vim.keymap.set("n", "<Up>", function()
    local line = math.max(vim.api.nvim_win_get_cursor(win)[1] - 1, 1)
    vim.api.nvim_win_set_cursor(win, { line, 0 })
  end, { buffer = buf, nowait = true })
end

---@param options? table user configuration
function M.setup(options)
  config.options = vim.tbl_deep_extend("force", config.defaults, options or {})
  M.fix_options()
  M.load_cmd(config.options)
end

return M