1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
|
---@class markdown
local mt = {}
mt.__index = mt
mt.__name = 'markdown'
mt._splitLine = false
function mt:__tostring()
return self:string()
end
---@param language string
---@param text string|markdown
function mt:add(language, text)
if not text then
return self
end
assert(type(text) == 'string')
self._cacheResult = nil
if type(text) == 'table' then
self[#self+1] = {
type = 'markdown',
markdown = text,
}
else
text = tostring(text)
self[#self+1] = {
type = 'text',
language = language,
text = text,
}
end
return self
end
function mt:splitLine()
self._cacheResult = nil
self[#self+1] = {
type = 'splitline',
}
return self
end
function mt:emptyLine()
self._cacheResult = nil
self[#self+1] = {
type = 'emptyline',
}
return self
end
function mt:string(nl)
if self._cacheResult then
return self._cacheResult
end
local lines = {}
local language = 'md'
local function concat(markdown)
for _, obj in ipairs(markdown) do
if obj.type == 'splitline' then
if language ~= 'md' then
lines[#lines+1] = '```'
language = 'md'
end
if #lines > 0
and lines[#lines] ~= '---' then
lines[#lines+1] = ''
lines[#lines+1] = '---'
end
elseif obj.type == 'emptyline' then
if #lines > 0
and lines[#lines] ~= '' then
lines[#lines+1] = ''
end
elseif obj.type == 'markdown' then
concat(obj.markdown)
else
if obj.language ~= language then
if language ~= 'md' then
lines[#lines+1] = '```'
end
if #lines > 0 then
lines[#lines+1] = ''
end
if obj.language ~= 'md' then
lines[#lines+1] = '```' .. obj.language
end
end
if obj.language == 'md' and #lines > 0 then
local last = lines[#lines]
if obj.text:sub(1, 1) == '@'
or last:sub(1, 1) == '@' then
if lines[#lines] ~= '' then
lines[#lines+1] = ''
end
end
end
lines[#lines+1] = obj.text
language = obj.language
end
end
end
concat(self)
if language ~= 'md' then
lines[#lines+1] = '```'
end
while true do
if lines[#lines] == '---'
or lines[#lines] == '' then
lines[#lines] = nil
else
break
end
end
local result = table.concat(lines, nl or '\n')
self._cacheResult = result
return result
end
return function ()
return setmetatable({}, mt)
end
|