Skip to content

Commit

Permalink
refactor: Reorganize modules
Browse files Browse the repository at this point in the history
Primarily:
- Utils
- Sidebar (removed the need of writer.lua)
- Resolve keymaps shortcut in config eraly
- Put highlight functions into highlight.lua
- Put functions that do stuff on outline window into view.lua
  • Loading branch information
hedyhli committed Nov 26, 2023
1 parent b83e84a commit 9f69f12
Show file tree
Hide file tree
Showing 12 changed files with 319 additions and 319 deletions.
6 changes: 6 additions & 0 deletions lua/outline/config.lua
Original file line number Diff line number Diff line change
Expand Up @@ -326,6 +326,12 @@ function M.resolve_config()
if type(au.only) ~= 'number' then
au.only = (au.only and 1) or 0
end
----- KEYMAPS -----
for action, keys in pairs(M.o.keymaps) do
if type(keys) == 'string' then
M.o.keymaps[action] = { keys }
end
end
end

---Ensure l is either table, false, or nil. If not, print warning using given
Expand Down
112 changes: 88 additions & 24 deletions lua/outline/highlight.lua
Original file line number Diff line number Diff line change
@@ -1,38 +1,102 @@
local M = {}
local M = {
ns = {
hover = vim.api.nvim_create_namespace('outline-current'),
items = vim.api.nvim_create_namespace('outline-items-highlight'),
vt = vim.api.nvim_create_namespace('outline-virt-text'),
},
}

M.hovered_hl_ns = vim.api.nvim_create_namespace('hovered_item')
---Clear all highlights in buffer
---@param bufnr integer
function M.clear_all_ns(bufnr)
vim.api.nvim_buf_clear_namespace(bufnr, -1, 0, -1)
end

function M.clear_hover_highlight(bufnr)
vim.api.nvim_buf_clear_namespace(bufnr, M.hovered_hl_ns, 0, -1)
---Clear hover highlights in buffer
---@param bufnr integer
function M.clear_hovers(bufnr)
vim.api.nvim_buf_clear_namespace(bufnr, M.ns.hover, 0, -1)
end

function M.add_hover_highlight(bufnr, line, col_start)
vim.api.nvim_buf_add_highlight(bufnr, M.hovered_hl_ns, 'OutlineCurrent', line, col_start, -1)
---Add single hover highlights
---@param bufnr integer
---@param nodes outline.FlatSymbolNode[]
function M.hovers(bufnr, nodes)
for line, node in ipairs(nodes) do
if node.hovered then
vim.api.nvim_buf_add_highlight(bufnr, M.ns.hover, 'OutlineCurrent', line - 1, node.prefix_length, -1)
end
end
end

local get_hl_by_name
---Add list of highlights `hl` for outline items
---@param bufnr integer
---@param hl_list outline.HL[]
function M.items(bufnr, hl_list)
for _, h in ipairs(hl_list) do
-- stylua: ignore start
vim.api.nvim_buf_add_highlight(
bufnr, M.ns.items,
h.name, h.line - 1, h.from, h.to
)
-- stylua: ignore end
end
end

if vim.fn.has('nvim-0.9') == 1 then
get_hl_by_name = function(name)
local hl = vim.api.nvim_get_hl(0, { name = name, link = false })
return { fg = hl.fg, bg = hl.bg, ctermfg = hl.ctermfg, ctermbg = hl.ctermbg }
---Add details virtual text
---@param bufnr integer Outline buffer
---@param details string[] Virtual text to add
function M.details(bufnr, details)
for index, detail in ipairs(details) do
vim.api.nvim_buf_set_extmark(bufnr, M.ns.vt, index - 1, -1, {
virt_text = { { detail, 'OutlineDetails' } },
virt_text_pos = 'eol',
hl_mode = 'combine',
})
end
else
get_hl_by_name = function(name)
---@diagnostic disable-next-line undefined-field
local hlrgb = vim.api.nvim_get_hl_by_name(name, true)
---@diagnostic disable-next-line undefined-field
local hl = vim.api.nvim_get_hl_by_name(name, false)
return {
fg = hlrgb.foreground,
bg = hlrgb.background,
ctermfg = hl.foreground,
ctermbg = hl.background,
}
end

---Add linenos virtual text
---@param bufnr integer Outline buffer
---@param linenos string[] Must already be padded
---@param hl_mode string Valid value for `buf_set_extmark` option `hl_mode`
function M.linenos(bufnr, linenos, hl_mode)
-- TODO: Fix lineno not appearing if text in line is truncated on the right
-- due to narrow window, after nvim fixes virt_text_hide.
for index, lineno in ipairs(linenos) do
vim.api.nvim_buf_set_extmark(bufnr, M.ns.vt, index - 1, -1, {
virt_text = { { lineno, 'OutlineLineno' } },
virt_text_pos = 'overlay',
virt_text_win_col = 0,
hl_mode = hl_mode,
})
end
end

function M.setup_highlights()
---Create Outline highlights with default values if they don't already exist
function M.setup()
local get_hl_by_name

if _G._outline_nvim_has[9] then
get_hl_by_name = function(name)
local hl = vim.api.nvim_get_hl(0, { name = name, link = false })
return { fg = hl.fg, bg = hl.bg, ctermfg = hl.ctermfg, ctermbg = hl.ctermbg }
end
else
get_hl_by_name = function(name)
---@diagnostic disable-next-line undefined-field
local hlrgb = vim.api.nvim_get_hl_by_name(name, true)
---@diagnostic disable-next-line undefined-field
local hl = vim.api.nvim_get_hl_by_name(name, false)
return {
fg = hlrgb.foreground,
bg = hlrgb.background,
ctermfg = hl.foreground,
ctermbg = hl.background,
}
end
end

-- Setup the OutlineCurrent highlight group if it hasn't been done already by
-- a theme or manually set
if vim.fn.hlexists('OutlineCurrent') == 0 then
Expand Down
2 changes: 1 addition & 1 deletion lua/outline/init.lua
Original file line number Diff line number Diff line change
Expand Up @@ -337,7 +337,7 @@ function M.setup(opts)
}

cfg.setup(opts)
highlight.setup_highlights()
highlight.setup()

setup_global_autocmd()
setup_commands()
Expand Down
68 changes: 65 additions & 3 deletions lua/outline/parser.lua
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
local cfg = require('outline.config')
local folding = require('outline.folding')
local lsp_utils = require('outline.utils.lsp_utils')
local lsp_utils = require('outline.utils.lsp')
local symbols = require('outline.symbols')
local t_utils = require('outline.utils.table')
local utils = require('outline.utils.init')

local M = {}

Expand Down Expand Up @@ -56,7 +56,7 @@ local function parse_result(result, depth, hierarchy, parent, bufnr)
local children = nil
if value.children ~= nil then
-- copy by value because we dont want it messing with the hir table
local child_hir = t_utils.array_copy(hir)
local child_hir = utils.array_copy(hir)
table.insert(child_hir, isLast)
children = parse_result(value.children, level + 1, child_hir, node, bufnr)
else
Expand Down Expand Up @@ -123,4 +123,66 @@ function M.preorder_iter(items, children_check)
end
end

---Merges a symbol tree recursively, only replacing nodes
---which have changed. This will maintain the folding
---status of any unchanged nodes.
---@param new_node table New node
---@param old_node table Old node
---@param index? number Index of old_item in parent
---@param parent? table Parent of old_item
function M.merge_items_rec(new_node, old_node, index, parent)
local failed = false

if not new_node or not old_node then
failed = true
else
for key, _ in pairs(new_node) do
if
vim.tbl_contains({
'parent',
'children',
'folded',
'hovered',
'line_in_outline',
'hierarchy',
}, key)
then
goto continue
end

if key == 'name' then
-- in the case of a rename, just rename the existing node
old_node['name'] = new_node['name']
else
if not vim.deep_equal(new_node[key], old_node[key]) then
failed = true
break
end
end

::continue::
end
end

if failed then
if parent and index then
parent[index] = new_node
end
else
local next_new_item = new_node.children or {}

-- in case new children are created on a node which
-- previously had no children
if #next_new_item > 0 and not old_node.children then
old_node.children = {}
end

local next_old_item = old_node.children or {}

for i = 1, math.max(#next_new_item, #next_old_item) do
M.merge_items_rec(next_new_item[i], next_old_item[i], i, next_old_item)
end
end
end

return M
2 changes: 1 addition & 1 deletion lua/outline/providers/nvim-lsp.lua
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
local config = require('outline.config')
local jsx = require('outline.providers.jsx')
local lsp_utils = require('outline.utils.lsp_utils')
local lsp_utils = require('outline.utils.lsp')

local M = {
name = 'lsp',
Expand Down
Loading

0 comments on commit 9f69f12

Please sign in to comment.