brevity 0.4.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (119) hide show
  1. checksums.yaml +7 -0
  2. data/.document +3 -0
  3. data/.gitignore +7 -0
  4. data/.rspec +1 -0
  5. data/.ruby-version +1 -0
  6. data/.yardopts +1 -0
  7. data/ChangeLog.rdoc +4 -0
  8. data/Gemfile +3 -0
  9. data/LICENSE.txt +20 -0
  10. data/README.rdoc +27 -0
  11. data/Rakefile +67 -0
  12. data/bin/debrief +56 -0
  13. data/brevity.gemspec +28 -0
  14. data/examples/alley_cat.br +50 -0
  15. data/examples/hip.br +15 -0
  16. data/examples/missed_connection.br +6 -0
  17. data/examples/song1.br +11 -0
  18. data/examples/song2.br +10 -0
  19. data/examples/twinkle.br +18 -0
  20. data/lib/brevity/commands/constants.rb +18 -0
  21. data/lib/brevity/commands/expr.rb +17 -0
  22. data/lib/brevity/commands/meter.rb +20 -0
  23. data/lib/brevity/commands/part.rb +47 -0
  24. data/lib/brevity/commands/tempo.rb +13 -0
  25. data/lib/brevity/itemization.rb +73 -0
  26. data/lib/brevity/parsing/expression/dynamic.rb +280 -0
  27. data/lib/brevity/parsing/expression/dynamic.treetop +41 -0
  28. data/lib/brevity/parsing/expression/dynamic_nodes.rb +55 -0
  29. data/lib/brevity/parsing/expression/expression.rb +429 -0
  30. data/lib/brevity/parsing/expression/expression.treetop +39 -0
  31. data/lib/brevity/parsing/expression/expression_nodes.rb +26 -0
  32. data/lib/brevity/parsing/expression/gradual.rb +44 -0
  33. data/lib/brevity/parsing/expression/gradual.treetop +9 -0
  34. data/lib/brevity/parsing/expression/gradual_node.rb +11 -0
  35. data/lib/brevity/parsing/expression/label.rb +75 -0
  36. data/lib/brevity/parsing/expression/label.treetop +9 -0
  37. data/lib/brevity/parsing/expression/label_node.rb +15 -0
  38. data/lib/brevity/parsing/expression/sequence.rb +130 -0
  39. data/lib/brevity/parsing/expression/sequence.treetop +12 -0
  40. data/lib/brevity/parsing/expression/sequence_node.rb +14 -0
  41. data/lib/brevity/parsing/file/command.rb +216 -0
  42. data/lib/brevity/parsing/file/command.treetop +17 -0
  43. data/lib/brevity/parsing/file/command_node.rb +11 -0
  44. data/lib/brevity/parsing/file/comment.rb +178 -0
  45. data/lib/brevity/parsing/file/comment.treetop +21 -0
  46. data/lib/brevity/parsing/file/comment_node.rb +3 -0
  47. data/lib/brevity/parsing/file/file.rb +152 -0
  48. data/lib/brevity/parsing/file/file.treetop +16 -0
  49. data/lib/brevity/parsing/file/file_node.rb +7 -0
  50. data/lib/brevity/parsing/file/path.rb +235 -0
  51. data/lib/brevity/parsing/file/path.treetop +12 -0
  52. data/lib/brevity/parsing/modifiers/duplicate_modifier.rb +65 -0
  53. data/lib/brevity/parsing/modifiers/duplicate_modifier.treetop +11 -0
  54. data/lib/brevity/parsing/modifiers/duplicate_modifier_node.rb +8 -0
  55. data/lib/brevity/parsing/modifiers/modifier.rb +64 -0
  56. data/lib/brevity/parsing/modifiers/modifier.treetop +13 -0
  57. data/lib/brevity/parsing/modifiers/stretch_modifier.rb +69 -0
  58. data/lib/brevity/parsing/modifiers/stretch_modifier.treetop +11 -0
  59. data/lib/brevity/parsing/modifiers/stretch_modifier_node.rb +21 -0
  60. data/lib/brevity/parsing/modifiers/transpose_modifier.rb +69 -0
  61. data/lib/brevity/parsing/modifiers/transpose_modifier.treetop +11 -0
  62. data/lib/brevity/parsing/modifiers/transpose_modifier_node.rb +13 -0
  63. data/lib/brevity/parsing/note/accent.rb +44 -0
  64. data/lib/brevity/parsing/note/accent.treetop +9 -0
  65. data/lib/brevity/parsing/note/duration.rb +203 -0
  66. data/lib/brevity/parsing/note/duration.treetop +23 -0
  67. data/lib/brevity/parsing/note/duration_nodes.rb +19 -0
  68. data/lib/brevity/parsing/note/link.rb +69 -0
  69. data/lib/brevity/parsing/note/link.treetop +11 -0
  70. data/lib/brevity/parsing/note/link_node.rb +19 -0
  71. data/lib/brevity/parsing/note/note.rb +300 -0
  72. data/lib/brevity/parsing/note/note.treetop +30 -0
  73. data/lib/brevity/parsing/note/note_nodes.rb +77 -0
  74. data/lib/brevity/parsing/note/pitch.rb +81 -0
  75. data/lib/brevity/parsing/note/pitch.treetop +9 -0
  76. data/lib/brevity/parsing/note/pitch_node.rb +50 -0
  77. data/lib/brevity/parsing/numbers/nonnegative_integer.rb +53 -0
  78. data/lib/brevity/parsing/numbers/nonnegative_integer.treetop +9 -0
  79. data/lib/brevity/parsing/numbers/positive_integer.rb +91 -0
  80. data/lib/brevity/parsing/numbers/positive_integer.treetop +15 -0
  81. data/lib/brevity/read_file.rb +18 -0
  82. data/lib/brevity/score_maker.rb +64 -0
  83. data/lib/brevity/version.rb +4 -0
  84. data/lib/brevity.rb +53 -0
  85. data/manuals/brevity.pdf +0 -0
  86. data/manuals/brevity.tex +273 -0
  87. data/spec/brevity_spec.rb +8 -0
  88. data/spec/commands/expr_spec.rb +15 -0
  89. data/spec/commands/meter_spec.rb +21 -0
  90. data/spec/commands/part_spec.rb +16 -0
  91. data/spec/commands/tempo_spec.rb +20 -0
  92. data/spec/itemization_spec.rb +46 -0
  93. data/spec/parsing/expression/dynamic_nodes_spec.rb +32 -0
  94. data/spec/parsing/expression/dynamic_spec.rb +23 -0
  95. data/spec/parsing/expression/expression_nodes_spec.rb +87 -0
  96. data/spec/parsing/expression/expression_spec.rb +85 -0
  97. data/spec/parsing/expression/gradual_spec.rb +10 -0
  98. data/spec/parsing/expression/label_node_spec.rb +13 -0
  99. data/spec/parsing/expression/label_spec.rb +35 -0
  100. data/spec/parsing/file/command_node_spec.rb +29 -0
  101. data/spec/parsing/file/command_spec.rb +18 -0
  102. data/spec/parsing/file/comment_spec.rb +14 -0
  103. data/spec/parsing/file/file_node_spec.rb +19 -0
  104. data/spec/parsing/file/file_spec.rb +30 -0
  105. data/spec/parsing/modifiers/modifier_nodes_spec.rb +25 -0
  106. data/spec/parsing/modifiers/modifier_parsers_spec.rb +20 -0
  107. data/spec/parsing/note/accent_spec.rb +27 -0
  108. data/spec/parsing/note/duration_nodes_spec.rb +79 -0
  109. data/spec/parsing/note/duration_spec.rb +69 -0
  110. data/spec/parsing/note/link_node_spec.rb +30 -0
  111. data/spec/parsing/note/link_spec.rb +23 -0
  112. data/spec/parsing/note/note_nodes_spec.rb +82 -0
  113. data/spec/parsing/note/note_spec.rb +188 -0
  114. data/spec/parsing/note/pitch_node_spec.rb +48 -0
  115. data/spec/parsing/note/pitch_spec.rb +23 -0
  116. data/spec/parsing/numbers/nonnegative_integer_spec.rb +11 -0
  117. data/spec/parsing/numbers/positive_integer_spec.rb +17 -0
  118. data/spec/spec_helper.rb +112 -0
  119. metadata +293 -0
@@ -0,0 +1,429 @@
1
+ # Autogenerated from a Treetop grammar. Edits may be lost.
2
+
3
+
4
+ module Brevity
5
+
6
+ module Expression
7
+ include Treetop::Runtime
8
+
9
+ def root
10
+ @root ||= :expression
11
+ end
12
+
13
+ include Gradual
14
+
15
+ include Dynamic
16
+
17
+ include Note
18
+
19
+ include Label
20
+
21
+ include Modifier
22
+
23
+ module Expression0
24
+ def expr
25
+ elements[1]
26
+ end
27
+ end
28
+
29
+ module Expression1
30
+ def expr
31
+ elements[1]
32
+ end
33
+
34
+ def more
35
+ elements[2]
36
+ end
37
+
38
+ end
39
+
40
+ def _nt_expression
41
+ start_index = index
42
+ if node_cache[:expression].has_key?(index)
43
+ cached = node_cache[:expression][index]
44
+ if cached
45
+ node_cache[:expression][index] = cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
46
+ @index = cached.interval.end
47
+ end
48
+ return cached
49
+ end
50
+
51
+ i0, s0 = index, []
52
+ s1, i1 = [], index
53
+ loop do
54
+ if has_terminal?(@regexps[gr = '\A[\\s]'] ||= Regexp.new(gr), :regexp, index)
55
+ r2 = true
56
+ @index += 1
57
+ else
58
+ terminal_parse_failure('[\\s]')
59
+ r2 = nil
60
+ end
61
+ if r2
62
+ s1 << r2
63
+ else
64
+ break
65
+ end
66
+ end
67
+ r1 = instantiate_node(SyntaxNode,input, i1...index, s1)
68
+ s0 << r1
69
+ if r1
70
+ r3 = _nt_expr
71
+ s0 << r3
72
+ if r3
73
+ s4, i4 = [], index
74
+ loop do
75
+ i5, s5 = index, []
76
+ s6, i6 = [], index
77
+ loop do
78
+ if has_terminal?(@regexps[gr = '\A[\\s]'] ||= Regexp.new(gr), :regexp, index)
79
+ r7 = true
80
+ @index += 1
81
+ else
82
+ terminal_parse_failure('[\\s]')
83
+ r7 = nil
84
+ end
85
+ if r7
86
+ s6 << r7
87
+ else
88
+ break
89
+ end
90
+ end
91
+ if s6.empty?
92
+ @index = i6
93
+ r6 = nil
94
+ else
95
+ r6 = instantiate_node(SyntaxNode,input, i6...index, s6)
96
+ end
97
+ s5 << r6
98
+ if r6
99
+ r8 = _nt_expr
100
+ s5 << r8
101
+ end
102
+ if s5.last
103
+ r5 = instantiate_node(SyntaxNode,input, i5...index, s5)
104
+ r5.extend(Expression0)
105
+ else
106
+ @index = i5
107
+ r5 = nil
108
+ end
109
+ if r5
110
+ s4 << r5
111
+ else
112
+ break
113
+ end
114
+ end
115
+ r4 = instantiate_node(SyntaxNode,input, i4...index, s4)
116
+ s0 << r4
117
+ if r4
118
+ s9, i9 = [], index
119
+ loop do
120
+ if has_terminal?(@regexps[gr = '\A[\\s]'] ||= Regexp.new(gr), :regexp, index)
121
+ r10 = true
122
+ @index += 1
123
+ else
124
+ terminal_parse_failure('[\\s]')
125
+ r10 = nil
126
+ end
127
+ if r10
128
+ s9 << r10
129
+ else
130
+ break
131
+ end
132
+ end
133
+ r9 = instantiate_node(SyntaxNode,input, i9...index, s9)
134
+ s0 << r9
135
+ end
136
+ end
137
+ end
138
+ if s0.last
139
+ r0 = instantiate_node(ExpressionNode,input, i0...index, s0)
140
+ r0.extend(Expression1)
141
+ else
142
+ @index = i0
143
+ r0 = nil
144
+ end
145
+
146
+ node_cache[:expression][start_index] = r0
147
+
148
+ r0
149
+ end
150
+
151
+ def _nt_expr_element
152
+ start_index = index
153
+ if node_cache[:expr_element].has_key?(index)
154
+ cached = node_cache[:expr_element][index]
155
+ if cached
156
+ node_cache[:expr_element][index] = cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
157
+ @index = cached.interval.end
158
+ end
159
+ return cached
160
+ end
161
+
162
+ i0 = index
163
+ r1 = _nt_gradual
164
+ if r1
165
+ r1 = SyntaxNode.new(input, (index-1)...index) if r1 == true
166
+ r0 = r1
167
+ else
168
+ r2 = _nt_dynamic
169
+ if r2
170
+ r2 = SyntaxNode.new(input, (index-1)...index) if r2 == true
171
+ r0 = r2
172
+ else
173
+ r3 = _nt_note
174
+ if r3
175
+ r3 = SyntaxNode.new(input, (index-1)...index) if r3 == true
176
+ r0 = r3
177
+ else
178
+ r4 = _nt_label
179
+ r4.extend(ExprElementNode)
180
+ if r4
181
+ r4 = SyntaxNode.new(input, (index-1)...index) if r4 == true
182
+ r0 = r4
183
+ else
184
+ @index = i0
185
+ r0 = nil
186
+ end
187
+ end
188
+ end
189
+ end
190
+
191
+ node_cache[:expr_element][start_index] = r0
192
+
193
+ r0
194
+ end
195
+
196
+ def _nt_expr
197
+ start_index = index
198
+ if node_cache[:expr].has_key?(index)
199
+ cached = node_cache[:expr][index]
200
+ if cached
201
+ node_cache[:expr][index] = cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
202
+ @index = cached.interval.end
203
+ end
204
+ return cached
205
+ end
206
+
207
+ i0 = index
208
+ r1 = _nt_nonmodifiable
209
+ if r1
210
+ r1 = SyntaxNode.new(input, (index-1)...index) if r1 == true
211
+ r0 = r1
212
+ else
213
+ r2 = _nt_modifiable
214
+ if r2
215
+ r2 = SyntaxNode.new(input, (index-1)...index) if r2 == true
216
+ r0 = r2
217
+ else
218
+ @index = i0
219
+ r0 = nil
220
+ end
221
+ end
222
+
223
+ node_cache[:expr][start_index] = r0
224
+
225
+ r0
226
+ end
227
+
228
+ module Modifiable0
229
+ def base
230
+ elements[0]
231
+ end
232
+
233
+ def mods
234
+ elements[1]
235
+ end
236
+ end
237
+
238
+ def _nt_modifiable
239
+ start_index = index
240
+ if node_cache[:modifiable].has_key?(index)
241
+ cached = node_cache[:modifiable][index]
242
+ if cached
243
+ node_cache[:modifiable][index] = cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
244
+ @index = cached.interval.end
245
+ end
246
+ return cached
247
+ end
248
+
249
+ i0, s0 = index, []
250
+ i1 = index
251
+ r2 = _nt_group
252
+ if r2
253
+ r2 = SyntaxNode.new(input, (index-1)...index) if r2 == true
254
+ r1 = r2
255
+ else
256
+ r3 = _nt_label
257
+ if r3
258
+ r3 = SyntaxNode.new(input, (index-1)...index) if r3 == true
259
+ r1 = r3
260
+ else
261
+ r4 = _nt_note
262
+ if r4
263
+ r4 = SyntaxNode.new(input, (index-1)...index) if r4 == true
264
+ r1 = r4
265
+ else
266
+ @index = i1
267
+ r1 = nil
268
+ end
269
+ end
270
+ end
271
+ s0 << r1
272
+ if r1
273
+ s5, i5 = [], index
274
+ loop do
275
+ r6 = _nt_modifier
276
+ if r6
277
+ s5 << r6
278
+ else
279
+ break
280
+ end
281
+ end
282
+ r5 = instantiate_node(SyntaxNode,input, i5...index, s5)
283
+ s0 << r5
284
+ end
285
+ if s0.last
286
+ r0 = instantiate_node(ModifiableNode,input, i0...index, s0)
287
+ r0.extend(Modifiable0)
288
+ else
289
+ @index = i0
290
+ r0 = nil
291
+ end
292
+
293
+ node_cache[:modifiable][start_index] = r0
294
+
295
+ r0
296
+ end
297
+
298
+ module Group0
299
+ def expression
300
+ elements[2]
301
+ end
302
+
303
+ end
304
+
305
+ def _nt_group
306
+ start_index = index
307
+ if node_cache[:group].has_key?(index)
308
+ cached = node_cache[:group][index]
309
+ if cached
310
+ node_cache[:group][index] = cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
311
+ @index = cached.interval.end
312
+ end
313
+ return cached
314
+ end
315
+
316
+ i0, s0 = index, []
317
+ if (match_len = has_terminal?("(", false, index))
318
+ r1 = true
319
+ @index += match_len
320
+ else
321
+ terminal_parse_failure("(")
322
+ r1 = nil
323
+ end
324
+ s0 << r1
325
+ if r1
326
+ s2, i2 = [], index
327
+ loop do
328
+ if has_terminal?(@regexps[gr = '\A[\\s]'] ||= Regexp.new(gr), :regexp, index)
329
+ r3 = true
330
+ @index += 1
331
+ else
332
+ terminal_parse_failure('[\\s]')
333
+ r3 = nil
334
+ end
335
+ if r3
336
+ s2 << r3
337
+ else
338
+ break
339
+ end
340
+ end
341
+ r2 = instantiate_node(SyntaxNode,input, i2...index, s2)
342
+ s0 << r2
343
+ if r2
344
+ r4 = _nt_expression
345
+ s0 << r4
346
+ if r4
347
+ s5, i5 = [], index
348
+ loop do
349
+ if has_terminal?(@regexps[gr = '\A[\\s]'] ||= Regexp.new(gr), :regexp, index)
350
+ r6 = true
351
+ @index += 1
352
+ else
353
+ terminal_parse_failure('[\\s]')
354
+ r6 = nil
355
+ end
356
+ if r6
357
+ s5 << r6
358
+ else
359
+ break
360
+ end
361
+ end
362
+ r5 = instantiate_node(SyntaxNode,input, i5...index, s5)
363
+ s0 << r5
364
+ if r5
365
+ if (match_len = has_terminal?(")", false, index))
366
+ r7 = true
367
+ @index += match_len
368
+ else
369
+ terminal_parse_failure(")")
370
+ r7 = nil
371
+ end
372
+ s0 << r7
373
+ end
374
+ end
375
+ end
376
+ end
377
+ if s0.last
378
+ r0 = instantiate_node(GroupNode,input, i0...index, s0)
379
+ r0.extend(Group0)
380
+ else
381
+ @index = i0
382
+ r0 = nil
383
+ end
384
+
385
+ node_cache[:group][start_index] = r0
386
+
387
+ r0
388
+ end
389
+
390
+ def _nt_nonmodifiable
391
+ start_index = index
392
+ if node_cache[:nonmodifiable].has_key?(index)
393
+ cached = node_cache[:nonmodifiable][index]
394
+ if cached
395
+ node_cache[:nonmodifiable][index] = cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
396
+ @index = cached.interval.end
397
+ end
398
+ return cached
399
+ end
400
+
401
+ i0 = index
402
+ r1 = _nt_gradual
403
+ if r1
404
+ r1 = SyntaxNode.new(input, (index-1)...index) if r1 == true
405
+ r0 = r1
406
+ else
407
+ r2 = _nt_dynamic
408
+ if r2
409
+ r2 = SyntaxNode.new(input, (index-1)...index) if r2 == true
410
+ r0 = r2
411
+ else
412
+ @index = i0
413
+ r0 = nil
414
+ end
415
+ end
416
+
417
+ node_cache[:nonmodifiable][start_index] = r0
418
+
419
+ r0
420
+ end
421
+
422
+ end
423
+
424
+ class ExpressionParser < Treetop::Runtime::CompiledParser
425
+ include Expression
426
+ end
427
+
428
+
429
+ end
@@ -0,0 +1,39 @@
1
+ module Brevity
2
+
3
+ grammar Expression
4
+ include Gradual
5
+ include Dynamic
6
+ include Note
7
+ include Label
8
+ include Modifier
9
+
10
+ rule expression
11
+ [\s]*
12
+ expr
13
+ more:([\s]+ expr)*
14
+ [\s]*
15
+ <ExpressionNode>
16
+ end
17
+
18
+ rule expr_element
19
+ gradual / dynamic / note / label <ExprElementNode>
20
+ end
21
+
22
+ rule expr
23
+ nonmodifiable / modifiable
24
+ end
25
+
26
+ rule modifiable
27
+ base:(group / label / note) mods:modifier* <ModifiableNode>
28
+ end
29
+
30
+ rule group
31
+ "(" [\s]* expression [\s]* ")" <GroupNode>
32
+ end
33
+
34
+ rule nonmodifiable
35
+ gradual / dynamic
36
+ end
37
+ end
38
+
39
+ end
@@ -0,0 +1,26 @@
1
+ module Brevity
2
+ class ExpressionNode < Treetop::Runtime::SyntaxNode
3
+ def primitives env
4
+ exprs = [expr] + more.elements.map {|el| el.expr}
5
+ return exprs.map {|e| e.primitives(env) }.flatten
6
+ end
7
+ end
8
+
9
+ class GroupNode < Treetop::Runtime::SyntaxNode
10
+ def primitives env
11
+ expression.primitives(env)
12
+ end
13
+ end
14
+
15
+ class ModifiableNode < Treetop::Runtime::SyntaxNode
16
+ def primitives env
17
+ primitives = base.primitives(env)
18
+
19
+ mods.elements.each do |modnode|
20
+ primitives = modnode.process primitives
21
+ end
22
+
23
+ return primitives
24
+ end
25
+ end
26
+ end
@@ -0,0 +1,44 @@
1
+ # Autogenerated from a Treetop grammar. Edits may be lost.
2
+
3
+
4
+ module Brevity
5
+
6
+ module Gradual
7
+ include Treetop::Runtime
8
+
9
+ def root
10
+ @root ||= :gradual
11
+ end
12
+
13
+ def _nt_gradual
14
+ start_index = index
15
+ if node_cache[:gradual].has_key?(index)
16
+ cached = node_cache[:gradual][index]
17
+ if cached
18
+ node_cache[:gradual][index] = cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
19
+ @index = cached.interval.end
20
+ end
21
+ return cached
22
+ end
23
+
24
+ if has_terminal?(@regexps[gr = '\A[<>]'] ||= Regexp.new(gr), :regexp, index)
25
+ r0 = instantiate_node(GradualNode,input, index...(index + 1))
26
+ @index += 1
27
+ else
28
+ terminal_parse_failure('[<>]')
29
+ r0 = nil
30
+ end
31
+
32
+ node_cache[:gradual][start_index] = r0
33
+
34
+ r0
35
+ end
36
+
37
+ end
38
+
39
+ class GradualParser < Treetop::Runtime::CompiledParser
40
+ include Gradual
41
+ end
42
+
43
+
44
+ end
@@ -0,0 +1,9 @@
1
+ module Brevity
2
+
3
+ grammar Gradual
4
+ rule gradual
5
+ [<>] <GradualNode>
6
+ end
7
+ end
8
+
9
+ end
@@ -0,0 +1,11 @@
1
+ module Brevity
2
+ class GradualNode < Treetop::Runtime::SyntaxNode
3
+ def primitives env
4
+ [ self ]
5
+ end
6
+
7
+ def ==(other)
8
+ other.is_a?(GradualNode)
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,75 @@
1
+ # Autogenerated from a Treetop grammar. Edits may be lost.
2
+
3
+
4
+ module Brevity
5
+
6
+ module Label
7
+ include Treetop::Runtime
8
+
9
+ def root
10
+ @root ||= :label
11
+ end
12
+
13
+ module Label0
14
+ end
15
+
16
+ def _nt_label
17
+ start_index = index
18
+ if node_cache[:label].has_key?(index)
19
+ cached = node_cache[:label][index]
20
+ if cached
21
+ node_cache[:label][index] = cached = SyntaxNode.new(input, index...(index + 1)) if cached == true
22
+ @index = cached.interval.end
23
+ end
24
+ return cached
25
+ end
26
+
27
+ i0, s0 = index, []
28
+ if has_terminal?(@regexps[gr = '\A[_A-Za-z]'] ||= Regexp.new(gr), :regexp, index)
29
+ r1 = true
30
+ @index += 1
31
+ else
32
+ terminal_parse_failure('[_A-Za-z]')
33
+ r1 = nil
34
+ end
35
+ s0 << r1
36
+ if r1
37
+ s2, i2 = [], index
38
+ loop do
39
+ if has_terminal?(@regexps[gr = '\A[_A-Za-z0-9]'] ||= Regexp.new(gr), :regexp, index)
40
+ r3 = true
41
+ @index += 1
42
+ else
43
+ terminal_parse_failure('[_A-Za-z0-9]')
44
+ r3 = nil
45
+ end
46
+ if r3
47
+ s2 << r3
48
+ else
49
+ break
50
+ end
51
+ end
52
+ r2 = instantiate_node(SyntaxNode,input, i2...index, s2)
53
+ s0 << r2
54
+ end
55
+ if s0.last
56
+ r0 = instantiate_node(LabelNode,input, i0...index, s0)
57
+ r0.extend(Label0)
58
+ else
59
+ @index = i0
60
+ r0 = nil
61
+ end
62
+
63
+ node_cache[:label][start_index] = r0
64
+
65
+ r0
66
+ end
67
+
68
+ end
69
+
70
+ class LabelParser < Treetop::Runtime::CompiledParser
71
+ include Label
72
+ end
73
+
74
+
75
+ end
@@ -0,0 +1,9 @@
1
+ module Brevity
2
+
3
+ grammar Label
4
+ rule label
5
+ [_A-Za-z] [_A-Za-z0-9]* <LabelNode>
6
+ end
7
+ end
8
+
9
+ end
@@ -0,0 +1,15 @@
1
+ module Brevity
2
+ class LabelNode < Treetop::Runtime::SyntaxNode
3
+ def to_key
4
+ text_value.to_sym
5
+ end
6
+
7
+ def primitives env
8
+ env.fetch(self.to_key).clone
9
+ end
10
+
11
+ def itemize(env)
12
+ env.fetch(self.to_key).clone
13
+ end
14
+ end
15
+ end