motion-markdown-it 12.0.6 → 13.0.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +4 -4
- data/lib/motion-markdown-it/index.rb +2 -2
- data/lib/motion-markdown-it/parser_core.rb +4 -1
- data/lib/motion-markdown-it/parser_inline.rb +11 -2
- data/lib/motion-markdown-it/presets/commonmark.rb +3 -2
- data/lib/motion-markdown-it/presets/zero.rb +4 -3
- data/lib/motion-markdown-it/renderer.rb +3 -3
- data/lib/motion-markdown-it/rules_block/code.rb +1 -1
- data/lib/motion-markdown-it/rules_block/html_block.rb +1 -1
- data/lib/motion-markdown-it/rules_block/list.rb +6 -2
- data/lib/motion-markdown-it/rules_block/table.rb +1 -1
- data/lib/motion-markdown-it/rules_core/linkify.rb +11 -1
- data/lib/motion-markdown-it/rules_core/replacements.rb +2 -3
- data/lib/motion-markdown-it/rules_core/text_join.rb +51 -0
- data/lib/motion-markdown-it/rules_inline/balance_pairs.rb +35 -13
- data/lib/motion-markdown-it/rules_inline/emphasis.rb +4 -11
- data/lib/motion-markdown-it/rules_inline/entity.rb +27 -22
- data/lib/motion-markdown-it/rules_inline/escape.rb +41 -22
- data/lib/motion-markdown-it/rules_inline/{text_collapse.rb → fragments_join.rb} +23 -22
- data/lib/motion-markdown-it/rules_inline/html_inline.rb +11 -0
- data/lib/motion-markdown-it/rules_inline/link.rb +3 -1
- data/lib/motion-markdown-it/rules_inline/linkify.rb +60 -0
- data/lib/motion-markdown-it/rules_inline/newline.rb +7 -1
- data/lib/motion-markdown-it/rules_inline/state_inline.rb +5 -1
- data/lib/motion-markdown-it/rules_inline/strikethrough.rb +0 -1
- data/lib/motion-markdown-it/token.rb +1 -0
- data/lib/motion-markdown-it/version.rb +1 -1
- data/lib/motion-markdown-it.rb +4 -2
- data/spec/motion-markdown-it/misc_spec.rb +47 -0
- metadata +5 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 527ad2365d9f847959cb068d6483944ece97a6f25198b159c342fd09d340e7f1
|
4
|
+
data.tar.gz: de08e3d6331f1fe3e359df0e935cead71a259bb211885084000e6b93ed9cd909
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 7abfc3bd88c7f30e93826a1ae27a00d95c8f47f6f9e634a739ddf597c7a0ffdc73fd295fa353f0e306861e5301b0190aba2f8fd1e56e4ffee5d3c61383be7f45
|
7
|
+
data.tar.gz: 10896d6c58b7d9675b52833ef975c77441fb4fa7c295aa6f38325226dd10de80609c892a1969f431bb0ce4b12565feb36a9ab6bdbfe4277cd116f5e43379dd08
|
data/README.md
CHANGED
@@ -7,7 +7,7 @@ Ruby/RubyMotion version of Markdown-it (CommonMark compliant and extendable)
|
|
7
7
|
|
8
8
|
This gem is a port of the [markdown-it Javascript package](https://github.com/markdown-it/markdown-it) by Vitaly Puzrin and Alex Kocharin.
|
9
9
|
|
10
|
-
_Currently synced with markdown-it
|
10
|
+
_Currently synced with markdown-it 13.0.1_
|
11
11
|
|
12
12
|
---
|
13
13
|
|
@@ -185,7 +185,7 @@ var md = require('markdown-it')({
|
|
185
185
|
highlight: function (str, lang) {
|
186
186
|
if (lang && hljs.getLanguage(lang)) {
|
187
187
|
try {
|
188
|
-
return hljs.highlight(
|
188
|
+
return hljs.highlight(str, { language: lang }).value;
|
189
189
|
} catch (__) {}
|
190
190
|
}
|
191
191
|
|
@@ -205,7 +205,7 @@ var md = require('markdown-it')({
|
|
205
205
|
if (lang && hljs.getLanguage(lang)) {
|
206
206
|
try {
|
207
207
|
return '<pre class="hljs"><code>' +
|
208
|
-
hljs.highlight(
|
208
|
+
hljs.highlight(str, { language: lang, ignoreIllegals: true }).value +
|
209
209
|
'</code></pre>';
|
210
210
|
} catch (__) {}
|
211
211
|
}
|
@@ -260,7 +260,7 @@ By default all rules are enabled, but can be restricted by options. On plugin
|
|
260
260
|
load all its rules are enabled automatically.
|
261
261
|
|
262
262
|
```js
|
263
|
-
// Activate/deactivate rules, with
|
263
|
+
// Activate/deactivate rules, with currying
|
264
264
|
var md = require('markdown-it')()
|
265
265
|
.disable([ 'link', 'image' ])
|
266
266
|
.enable([ 'link' ])
|
@@ -190,7 +190,7 @@ module MarkdownIt
|
|
190
190
|
# highlight: function (str, lang) {
|
191
191
|
# if (lang && hljs.getLanguage(lang)) {
|
192
192
|
# try {
|
193
|
-
# return hljs.highlight(
|
193
|
+
# return hljs.highlight(str, { language: lang, ignoreIllegals: true }).value;
|
194
194
|
# } catch (__) {}
|
195
195
|
# }
|
196
196
|
#
|
@@ -210,7 +210,7 @@ module MarkdownIt
|
|
210
210
|
# if (lang && hljs.getLanguage(lang)) {
|
211
211
|
# try {
|
212
212
|
# return '<pre class="hljs"><code>' +
|
213
|
-
# hljs.highlight(
|
213
|
+
# hljs.highlight(str, { language: lang, ignoreIllegals: true }).value +
|
214
214
|
# '</code></pre>';
|
215
215
|
# } catch (__) {}
|
216
216
|
# }
|
@@ -10,12 +10,15 @@ module MarkdownIt
|
|
10
10
|
attr_accessor :ruler
|
11
11
|
|
12
12
|
RULES = [
|
13
|
-
[ 'normalize', lambda { |state| RulesCore::Normalize.normalize(state) }
|
13
|
+
[ 'normalize', lambda { |state| RulesCore::Normalize.normalize(state) } ],
|
14
14
|
[ 'block', lambda { |state| RulesCore::Block.block(state) } ],
|
15
15
|
[ 'inline', lambda { |state| RulesCore::Inline.inline(state) } ],
|
16
16
|
[ 'linkify', lambda { |state| RulesCore::Linkify.linkify(state) } ],
|
17
17
|
[ 'replacements', lambda { |state| RulesCore::Replacements.replace(state) } ],
|
18
18
|
[ 'smartquotes', lambda { |state| RulesCore::Smartquotes.smartquotes(state) } ],
|
19
|
+
# `text_join` finds `text_special` tokens (for escape sequences)
|
20
|
+
# and joins them with the rest of the text
|
21
|
+
[ 'text_join', lambda { |state| RulesCore::TextJoin.text_join(state) } ],
|
19
22
|
]
|
20
23
|
|
21
24
|
|
@@ -13,6 +13,7 @@ module MarkdownIt
|
|
13
13
|
|
14
14
|
RULES = [
|
15
15
|
[ 'text', lambda { |state, startLine| RulesInline::Text.text(state, startLine) } ],
|
16
|
+
[ 'linkify', lambda { |state, silent| RulesInline::Linkify.linkify(state, silent) } ],
|
16
17
|
[ 'newline', lambda { |state, startLine| RulesInline::Newline.newline(state, startLine) } ],
|
17
18
|
[ 'escape', lambda { |state, startLine| RulesInline::Escape.escape(state, startLine) } ],
|
18
19
|
[ 'backticks', lambda { |state, startLine| RulesInline::Backticks.backtick(state, startLine) } ],
|
@@ -25,11 +26,19 @@ module MarkdownIt
|
|
25
26
|
[ 'entity', lambda { |state, startLine| RulesInline::Entity.entity(state, startLine) } ],
|
26
27
|
]
|
27
28
|
|
29
|
+
# `rule2` ruleset was created specifically for emphasis/strikethrough
|
30
|
+
# post-processing and may be changed in the future.
|
31
|
+
#
|
32
|
+
# Don't use this for anything except pairs (plugins working with `balance_pairs`).
|
33
|
+
#
|
28
34
|
RULES2 = [
|
29
35
|
[ 'balance_pairs', lambda { |state| RulesInline::BalancePairs.link_pairs(state) } ],
|
30
36
|
[ 'strikethrough', lambda { |state| RulesInline::Strikethrough.postProcess(state) } ],
|
31
37
|
[ 'emphasis', lambda { |state| RulesInline::Emphasis.postProcess(state) } ],
|
32
|
-
[ 'text_collapse', lambda { |state| RulesInline::TextCollapse.text_collapse(state) } ]
|
38
|
+
# [ 'text_collapse', lambda { |state| RulesInline::TextCollapse.text_collapse(state) } ]
|
39
|
+
# rules for pairs separate '**' into its own text tokens, which may be left unused,
|
40
|
+
# rule below merges unused segments back with the rest of the text
|
41
|
+
[ 'fragments_join', lambda { |state| RulesInline::FragmentsJoin.fragments_join(state) } ]
|
33
42
|
];
|
34
43
|
|
35
44
|
#------------------------------------------------------------------------------
|
@@ -154,4 +163,4 @@ module MarkdownIt
|
|
154
163
|
end
|
155
164
|
end
|
156
165
|
end
|
157
|
-
end
|
166
|
+
end
|
@@ -39,7 +39,8 @@ module MarkdownIt
|
|
39
39
|
rules: [
|
40
40
|
'normalize',
|
41
41
|
'block',
|
42
|
-
'inline'
|
42
|
+
'inline',
|
43
|
+
'text_join'
|
43
44
|
]
|
44
45
|
},
|
45
46
|
|
@@ -74,7 +75,7 @@ module MarkdownIt
|
|
74
75
|
rules2: [
|
75
76
|
'balance_pairs',
|
76
77
|
'emphasis',
|
77
|
-
'
|
78
|
+
'fragments_join'
|
78
79
|
]
|
79
80
|
}
|
80
81
|
}
|
@@ -40,7 +40,8 @@ module MarkdownIt
|
|
40
40
|
rules: [
|
41
41
|
'normalize',
|
42
42
|
'block',
|
43
|
-
'inline'
|
43
|
+
'inline',
|
44
|
+
'text_join'
|
44
45
|
]
|
45
46
|
},
|
46
47
|
|
@@ -56,7 +57,7 @@ module MarkdownIt
|
|
56
57
|
],
|
57
58
|
rules2: [
|
58
59
|
'balance_pairs',
|
59
|
-
'
|
60
|
+
'fragments_join'
|
60
61
|
]
|
61
62
|
}
|
62
63
|
}
|
@@ -64,4 +65,4 @@ module MarkdownIt
|
|
64
65
|
end
|
65
66
|
end
|
66
67
|
end
|
67
|
-
end
|
68
|
+
end
|
@@ -245,7 +245,7 @@ module MarkdownIt
|
|
245
245
|
|
246
246
|
|
247
247
|
# Renderer.renderInline(tokens, options, env) -> String
|
248
|
-
# - tokens (Array): list on block tokens to
|
248
|
+
# - tokens (Array): list on block tokens to render
|
249
249
|
# - options (Object): params of parser instance
|
250
250
|
# - env (Object): additional data from parsed input (references, for example)
|
251
251
|
#
|
@@ -271,7 +271,7 @@ module MarkdownIt
|
|
271
271
|
|
272
272
|
# internal
|
273
273
|
# Renderer.renderInlineAsText(tokens, options, env) -> String
|
274
|
-
# - tokens (Array): list on block tokens to
|
274
|
+
# - tokens (Array): list on block tokens to render
|
275
275
|
# - options (Object): params of parser instance
|
276
276
|
# - env (Object): additional data from parsed input (references, for example)
|
277
277
|
#
|
@@ -297,7 +297,7 @@ module MarkdownIt
|
|
297
297
|
|
298
298
|
|
299
299
|
# Renderer.render(tokens, options, env) -> String
|
300
|
-
# - tokens (Array): list on block tokens to
|
300
|
+
# - tokens (Array): list on block tokens to render
|
301
301
|
# - options (Object): params of parser instance
|
302
302
|
# - env (Object): additional data from parsed input (references, for example)
|
303
303
|
#
|
@@ -26,7 +26,7 @@ module MarkdownIt
|
|
26
26
|
state.line = last
|
27
27
|
|
28
28
|
token = state.push('code_block', 'code', 0)
|
29
|
-
token.content = state.getLines(startLine, last, 4 + state.blkIndent,
|
29
|
+
token.content = state.getLines(startLine, last, 4 + state.blkIndent, false) + "\n"
|
30
30
|
token.map = [ startLine, state.line ]
|
31
31
|
return true
|
32
32
|
end
|
@@ -11,7 +11,7 @@ module MarkdownIt
|
|
11
11
|
# last argument defines whether it can terminate a paragraph or not
|
12
12
|
#
|
13
13
|
HTML_SEQUENCES = [
|
14
|
-
[ /^<(script|pre|style)(?=(\s|>|$))/i, /<\/(script|pre|style)>/i, true ],
|
14
|
+
[ /^<(script|pre|style|textarea)(?=(\s|>|$))/i, /<\/(script|pre|style|textarea)>/i, true ],
|
15
15
|
[ /^<!--/, /-->/, true ],
|
16
16
|
[ /^<\?/, /\?>/, true ],
|
17
17
|
[ /^<![A-Z]/, />/, true ],
|
@@ -129,7 +129,7 @@ module MarkdownIt
|
|
129
129
|
# This code can fail if plugins use blkIndent as well as lists,
|
130
130
|
# but I hope the spec gets fixed long before that happens.
|
131
131
|
#
|
132
|
-
if state.
|
132
|
+
if state.sCount[startLine] >= state.blkIndent
|
133
133
|
isTerminatingParagraph = true
|
134
134
|
end
|
135
135
|
end
|
@@ -138,7 +138,7 @@ module MarkdownIt
|
|
138
138
|
if ((posAfterMarker = skipOrderedListMarker(state, startLine)) >= 0)
|
139
139
|
isOrdered = true
|
140
140
|
start = state.bMarks[startLine] + state.tShift[startLine]
|
141
|
-
markerValue = state.src[start, posAfterMarker -
|
141
|
+
markerValue = state.src[start, posAfterMarker - 1].to_i
|
142
142
|
|
143
143
|
# If we're starting a new ordered list right after
|
144
144
|
# a paragraph, it should start with 1.
|
@@ -231,6 +231,9 @@ module MarkdownIt
|
|
231
231
|
token = state.push('list_item_open', 'li', 1)
|
232
232
|
token.markup = markerCharCode.chr
|
233
233
|
token.map = itemLines = [ startLine, 0 ]
|
234
|
+
if (isOrdered)
|
235
|
+
token.info = state.src.slice(start...posAfterMarker - 1)
|
236
|
+
end
|
234
237
|
|
235
238
|
# change current state, then restore it after parser subcall
|
236
239
|
oldTight = state.tight
|
@@ -307,6 +310,7 @@ module MarkdownIt
|
|
307
310
|
if (isOrdered)
|
308
311
|
posAfterMarker = skipOrderedListMarker(state, nextLine)
|
309
312
|
break if (posAfterMarker < 0)
|
313
|
+
start = state.bMarks[nextLine] + state.tShift[nextLine]
|
310
314
|
else
|
311
315
|
posAfterMarker = skipBulletListMarker(state, nextLine)
|
312
316
|
break if (posAfterMarker < 0)
|
@@ -66,6 +66,16 @@ module MarkdownIt
|
|
66
66
|
level = currentToken.level
|
67
67
|
lastPos = 0
|
68
68
|
|
69
|
+
# forbid escape sequence at the start of the string,
|
70
|
+
# this avoids http\://example.com/ from being linkified as
|
71
|
+
# http:<a href="//example.com/">//example.com/</a>
|
72
|
+
if (links.length > 0 &&
|
73
|
+
links[0].index == 0 &&
|
74
|
+
i > 0 &&
|
75
|
+
tokens[i - 1].type == 'text_special')
|
76
|
+
links = links.slice(1..-1)
|
77
|
+
end
|
78
|
+
|
69
79
|
(0...links.length).each do |ln|
|
70
80
|
url = links[ln].url
|
71
81
|
fullUrl = state.md.normalizeLink.call(url)
|
@@ -133,4 +143,4 @@ module MarkdownIt
|
|
133
143
|
|
134
144
|
end
|
135
145
|
end
|
136
|
-
end
|
146
|
+
end
|
@@ -15,15 +15,14 @@ module MarkdownIt
|
|
15
15
|
|
16
16
|
# TODO (from original)
|
17
17
|
# - fractionals 1/2, 1/4, 3/4 -> ½, ¼, ¾
|
18
|
-
# -
|
18
|
+
# - multiplications 2 x 4 -> 2 × 4
|
19
19
|
|
20
20
|
RARE_RE = /\+-|\.\.|\?\?\?\?|!!!!|,,|--/
|
21
21
|
|
22
|
-
SCOPED_ABBR_RE = /\((c|tm|r
|
22
|
+
SCOPED_ABBR_RE = /\((c|tm|r)\)/i
|
23
23
|
SCOPED_ABBR = {
|
24
24
|
'c' => '©',
|
25
25
|
'r' => '®',
|
26
|
-
'p' => '§',
|
27
26
|
'tm' => '™'
|
28
27
|
}
|
29
28
|
|
@@ -0,0 +1,51 @@
|
|
1
|
+
# Join raw text tokens with the rest of the text
|
2
|
+
#
|
3
|
+
# This is set as a separate rule to provide an opportunity for plugins
|
4
|
+
# to run text replacements after text join, but before escape join.
|
5
|
+
#
|
6
|
+
# For example, `\:)` shouldn't be replaced with an emoji.
|
7
|
+
#
|
8
|
+
module MarkdownIt
|
9
|
+
module RulesCore
|
10
|
+
class TextJoin
|
11
|
+
def self.text_join(state)
|
12
|
+
blockTokens = state.tokens
|
13
|
+
|
14
|
+
(0...blockTokens.length).each do |j|
|
15
|
+
next if (blockTokens[j].type != 'inline')
|
16
|
+
|
17
|
+
tokens = blockTokens[j].children
|
18
|
+
max = tokens.length
|
19
|
+
|
20
|
+
(0...max).each do |curr|
|
21
|
+
if (tokens[curr].type == 'text_special')
|
22
|
+
tokens[curr].type = 'text'
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
last = 0
|
27
|
+
curr = 0
|
28
|
+
while curr < max
|
29
|
+
if (tokens[curr].type == 'text' &&
|
30
|
+
curr + 1 < max &&
|
31
|
+
tokens[curr + 1].type == 'text')
|
32
|
+
|
33
|
+
# collapse two adjacent text nodes
|
34
|
+
tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content
|
35
|
+
else
|
36
|
+
tokens[last] = tokens[curr] if (curr != last)
|
37
|
+
|
38
|
+
last += 1
|
39
|
+
end
|
40
|
+
|
41
|
+
curr += 1
|
42
|
+
end
|
43
|
+
|
44
|
+
if (curr != last)
|
45
|
+
tokens.pop(tokens.length - last)
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
@@ -9,9 +9,28 @@ module MarkdownIt
|
|
9
9
|
openersBottom = {}
|
10
10
|
max = delimiters.length
|
11
11
|
|
12
|
+
return if (!max)
|
13
|
+
|
14
|
+
# headerIdx is the first delimiter of the current (where closer is) delimiter run
|
15
|
+
headerIdx = 0
|
16
|
+
lastTokenIdx = -2 # needs any value lower than -1
|
17
|
+
jumps = []
|
18
|
+
|
12
19
|
0.upto(max - 1) do |closerIdx|
|
13
20
|
closer = delimiters[closerIdx]
|
14
21
|
|
22
|
+
jumps.push(0)
|
23
|
+
|
24
|
+
# markers belong to same delimiter run if:
|
25
|
+
# - they have adjacent tokens
|
26
|
+
# - AND markers are the same
|
27
|
+
#
|
28
|
+
if (delimiters[headerIdx][:marker] != closer[:marker] || lastTokenIdx != closer[:token] - 1)
|
29
|
+
headerIdx = closerIdx
|
30
|
+
end
|
31
|
+
|
32
|
+
lastTokenIdx = closer[:token]
|
33
|
+
|
15
34
|
# Length is only used for emphasis-specific "rule of 3",
|
16
35
|
# if it's not defined (in strikethrough or 3rd party plugins),
|
17
36
|
# we can default it to 0 to disable those checks.
|
@@ -21,24 +40,23 @@ module MarkdownIt
|
|
21
40
|
next if (!closer[:close])
|
22
41
|
|
23
42
|
# Previously calculated lower bounds (previous fails)
|
24
|
-
# for each marker
|
43
|
+
# for each marker, each delimiter length modulo 3,
|
44
|
+
# and for whether this closer can be an opener;
|
45
|
+
# https://github.com/commonmark/cmark/commit/34250e12ccebdc6372b8b49c44fab57c72443460
|
25
46
|
unless openersBottom[closer[:marker]]
|
26
|
-
openersBottom[closer[:marker]] = [ -1, -1, -1 ]
|
47
|
+
openersBottom[closer[:marker]] = [ -1, -1, -1, -1, -1, -1 ]
|
27
48
|
end
|
28
49
|
|
29
|
-
minOpenerIdx = openersBottom[closer[:marker]][closer[:length] % 3]
|
50
|
+
minOpenerIdx = openersBottom[closer[:marker]][(closer[:open] ? 3 : 0) + (closer[:length] % 3)]
|
30
51
|
|
31
|
-
openerIdx =
|
32
|
-
|
33
|
-
# avoid crash if `closer.jump` is pointing outside of the array, see #742
|
34
|
-
openerIdx = -1 if (openerIdx < -1)
|
52
|
+
openerIdx = headerIdx - jumps[headerIdx] - 1
|
35
53
|
|
36
54
|
newMinOpenerIdx = openerIdx
|
37
55
|
|
38
56
|
while openerIdx > minOpenerIdx
|
39
57
|
opener = delimiters[openerIdx]
|
40
58
|
|
41
|
-
(openerIdx -=
|
59
|
+
(openerIdx -= jumps[openerIdx] + 1) && next if (opener[:marker] != closer[:marker])
|
42
60
|
|
43
61
|
if (opener[:open] && opener[:end] < 0)
|
44
62
|
|
@@ -65,19 +83,23 @@ module MarkdownIt
|
|
65
83
|
# sure algorithm has linear complexity (see *_*_*_*_*_... case).
|
66
84
|
#
|
67
85
|
lastJump = openerIdx > 0 && !delimiters[openerIdx - 1][:open] ?
|
68
|
-
|
86
|
+
jumps[openerIdx - 1] + 1 : 0
|
69
87
|
|
70
|
-
|
88
|
+
jumps[closerIdx] = closerIdx - openerIdx + lastJump
|
89
|
+
jumps[openerIdx] = lastJump
|
90
|
+
|
71
91
|
closer[:open] = false
|
72
92
|
opener[:end] = closerIdx
|
73
|
-
opener[:jump] = lastJump
|
74
93
|
opener[:close] = false
|
75
94
|
newMinOpenerIdx = -1
|
95
|
+
# treat next token as start of run,
|
96
|
+
# it optimizes skips in **<...>**a**<...>** pathological case
|
97
|
+
lastTokenIdx = -2
|
76
98
|
break
|
77
99
|
end
|
78
100
|
end
|
79
101
|
|
80
|
-
openerIdx -=
|
102
|
+
openerIdx -= jumps[openerIdx] + 1
|
81
103
|
end
|
82
104
|
|
83
105
|
if (newMinOpenerIdx != -1)
|
@@ -88,7 +110,7 @@ module MarkdownIt
|
|
88
110
|
# See details here:
|
89
111
|
# https://github.com/commonmark/cmark/issues/178#issuecomment-270417442
|
90
112
|
#
|
91
|
-
openersBottom[closer[:marker]][(closer[:length] || 0) % 3] = newMinOpenerIdx
|
113
|
+
openersBottom[closer[:marker]][(closer[:open] ? 3 : 0) + ((closer[:length] || 0) % 3)] = newMinOpenerIdx
|
92
114
|
end
|
93
115
|
end
|
94
116
|
end
|
@@ -30,15 +30,6 @@ module MarkdownIt
|
|
30
30
|
#
|
31
31
|
length: scanned[:length],
|
32
32
|
|
33
|
-
# An amount of characters before this one that's equivalent to
|
34
|
-
# current one. In plain English: if this delimiter does not open
|
35
|
-
# an emphasis, neither do previous `jump` characters.
|
36
|
-
#
|
37
|
-
# Used to skip sequences like "*****" in one step, for 1st asterisk
|
38
|
-
# value will be 0, for 2nd it's 1 and so on.
|
39
|
-
#
|
40
|
-
jump: i,
|
41
|
-
|
42
33
|
# A position of the token this delimiter corresponds to.
|
43
34
|
#
|
44
35
|
token: state.tokens.length - 1,
|
@@ -82,9 +73,11 @@ module MarkdownIt
|
|
82
73
|
#
|
83
74
|
isStrong = i > 0 &&
|
84
75
|
delimiters[i - 1][:end] == startDelim[:end] + 1 &&
|
76
|
+
# check that first two markers match and adjacent
|
77
|
+
delimiters[i - 1][:marker] == startDelim[:marker] &&
|
85
78
|
delimiters[i - 1][:token] == startDelim[:token] - 1 &&
|
86
|
-
|
87
|
-
delimiters[
|
79
|
+
# check that last two markers are adjacent (we can safely assume they match)
|
80
|
+
delimiters[startDelim[:end] + 1][:token] == endDelim[:token] + 1
|
88
81
|
|
89
82
|
ch = fromCodePoint(startDelim[:marker])
|
90
83
|
|
@@ -8,44 +8,49 @@ module MarkdownIt
|
|
8
8
|
DIGITAL_RE = /^&#((?:x[a-f0-9]{1,6}|[0-9]{1,7}));/i
|
9
9
|
NAMED_RE = /^&([a-z][a-z0-9]{1,31});/i
|
10
10
|
|
11
|
-
|
12
11
|
#------------------------------------------------------------------------------
|
13
12
|
def self.entity(state, silent)
|
14
13
|
pos = state.pos
|
15
14
|
max = state.posMax
|
16
15
|
|
17
|
-
return false if charCodeAt(state.src, pos) != 0x26
|
16
|
+
return false if charCodeAt(state.src, pos) != 0x26 # &
|
17
|
+
|
18
|
+
return false if pos + 1 >= max
|
18
19
|
|
19
|
-
|
20
|
-
ch = charCodeAt(state.src, pos + 1)
|
20
|
+
ch = charCodeAt(state.src, pos + 1)
|
21
21
|
|
22
|
-
|
23
|
-
|
24
|
-
|
22
|
+
if ch == 0x23 # '#'
|
23
|
+
match = state.src[pos..-1].match(DIGITAL_RE)
|
24
|
+
if match
|
25
|
+
if !silent
|
26
|
+
code = match[1][0].downcase == 'x' ? match[1][1..-1].to_i(16) : match[1].to_i
|
27
|
+
|
28
|
+
token = state.push('text_special', '', 0)
|
29
|
+
token.content = isValidEntityCode(code) ? fromCodePoint(code) : fromCodePoint(0xFFFD)
|
30
|
+
token.markup = match[0]
|
31
|
+
token.info = 'entity'
|
32
|
+
end
|
33
|
+
state.pos += match[0].length
|
34
|
+
return true
|
35
|
+
end
|
36
|
+
else
|
37
|
+
match = state.src[pos..-1].match(NAMED_RE)
|
38
|
+
if match
|
39
|
+
if MarkdownIt::HTMLEntities::MAPPINGS[match[1]]
|
25
40
|
if !silent
|
26
|
-
|
27
|
-
|
41
|
+
token = state.push('text_special', '', 0)
|
42
|
+
token.content += fromCodePoint(MarkdownIt::HTMLEntities::MAPPINGS[match[1]])
|
43
|
+
token.markup = match[0]
|
44
|
+
token.info = 'entity'
|
28
45
|
end
|
29
46
|
state.pos += match[0].length
|
30
47
|
return true
|
31
48
|
end
|
32
|
-
else
|
33
|
-
match = state.src[pos..-1].match(NAMED_RE)
|
34
|
-
if match
|
35
|
-
if MarkdownIt::HTMLEntities::MAPPINGS[match[1]]
|
36
|
-
state.pending += fromCodePoint(MarkdownIt::HTMLEntities::MAPPINGS[match[1]]) if !silent
|
37
|
-
state.pos += match[0].length
|
38
|
-
return true
|
39
|
-
end
|
40
|
-
end
|
41
49
|
end
|
42
50
|
end
|
43
51
|
|
44
|
-
|
45
|
-
state.pos += 1
|
46
|
-
return true
|
52
|
+
return false
|
47
53
|
end
|
48
|
-
|
49
54
|
end
|
50
55
|
end
|
51
56
|
end
|
@@ -11,7 +11,6 @@ module MarkdownIt
|
|
11
11
|
|
12
12
|
'\\!"#$%&\'()*+,./:;<=>?@[]^_`{|}~-'.split('').each { |ch| ESCAPED[ch.ord] = 1 }
|
13
13
|
|
14
|
-
|
15
14
|
#------------------------------------------------------------------------------
|
16
15
|
def self.escape(state, silent)
|
17
16
|
pos = state.pos
|
@@ -21,35 +20,55 @@ module MarkdownIt
|
|
21
20
|
|
22
21
|
pos += 1
|
23
22
|
|
24
|
-
|
25
|
-
|
23
|
+
# '\' at the end of the inline block
|
24
|
+
return false if pos >= max
|
25
|
+
|
26
|
+
ch1 = charCodeAt(state.src, pos)
|
27
|
+
|
28
|
+
if ch1 == 0x0A
|
29
|
+
if !silent
|
30
|
+
state.push('hardbreak', 'br', 0)
|
31
|
+
end
|
26
32
|
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
33
|
+
pos += 1
|
34
|
+
# skip leading whitespaces from next line
|
35
|
+
while pos < max
|
36
|
+
ch1 = charCodeAt(state.src, pos)
|
37
|
+
break if !isSpace(ch1)
|
38
|
+
pos += 1
|
31
39
|
end
|
32
40
|
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
41
|
+
state.pos = pos
|
42
|
+
return true
|
43
|
+
end
|
44
|
+
|
45
|
+
escapedStr = state.src[pos]
|
37
46
|
|
47
|
+
if (ch1 >= 0xD800 && ch1 <= 0xDBFF && pos + 1 < max)
|
48
|
+
ch2 = charCodeAt(state.src, pos + 1)
|
49
|
+
|
50
|
+
if (ch2 >= 0xDC00 && ch2 <= 0xDFFF)
|
51
|
+
escapedStr += state.src[pos + 1]
|
38
52
|
pos += 1
|
39
|
-
# skip leading whitespaces from next line
|
40
|
-
while pos < max
|
41
|
-
ch = charCodeAt(state.src, pos)
|
42
|
-
break if !isSpace(ch)
|
43
|
-
pos += 1
|
44
|
-
end
|
45
|
-
|
46
|
-
state.pos = pos
|
47
|
-
return true
|
48
53
|
end
|
49
54
|
end
|
50
55
|
|
51
|
-
|
52
|
-
|
56
|
+
origStr = '\\' + escapedStr
|
57
|
+
|
58
|
+
if (!silent)
|
59
|
+
token = state.push('text_special', '', 0)
|
60
|
+
|
61
|
+
if ch1 < 256 && ESCAPED[ch1] != 0
|
62
|
+
token.content = escapedStr
|
63
|
+
else
|
64
|
+
token.content = origStr
|
65
|
+
end
|
66
|
+
|
67
|
+
token.markup = origStr
|
68
|
+
token.info = 'escape'
|
69
|
+
end
|
70
|
+
|
71
|
+
state.pos = pos + 1
|
53
72
|
return true
|
54
73
|
end
|
55
74
|
end
|
@@ -1,47 +1,48 @@
|
|
1
1
|
# Clean up tokens after emphasis and strikethrough postprocessing:
|
2
|
-
#
|
2
|
+
# merge adjacent text nodes into one and re-calculate all token levels
|
3
3
|
#
|
4
4
|
# This is necessary because initially emphasis delimiter markers (*, _, ~)
|
5
5
|
# are treated as their own separate text tokens. Then emphasis rule either
|
6
6
|
# leaves them as text (needed to merge with adjacent text) or turns them
|
7
7
|
# into opening/closing tags (which messes up levels inside).
|
8
|
-
|
8
|
+
#
|
9
9
|
module MarkdownIt
|
10
10
|
module RulesInline
|
11
|
-
class
|
11
|
+
class FragmentsJoin
|
12
|
+
extend Common::Utils
|
12
13
|
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
max = state.tokens.length
|
14
|
+
def self.fragments_join(state)
|
15
|
+
level = 0
|
16
|
+
tokens = state.tokens
|
17
|
+
max = state.tokens.length
|
18
18
|
|
19
|
-
last =
|
19
|
+
last = 0
|
20
|
+
curr = 0
|
20
21
|
while curr < max
|
21
22
|
# re-calculate levels after emphasis/strikethrough turns some text nodes
|
22
23
|
# into opening/closing tags
|
23
|
-
level -= 1 if tokens[curr].nesting < 0 # closing tag
|
24
|
+
level -= 1 if (tokens[curr].nesting < 0) # closing tag
|
24
25
|
tokens[curr].level = level
|
25
|
-
level +=
|
26
|
-
|
27
|
-
if tokens[curr].type == 'text' &&
|
26
|
+
level +=1 if (tokens[curr].nesting > 0) # opening tag
|
27
|
+
|
28
|
+
if (tokens[curr].type == 'text' &&
|
28
29
|
curr + 1 < max &&
|
29
|
-
tokens[curr + 1].type == 'text'
|
30
|
-
|
30
|
+
tokens[curr + 1].type == 'text')
|
31
|
+
|
31
32
|
# collapse two adjacent text nodes
|
32
33
|
tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content
|
33
34
|
else
|
34
|
-
tokens[last] = tokens[curr] if curr != last
|
35
|
-
|
35
|
+
tokens[last] = tokens[curr] if (curr != last)
|
36
|
+
|
36
37
|
last += 1
|
37
38
|
end
|
38
|
-
|
39
|
+
|
39
40
|
curr += 1
|
40
41
|
end
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
42
|
+
|
43
|
+
if (curr != last)
|
44
|
+
tokens.pop(tokens.length - last)
|
45
|
+
end
|
45
46
|
end
|
46
47
|
end
|
47
48
|
end
|
@@ -6,6 +6,14 @@ module MarkdownIt
|
|
6
6
|
extend Common::Utils
|
7
7
|
include MarkdownIt::Common::HtmlRe
|
8
8
|
|
9
|
+
#------------------------------------------------------------------------------
|
10
|
+
def self.isLinkOpen(str)
|
11
|
+
return !(/^<a[>\s]/i =~ str).nil?
|
12
|
+
end
|
13
|
+
def self.isLinkClose(str)
|
14
|
+
return !(/^<\/a\s*>/i =~ str).nil?
|
15
|
+
end
|
16
|
+
|
9
17
|
#------------------------------------------------------------------------------
|
10
18
|
def self.isLetter(ch)
|
11
19
|
lc = ch | 0x20 # to lower case
|
@@ -39,6 +47,9 @@ module MarkdownIt
|
|
39
47
|
if !silent
|
40
48
|
token = state.push('html_inline', '', 0)
|
41
49
|
token.content = state.src.slice(pos...(pos + match[0].length))
|
50
|
+
|
51
|
+
state.linkLevel += 1 if (isLinkOpen(token.content))
|
52
|
+
state.linkLevel -= 1 if (isLinkClose(token.content))
|
42
53
|
end
|
43
54
|
state.pos += match[0].length
|
44
55
|
return true
|
@@ -132,9 +132,11 @@ module MarkdownIt
|
|
132
132
|
attrs.push([ 'title', title ])
|
133
133
|
end
|
134
134
|
|
135
|
+
state.linkLevel += 1
|
135
136
|
state.md.inline.tokenize(state)
|
137
|
+
state.linkLevel -= 1
|
136
138
|
|
137
|
-
token
|
139
|
+
token = state.push('link_close', 'a', -1)
|
138
140
|
end
|
139
141
|
|
140
142
|
state.pos = pos
|
@@ -0,0 +1,60 @@
|
|
1
|
+
# Process links like https://example.org/
|
2
|
+
module MarkdownIt
|
3
|
+
module RulesInline
|
4
|
+
class Linkify
|
5
|
+
extend Common::Utils
|
6
|
+
|
7
|
+
# RFC3986: scheme = ALPHA *( ALPHA / DIGIT / "+" / "-" / "." )
|
8
|
+
SCHEME_RE = /(?:^|[^a-z0-9.+-])([a-z][a-z0-9.+-]*)$/i
|
9
|
+
|
10
|
+
#------------------------------------------------------------------------------
|
11
|
+
def self.linkify(state, silent)
|
12
|
+
return false if (!state.md.options[:linkify])
|
13
|
+
return false if (state.linkLevel > 0)
|
14
|
+
|
15
|
+
pos = state.pos
|
16
|
+
max = state.posMax
|
17
|
+
|
18
|
+
return false if (pos + 3 > max)
|
19
|
+
return false if (charCodeAt(state.src, pos) != 0x3A) # :
|
20
|
+
return false if (charCodeAt(state.src, pos + 1) != 0x2F) # /
|
21
|
+
return false if (charCodeAt(state.src, pos + 2) != 0x2F) # /
|
22
|
+
|
23
|
+
match = state.pending.match(SCHEME_RE)
|
24
|
+
return false if (!match)
|
25
|
+
|
26
|
+
proto = match[1]
|
27
|
+
|
28
|
+
link = state.md.linkify.matchAtStart(state.src.slice((pos - proto.length)..-1))
|
29
|
+
return false if (!link)
|
30
|
+
|
31
|
+
url = link.url
|
32
|
+
|
33
|
+
# disallow '*' at the end of the link (conflicts with emphasis)
|
34
|
+
url = url.sub(/\*+$/, '')
|
35
|
+
|
36
|
+
fullUrl = state.md.normalizeLink.call(url)
|
37
|
+
return false if (!state.md.validateLink.call(fullUrl))
|
38
|
+
|
39
|
+
if (!silent)
|
40
|
+
state.pending = state.pending[0...-proto.length]
|
41
|
+
|
42
|
+
token = state.push('link_open', 'a', 1)
|
43
|
+
token.attrs = [ [ 'href', fullUrl ] ]
|
44
|
+
token.markup = 'linkify'
|
45
|
+
token.info = 'auto'
|
46
|
+
|
47
|
+
token = state.push('text', '', 0)
|
48
|
+
token.content = state.md.normalizeLinkText.call(url)
|
49
|
+
|
50
|
+
token = state.push('link_close', 'a', -1)
|
51
|
+
token.markup = 'linkify'
|
52
|
+
token.info = 'auto'
|
53
|
+
end
|
54
|
+
|
55
|
+
state.pos += url.length - proto.length
|
56
|
+
return true
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
@@ -20,7 +20,13 @@ module MarkdownIt
|
|
20
20
|
if !silent
|
21
21
|
if pmax >= 0 && charCodeAt(state.pending, pmax) == 0x20
|
22
22
|
if pmax >= 1 && charCodeAt(state.pending, pmax - 1) == 0x20
|
23
|
-
|
23
|
+
# Find whitespaces tail of pending chars.
|
24
|
+
ws = pmax - 1
|
25
|
+
while (ws >= 1 && charCodeAt(state.pending, ws - 1) == 0x20)
|
26
|
+
ws -= 1
|
27
|
+
end
|
28
|
+
|
29
|
+
state.pending = state.pending.slice(0...ws)
|
24
30
|
state.push('hardbreak', 'br', 0)
|
25
31
|
else
|
26
32
|
state.pending = state.pending.slice(0...-1)
|
@@ -7,7 +7,7 @@ module MarkdownIt
|
|
7
7
|
|
8
8
|
attr_accessor :src, :env, :md, :tokens, :pos, :posMax, :level, :tokens_meta
|
9
9
|
attr_accessor :pending, :pendingLevel, :cache, :delimiters
|
10
|
-
attr_accessor :backticks, :backticksScanned
|
10
|
+
attr_accessor :backticks, :backticksScanned, :linkLevel
|
11
11
|
|
12
12
|
#------------------------------------------------------------------------------
|
13
13
|
def initialize(src, md, env, outTokens)
|
@@ -36,6 +36,10 @@ module MarkdownIt
|
|
36
36
|
# backtick length => last seen position
|
37
37
|
@backticks = {}
|
38
38
|
@backticksScanned = false
|
39
|
+
|
40
|
+
# Counter used to disable inline linkify-it execution
|
41
|
+
# inside <a> and markdown links
|
42
|
+
@linkLevel = 0
|
39
43
|
end
|
40
44
|
|
41
45
|
|
@@ -67,6 +67,7 @@ module MarkdownIt
|
|
67
67
|
# *
|
68
68
|
# * - Info string for "fence" tokens
|
69
69
|
# * - The value "auto" for autolink "link_open" and "link_close" tokens
|
70
|
+
# * - The string value of the item marker for ordered-list "list_item_open" tokens
|
70
71
|
@info = ''
|
71
72
|
|
72
73
|
# * Token#meta -> Object
|
data/lib/motion-markdown-it.rb
CHANGED
@@ -40,6 +40,7 @@ else
|
|
40
40
|
require 'motion-markdown-it/rules_core/replacements'
|
41
41
|
require 'motion-markdown-it/rules_core/smartquotes'
|
42
42
|
require 'motion-markdown-it/rules_core/state_core'
|
43
|
+
require 'motion-markdown-it/rules_core/text_join'
|
43
44
|
require 'motion-markdown-it/rules_block/blockquote'
|
44
45
|
require 'motion-markdown-it/rules_block/code'
|
45
46
|
require 'motion-markdown-it/rules_block/fence'
|
@@ -58,17 +59,18 @@ else
|
|
58
59
|
require 'motion-markdown-it/rules_inline/emphasis'
|
59
60
|
require 'motion-markdown-it/rules_inline/entity'
|
60
61
|
require 'motion-markdown-it/rules_inline/escape'
|
62
|
+
require 'motion-markdown-it/rules_inline/fragments_join'
|
61
63
|
require 'motion-markdown-it/rules_inline/html_inline'
|
62
64
|
require 'motion-markdown-it/rules_inline/image'
|
63
65
|
require 'motion-markdown-it/rules_inline/link'
|
66
|
+
require 'motion-markdown-it/rules_inline/linkify'
|
64
67
|
require 'motion-markdown-it/rules_inline/newline'
|
65
68
|
require 'motion-markdown-it/rules_inline/state_inline'
|
66
69
|
require 'motion-markdown-it/rules_inline/strikethrough'
|
67
|
-
require 'motion-markdown-it/rules_inline/text_collapse'
|
68
70
|
require 'motion-markdown-it/rules_inline/text'
|
69
71
|
|
70
72
|
require 'motion-markdown-it/ruler'
|
71
73
|
require 'motion-markdown-it/token'
|
72
74
|
require 'motion-markdown-it/index'
|
73
75
|
|
74
|
-
end
|
76
|
+
end
|
@@ -195,6 +195,9 @@ describe 'Misc' do
|
|
195
195
|
|
196
196
|
expect(md.render('123')).to eq "<p>123</p>\n"
|
197
197
|
expect(md.render("123\n")).to eq "<p>123</p>\n"
|
198
|
+
|
199
|
+
expect(md.render(' codeblock')).to eq "<pre><code>codeblock\n</code></pre>\n"
|
200
|
+
expect(md.render(" codeblock\n")).to eq "<pre><code>codeblock\n</code></pre>\n"
|
198
201
|
end
|
199
202
|
|
200
203
|
#------------------------------------------------------------------------------
|
@@ -273,6 +276,14 @@ describe 'Misc' do
|
|
273
276
|
# );
|
274
277
|
# end
|
275
278
|
|
279
|
+
# TODO ------------------------------------------------------------------------------
|
280
|
+
# it 'Should escape surrogate pairs (coverage)' do
|
281
|
+
# md = MarkdownIt::Parser.new({})
|
282
|
+
#
|
283
|
+
# expect(md.render("\\\uD835\uDC9C")).to eq "<p>\\\uD835\uDC9C</p>\n"
|
284
|
+
# expect(md.render("\\\uD835x")).to eq "<p>\\\uD835x</p>\n"
|
285
|
+
# expect(md.render("\\\uD835")).to eq "<p>\\\uD835</p>\n"
|
286
|
+
# end
|
276
287
|
end
|
277
288
|
|
278
289
|
|
@@ -371,6 +382,42 @@ describe 'smartquotes' do
|
|
371
382
|
end
|
372
383
|
end
|
373
384
|
|
385
|
+
describe 'Ordered list info' do
|
386
|
+
md = MarkdownIt::Parser.new
|
387
|
+
|
388
|
+
def type_filter(tokens, type)
|
389
|
+
return tokens.select { |t| t.type === type }
|
390
|
+
end
|
391
|
+
|
392
|
+
it 'Should mark ordered list item tokens with info' do
|
393
|
+
tokens = md.parse("1. Foo\n2. Bar\n20. Fuzz", {})
|
394
|
+
expect(type_filter(tokens, 'ordered_list_open').length).to eq 1
|
395
|
+
|
396
|
+
tokens = type_filter(tokens, 'list_item_open')
|
397
|
+
expect(tokens.length).to eq 3
|
398
|
+
expect(tokens[0].info).to eq '1'
|
399
|
+
expect(tokens[0].markup).to eq '.'
|
400
|
+
expect(tokens[1].info).to eq '2'
|
401
|
+
expect(tokens[1].markup).to eq '.'
|
402
|
+
expect(tokens[2].info).to eq '20'
|
403
|
+
expect(tokens[2].markup).to eq '.'
|
404
|
+
|
405
|
+
tokens = md.parse(" 1. Foo\n2. Bar\n 20. Fuzz\n 199. Flp", {})
|
406
|
+
expect(type_filter(tokens, 'ordered_list_open').length).to eq 1
|
407
|
+
|
408
|
+
tokens = type_filter(tokens, 'list_item_open')
|
409
|
+
expect(tokens.length).to eq 4
|
410
|
+
expect(tokens[0].info).to eq '1'
|
411
|
+
expect(tokens[0].markup).to eq '.'
|
412
|
+
expect(tokens[1].info).to eq '2'
|
413
|
+
expect(tokens[1].markup).to eq '.'
|
414
|
+
expect(tokens[2].info).to eq '20'
|
415
|
+
expect(tokens[2].markup).to eq '.'
|
416
|
+
expect(tokens[3].info).to eq '199'
|
417
|
+
expect(tokens[3].markup).to eq '.'
|
418
|
+
end
|
419
|
+
end
|
420
|
+
|
374
421
|
#------------------------------------------------------------------------------
|
375
422
|
describe 'Token attributes' do
|
376
423
|
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: motion-markdown-it
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 13.0.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Brett Walker
|
@@ -10,7 +10,7 @@ authors:
|
|
10
10
|
autorequire:
|
11
11
|
bindir: bin
|
12
12
|
cert_chain: []
|
13
|
-
date: 2023-01-
|
13
|
+
date: 2023-01-19 00:00:00.000000000 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: mdurl-rb
|
@@ -113,20 +113,22 @@ files:
|
|
113
113
|
- lib/motion-markdown-it/rules_core/replacements.rb
|
114
114
|
- lib/motion-markdown-it/rules_core/smartquotes.rb
|
115
115
|
- lib/motion-markdown-it/rules_core/state_core.rb
|
116
|
+
- lib/motion-markdown-it/rules_core/text_join.rb
|
116
117
|
- lib/motion-markdown-it/rules_inline/autolink.rb
|
117
118
|
- lib/motion-markdown-it/rules_inline/backticks.rb
|
118
119
|
- lib/motion-markdown-it/rules_inline/balance_pairs.rb
|
119
120
|
- lib/motion-markdown-it/rules_inline/emphasis.rb
|
120
121
|
- lib/motion-markdown-it/rules_inline/entity.rb
|
121
122
|
- lib/motion-markdown-it/rules_inline/escape.rb
|
123
|
+
- lib/motion-markdown-it/rules_inline/fragments_join.rb
|
122
124
|
- lib/motion-markdown-it/rules_inline/html_inline.rb
|
123
125
|
- lib/motion-markdown-it/rules_inline/image.rb
|
124
126
|
- lib/motion-markdown-it/rules_inline/link.rb
|
127
|
+
- lib/motion-markdown-it/rules_inline/linkify.rb
|
125
128
|
- lib/motion-markdown-it/rules_inline/newline.rb
|
126
129
|
- lib/motion-markdown-it/rules_inline/state_inline.rb
|
127
130
|
- lib/motion-markdown-it/rules_inline/strikethrough.rb
|
128
131
|
- lib/motion-markdown-it/rules_inline/text.rb
|
129
|
-
- lib/motion-markdown-it/rules_inline/text_collapse.rb
|
130
132
|
- lib/motion-markdown-it/token.rb
|
131
133
|
- lib/motion-markdown-it/version.rb
|
132
134
|
- spec/motion-markdown-it/commonmark_spec.rb
|