X-Git-Url: https://git.r.bdr.sh/rbdr/nota.nvim/blobdiff_plain/56292c7915662bbf721ca8c3d2cee6a04134a9c6..9e9e89d8556ecafa6b11ab21aa9ffab550f7f3ad:/lua/task_views.lua diff --git a/lua/task_views.lua b/lua/task_views.lua index f763996..9309ad3 100644 --- a/lua/task_views.lua +++ b/lua/task_views.lua @@ -1,28 +1,137 @@ ------------------------------------------------------------------------------- -- Tools to deal with task views ------------------------------------------------------------------------------- +local TaskViews = {} +local Util = require('util') +local Configuration = require('configuration') +local api = vim.api +------------------------------------------------------------------------------- +-- Internal Functions +------------------------------------------------------------------------------- +local function get_this_weeks_files() + local today = os.time() + local day_of_week = os.date('*t', today).wday + local week_start = today - (day_of_week - 2) * 86400 + local filenames = {} + + for i = 0, 6 do + local date = os.date('*t', week_start + i * 86400) + table.insert(filenames, string.format('%04d-%02d-%02d.md', date.year, date.month, date.day)) + end + + return filenames +end + +local function find_tasks(completed, important) + local file_directory_path = Configuration.path_for() + + local completed_fragment = '(\\s|x)' + if completed == 1 then + completed_fragment = 'x' + elseif completed == 0 then + completed_fragment = '\\s' + end + + local important_fragment = '(\\-|\\*)' + if important == 1 then + important_fragment = '\\*' + elseif important == 0 then + important_fragment = '\\-' + end + + + local pattern = '^\\s*' .. important_fragment .. '\\s\\[' .. completed_fragment .. ']' + + local command = string.format('rg --vimgrep \'%s\' \'%s\'', pattern, file_directory_path) + local results = vim.fn.systemlist(command) + + if vim.v.shell_error == 0 then + local items = {} + for _, line in ipairs(results) do + local filename, lnum, col, text = line:match('([^:]+):(%d+):(%d+):(.*)') + table.insert(items, { + filename = filename, + lnum = tonumber(lnum), + col = tonumber(col), + text = text, + }) + end + + -- Set location list for the current window and open it + vim.fn.setloclist(0, items) + vim.cmd('lopen') + end +end + +local function populate_quicklist_with_files(filenames) + local uv = vim.loop + local items = {} + local task_pattern = '^%s*%- %[[ ]?x?%]' + local important_task_pattern = '^%s*%* %[[ ]?x?%]' + + local file_directory_path = Configuration.path_for(Configuration.configuration.periodic_locations.daily) + Util.ensure_directory_exists(file_directory_path) + + for _, filename in ipairs(filenames) do + local daily_note = Util.join(file_directory_path, filename) + local stat = uv.fs_stat(daily_note) + + if stat then -- File exists + local file, err = io.open(daily_note, 'r') + if file then + local set_header = 0 + local line_number = 0 + for line in file:lines() do + line_number = line_number + 1 + if line:match(task_pattern) or line:match(important_task_pattern) then + if set_header == 0 then + local header = string.sub(filename:match('([^/\\]+)$'), 1, -4) + table.insert(items, {filename = '', lnum = 0, text = header}) + set_header = 1 + end + table.insert(items, {filename = daily_note, text = line, lnum = line_number}) + end + end + file:close() + end + end + end + vim.fn.setloclist(0, {}, ' ', {title = 'Weekly Tasks', items = items}) + vim.cmd('lopen') +end + ------------------------------------------------------------------------------- -- Public Interface ------------------------------------------------------------------------------- --- Opens the agenda view to show tasks --- @param configuration tNotaConfiguration the plugin configuration -function open_agenda(configuration) - error("Not yet implemented") +function TaskViews.open_agenda() + local week_filenames = get_this_weeks_files() + populate_quicklist_with_files(week_filenames) end --- Opens the view to show open tasks --- @param configuration tNotaConfiguration the plugin configuration -function open_open(configuration) - error("Not yet implemented") +function TaskViews.open_open() + find_tasks(0) +end + +--- Opens the view to show open important tasks +function TaskViews.open_open_important() + find_tasks(0, 1) end --- Opens the view to search the journal --- @param configuration tNotaConfiguration the plugin configuration -function open_journal(configuration) - error("Not yet implemented") +function TaskViews.open_journal() + local pattern = '^\\s*(\\*|\\-)\\s\\[x]' + -- local pattern = 'hell' + local success, module = pcall(require, 'fzf-lua') + if success then + local notes_path = Configuration.path_for() + Util.ensure_directory_exists(notes_path) + module.files({ cwd = notes_path, cmd = 'rg --line-number --no-heading -- \'' .. pattern ..'\''}) + else + api.nvim_err_writeln('This feature requires optional dependency fzf-lua') + end end -------------------------------------------------------------------------------- --- Internal Functions -------------------------------------------------------------------------------- +return TaskViews