1 | 'use strict'
|
2 |
|
3 | var extend = require('extend')
|
4 |
|
5 | module.exports = contents
|
6 |
|
7 | var LIST = 'list'
|
8 | var LIST_ITEM = 'listItem'
|
9 | var PARAGRAPH = 'paragraph'
|
10 | var LINK = 'link'
|
11 | var LINK_REFERENCE = 'linkReference'
|
12 |
|
13 |
|
14 | function contents(map, tight, prefix) {
|
15 | var minDepth = Infinity
|
16 | var index = -1
|
17 | var length = map.length
|
18 | var table
|
19 |
|
20 |
|
21 | while (++index < length) {
|
22 | if (map[index].depth < minDepth) {
|
23 | minDepth = map[index].depth
|
24 | }
|
25 | }
|
26 |
|
27 |
|
28 | index = -1
|
29 |
|
30 | while (++index < length) {
|
31 | map[index].depth -= minDepth - 1
|
32 | }
|
33 |
|
34 |
|
35 | table = list()
|
36 |
|
37 |
|
38 | index = -1
|
39 |
|
40 | while (++index < length) {
|
41 | insert(map[index], table, tight, prefix)
|
42 | }
|
43 |
|
44 | return table
|
45 | }
|
46 |
|
47 |
|
48 | function insert(entry, parent, tight, prefix) {
|
49 | var children = parent.children
|
50 | var length = children.length
|
51 | var last = children[length - 1]
|
52 | var isLoose = false
|
53 | var index
|
54 | var item
|
55 |
|
56 | if (entry.depth === 1) {
|
57 | item = listItem()
|
58 |
|
59 | item.children.push({
|
60 | type: PARAGRAPH,
|
61 | children: [
|
62 | {
|
63 | type: LINK,
|
64 | title: null,
|
65 | url: '#' + (prefix || '') + entry.id,
|
66 | children: all(entry.children)
|
67 | }
|
68 | ]
|
69 | })
|
70 |
|
71 | children.push(item)
|
72 | } else if (last && last.type === LIST_ITEM) {
|
73 | insert(entry, last, tight, prefix)
|
74 | } else if (last && last.type === LIST) {
|
75 | entry.depth--
|
76 |
|
77 | insert(entry, last, tight, prefix)
|
78 | } else if (parent.type === LIST) {
|
79 | item = listItem()
|
80 |
|
81 | insert(entry, item, tight, prefix)
|
82 |
|
83 | children.push(item)
|
84 | } else {
|
85 | item = list()
|
86 | entry.depth--
|
87 |
|
88 | insert(entry, item, tight, prefix)
|
89 |
|
90 | children.push(item)
|
91 | }
|
92 |
|
93 |
|
94 | parent.spread = !tight
|
95 |
|
96 | if (parent.type === LIST && parent.spread) {
|
97 | parent.spread = false
|
98 | index = -1
|
99 |
|
100 | while (++index < length) {
|
101 | if (children[index].children.length > 1) {
|
102 | parent.spread = true
|
103 | break
|
104 | }
|
105 | }
|
106 | }
|
107 |
|
108 |
|
109 | if (parent.type === LIST_ITEM) {
|
110 | parent.loose = tight ? false : children.length > 1
|
111 | } else {
|
112 | if (tight) {
|
113 | isLoose = false
|
114 | } else {
|
115 | index = -1
|
116 |
|
117 | while (++index < length) {
|
118 | if (children[index].loose) {
|
119 | isLoose = true
|
120 |
|
121 | break
|
122 | }
|
123 | }
|
124 | }
|
125 |
|
126 | index = -1
|
127 |
|
128 | while (++index < length) {
|
129 | children[index].loose = isLoose
|
130 | }
|
131 | }
|
132 | }
|
133 |
|
134 | function all(children) {
|
135 | var result = []
|
136 | var length = children.length
|
137 | var index = -1
|
138 |
|
139 | while (++index < length) {
|
140 | result = result.concat(one(children[index]))
|
141 | }
|
142 |
|
143 | return result
|
144 | }
|
145 |
|
146 | function one(node) {
|
147 | var copy
|
148 |
|
149 | if (node.type === LINK || node.type === LINK_REFERENCE) {
|
150 | return all(node.children)
|
151 | }
|
152 |
|
153 | copy = extend({}, node)
|
154 |
|
155 | delete copy.children
|
156 | delete copy.position
|
157 |
|
158 | copy = extend(true, {}, copy)
|
159 |
|
160 | if (node.children) {
|
161 | copy.children = all(node.children)
|
162 | }
|
163 |
|
164 | return copy
|
165 | }
|
166 |
|
167 |
|
168 | function list() {
|
169 | return {type: LIST, ordered: false, spread: false, children: []}
|
170 | }
|
171 |
|
172 |
|
173 | function listItem() {
|
174 |
|
175 | return {type: LIST_ITEM, loose: false, spread: false, children: []}
|
176 | }
|