Skip to content

Commit

Permalink
markup/goldmark: support latex fences $ and $$
Browse files Browse the repository at this point in the history
Patched and updated from
janhuenermann@ad38246
  • Loading branch information
j2kun committed Jan 6, 2024
1 parent 0ee8248 commit 3f5e9e4
Show file tree
Hide file tree
Showing 3 changed files with 114 additions and 0 deletions.
5 changes: 5 additions & 0 deletions markup/goldmark/convert.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ import (
"github.com/gohugoio/hugo/markup/goldmark/goldmark_config"
"github.com/gohugoio/hugo/markup/goldmark/images"
"github.com/gohugoio/hugo/markup/goldmark/internal/extensions/attributes"
"github.com/gohugoio/hugo/markup/goldmark/internal/extensions/latex"
"github.com/gohugoio/hugo/markup/goldmark/internal/render"

"github.com/gohugoio/hugo/markup/converter"
Expand Down Expand Up @@ -154,6 +155,10 @@ func newMarkdown(pcfg converter.ProviderConfig) goldmark.Markdown {
extensions = append(extensions, c)
}

if cfg.Extensions.Latex {
extensions = append(extensions, &latex.LatexAsPlainTextExtension{})
}

if pcfg.Conf.EnableEmoji() {
extensions = append(extensions, emoji.Emoji)
}
Expand Down
2 changes: 2 additions & 0 deletions markup/goldmark/goldmark_config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ var Default = Config{
},
Footnote: true,
DefinitionList: true,
Latex: false,
Table: true,
Strikethrough: true,
Linkify: true,
Expand Down Expand Up @@ -75,6 +76,7 @@ type Extensions struct {
Typographer Typographer
Footnote bool
DefinitionList bool
Latex bool

// GitHub flavored markdown
Table bool
Expand Down
107 changes: 107 additions & 0 deletions markup/goldmark/internal/extensions/latex/latex.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
package latex

import (
"github.com/yuin/goldmark"
"github.com/yuin/goldmark/ast"
"github.com/yuin/goldmark/parser"
"github.com/yuin/goldmark/text"
"github.com/yuin/goldmark/util"
)

const LatexTrigger = byte('$')

type LatexParser struct {
}

func (s *LatexParser) Trigger() []byte {
return []byte{LatexTrigger}
}

func (s *LatexParser) Parse(parent ast.Node, block text.Reader, pc parser.Context) ast.Node {
// Finds any LaTeX inlines/blocks and returns an AST text node, ensuring
// that other parsers don't pick up the LaTeX syntax.
// Source: https://github.com/FurqanSoftware/goldmark-katex/blob/0bf781ec55b4dcac337505863ecccf093e4ee967/parser.go

buf := block.Source()
ln, pos := block.Position()

lstart := pos.Start
lend := pos.Stop
line := buf[lstart:lend]

var start, end, advance int

if len(line) > 1 && line[1] == LatexTrigger {
// Block LaTeX
start = lstart + 2
offset := 2

L:
for x := 0; x < 5; x++ {
for j := offset; j < len(line); j++ {
if len(line) > j+1 && line[j] == LatexTrigger && line[j+1] == LatexTrigger {
end = lstart + j
advance = 2
break L
}
}
if lend == len(buf) {
break
}
if end == 0 {
rest := buf[lend:]
j := 1
for j < len(rest) && rest[j] != '\n' {
j++
}
lstart = lend
lend += j
line = buf[lstart:lend]
ln++
offset = 0
}
}

} else {
// Inline LaTeX
start = lstart + 1

for i := 1; i < len(line); i++ {
c := line[i]
if c == '\\' {
i++
continue
}
if c == LatexTrigger {
end = lstart + i
advance = 1
break
}
}
if end >= len(buf) || buf[end] != LatexTrigger {
return nil
}
}

if start >= end {
return nil
}

newpos := end + advance
if newpos < lend {
block.SetPosition(ln, text.NewSegment(newpos, lend))
} else {
block.Advance(newpos)
}

return ast.NewTextSegment(text.NewSegment(lstart, newpos))
}

type LatexAsPlainTextExtension struct {
}

func (e *LatexAsPlainTextExtension) Extend(m goldmark.Markdown) {
m.Parser().AddOptions(parser.WithInlineParsers(
util.Prioritized(&LatexParser{}, 0),
))
}

0 comments on commit 3f5e9e4

Please sign in to comment.