-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathremark-span-words.ts
executable file
·46 lines (38 loc) · 1.19 KB
/
remark-span-words.ts
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
// plugins/remark-span-words.ts
import type { Literal, Node, Parent, Text } from '@nuxtjs/mdc'
import { visit } from 'unist-util-visit'
// Define the plugin with explicit UnistPlugin typing
function remarkSpanWords() {
return (tree: Node) => {
let wordIndex = 0
visit(tree, 'text', (node: Text, index: number | null, parent: Parent | null) => {
if (!parent || index === null)
return
// Split the text into words, preserving punctuation
const words = node.value.split(/(\s+)/)
const newNodes: Literal[] = []
words.forEach((word) => {
// Preserve whitespace
if (/^\s+$/.test(word)) {
newNodes.push({
type: 'text',
value: word,
})
return
}
// Skip empty strings
if (!word.trim())
return
// Create a span node for each non-whitespace word
newNodes.push({
type: 'html',
value: `<span data-tts="${wordIndex}">${word}</span>`,
})
wordIndex++
})
// Replace the original text node with our new nodes
parent.children.splice(index, 1, ...newNodes as any)
})
}
}
export default remarkSpanWords