Skip to content

Commit

Permalink
Handle math expressions in markdown renderer (#183)
Browse files Browse the repository at this point in the history
Fixes #182
  • Loading branch information
ajalt authored Jul 5, 2024
1 parent 687e8eb commit 75bc2a4
Show file tree
Hide file tree
Showing 5 changed files with 307 additions and 127 deletions.
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
# Changelog

## Unreleased
### Fixed
- Fix markdown rendering not supporting math blocks [(#182)](https://github.com/ajalt/mordant/issues/182)

## 2.7.0
### Added
Expand Down
2 changes: 1 addition & 1 deletion gradle/wrapper/gradle-wrapper.properties
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-8.7-bin.zip
distributionUrl=https\://services.gradle.org/distributions/gradle-8.8-bin.zip
networkTimeout=10000
validateDistributionUrl=true
zipStoreBase=GRADLE_USER_HOME
Expand Down
2 changes: 1 addition & 1 deletion gradlew
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@
# Darwin, MinGW, and NonStop.
#
# (3) This script is generated from the Groovy template
# https://github.com/gradle/gradle/blob/HEAD/subprojects/plugins/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt
# https://github.com/gradle/gradle/blob/HEAD/platforms/jvm/plugins-application/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt
# within the Gradle project.
#
# You can find Gradle at https://github.com/gradle/gradle/.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,10 @@ internal class MarkdownRenderer(
// skip the extra EOL after top level block, since the layout adds it for us
if (node.type == MarkdownTokenTypes.EOL
&& i in 1..<nodes.lastIndex
&& nodes[i - 1].type !in listOf(MarkdownTokenTypes.EOL, MarkdownTokenTypes.WHITE_SPACE)
&& nodes[i - 1].type !in listOf(
MarkdownTokenTypes.EOL,
MarkdownTokenTypes.WHITE_SPACE
)
) {
continue
}
Expand Down Expand Up @@ -91,8 +94,10 @@ internal class MarkdownRenderer(
}

MarkdownElementTypes.CODE_FENCE -> {
val start = node.children.indexOfFirst { it.type == MarkdownTokenTypes.CODE_FENCE_CONTENT }
val end = node.children.indexOfLast { it.type == MarkdownTokenTypes.CODE_FENCE_CONTENT }
val start =
node.children.indexOfFirst { it.type == MarkdownTokenTypes.CODE_FENCE_CONTENT }
val end =
node.children.indexOfLast { it.type == MarkdownTokenTypes.CODE_FENCE_CONTENT }
val dropLast = if (end < 0) 0 else node.children.lastIndex - end
val inner = innerInlines(node, drop = start, dropLast = dropLast)
val content = Text(
Expand All @@ -102,7 +107,7 @@ internal class MarkdownRenderer(
if (theme.flag("markdown.code.block.border")) Panel(content) else content
}

MarkdownElementTypes.CODE_BLOCK -> {
MarkdownElementTypes.CODE_BLOCK-> {
val content = Text(
theme.style("markdown.code.block")(innerInlines(node)),
whitespace = Whitespace.PRE_WRAP
Expand All @@ -127,14 +132,53 @@ internal class MarkdownRenderer(
)
}

MarkdownElementTypes.SETEXT_1 -> setext(theme.string("markdown.h1.rule"), theme.style("markdown.h1"), node)
MarkdownElementTypes.SETEXT_2 -> setext(theme.string("markdown.h2.rule"), theme.style("markdown.h2"), node)
MarkdownElementTypes.ATX_1 -> atxHr(theme.string("markdown.h1.rule"), theme.style("markdown.h1"), node)
MarkdownElementTypes.ATX_2 -> atxHr(theme.string("markdown.h2.rule"), theme.style("markdown.h2"), node)
MarkdownElementTypes.ATX_3 -> atxHr(theme.string("markdown.h3.rule"), theme.style("markdown.h3"), node)
MarkdownElementTypes.ATX_4 -> atxHr(theme.string("markdown.h4.rule"), theme.style("markdown.h4"), node)
MarkdownElementTypes.ATX_5 -> atxHr(theme.string("markdown.h5.rule"), theme.style("markdown.h5"), node)
MarkdownElementTypes.ATX_6 -> atxHr(theme.string("markdown.h6.rule"), theme.style("markdown.h6"), node)
MarkdownElementTypes.SETEXT_1 -> setext(
theme.string("markdown.h1.rule"),
theme.style("markdown.h1"),
node
)

MarkdownElementTypes.SETEXT_2 -> setext(
theme.string("markdown.h2.rule"),
theme.style("markdown.h2"),
node
)

MarkdownElementTypes.ATX_1 -> atxHr(
theme.string("markdown.h1.rule"),
theme.style("markdown.h1"),
node
)

MarkdownElementTypes.ATX_2 -> atxHr(
theme.string("markdown.h2.rule"),
theme.style("markdown.h2"),
node
)

MarkdownElementTypes.ATX_3 -> atxHr(
theme.string("markdown.h3.rule"),
theme.style("markdown.h3"),
node
)

MarkdownElementTypes.ATX_4 -> atxHr(
theme.string("markdown.h4.rule"),
theme.style("markdown.h4"),
node
)

MarkdownElementTypes.ATX_5 -> atxHr(
theme.string("markdown.h5.rule"),
theme.style("markdown.h5"),
node
)

MarkdownElementTypes.ATX_6 -> atxHr(
theme.string("markdown.h6.rule"),
theme.style("markdown.h6"),
node
)

GFMElementTypes.TABLE -> table {
borderType = when {
Expand Down Expand Up @@ -166,7 +210,7 @@ internal class MarkdownRenderer(
private fun parseInlines(node: ASTNode): String {
return when (node.type) {
// ElementTypes
MarkdownElementTypes.CODE_SPAN -> {
MarkdownElementTypes.CODE_SPAN, GFMElementTypes.INLINE_MATH -> {
// Trim the code as a kludge to prevent the background style from extending if the
// code ends with whitespace. It would be better to fix this in the text wrapping code.
theme.style("markdown.code.span")(
Expand All @@ -177,6 +221,16 @@ internal class MarkdownRenderer(
)
}

// For some reason, math blocks are in a paragraph, unlike code blocks
GFMElementTypes.BLOCK_MATH -> {
theme.style("markdown.code.block")(
input.substring(
node.children[1].startOffset,
node.children.last().startOffset
).trim()
)
}

MarkdownElementTypes.EMPH -> {
theme.style("markdown.emph")(innerInlines(node, drop = 1))
}
Expand Down Expand Up @@ -251,6 +305,7 @@ internal class MarkdownRenderer(
MarkdownTokenTypes.URL,
MarkdownTokenTypes.WHITE_SPACE,
GFMTokenTypes.TILDE,
GFMTokenTypes.DOLLAR,
-> node.nodeText()

MarkdownTokenTypes.EOL -> {
Expand Down Expand Up @@ -323,7 +378,7 @@ internal class MarkdownRenderer(
return HorizontalRule(
content,
ruleCharacter = bar,
ruleStyle = TextStyle(style.color, style.bgColor)
ruleStyle = TextStyle(style.color, style.bgColor)
).withPadding { vertical = theme.dimension("markdown.header.padding") }
}

Expand Down Expand Up @@ -407,7 +462,8 @@ internal class MarkdownRenderer(
}

private fun findLinkText(node: ASTNode): String? {
return node.findChildOfType(MarkdownElementTypes.LINK_TEXT)?.let { innerInlines(it, drop = 1) }
return node.findChildOfType(MarkdownElementTypes.LINK_TEXT)
?.let { innerInlines(it, drop = 1) }
}
}

Expand Down
Loading

0 comments on commit 75bc2a4

Please sign in to comment.