aboutsummaryrefslogtreecommitdiff
path: root/vendor/commonmark/doc.odin
blob: 64822623428f301cef800e77085c6c4dd9668a5a (plain)
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
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
/*
Bindings for [[ CMark; https://github.com/commonmark/cmark ]].

Original authors: John MacFarlane, Vicent Marti, rlis Gaņģis, Nick Wellnhofer.
See LICENSE for license details.

Example:
	import cm "vendor:commonmark"

	// Parsing - Simple interface
	hellope_world :: proc() {
		fmt.printf("CMark version: %v\n", cm.version_string())

		str := "Hellope *world*!"
		root := cm.parse_document(raw_data(str), len(str), cm.DEFAULT_OPTIONS)
		defer cm.node_free(root)

		html := cm.render_html(root, cm.DEFAULT_OPTIONS)
		defer cm.free(html)

		fmt.println(html)
	}

	// Parsing - Streaming interface
	streaming :: proc() {
		using cm

		STR :: "Hellope *world*!\n\n"
		N   :: 50
		STREAM_SIZE :: 42

		str_buf: [len(STR) * N]u8
		for i in 0..<N {
			copy(str_buf[i*len(STR):], STR)
		}

		parser := parser_new(DEFAULT_OPTIONS)
		defer parser_free(parser)

		buf := str_buf[:]
		for len(buf) > STREAM_SIZE {
			parser_feed(parser, raw_data(buf), STREAM_SIZE)
			buf = buf[STREAM_SIZE:]
		}

		if len(buf) > 0 {
			parser_feed(parser, raw_data(buf), len(buf))
			buf = buf[len(buf):]
		}

		root := parser_finish(parser)
		defer cm.node_free(root)

		html := cm.render_html(root, cm.DEFAULT_OPTIONS)
		defer cm.free(html)

		fmt.println(html)
	}

An iterator will walk through a tree of nodes, starting from a root
node, returning one node at a time, together with information about
whether the node is being entered or exited.

The iterator will first descend to a child node, if there is one.
When there is no child, the iterator will go to the next sibling.
When there is no next sibling, the iterator will return to the parent
(but with an `Event_Type.Exit`).

The iterator will return `.Done` when it reaches the root node again.

One natural application is an HTML renderer, where an `.Enter` event
outputs an open tag and an `.Exit` event outputs a close tag.

An iterator might also be used to transform an AST in some systematic
way, for example, turning all level-3 headings into regular paragraphs.

    usage_example(root: ^Node) {
        ev_type: Event_Type
        iter := iter_new(root)
        defer iter_free(iter)
        for {
            ev_type = iter_next(iter)
            if ev_type == .Done do break
            cur := iter_get_node(iter)
            // Do something with `cur` and `ev_type`
        }
    }

Iterators will never return `.Exit` events for leaf nodes,
which are nodes of type:

* HTML_Block
* Thematic_Break
* Code_Block
* Text
* Soft_Break
* Line_Break
* Code
* HTML_Inline

Nodes must only be modified after an `.Exit` event, or an `.Enter` event for
leaf nodes.
*/
package vendor_commonmark