-------------------------------------------------------------------------------
-- Tools to deal with tasks
-------------------------------------------------------------------------------
+local Tasks = {}
+local Configuration = require('configuration')
+local Notes = require('notes')
+local Util = require('util')
+local api = vim.api
+-------------------------------------------------------------------------------
+-- Internal Functions
+-------------------------------------------------------------------------------
+local unchecked_pattern = '^(%s*)%- %[ %]'
+local unchecked_important_pattern = '^(%s*)%* %[ %]'
+local checked_pattern = '^(%s*)%- %[x%]'
+local checked_important_pattern = '^(%s*)%* %[x%]'
+
+local function open(path)
+ local parent = Util.directory_name(path)
+ Util.ensure_directory_exists(parent)
+ vim.cmd('edit ' .. path)
+end
+
+local function open_inbox()
+ local path = Configuration.path_for(Configuration.configuration.tasks.inbox)
+ open(path)
+end
+local function open_someday()
+ local path = Configuration.path_for(Configuration.configuration.tasks.someday)
+ open(path)
+end
-------------------------------------------------------------------------------
-- Public Interface
-------------------------------------------------------------------------------
--- Toggles a task completion status
--- @param configuration tNotaConfiguration the plugin configuration
-function toggle(configuration)
- error("Not yet implemented")
+function Tasks.toggle()
+ local line_number = api.nvim_win_get_cursor(0)[1]
+ local line = api.nvim_get_current_line()
+
+ if line:match(unchecked_pattern) then
+ line = line:gsub(unchecked_pattern, '%1- [x]', 1)
+ elseif line:match(unchecked_important_pattern) then
+ line = line:gsub(unchecked_important_pattern, '%1* [x]', 1)
+ elseif line:match(checked_pattern) then
+ line = line:gsub(checked_pattern, '%1- [ ]', 1)
+ elseif line:match(checked_important_pattern) then
+ line = line:gsub(checked_important_pattern, '%1* [ ]', 1)
+ end
+
+ api.nvim_buf_set_lines(0, line_number - 1, line_number, false, {line})
+end
+
+--- Toggles a task completion status
+function Tasks.toggle_importance()
+ local line_number = api.nvim_win_get_cursor(0)[1]
+ local line = api.nvim_get_current_line()
+
+ if line:match(unchecked_pattern) then
+ line = line:gsub(unchecked_pattern, '%1* [ ]', 1)
+ elseif line:match(unchecked_important_pattern) then
+ line = line:gsub(unchecked_important_pattern, '%1- [ ]', 1)
+ elseif line:match(checked_pattern) then
+ line = line:gsub(checked_pattern, '%1* [x]', 1)
+ elseif line:match(checked_important_pattern) then
+ line = line:gsub(checked_important_pattern, '%1- [x]', 1)
+ end
+
+ api.nvim_buf_set_lines(0, line_number - 1, line_number, false, {line})
end
--- Inserts a new task at the cursor location
--- @param configuration tNotaConfiguration the plugin configuration
-function insert(configuration)
- error("Not yet implemented")
+function Tasks.insert()
+ vim.cmd('normal! o- [ ] ')
+ vim.cmd('startinsert!')
end
--- Captures a new task into the inbox
--- @param configuration tNotaConfiguration the plugin configuration
-function capture(configuration)
- error("Not yet implemented")
+function Tasks.capture()
+ local prefix = '- [ ] '
+ open_inbox()
+ vim.cmd('normal! Go'..prefix)
+ vim.cmd('startinsert!')
end
--- Tag a task
--- @param configuration tNotaConfiguration the plugin configuration
-function tag(configuration)
- error("Not yet implemented")
+function Tasks.tag()
+ error('Not yet implemented')
end
--- Reschedule a task for today
--- @param configuration tNotaConfiguration the plugin configuration
-function reschedule_for_today(configuration)
- error("Not yet implemented")
+function Tasks.reschedule_for_today()
+ local today = os.date('%Y-%m-%d')
+ Tasks.reschedule(today)
end
--- Reschedule a task for tomorrow
--- @param configuration tNotaConfiguration the plugin configuration
-function reschedule_for_tomorrow(configuration)
- error("Not yet implemented")
+function Tasks.reschedule_for_tomorrow()
+ local tomorrow = os.date('%Y-%m-%d', os.time() + 24*60*60)
+ Tasks.reschedule(tomorrow)
end
--- Reschedule a task for someday
--- @param configuration tNotaConfiguration the plugin someday
-function reschedule_for_someday(configuration)
- error("Not yet implemented")
+function Tasks.reschedule_for_someday()
+ Tasks.reschedule('someday')
end
--- Reschedule a task for an arbitrary date
--- @param configuration tNotaConfiguration the plugin someday
-function reschedule(configuration, new_date)
- error("Not yet implemented")
-end
+function Tasks.reschedule(new_date)
--------------------------------------------------------------------------------
--- Internal Functions
--------------------------------------------------------------------------------
+ if not new_date or new_date == '' then
+ new_date = vim.fn.input('Reschedule for which date (YYYY-mm-dd): ')
+ end
+
+ if not Util.is_valid_date(new_date) and new_date ~= 'someday' then
+ api.nvim_err_writeln(new_date .. ' is not a valid date in the format YYYY-mm-dd')
+ return
+ end
+
+ local line_number = api.nvim_win_get_cursor(0)[1]
+ local buffer = api.nvim_get_current_buf()
+ local line = api.nvim_get_current_line()
+ local filename = vim.fn.expand('%:t:r')
+
+ if line:match(unchecked_pattern) or line:match(unchecked_important_pattern) then
+ if Util.is_before_today(filename) and line:match(unchecked_pattern) then
+ local rescheduled_line = line:gsub(unchecked_pattern, '%1- [>' .. new_date .. ']', 1)
+ api.nvim_buf_set_lines(0, line_number - 1, line_number, false, {rescheduled_line})
+ elseif Util.is_before_today(filename) and line:match(unchecked_important_pattern) then
+ local rescheduled_line = line:gsub(unchecked_important_pattern, '%1* [>' .. new_date .. ']', 1)
+ api.nvim_buf_set_lines(0, line_number - 1, line_number, false, {rescheduled_line})
+ else
+ api.nvim_buf_set_lines(buffer, line_number - 1, line_number, false, {})
+ end
+
+ vim.cmd('write')
+
+ if new_date == 'someday' then
+ open_someday()
+ else
+ Notes.open_daily(new_date)
+ end
+
+ local line_count = api.nvim_buf_line_count(0)
+ api.nvim_buf_set_lines(0, line_count, line_count, false, {line})
+ api.nvim_win_set_cursor(0, {line_count, 0})
+ else
+ api.nvim_err_writeln('Reschedule only works on open tasks')
+ end
+end
+return Tasks