优化markd对列表的解析

master
yutent 2023-05-23 17:09:22 +08:00
parent 2dc42a8d4e
commit 226ccb6ffd
1 changed files with 85 additions and 42 deletions

View File

@ -271,8 +271,7 @@ class Tool {
let isParagraph = false
let isList = false
let orderListLevel = -1
let unorderListLevel = -1
let listTagQueue = []
let isQuoteList = false // 引用中的列表, 只支持一层级
let quoteListStyle = 0 // 1有序, 2 无序
@ -282,10 +281,19 @@ class Tool {
for (let it of this.list) {
// 非空行
if (it) {
let lastLineIsEmpty = emptyLineLength > 0
emptyLineLength = 0
if (~it.indexOf('<table>') || ~it.indexOf('</table>')) {
if (isList) {
if (isTable) {
html += it + `${' '.repeat(listTagQueue.length)}</li>\n`
} else {
html = html.replace(/<\/li>\n*?$/, '') + it
}
} else {
html += it
}
isTable = !isTable
tableAlign = true
isHtmlBlock = false
@ -328,7 +336,15 @@ class Tool {
isParagraph = false
html += '</p>\n'
}
if (isList) {
if (isCodeBlock) {
html += it + `${' '.repeat(listTagQueue.length)}</li>\n`
} else {
html = html.replace(/<\/li>\n*?$/, '') + it
}
} else {
html += it
}
isCodeBlock = !isCodeBlock
isHtmlBlock = false
continue
@ -345,6 +361,7 @@ class Tool {
let hrName = Helper.isHr(it)
if (typeof hrName === 'string') {
html += Decoder.hr(hrName)
emptyLineLength = 0
continue
}
@ -368,13 +385,13 @@ class Tool {
}
// 有列表也先结束
if (isList) {
while (orderListLevel > -1 || unorderListLevel > -1) {
if (orderListLevel > unorderListLevel) {
html += '</ol>\n'
orderListLevel--
} else {
html += '</ul>\n'
unorderListLevel--
while (listTagQueue.length) {
let tag = listTagQueue.pop()
html += `${' '.repeat(
listTagQueue.length ? listTagQueue.length + 1 : 0
)}</${tag}>\n`
if (listTagQueue.length) {
html += `${' '.repeat(listTagQueue.length)}</li>\n`
}
}
isList = false
@ -469,45 +486,47 @@ class Tool {
let tmp = Helper.ltrim(it)
let ltrim = it.length - tmp.length
let word = tmp.replace(LIST_RE, '').trim()
let level = Math.floor(ltrim / 2) //缩进级别
let _level = listTagQueue.length - 1 // 上一个缩进级别
let level = Math.floor(ltrim / 2) // 当前缩进级别
let tag = listChecked === 1 ? 'ol' : 'ul'
if (isParagraph) {
isParagraph = false
if (!isList) {
html = trimBr(html)
html += '</p>\n'
}
}
if (isList) {
let _level = listChecked === 1 ? orderListLevel : unorderListLevel
// 大于上一个缩进
if (level > _level) {
listTagQueue.push(tag)
// 需要先把上一个列表的结束符去掉
html = html.trim().replace(/<\/li>$/, '')
html += `\n<${tag}>\n<li>${word}</li>\n`
html += `\n${' '.repeat(level + 1)}<${tag}>\n${' '.repeat(
level + 1
)}<li>${word}</li>\n`
}
// 跟上一个平级
else if (level === _level) {
html += `<li>${word}</li>\n`
html += `${' '.repeat(level + 1)}<li>${word}</li>\n`
}
// 比上一个缩进要小
else {
html += `</${tag}>\n</li>\n<li>${word}</li>\n`
for (let i = _level - level; i > 0; i--) {
let _tag = listTagQueue.pop()
html += `${' '.repeat(level + i + 1)}</${_tag}>\n${' '.repeat(
level + i
)}</li>\n`
}
if (listChecked === 1) {
orderListLevel = level
} else {
unorderListLevel = level
html += `${' '.repeat(level + 1)}<li>${word}</li>\n`
}
} else {
html += `<${tag}>\n`
if (listChecked === 1) {
orderListLevel = level
} else {
unorderListLevel = level
}
html += `<li>${word}</li>\n`
listTagQueue.push(tag)
html += `<${tag}>\n <li>${word}</li>\n`
}
isList = true
@ -521,6 +540,20 @@ class Tool {
continue
}
// 列表之后, 有段落时, 先结束列表
if (isList && lastLineIsEmpty) {
while (listTagQueue.length) {
let tag = listTagQueue.pop()
html += `${' '.repeat(
listTagQueue.length ? listTagQueue.length + 1 : 0
)}</${tag}>\n`
if (listTagQueue.length) {
html += `${' '.repeat(listTagQueue.length)}</li>\n`
}
}
isList = false
}
if (isHtmlBlock || isSingleLineHtml) {
if (isParagraph) {
isParagraph = false
@ -536,14 +569,22 @@ class Tool {
}
isHtmlBlock = !isHtmlBlock
html += `${it}\n`
} else {
if (isList) {
if (isParagraph) {
html += it + `</p>\n${' '.repeat(listTagQueue.length)}</li>\n`
} else {
html = html.replace(/<\/li>\n*?$/, '') + `\n<p>${it}`
}
} else {
if (isParagraph) {
html += `${it}\n`
} else {
html += `\n<p>${it}`
isParagraph = true
}
}
isParagraph = true
}
} else {
// 如果是在代码中, 直接拼接, 并加上换行
if (isCodeBlock) {
@ -566,13 +607,13 @@ class Tool {
if (isList) {
if (emptyLineLength > 1) {
while (orderListLevel > -1 || unorderListLevel > -1) {
if (orderListLevel > unorderListLevel) {
html += '</ol>\n'
orderListLevel--
} else {
html += '</ul>\n'
unorderListLevel--
while (listTagQueue.length) {
let tag = listTagQueue.pop()
html += `${' '.repeat(
listTagQueue.length ? listTagQueue.length + 1 : 0
)}</${tag}>\n`
if (listTagQueue.length) {
html += `${' '.repeat(listTagQueue.length)}</li>\n`
}
}
isList = false
@ -596,9 +637,11 @@ class Tool {
}
}
console.log('>>>>')
if (isParagraph) {
html += '</p>'
}
console.log(html)
delete this.list
delete this.__LINKS__
return html.trim()
@ -606,5 +649,5 @@ class Tool {
}
export default function (str) {
return Tool.init(str).parse() //.replace(/\\</g, '<').replace(/\\>/g, '>')
return Tool.init(str).parse()
}