Skip to content

Commit 42dbd09

Browse files
feat: make custom link order deterministic
## Details Request: #146 Currently we pick the first matching custom link when selecting an icon for a destination. However because our table is keyed on strings we iterate through it using pairs and the order of pairs is not deterministic. To fix this collect all matching patterns into a list. Then pick the match with the longest string pattern length. The idea being that longer patterns are more specific and likely are what the user prefers to use. This allows doing fallbacks, like www.example.com for a specific website then www. for all other websites.
1 parent 92e1963 commit 42dbd09

File tree

6 files changed

+46
-29
lines changed

6 files changed

+46
-29
lines changed

doc/render-markdown.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
*render-markdown.txt* For 0.10.0 Last change: 2024 August 24
1+
*render-markdown.txt* For 0.10.0 Last change: 2024 August 25
22

33
==============================================================================
44
Table of Contents *render-markdown-table-of-contents*

lua/render-markdown/handler/markdown_inline.lua

Lines changed: 14 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -196,12 +196,21 @@ end
196196
---@return string, string
197197
function Handler:dest_virt_text(destination)
198198
local link = self.config.link
199-
for _, link_component in pairs(link.custom) do
200-
if destination:find(link_component.pattern) then
201-
return link_component.icon, link_component.highlight
202-
end
199+
200+
---@type render.md.LinkComponent[]
201+
local link_components = vim.tbl_filter(function(link_component)
202+
return destination:find(link_component.pattern) ~= nil
203+
end, link.custom)
204+
table.sort(link_components, function(a, b)
205+
return str.width(a.pattern) < str.width(b.pattern)
206+
end)
207+
208+
if #link_components > 0 then
209+
local link_component = link_components[#link_components]
210+
return link_component.icon, link_component.highlight
211+
else
212+
return link.hyperlink, link.highlight
203213
end
204-
return link.hyperlink, link.highlight
205214
end
206215

207216
---@class render.md.handler.MarkdownInline: render.md.Handler

lua/render-markdown/health.lua

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ local M = {}
55

66
---@private
77
---@type string
8-
M.version = '6.2.5'
8+
M.version = '6.2.6'
99

1010
function M.check()
1111
vim.health.start('render-markdown.nvim [version]')

lua/render-markdown/node_info.lua

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -36,11 +36,11 @@ end
3636

3737
---@param infos render.md.NodeInfo[]
3838
function NodeInfo.sort_inplace(infos)
39-
table.sort(infos, function(info1, info2)
40-
if info1.start_row ~= info2.start_row then
41-
return info1.start_row < info2.start_row
39+
table.sort(infos, function(a, b)
40+
if a.start_row ~= b.start_row then
41+
return a.start_row < b.start_row
4242
else
43-
return info1.start_col < info2.start_col
43+
return a.start_col < b.start_col
4444
end
4545
end)
4646
end

tests/ad_hoc_spec.lua

Lines changed: 21 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -3,32 +3,42 @@
33
local util = require('tests.util')
44

55
---@param row integer
6-
---@param col integer
6+
---@param length integer
77
---@param link_text string
8-
---@return render.md.MarkInfo
9-
local function conceal_link(row, col, link_text)
8+
---@param conceal string?
9+
---@return render.md.MarkInfo[]
10+
local function bullet_link(row, length, link_text, conceal)
1011
---@type render.md.MarkInfo
11-
return {
12+
local link = {
1213
row = { row, row },
13-
col = { 0, col },
14+
col = { 2, 2 + length },
1415
virt_text = { { link_text, util.hl('Link') } },
1516
virt_text_pos = 'inline',
16-
conceal = '',
17+
conceal = conceal,
1718
}
19+
return { util.bullet(row, 0, 1), link }
1820
end
1921

2022
describe('ad_hoc.md', function()
21-
it('default', function()
22-
util.setup('tests/data/ad_hoc.md')
23+
it('custom', function()
24+
util.setup('tests/data/ad_hoc.md', {
25+
link = {
26+
custom = {
27+
youtube = { pattern = 'www%.youtube%.com/', icon = '', highlight = util.hl('Link') },
28+
},
29+
},
30+
})
2331

2432
local expected, row = {}, util.row()
2533

2634
vim.list_extend(expected, util.heading(row:get(), 1))
2735

2836
vim.list_extend(expected, {
29-
conceal_link(row:increment(4), 13, '󰌹 Basic One'),
30-
conceal_link(row:increment(2), 23, '󰌹 With Alias'),
31-
conceal_link(row:increment(2), 18, '󰀓 [email protected]'),
37+
util.bullet(row:increment(2), 0, 1),
38+
bullet_link(row:increment(), 13, '󰌹 Basic One', ''),
39+
bullet_link(row:increment(), 23, '󰌹 With Alias', ''),
40+
bullet_link(row:increment(), 18, '󰀓 [email protected]', ''),
41+
bullet_link(row:increment(), 59, '', nil),
3242
})
3343

3444
local actual = util.get_actual_marks()

tests/data/ad_hoc.md

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,7 @@
11
# Heading
22

3-
[Normal Shortcut]
4-
5-
[[Basic One]] Then normal text
6-
7-
[[Nickname|With Alias]] Something important
8-
9-
3+
- [Normal Shortcut]
4+
- [[Basic One]] Then normal text
5+
- [[Nickname|With Alias]] Something important
6+
7+
- [Youtube Link](https://www.youtube.com/watch?v=dQw4w9WgXcQ)

0 commit comments

Comments
 (0)