Skip to content

Commit ec502be

Browse files
feat(indent): Always check for b:org_indent_mode if available (#669)
1 parent 5a238a2 commit ec502be

File tree

6 files changed

+68
-56
lines changed

6 files changed

+68
-56
lines changed

lua/orgmode/config/init.lua

Lines changed: 15 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -394,6 +394,7 @@ function Config:ts_highlights_enabled()
394394
return false
395395
end
396396

397+
---@diagnostic disable-next-line: param-type-mismatch
397398
if type(hl_module.disable) == 'table' and vim.tbl_contains(hl_module.disable, 'org') then
398399
return false
399400
end
@@ -413,33 +414,26 @@ function Config:respect_blank_before_new_entry(content, option, prepend_content)
413414
return content
414415
end
415416

416-
---@param amount number
417-
---@return string
418-
function Config:get_indent(amount)
419-
if self.org_adapt_indentation then
420-
return string.rep(' ', amount)
417+
---Check if buffer should apply indentation
418+
---@param bufnr number
419+
---@return boolean
420+
function Config:should_indent(bufnr)
421+
if bufnr > -1 and vim.b[bufnr].org_indent_mode then
422+
return not self.opts.org_indent_mode_turns_off_org_adapt_indentation
421423
end
422-
return ''
424+
425+
return self.org_adapt_indentation
423426
end
424427

425-
---@param content string|string[]
426428
---@param amount number
427-
---@return string|string[]
428-
function Config:apply_indent(content, amount)
429-
local indent = self:get_indent(amount)
430-
431-
if indent == '' then
432-
return content
433-
end
434-
435-
if type(content) ~= 'table' then
436-
return indent .. content
429+
---@param bufnr number
430+
---@return string
431+
function Config:get_indent(amount, bufnr)
432+
if self:should_indent(bufnr) then
433+
return string.rep(' ', amount)
437434
end
438435

439-
for i, line in ipairs(content) do
440-
content[i] = indent .. line
441-
end
442-
return content
436+
return ''
443437
end
444438

445439
---@param bufnr number

lua/orgmode/files/elements/logbook.lua

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -159,7 +159,7 @@ end
159159
---@param headline OrgHeadline
160160
function Logbook.new_from_headline(headline)
161161
local append_line = headline:get_append_line()
162-
local indent = config:get_indent(headline:get_level() + 1)
162+
local indent = headline:get_indent()
163163

164164
local date = Date.now({ active = false })
165165
local content = {

lua/orgmode/files/elements/table/init.lua

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -86,7 +86,7 @@ function Table:reformat()
8686
return false
8787
end
8888
local _, start_col = self.node:range()
89-
local indent = config:get_indent(start_col)
89+
local indent = config:get_indent(start_col, vim.api.nvim_get_current_buf())
9090
local contents = vim.tbl_map(function(line)
9191
return ('%s%s'):format(indent, line)
9292
end, self:draw())
@@ -104,7 +104,7 @@ function Table:handle_cr()
104104

105105
local line = vim.fn.line('.') or 0
106106
local indent_amount = vim.fn.indent(line) or 0
107-
local indent = config:get_indent(indent_amount)
107+
local indent = config:get_indent(indent_amount, vim.api.nvim_get_current_buf())
108108
vim.api.nvim_buf_set_lines(0, line, line, true, { ('%s|'):format(indent) })
109109
local tbl = Table.from_current_node({ line, vim.fn.col('.') })
110110
if tbl then

lua/orgmode/files/headline.lua

Lines changed: 33 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -87,11 +87,11 @@ function Headline:promote(amount, recursive, dryRun)
8787
if line:sub(1, 1) == '*' then
8888
lines[i] = line:sub(1 + amount)
8989
elseif vim.trim(line:sub(1, amount)) == '' then
90-
if config.org_adapt_indentation then
90+
if config:should_indent(self.file:bufnr()) then
9191
lines[i] = line:sub(1 + amount)
9292
else
9393
line, _ = line:gsub('^%s+', '')
94-
local indent_amount = indent.indentexpr(start_line + i)
94+
local indent_amount = indent.indentexpr(start_line + i, self.file:bufnr())
9595
lines[i] = string.rep(' ', indent_amount) .. line
9696
end
9797
end
@@ -113,11 +113,11 @@ function Headline:demote(amount, recursive, dryRun)
113113
if line:sub(1, 1) == '*' then
114114
lines[i] = string.rep('*', amount) .. line
115115
else
116-
if config.org_adapt_indentation then
117-
lines[i] = config:apply_indent(line, amount)
116+
if config:should_indent(self.file:bufnr()) then
117+
lines[i] = self:_apply_indent(line, amount)
118118
else
119119
line, _ = line:gsub('^%s+', '')
120-
local indent_amount = indent.indentexpr(start_line + i)
120+
local indent_amount = indent.indentexpr(start_line + i, self.file:bufnr())
121121
lines[i] = string.rep(' ', indent_amount) .. line
122122
end
123123
end
@@ -384,7 +384,7 @@ function Headline:set_property(name, value)
384384
local properties = self:get_properties()
385385
if not properties then
386386
local append_line = self:get_append_line()
387-
local property_drawer = self:_apply_indent({ ':PROPERTIES:', ':END:' })
387+
local property_drawer = self:_apply_indent({ ':PROPERTIES:', ':END:' }) --[[ @as string[] ]]
388388
vim.api.nvim_buf_set_lines(0, append_line, append_line, false, property_drawer)
389389
properties = self:refresh():get_properties()
390390
end
@@ -395,7 +395,9 @@ function Headline:set_property(name, value)
395395
return self:_set_node_text(property_node, property)
396396
end
397397
local property_end = properties and properties:end_()
398-
vim.api.nvim_buf_set_lines(0, property_end - 1, property_end - 1, false, self:_apply_indent(property))
398+
399+
local new_line = self:_apply_indent(property) --[[@as string]]
400+
vim.api.nvim_buf_set_lines(0, property_end - 1, property_end - 1, false, { new_line })
399401
return self:refresh()
400402
end
401403

@@ -782,7 +784,7 @@ function Headline:get_drawer_append_line(name)
782784

783785
if not drawer then
784786
local append_line = self:get_append_line()
785-
local new_drawer = self:_apply_indent({ ':' .. name .. ':', ':END:' })
787+
local new_drawer = self:_apply_indent({ ':' .. name .. ':', ':END:' }) --[[ @as string[] ]]
786788
vim.api.nvim_buf_set_lines(0, append_line, append_line, false, new_drawer)
787789
drawer = self:get_drawer(name)
788790
end
@@ -806,6 +808,12 @@ function Headline:get_headline_line_content()
806808
return line
807809
end
808810

811+
---@param amount? number
812+
---@return string
813+
function Headline:get_indent(amount)
814+
return config:get_indent(amount or self:get_level() + 1, self.file:bufnr())
815+
end
816+
809817
function Headline:is_same(other_headline)
810818
return self.file.filename == other_headline.filename
811819
and self:get_headline_line_content() == other_headline:get_headline_line_content()
@@ -829,9 +837,8 @@ function Headline:_add_date(type, date, active)
829837
local _, date_nodes, has_plan_dates = self:get_plan_dates()
830838
local text = type .. ': ' .. date:to_wrapped_string(active)
831839
if not has_plan_dates then
832-
local indentation = config:get_indent(self:get_level() + 1)
833840
local start_line = self:node():start()
834-
vim.fn.append(start_line + 1, ('%s%s'):format(indentation, text))
841+
vim.fn.append(start_line + 1, self:_apply_indent(text))
835842
return self:refresh()
836843
end
837844
if date_nodes[type] then
@@ -869,13 +876,23 @@ function Headline:_remove_date(type)
869876
end
870877

871878
---@param text string[]|string
872-
---@return string[]
873-
function Headline:_apply_indent(text)
874-
local indented = config:apply_indent(text, self:get_level() + 1)
875-
if type(indented) == 'string' then
876-
return { indented }
879+
---@param amount? number
880+
function Headline:_apply_indent(text, amount)
881+
local indent_text = self:get_indent(amount)
882+
883+
if indent_text == '' then
884+
return text
877885
end
878-
return indented
886+
887+
if type(text) ~= 'table' then
888+
return indent_text .. text
889+
end
890+
891+
for i, line in ipairs(text) do
892+
text[i] = indent_text .. line
893+
end
894+
895+
return text
879896
end
880897

881898
function Headline:_get_child_node(name)

lua/orgmode/org/indent.lua

Lines changed: 15 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,8 @@ local ts_utils = require('orgmode.utils.treesitter')
44
---@type Query
55
local query = nil
66

7-
local function get_indent_pad(linenr)
8-
if config.org_adapt_indentation then
7+
local function get_indent_pad(linenr, bufnr)
8+
if config:should_indent(bufnr) then
99
local headline = ts_utils.closest_headline_node({ linenr, 0 })
1010
if not headline then
1111
return 0
@@ -16,7 +16,7 @@ local function get_indent_pad(linenr)
1616
return 0
1717
end
1818

19-
local function get_indent_for_match(matches, linenr, mode)
19+
local function get_indent_for_match(matches, linenr, mode, bufnr)
2020
linenr = linenr or vim.v.lnum
2121
mode = mode or vim.fn.mode()
2222
local prev_linenr = vim.fn.prevnonblank(linenr - 1)
@@ -25,7 +25,7 @@ local function get_indent_for_match(matches, linenr, mode)
2525
local indent = 0
2626

2727
if not match and not prev_line_match then
28-
return indent + get_indent_pad(linenr)
28+
return indent + get_indent_pad(linenr, bufnr)
2929
end
3030

3131
match = match or {}
@@ -50,7 +50,7 @@ local function get_indent_for_match(matches, linenr, mode)
5050
end
5151
end
5252
-- If the first_line_indent wasn't found then this is the root of the list, as such we just pad accordingly
53-
indent = first_line_indent or (0 + get_indent_pad(linenr))
53+
indent = first_line_indent or (0 + get_indent_pad(linenr, bufnr))
5454
-- If the current line is hanging content as part of the listitem but not on the same line we want to indent it
5555
-- such that it's in line with the general content body, not the bullet.
5656
--
@@ -69,7 +69,7 @@ local function get_indent_for_match(matches, linenr, mode)
6969
-- After the first line of a listitem, we have to add the overhang to the
7070
-- listitem's own base indent. After all further lines, we can simply copy
7171
-- the indentation.
72-
indent = get_indent_for_match(matches, prev_linenr)
72+
indent = get_indent_for_match(matches, prev_linenr, mode, bufnr)
7373
if prev_linenr == prev_line_match.line_nr then
7474
indent = indent + prev_line_match.overhang
7575
end
@@ -81,7 +81,7 @@ local function get_indent_for_match(matches, linenr, mode)
8181
return match.indent
8282
end
8383

84-
return indent + get_indent_pad(linenr)
84+
return indent + get_indent_pad(linenr, bufnr)
8585
end
8686

8787
local get_matches = ts_utils.memoize_by_buf_tick(function(bufnr)
@@ -90,6 +90,7 @@ local get_matches = ts_utils.memoize_by_buf_tick(function(bufnr)
9090
return {}
9191
end
9292
local matches = {}
93+
local mode = vim.fn.mode()
9394
local root = tree[1]:root()
9495
for _, match, _ in query:iter_matches(root, bufnr, 0, -1) do
9596
for id, node in pairs(match) do
@@ -150,13 +151,13 @@ local get_matches = ts_utils.memoize_by_buf_tick(function(bufnr)
150151
-- block header and footer. This keeps code correctly indented in `BEGIN_SRC` blocks as well as ensuring
151152
-- `BEGIN_EXAMPLE` blocks don't have their indentation changed inside of them.
152153
local parent_linenr = parent:start() + 1
153-
local parent_indent = get_indent_for_match(matches, parent:start() + 1)
154+
local parent_indent = get_indent_for_match(matches, parent:start() + 1, mode, bufnr)
154155

155156
-- We want to align to the listitem body, not the bullet
156157
if parent:type() == 'listitem' then
157158
parent_indent = parent_indent + matches[parent_linenr].overhang
158159
else
159-
parent_indent = get_indent_pad(range.start.line + 1)
160+
parent_indent = get_indent_pad(range.start.line + 1, bufnr)
160161
end
161162

162163
local curr_header_indent = vim.fn.indent(range.start.line + 1)
@@ -270,18 +271,18 @@ end
270271
--
271272
-- TLDR: The caching avoids some inconsistent race conditions with getting the Treesitter matches.
272273
local buf_indentexpr_cache = {}
273-
local function indentexpr(linenr, mode)
274+
local function indentexpr(linenr, bufnr)
274275
linenr = linenr or vim.v.lnum
275-
mode = mode or vim.fn.mode()
276+
local mode = vim.fn.mode()
276277
query = query or vim.treesitter.query.get('org', 'org_indent')
277278

278-
local bufnr = vim.api.nvim_get_current_buf()
279+
bufnr = bufnr or vim.api.nvim_get_current_buf()
279280
local indentexpr_cache = buf_indentexpr_cache[bufnr] or { prev_linenr = -1 }
280281
if indentexpr_cache.prev_linenr ~= linenr - 1 or not mode:lower():find('n') then
281-
indentexpr_cache.matches = get_matches(0)
282+
indentexpr_cache.matches = get_matches(bufnr)
282283
end
283284

284-
local new_indent = get_indent_for_match(indentexpr_cache.matches, linenr, mode)
285+
local new_indent = get_indent_for_match(indentexpr_cache.matches, linenr, mode, bufnr)
285286
local match = indentexpr_cache.matches[linenr]
286287
if match then
287288
match.indent = new_indent

lua/orgmode/org/mappings.lua

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,7 @@ function OrgMappings:archive()
6060
local lines = headline:get_lines()
6161
local properties_node = headline:get_properties()
6262
local append_line = headline:get_append_line() - start_line
63-
local indent = config:get_indent(headline:get_level() + 1)
63+
local indent = headline:get_indent()
6464

6565
local archive_props = {
6666
('%s:ARCHIVE_TIME: %s'):format(indent, Date.now():to_string()),
@@ -439,7 +439,7 @@ function OrgMappings:_todo_change_state(direction)
439439
local log_note = config.org_log_done == 'note'
440440
local log_time = config.org_log_done == 'time'
441441
local should_log_time = log_note or log_time
442-
local indent = config:get_indent(headline:get_level() + 1)
442+
local indent = headline:get_indent()
443443

444444
local get_note = function(note)
445445
if note == nil then

0 commit comments

Comments
 (0)