hemingway 0.0.0 → 0.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.gitignore +19 -0
- data/.travis.yml +4 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +22 -0
- data/README.md +297 -0
- data/Rakefile +1 -0
- data/hemingway.gemspec +23 -0
- data/lib/hemingway/block/block.rb +378 -0
- data/lib/hemingway/block/block.treetop +36 -0
- data/lib/hemingway/block/block_nodes.rb +9 -0
- data/lib/hemingway/block/list/list.rb +412 -0
- data/lib/hemingway/block/list/list.treetop +51 -0
- data/lib/hemingway/block/list/list_nodes.rb +39 -0
- data/lib/hemingway/block/quote/quote.rb +192 -0
- data/lib/hemingway/block/quote/quote.treetop +27 -0
- data/lib/hemingway/block/quote/quote_nodes.rb +25 -0
- data/lib/hemingway/block/verbatim/verbatim.rb +159 -0
- data/lib/hemingway/block/verbatim/verbatim.treetop +21 -0
- data/lib/hemingway/block/verbatim/verbatim_nodes.rb +9 -0
- data/lib/hemingway/build.rb +65 -0
- data/lib/hemingway/footnote/footnote.rb +83 -0
- data/lib/hemingway/footnote/footnote.treetop +11 -0
- data/lib/hemingway/footnote/footnote_nodes.rb +21 -0
- data/lib/hemingway/latex.rb +409 -0
- data/lib/hemingway/latex.treetop +81 -0
- data/lib/hemingway/latex_nodes.rb +45 -0
- data/lib/hemingway/math/math.rb +135 -0
- data/lib/hemingway/math/math.treetop +29 -0
- data/lib/hemingway/math/math_nodes.rb +7 -0
- data/lib/hemingway/special/special.rb +164 -0
- data/lib/hemingway/special/special.treetop +17 -0
- data/lib/hemingway/special/special_nodes.rb +7 -0
- data/lib/hemingway/symbol/symbol.rb +460 -0
- data/lib/hemingway/symbol/symbol.treetop +47 -0
- data/lib/hemingway/symbol/symbol_nodes.rb +7 -0
- data/lib/hemingway/tag/tag.rb +538 -0
- data/lib/hemingway/tag/tag.treetop +63 -0
- data/lib/hemingway/tag/tag_nodes.rb +49 -0
- data/lib/hemingway/text/text.rb +121 -0
- data/lib/hemingway/text/text.treetop +35 -0
- data/lib/hemingway/text/text_nodes.rb +7 -0
- data/lib/hemingway/version.rb +3 -0
- data/lib/hemingway.rb +7 -0
- data/script/build +22 -0
- data/script/test +2 -0
- data/spec/build_spec.rb +65 -0
- data/spec/nodes/block/list_spec.rb +91 -0
- data/spec/nodes/block/quote_spec.rb +31 -0
- data/spec/nodes/block/verbatim_spec.rb +27 -0
- data/spec/nodes/block_spec.rb +21 -0
- data/spec/nodes/footnote_spec.rb +42 -0
- data/spec/nodes/math_spec.rb +31 -0
- data/spec/nodes/special_spec.rb +27 -0
- data/spec/nodes/tag_spec.rb +98 -0
- data/spec/parser_spec.rb +48 -0
- data/spec/spec_helper.rb +5 -0
- metadata +110 -18
@@ -0,0 +1,409 @@
|
|
1
|
+
# Autogenerated from a Treetop grammar. Edits may be lost.
|
2
|
+
|
3
|
+
|
4
|
+
require 'hemingway/build'
|
5
|
+
require 'hemingway/latex_nodes'
|
6
|
+
require "hemingway/block/block"
|
7
|
+
require "hemingway/footnote/footnote"
|
8
|
+
require "hemingway/math/math"
|
9
|
+
require "hemingway/special/special"
|
10
|
+
require "hemingway/symbol/symbol"
|
11
|
+
require "hemingway/tag/tag"
|
12
|
+
require "hemingway/text/text"
|
13
|
+
|
14
|
+
module Hemingway
|
15
|
+
module Latex
|
16
|
+
include Treetop::Runtime
|
17
|
+
|
18
|
+
def root
|
19
|
+
@root ||= :document
|
20
|
+
end
|
21
|
+
|
22
|
+
include Block
|
23
|
+
|
24
|
+
include Footnote
|
25
|
+
|
26
|
+
include Math
|
27
|
+
|
28
|
+
include Special
|
29
|
+
|
30
|
+
include Symbol
|
31
|
+
|
32
|
+
include Tag
|
33
|
+
|
34
|
+
include Text
|
35
|
+
|
36
|
+
def _nt_document
|
37
|
+
start_index = index
|
38
|
+
if node_cache[:document].has_key?(index)
|
39
|
+
cached = node_cache[:document][index]
|
40
|
+
if cached
|
41
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
42
|
+
@index = cached.interval.end
|
43
|
+
end
|
44
|
+
return cached
|
45
|
+
end
|
46
|
+
|
47
|
+
r0 = _nt_entry
|
48
|
+
|
49
|
+
node_cache[:document][start_index] = r0
|
50
|
+
|
51
|
+
r0
|
52
|
+
end
|
53
|
+
|
54
|
+
def _nt_entry
|
55
|
+
start_index = index
|
56
|
+
if node_cache[:entry].has_key?(index)
|
57
|
+
cached = node_cache[:entry][index]
|
58
|
+
if cached
|
59
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
60
|
+
@index = cached.interval.end
|
61
|
+
end
|
62
|
+
return cached
|
63
|
+
end
|
64
|
+
|
65
|
+
s0, i0 = [], index
|
66
|
+
loop do
|
67
|
+
i1 = index
|
68
|
+
r2 = _nt_paragraph
|
69
|
+
if r2
|
70
|
+
r1 = r2
|
71
|
+
else
|
72
|
+
r3 = _nt_last_paragraph
|
73
|
+
if r3
|
74
|
+
r1 = r3
|
75
|
+
else
|
76
|
+
@index = i1
|
77
|
+
r1 = nil
|
78
|
+
end
|
79
|
+
end
|
80
|
+
if r1
|
81
|
+
s0 << r1
|
82
|
+
else
|
83
|
+
break
|
84
|
+
end
|
85
|
+
end
|
86
|
+
r0 = instantiate_node(EntryNode,input, i0...index, s0)
|
87
|
+
|
88
|
+
node_cache[:entry][start_index] = r0
|
89
|
+
|
90
|
+
r0
|
91
|
+
end
|
92
|
+
|
93
|
+
module Paragraph0
|
94
|
+
def sequence
|
95
|
+
elements[0]
|
96
|
+
end
|
97
|
+
|
98
|
+
def eop
|
99
|
+
elements[1]
|
100
|
+
end
|
101
|
+
end
|
102
|
+
|
103
|
+
def _nt_paragraph
|
104
|
+
start_index = index
|
105
|
+
if node_cache[:paragraph].has_key?(index)
|
106
|
+
cached = node_cache[:paragraph][index]
|
107
|
+
if cached
|
108
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
109
|
+
@index = cached.interval.end
|
110
|
+
end
|
111
|
+
return cached
|
112
|
+
end
|
113
|
+
|
114
|
+
i0, s0 = index, []
|
115
|
+
s1, i1 = [], index
|
116
|
+
loop do
|
117
|
+
i2 = index
|
118
|
+
r3 = _nt_content
|
119
|
+
if r3
|
120
|
+
r2 = r3
|
121
|
+
else
|
122
|
+
r4 = _nt_footnote
|
123
|
+
if r4
|
124
|
+
r2 = r4
|
125
|
+
else
|
126
|
+
@index = i2
|
127
|
+
r2 = nil
|
128
|
+
end
|
129
|
+
end
|
130
|
+
if r2
|
131
|
+
s1 << r2
|
132
|
+
else
|
133
|
+
break
|
134
|
+
end
|
135
|
+
end
|
136
|
+
r1 = instantiate_node(SyntaxNode,input, i1...index, s1)
|
137
|
+
s0 << r1
|
138
|
+
if r1
|
139
|
+
r5 = _nt_eop
|
140
|
+
s0 << r5
|
141
|
+
end
|
142
|
+
if s0.last
|
143
|
+
r0 = instantiate_node(ParagraphNode,input, i0...index, s0)
|
144
|
+
r0.extend(Paragraph0)
|
145
|
+
else
|
146
|
+
@index = i0
|
147
|
+
r0 = nil
|
148
|
+
end
|
149
|
+
|
150
|
+
node_cache[:paragraph][start_index] = r0
|
151
|
+
|
152
|
+
r0
|
153
|
+
end
|
154
|
+
|
155
|
+
module LastParagraph0
|
156
|
+
def sequence
|
157
|
+
elements[0]
|
158
|
+
end
|
159
|
+
|
160
|
+
end
|
161
|
+
|
162
|
+
def _nt_last_paragraph
|
163
|
+
start_index = index
|
164
|
+
if node_cache[:last_paragraph].has_key?(index)
|
165
|
+
cached = node_cache[:last_paragraph][index]
|
166
|
+
if cached
|
167
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
168
|
+
@index = cached.interval.end
|
169
|
+
end
|
170
|
+
return cached
|
171
|
+
end
|
172
|
+
|
173
|
+
i0, s0 = index, []
|
174
|
+
s1, i1 = [], index
|
175
|
+
loop do
|
176
|
+
i2 = index
|
177
|
+
r3 = _nt_content
|
178
|
+
if r3
|
179
|
+
r2 = r3
|
180
|
+
else
|
181
|
+
r4 = _nt_footnote
|
182
|
+
if r4
|
183
|
+
r2 = r4
|
184
|
+
else
|
185
|
+
@index = i2
|
186
|
+
r2 = nil
|
187
|
+
end
|
188
|
+
end
|
189
|
+
if r2
|
190
|
+
s1 << r2
|
191
|
+
else
|
192
|
+
break
|
193
|
+
end
|
194
|
+
end
|
195
|
+
if s1.empty?
|
196
|
+
@index = i1
|
197
|
+
r1 = nil
|
198
|
+
else
|
199
|
+
r1 = instantiate_node(SyntaxNode,input, i1...index, s1)
|
200
|
+
end
|
201
|
+
s0 << r1
|
202
|
+
if r1
|
203
|
+
r6 = _nt_eop
|
204
|
+
if r6
|
205
|
+
r5 = r6
|
206
|
+
else
|
207
|
+
r5 = instantiate_node(SyntaxNode,input, index...index)
|
208
|
+
end
|
209
|
+
s0 << r5
|
210
|
+
end
|
211
|
+
if s0.last
|
212
|
+
r0 = instantiate_node(ParagraphNode,input, i0...index, s0)
|
213
|
+
r0.extend(LastParagraph0)
|
214
|
+
else
|
215
|
+
@index = i0
|
216
|
+
r0 = nil
|
217
|
+
end
|
218
|
+
|
219
|
+
node_cache[:last_paragraph][start_index] = r0
|
220
|
+
|
221
|
+
r0
|
222
|
+
end
|
223
|
+
|
224
|
+
def _nt_content
|
225
|
+
start_index = index
|
226
|
+
if node_cache[:content].has_key?(index)
|
227
|
+
cached = node_cache[:content][index]
|
228
|
+
if cached
|
229
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
230
|
+
@index = cached.interval.end
|
231
|
+
end
|
232
|
+
return cached
|
233
|
+
end
|
234
|
+
|
235
|
+
i0 = index
|
236
|
+
r1 = _nt_special
|
237
|
+
if r1
|
238
|
+
r0 = r1
|
239
|
+
else
|
240
|
+
r2 = _nt_tag
|
241
|
+
if r2
|
242
|
+
r0 = r2
|
243
|
+
else
|
244
|
+
r3 = _nt_block
|
245
|
+
if r3
|
246
|
+
r0 = r3
|
247
|
+
else
|
248
|
+
r4 = _nt_math
|
249
|
+
if r4
|
250
|
+
r0 = r4
|
251
|
+
else
|
252
|
+
r5 = _nt_text
|
253
|
+
if r5
|
254
|
+
r0 = r5
|
255
|
+
else
|
256
|
+
@index = i0
|
257
|
+
r0 = nil
|
258
|
+
end
|
259
|
+
end
|
260
|
+
end
|
261
|
+
end
|
262
|
+
end
|
263
|
+
|
264
|
+
node_cache[:content][start_index] = r0
|
265
|
+
|
266
|
+
r0
|
267
|
+
end
|
268
|
+
|
269
|
+
def _nt_whitespace
|
270
|
+
start_index = index
|
271
|
+
if node_cache[:whitespace].has_key?(index)
|
272
|
+
cached = node_cache[:whitespace][index]
|
273
|
+
if cached
|
274
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
275
|
+
@index = cached.interval.end
|
276
|
+
end
|
277
|
+
return cached
|
278
|
+
end
|
279
|
+
|
280
|
+
s0, i0 = [], index
|
281
|
+
loop do
|
282
|
+
i1 = index
|
283
|
+
if has_terminal?(" ", false, index)
|
284
|
+
r2 = instantiate_node(SyntaxNode,input, index...(index + 1))
|
285
|
+
@index += 1
|
286
|
+
else
|
287
|
+
terminal_parse_failure(" ")
|
288
|
+
r2 = nil
|
289
|
+
end
|
290
|
+
if r2
|
291
|
+
r1 = r2
|
292
|
+
else
|
293
|
+
r3 = _nt_newline
|
294
|
+
if r3
|
295
|
+
r1 = r3
|
296
|
+
else
|
297
|
+
@index = i1
|
298
|
+
r1 = nil
|
299
|
+
end
|
300
|
+
end
|
301
|
+
if r1
|
302
|
+
s0 << r1
|
303
|
+
else
|
304
|
+
break
|
305
|
+
end
|
306
|
+
end
|
307
|
+
r0 = instantiate_node(SyntaxNode,input, i0...index, s0)
|
308
|
+
|
309
|
+
node_cache[:whitespace][start_index] = r0
|
310
|
+
|
311
|
+
r0
|
312
|
+
end
|
313
|
+
|
314
|
+
def _nt_spaces
|
315
|
+
start_index = index
|
316
|
+
if node_cache[:spaces].has_key?(index)
|
317
|
+
cached = node_cache[:spaces][index]
|
318
|
+
if cached
|
319
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
320
|
+
@index = cached.interval.end
|
321
|
+
end
|
322
|
+
return cached
|
323
|
+
end
|
324
|
+
|
325
|
+
s0, i0 = [], index
|
326
|
+
loop do
|
327
|
+
if has_terminal?(" ", false, index)
|
328
|
+
r1 = instantiate_node(SyntaxNode,input, index...(index + 1))
|
329
|
+
@index += 1
|
330
|
+
else
|
331
|
+
terminal_parse_failure(" ")
|
332
|
+
r1 = nil
|
333
|
+
end
|
334
|
+
if r1
|
335
|
+
s0 << r1
|
336
|
+
else
|
337
|
+
break
|
338
|
+
end
|
339
|
+
end
|
340
|
+
r0 = instantiate_node(SyntaxNode,input, i0...index, s0)
|
341
|
+
|
342
|
+
node_cache[:spaces][start_index] = r0
|
343
|
+
|
344
|
+
r0
|
345
|
+
end
|
346
|
+
|
347
|
+
def _nt_eop
|
348
|
+
start_index = index
|
349
|
+
if node_cache[:eop].has_key?(index)
|
350
|
+
cached = node_cache[:eop][index]
|
351
|
+
if cached
|
352
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
353
|
+
@index = cached.interval.end
|
354
|
+
end
|
355
|
+
return cached
|
356
|
+
end
|
357
|
+
|
358
|
+
s0, i0 = [], index
|
359
|
+
loop do
|
360
|
+
r1 = _nt_newline
|
361
|
+
if r1
|
362
|
+
s0 << r1
|
363
|
+
else
|
364
|
+
break
|
365
|
+
end
|
366
|
+
end
|
367
|
+
if s0.size < 2
|
368
|
+
@index = i0
|
369
|
+
r0 = nil
|
370
|
+
else
|
371
|
+
r0 = instantiate_node(SyntaxNode,input, i0...index, s0)
|
372
|
+
end
|
373
|
+
|
374
|
+
node_cache[:eop][start_index] = r0
|
375
|
+
|
376
|
+
r0
|
377
|
+
end
|
378
|
+
|
379
|
+
def _nt_newline
|
380
|
+
start_index = index
|
381
|
+
if node_cache[:newline].has_key?(index)
|
382
|
+
cached = node_cache[:newline][index]
|
383
|
+
if cached
|
384
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
385
|
+
@index = cached.interval.end
|
386
|
+
end
|
387
|
+
return cached
|
388
|
+
end
|
389
|
+
|
390
|
+
if has_terminal?("\n", false, index)
|
391
|
+
r0 = instantiate_node(SyntaxNode,input, index...(index + 1))
|
392
|
+
@index += 1
|
393
|
+
else
|
394
|
+
terminal_parse_failure("\n")
|
395
|
+
r0 = nil
|
396
|
+
end
|
397
|
+
|
398
|
+
node_cache[:newline][start_index] = r0
|
399
|
+
|
400
|
+
r0
|
401
|
+
end
|
402
|
+
|
403
|
+
end
|
404
|
+
|
405
|
+
class LatexParser < Treetop::Runtime::CompiledParser
|
406
|
+
include Latex
|
407
|
+
end
|
408
|
+
|
409
|
+
end
|
@@ -0,0 +1,81 @@
|
|
1
|
+
require 'hemingway/build'
|
2
|
+
require 'hemingway/latex_nodes'
|
3
|
+
require "hemingway/block/block"
|
4
|
+
require "hemingway/footnote/footnote"
|
5
|
+
require "hemingway/math/math"
|
6
|
+
require "hemingway/special/special"
|
7
|
+
require "hemingway/symbol/symbol"
|
8
|
+
require "hemingway/tag/tag"
|
9
|
+
require "hemingway/text/text"
|
10
|
+
|
11
|
+
module Hemingway
|
12
|
+
grammar Latex
|
13
|
+
|
14
|
+
include Block
|
15
|
+
include Footnote
|
16
|
+
include Math
|
17
|
+
include Special
|
18
|
+
include Symbol
|
19
|
+
include Tag
|
20
|
+
include Text
|
21
|
+
|
22
|
+
rule document
|
23
|
+
entry
|
24
|
+
end
|
25
|
+
|
26
|
+
rule entry
|
27
|
+
( paragraph / last_paragraph )* <EntryNode>
|
28
|
+
end
|
29
|
+
|
30
|
+
# Example: These aren't the \n\n droids you're looking for \n\n.
|
31
|
+
# Notes:
|
32
|
+
# - Okay so this is interesting. When you reference something with a * or
|
33
|
+
# a +, then you're creating a top level array-like structure that you'll
|
34
|
+
# have to dig past to get at the list. elements[0] refers to the array of
|
35
|
+
# tags or texts here.
|
36
|
+
rule paragraph
|
37
|
+
sequence:( content / footnote )* eop <ParagraphNode>
|
38
|
+
end
|
39
|
+
|
40
|
+
# The last paragraph in an entry need not end with \n\n. Because this
|
41
|
+
# comes second in the ordered choice for entry, it will only be used
|
42
|
+
# if a paragraph has concluded for some reason and there wasn't an eop
|
43
|
+
# to consume. The only time I can imagine this happening would be at
|
44
|
+
# the end of an entry.
|
45
|
+
rule last_paragraph
|
46
|
+
sequence:( content / footnote )+ eop? <ParagraphNode>
|
47
|
+
end
|
48
|
+
|
49
|
+
# Example: \tag{text} or just text or $\Delta$
|
50
|
+
# Notes:
|
51
|
+
# - So I can define methods based on the ordered choice in the top
|
52
|
+
# level of this rule. Text is already its own thing though, so an html
|
53
|
+
# method need not be defined on it because alas, it already exists as
|
54
|
+
# defined in the text rule itself!
|
55
|
+
rule content
|
56
|
+
special / tag / block / math / text
|
57
|
+
end
|
58
|
+
|
59
|
+
# Treetop does not separate lexing from parsing. Must consume all input.
|
60
|
+
rule whitespace
|
61
|
+
( " " / newline )*
|
62
|
+
end
|
63
|
+
|
64
|
+
rule spaces
|
65
|
+
( " " )*
|
66
|
+
end
|
67
|
+
|
68
|
+
# End of paragraph. Originally this had a choice for EOF, but I can't
|
69
|
+
# seem to find a good way for Treetop to process that. My workaround
|
70
|
+
# strategy will be to append some newlines onto the end of the input
|
71
|
+
# string.
|
72
|
+
rule eop
|
73
|
+
newline 2..
|
74
|
+
end
|
75
|
+
|
76
|
+
rule newline
|
77
|
+
"\n"
|
78
|
+
end
|
79
|
+
|
80
|
+
end
|
81
|
+
end
|
@@ -0,0 +1,45 @@
|
|
1
|
+
module Hemingway
|
2
|
+
|
3
|
+
module EntryNode
|
4
|
+
def html
|
5
|
+
footnote_content = []
|
6
|
+
paragraph_html = ""
|
7
|
+
|
8
|
+
elements.each do |e|
|
9
|
+
paragraph_html += e.html(footnote_content.size)
|
10
|
+
footnote_content += e.footnote_html(footnote_content.size)
|
11
|
+
end
|
12
|
+
|
13
|
+
footnote_html = footnote_content.join
|
14
|
+
|
15
|
+
Build.tag("div", paragraph_html + footnote_html, :class => "entry")
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
module ParagraphNode
|
20
|
+
def html(footnote_seed)
|
21
|
+
paragraph_content = sequence.elements.map do |element|
|
22
|
+
if element.respond_to?(:footnote_html)
|
23
|
+
footnote_seed += 1
|
24
|
+
element.html(footnote_seed)
|
25
|
+
else
|
26
|
+
element.html
|
27
|
+
end
|
28
|
+
end.join
|
29
|
+
|
30
|
+
Build.tag("p", paragraph_content)
|
31
|
+
end
|
32
|
+
|
33
|
+
def footnote_html(footnote_seed)
|
34
|
+
footnote_content = sequence.elements.reduce([]) do |memo, element|
|
35
|
+
if element.respond_to?(:footnote_html)
|
36
|
+
footnote_seed += 1
|
37
|
+
memo + [element.footnote_html(footnote_seed)]
|
38
|
+
else
|
39
|
+
memo
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
end
|
45
|
+
end
|
@@ -0,0 +1,135 @@
|
|
1
|
+
# Autogenerated from a Treetop grammar. Edits may be lost.
|
2
|
+
|
3
|
+
|
4
|
+
require "hemingway/math/math_nodes"
|
5
|
+
|
6
|
+
module Hemingway
|
7
|
+
module Math
|
8
|
+
include Treetop::Runtime
|
9
|
+
|
10
|
+
def root
|
11
|
+
@root ||= :math
|
12
|
+
end
|
13
|
+
|
14
|
+
module Math0
|
15
|
+
def math_start
|
16
|
+
elements[0]
|
17
|
+
end
|
18
|
+
|
19
|
+
def symbol
|
20
|
+
elements[1]
|
21
|
+
end
|
22
|
+
|
23
|
+
def math_end
|
24
|
+
elements[2]
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
def _nt_math
|
29
|
+
start_index = index
|
30
|
+
if node_cache[:math].has_key?(index)
|
31
|
+
cached = node_cache[:math][index]
|
32
|
+
if cached
|
33
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
34
|
+
@index = cached.interval.end
|
35
|
+
end
|
36
|
+
return cached
|
37
|
+
end
|
38
|
+
|
39
|
+
i0, s0 = index, []
|
40
|
+
r1 = _nt_math_start
|
41
|
+
s0 << r1
|
42
|
+
if r1
|
43
|
+
r2 = _nt_symbol
|
44
|
+
s0 << r2
|
45
|
+
if r2
|
46
|
+
r3 = _nt_math_end
|
47
|
+
s0 << r3
|
48
|
+
end
|
49
|
+
end
|
50
|
+
if s0.last
|
51
|
+
r0 = instantiate_node(MathNode,input, i0...index, s0)
|
52
|
+
r0.extend(Math0)
|
53
|
+
else
|
54
|
+
@index = i0
|
55
|
+
r0 = nil
|
56
|
+
end
|
57
|
+
|
58
|
+
node_cache[:math][start_index] = r0
|
59
|
+
|
60
|
+
r0
|
61
|
+
end
|
62
|
+
|
63
|
+
def _nt_symbol
|
64
|
+
start_index = index
|
65
|
+
if node_cache[:symbol].has_key?(index)
|
66
|
+
cached = node_cache[:symbol][index]
|
67
|
+
if cached
|
68
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
69
|
+
@index = cached.interval.end
|
70
|
+
end
|
71
|
+
return cached
|
72
|
+
end
|
73
|
+
|
74
|
+
r0 = _nt_math_symbol
|
75
|
+
|
76
|
+
node_cache[:symbol][start_index] = r0
|
77
|
+
|
78
|
+
r0
|
79
|
+
end
|
80
|
+
|
81
|
+
def _nt_math_start
|
82
|
+
start_index = index
|
83
|
+
if node_cache[:math_start].has_key?(index)
|
84
|
+
cached = node_cache[:math_start][index]
|
85
|
+
if cached
|
86
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
87
|
+
@index = cached.interval.end
|
88
|
+
end
|
89
|
+
return cached
|
90
|
+
end
|
91
|
+
|
92
|
+
if has_terminal?("$", false, index)
|
93
|
+
r0 = instantiate_node(SyntaxNode,input, index...(index + 1))
|
94
|
+
@index += 1
|
95
|
+
else
|
96
|
+
terminal_parse_failure("$")
|
97
|
+
r0 = nil
|
98
|
+
end
|
99
|
+
|
100
|
+
node_cache[:math_start][start_index] = r0
|
101
|
+
|
102
|
+
r0
|
103
|
+
end
|
104
|
+
|
105
|
+
def _nt_math_end
|
106
|
+
start_index = index
|
107
|
+
if node_cache[:math_end].has_key?(index)
|
108
|
+
cached = node_cache[:math_end][index]
|
109
|
+
if cached
|
110
|
+
cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
|
111
|
+
@index = cached.interval.end
|
112
|
+
end
|
113
|
+
return cached
|
114
|
+
end
|
115
|
+
|
116
|
+
if has_terminal?("$", false, index)
|
117
|
+
r0 = instantiate_node(SyntaxNode,input, index...(index + 1))
|
118
|
+
@index += 1
|
119
|
+
else
|
120
|
+
terminal_parse_failure("$")
|
121
|
+
r0 = nil
|
122
|
+
end
|
123
|
+
|
124
|
+
node_cache[:math_end][start_index] = r0
|
125
|
+
|
126
|
+
r0
|
127
|
+
end
|
128
|
+
|
129
|
+
end
|
130
|
+
|
131
|
+
class MathParser < Treetop::Runtime::CompiledParser
|
132
|
+
include Math
|
133
|
+
end
|
134
|
+
|
135
|
+
end
|
@@ -0,0 +1,29 @@
|
|
1
|
+
require "hemingway/math/math_nodes"
|
2
|
+
|
3
|
+
module Hemingway
|
4
|
+
grammar Math
|
5
|
+
|
6
|
+
# Example: $ \Pi = 3.14159 $
|
7
|
+
rule math
|
8
|
+
math_start symbol math_end <MathNode>
|
9
|
+
end
|
10
|
+
|
11
|
+
# Example : \Pi
|
12
|
+
# Notes:
|
13
|
+
# - Once again, math_symbol need not have an html method defined on it.
|
14
|
+
# When .html is called on symbol, it knows the match is actually a
|
15
|
+
# math_symbol, so that is what symbol.html is actually calling.
|
16
|
+
rule symbol
|
17
|
+
math_symbol
|
18
|
+
end
|
19
|
+
|
20
|
+
rule math_start
|
21
|
+
"$"
|
22
|
+
end
|
23
|
+
|
24
|
+
rule math_end
|
25
|
+
"$"
|
26
|
+
end
|
27
|
+
|
28
|
+
end
|
29
|
+
end
|