weskit 0.1.0 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
data/.gitignore CHANGED
@@ -1,4 +1,5 @@
1
1
  .bundle
2
+ .rbx
2
3
  .redcar
3
4
  .yardoc
4
5
  *.gem
data/README.md CHANGED
@@ -6,7 +6,7 @@ them is the key to understaning any other stuff bundled. This README gives quick
6
6
  overview of Weskit WML capabilities. For more information you have to check source code and
7
7
  [generated documentation](http://www.rubydoc.info/github/f6p/weskit/frames).
8
8
 
9
- ## WML Containers
9
+ ## Containers
10
10
 
11
11
  Elements in WML document dosn't have one parent. Instead of using arrays to store multiple WML objects
12
12
  create instance of Weskit::WML::Root. It will let you to call advanced features avaiable for other
@@ -78,10 +78,13 @@ you can do this:
78
78
  id is a helper method (as it interfers with Object#id) that is equivalent to:
79
79
 
80
80
  ```ruby
81
- attribute :id, value
81
+ attribute(:id, value)
82
82
  ```
83
83
 
84
- ## Searching for objects
84
+ And oh well... Let's not forget that after all builder block is
85
+ Ruby code so you can use any langague construct inside it as well.
86
+
87
+ ## Tree searching
85
88
 
86
89
  You can search WML elements and containers for nodes of specific type. For
87
90
  example lets say there is a object tree representing such WML structure:
@@ -107,8 +110,8 @@ To get Weskit::WML::Elements container with references to all b elements you can
107
110
  root.a.b
108
111
  ```
109
112
 
110
- This code takes advantage of method_missing and if you can't do that
111
- (because of method name conflicts) equivalent code can be used:
113
+ This code takes advantage of method_missing as well and if you can't use
114
+ it that (because of method name conflicts) its equivalent can be used:
112
115
 
113
116
  ```ruby
114
117
  root.find(:a).find(:b)
@@ -117,19 +120,31 @@ This code takes advantage of method_missing and if you can't do that
117
120
  as missing calls are delegated to find method. There is also find_recursively
118
121
  method that lets you to find elements using object criteria specified in block.
119
122
 
120
- ## Object representation
123
+ ## Representation
121
124
 
122
125
  Weskit::WML objects dosn't have any representation code coupled. Special class of objects called Formatters is
123
126
  used to handle their display. Most commonly you will use plain text representation (default formatter)
124
127
  or terminal friendly colorful version of it (color formatter). Most of WML objects provide formatter
125
128
  seter to replace formatter associated with them but you can as well change default formatter globally
126
- by calling Formatter.default= setter method.
129
+ by calling Formatter.default= method.
127
130
 
128
131
  Whatever representation you need (JSON, XML, YAML) creating new formaters shouldn't
129
132
  be hard. Take look at Weskit::WML::Formatters module for further reference on that matter.
130
133
 
131
- ## WML Parser
134
+ ## Parser
132
135
 
133
- Parser dosn't support preprocessor (at least yet). It provides two methods: string - for parsing strings and uri - for
134
- parsing files. uri method can load remote files as well as it transparently handles archive extraction. Parsing
136
+ Parser provides two methods: string - for parsing strings and uri - for parsing files. uri
137
+ method can load remote files as well as it transparently handles archive extraction. Parsing
135
138
  results in return of WML object tree with one Weskit::WML::Root as the top-most element.
139
+
140
+ ## Limitations
141
+
142
+ Lack of preprocessor support as WML module is supposed to work with preprocessed files
143
+ (at least for now). Preprocessor directives will be consumed as comments and that can
144
+ lead to unexpected behaviour at times. For example if you have macro defined its
145
+ contents will be added to parent element.
146
+
147
+ ## TODO
148
+
149
+ Implement preprocessor directives as first class memebers
150
+ that could be manipulated like any other WML node.
data/Rakefile CHANGED
@@ -2,4 +2,11 @@ require "bundler/gem_tasks"
2
2
  require 'rspec/core/rake_task'
3
3
 
4
4
  RSpec::Core::RakeTask.new 'spec'
5
- task :default => :spec
5
+ task :default => :spec
6
+
7
+ namespace :kpeg do
8
+ desc 'Re-build KPEGParser'
9
+ task :rebuild do
10
+ puts %x(kpeg -fsvo lib/weskit/wml/kpeg_parser.rb lib/weskit/wml/grammars/wml.kpeg)
11
+ end
12
+ end
@@ -1,3 +1,3 @@
1
1
  module Weskit
2
- VERSION = '0.1.0'
2
+ VERSION = '0.2.0'
3
3
  end
data/lib/weskit/wml.rb CHANGED
@@ -14,4 +14,4 @@ w.require_all %w{validator grammar searchable container}, :mixins
14
14
  w.require_all %w{object}, :extensions
15
15
  w.require_all %w{error invalid_identifier invalid_item invalid_option invalid_parameters parse_error read_error}, :errors
16
16
  w.require_all %w{item_formatter attribute element ansi_color ansi_color_attribute ansi_color_element}, :formatters
17
- w.require_all %w{item items attribute attributes builder element elements formatter wml parser root}
17
+ w.require_all %w{item items attribute attributes builder element elements formatter kpeg_parser parser root}
@@ -1,9 +1,5 @@
1
- require 'observer'
2
-
3
1
  module Weskit::WML
4
2
  class Attribute < Item
5
- include Observable
6
-
7
3
  attachable_to :element
8
4
 
9
5
  attr_reader :value
@@ -0,0 +1,91 @@
1
+ # Parser =======================================================================
2
+
3
+ %% header {
4
+ module Weskit::WML
5
+ }
6
+
7
+ %% name = KPEGParser
8
+
9
+ %% {
10
+ attr_accessor :result
11
+
12
+ private
13
+
14
+ def strip_chars string, chars
15
+ string[chars, string.length - chars * 2]
16
+ end
17
+ }
18
+
19
+ %% footer {
20
+ end
21
+ }
22
+
23
+ # Rules ========================================================================
24
+
25
+ id = < /[a-z][a-z_]*/i > { text }
26
+ ids = ids:i1 - ',' - ids:i2 { i1 + i2 }
27
+ | id:i { [i] }
28
+
29
+ item = attribute | attributes | element
30
+ items = items:i1 items:i2 { i1 + i2 }
31
+ | item:i { (i.is_a? Array) ? i : [i] }
32
+
33
+ contents = items?:i { i.to_a }
34
+
35
+ # Attributes -------------------------------------------------------------------
36
+
37
+ single_attr = - id:n - '=' - val:v - eol
38
+ { Attribute.new n, *v }
39
+ multiple_attrs = - ids:n - '=' - vals:v - eol
40
+ { n.reduce(Array.new) do |attrs, name|
41
+ value =v.shift or [nil]
42
+ attrs << Attribute.new(name, *value)
43
+ end }
44
+
45
+ attribute = blk_lines single_attr:a blk_lines { a }
46
+ attributes = blk_lines multiple_attrs:a blk_lines { a }
47
+
48
+ # Attribute values -------------------------------------------------------------
49
+
50
+ code = < /<<.*?>>/m > { [strip_chars(text, 2), {:code => true}] }
51
+ in_brackets = < /\(.*?\)/m > { [strip_chars(text, 1)] }
52
+ in_quotes = < /".*?"/m > { [strip_chars(text, 1)] }
53
+ raw = < /.*/ > { [text.strip] }
54
+
55
+ escaped = in_quotes:s1 escaped:s2 { s1[0] += '"' + s2[0] ; s1 }
56
+ | in_quotes
57
+ i18n = '_' - (in_brackets | in_quotes):s { [s[0], {:translatable => true}] }
58
+
59
+ val = val:v1 - '+' sp_lf val:v2 { v1[0] += v2[0] ; v1 }
60
+ | escaped | i18n | code | in_brackets | in_quotes | raw
61
+ vals = vals:v1 - ',' - vals:v2 { v1 + v2 }
62
+ | val:v { [v] }
63
+
64
+ # Elements ---------------------------------------------------------------------
65
+
66
+ amendment = - amending_tag:n - eol contents:c - closing_tag(n) - eol
67
+ { Element.new(n, :amendment => true).push *c }
68
+ regular = - opening_tag:n - eol contents:c - closing_tag(n) - eol
69
+ { Element.new(n).push *c }
70
+
71
+ element = blk_lines (amendment | regular):e blk_lines { e }
72
+
73
+ # Tags -------------------------------------------------------------------------
74
+
75
+ amending_tag = '[+' id:n ']' { n }
76
+ closing_tag(m) = '[/' id:n ']' &{ n == m }
77
+ opening_tag = '[' id:n ']' { n }
78
+
79
+ # Whitespace -------------------------------------------------------------------
80
+
81
+ eof = !.
82
+ eol = "\r\n" | "\n"
83
+ sp = " " | "\t"
84
+
85
+ - = sp*
86
+ sp_lf = (sp | eol)*
87
+ blk_lines = (- eol)*
88
+
89
+ # Root -------------------------------------------------------------------------
90
+
91
+ root = contents:c { Root.new.push *c }
@@ -0,0 +1,1521 @@
1
+ module Weskit::WML
2
+ class KPEGParser
3
+ # :stopdoc:
4
+
5
+ # This is distinct from setup_parser so that a standalone parser
6
+ # can redefine #initialize and still have access to the proper
7
+ # parser setup code.
8
+ def initialize(str, debug=false)
9
+ setup_parser(str, debug)
10
+ end
11
+
12
+
13
+
14
+ # Prepares for parsing +str+. If you define a custom initialize you must
15
+ # call this method before #parse
16
+ def setup_parser(str, debug=false)
17
+ @string = str
18
+ @pos = 0
19
+ @memoizations = Hash.new { |h,k| h[k] = {} }
20
+ @result = nil
21
+ @failed_rule = nil
22
+ @failing_rule_offset = -1
23
+
24
+ setup_foreign_grammar
25
+ end
26
+
27
+ attr_reader :string
28
+ attr_reader :failing_rule_offset
29
+ attr_accessor :result, :pos
30
+
31
+
32
+ def current_column(target=pos)
33
+ if c = string.rindex("\n", target-1)
34
+ return target - c - 1
35
+ end
36
+
37
+ target + 1
38
+ end
39
+
40
+ def current_line(target=pos)
41
+ cur_offset = 0
42
+ cur_line = 0
43
+
44
+ string.each_line do |line|
45
+ cur_line += 1
46
+ cur_offset += line.size
47
+ return cur_line if cur_offset >= target
48
+ end
49
+
50
+ -1
51
+ end
52
+
53
+ def lines
54
+ lines = []
55
+ string.each_line { |l| lines << l }
56
+ lines
57
+ end
58
+
59
+
60
+
61
+ def get_text(start)
62
+ @string[start..@pos-1]
63
+ end
64
+
65
+ def show_pos
66
+ width = 10
67
+ if @pos < width
68
+ "#{@pos} (\"#{@string[0,@pos]}\" @ \"#{@string[@pos,width]}\")"
69
+ else
70
+ "#{@pos} (\"... #{@string[@pos - width, width]}\" @ \"#{@string[@pos,width]}\")"
71
+ end
72
+ end
73
+
74
+ def failure_info
75
+ l = current_line @failing_rule_offset
76
+ c = current_column @failing_rule_offset
77
+
78
+ if @failed_rule.kind_of? Symbol
79
+ info = self.class::Rules[@failed_rule]
80
+ "line #{l}, column #{c}: failed rule '#{info.name}' = '#{info.rendered}'"
81
+ else
82
+ "line #{l}, column #{c}: failed rule '#{@failed_rule}'"
83
+ end
84
+ end
85
+
86
+ def failure_caret
87
+ l = current_line @failing_rule_offset
88
+ c = current_column @failing_rule_offset
89
+
90
+ line = lines[l-1]
91
+ "#{line}\n#{' ' * (c - 1)}^"
92
+ end
93
+
94
+ def failure_character
95
+ l = current_line @failing_rule_offset
96
+ c = current_column @failing_rule_offset
97
+ lines[l-1][c-1, 1]
98
+ end
99
+
100
+ def failure_oneline
101
+ l = current_line @failing_rule_offset
102
+ c = current_column @failing_rule_offset
103
+
104
+ char = lines[l-1][c-1, 1]
105
+
106
+ if @failed_rule.kind_of? Symbol
107
+ info = self.class::Rules[@failed_rule]
108
+ "@#{l}:#{c} failed rule '#{info.name}', got '#{char}'"
109
+ else
110
+ "@#{l}:#{c} failed rule '#{@failed_rule}', got '#{char}'"
111
+ end
112
+ end
113
+
114
+ class ParseError < RuntimeError
115
+ end
116
+
117
+ def raise_error
118
+ raise ParseError, failure_oneline
119
+ end
120
+
121
+ def show_error(io=STDOUT)
122
+ error_pos = @failing_rule_offset
123
+ line_no = current_line(error_pos)
124
+ col_no = current_column(error_pos)
125
+
126
+ io.puts "On line #{line_no}, column #{col_no}:"
127
+
128
+ if @failed_rule.kind_of? Symbol
129
+ info = self.class::Rules[@failed_rule]
130
+ io.puts "Failed to match '#{info.rendered}' (rule '#{info.name}')"
131
+ else
132
+ io.puts "Failed to match rule '#{@failed_rule}'"
133
+ end
134
+
135
+ io.puts "Got: #{string[error_pos,1].inspect}"
136
+ line = lines[line_no-1]
137
+ io.puts "=> #{line}"
138
+ io.print(" " * (col_no + 3))
139
+ io.puts "^"
140
+ end
141
+
142
+ def set_failed_rule(name)
143
+ if @pos > @failing_rule_offset
144
+ @failed_rule = name
145
+ @failing_rule_offset = @pos
146
+ end
147
+ end
148
+
149
+ attr_reader :failed_rule
150
+
151
+ def match_string(str)
152
+ len = str.size
153
+ if @string[pos,len] == str
154
+ @pos += len
155
+ return str
156
+ end
157
+
158
+ return nil
159
+ end
160
+
161
+ def scan(reg)
162
+ if m = reg.match(@string[@pos..-1])
163
+ width = m.end(0)
164
+ @pos += width
165
+ return true
166
+ end
167
+
168
+ return nil
169
+ end
170
+
171
+ if "".respond_to? :getbyte
172
+ def get_byte
173
+ if @pos >= @string.size
174
+ return nil
175
+ end
176
+
177
+ s = @string.getbyte @pos
178
+ @pos += 1
179
+ s
180
+ end
181
+ else
182
+ def get_byte
183
+ if @pos >= @string.size
184
+ return nil
185
+ end
186
+
187
+ s = @string[@pos]
188
+ @pos += 1
189
+ s
190
+ end
191
+ end
192
+
193
+ def parse(rule=nil)
194
+ # We invoke the rules indirectly via apply
195
+ # instead of by just calling them as methods because
196
+ # if the rules use left recursion, apply needs to
197
+ # manage that.
198
+
199
+ if !rule
200
+ apply(:_root)
201
+ else
202
+ method = rule.gsub("-","_hyphen_")
203
+ apply :"_#{method}"
204
+ end
205
+ end
206
+
207
+ class MemoEntry
208
+ def initialize(ans, pos)
209
+ @ans = ans
210
+ @pos = pos
211
+ @result = nil
212
+ @set = false
213
+ @left_rec = false
214
+ end
215
+
216
+ attr_reader :ans, :pos, :result, :set
217
+ attr_accessor :left_rec
218
+
219
+ def move!(ans, pos, result)
220
+ @ans = ans
221
+ @pos = pos
222
+ @result = result
223
+ @set = true
224
+ @left_rec = false
225
+ end
226
+ end
227
+
228
+ def external_invoke(other, rule, *args)
229
+ old_pos = @pos
230
+ old_string = @string
231
+
232
+ @pos = other.pos
233
+ @string = other.string
234
+
235
+ begin
236
+ if val = __send__(rule, *args)
237
+ other.pos = @pos
238
+ other.result = @result
239
+ else
240
+ other.set_failed_rule "#{self.class}##{rule}"
241
+ end
242
+ val
243
+ ensure
244
+ @pos = old_pos
245
+ @string = old_string
246
+ end
247
+ end
248
+
249
+ def apply_with_args(rule, *args)
250
+ memo_key = [rule, args]
251
+ if m = @memoizations[memo_key][@pos]
252
+ @pos = m.pos
253
+ if !m.set
254
+ m.left_rec = true
255
+ return nil
256
+ end
257
+
258
+ @result = m.result
259
+
260
+ return m.ans
261
+ else
262
+ m = MemoEntry.new(nil, @pos)
263
+ @memoizations[memo_key][@pos] = m
264
+ start_pos = @pos
265
+
266
+ ans = __send__ rule, *args
267
+
268
+ lr = m.left_rec
269
+
270
+ m.move! ans, @pos, @result
271
+
272
+ # Don't bother trying to grow the left recursion
273
+ # if it's failing straight away (thus there is no seed)
274
+ if ans and lr
275
+ return grow_lr(rule, args, start_pos, m)
276
+ else
277
+ return ans
278
+ end
279
+
280
+ return ans
281
+ end
282
+ end
283
+
284
+ def apply(rule)
285
+ if m = @memoizations[rule][@pos]
286
+ @pos = m.pos
287
+ if !m.set
288
+ m.left_rec = true
289
+ return nil
290
+ end
291
+
292
+ @result = m.result
293
+
294
+ return m.ans
295
+ else
296
+ m = MemoEntry.new(nil, @pos)
297
+ @memoizations[rule][@pos] = m
298
+ start_pos = @pos
299
+
300
+ ans = __send__ rule
301
+
302
+ lr = m.left_rec
303
+
304
+ m.move! ans, @pos, @result
305
+
306
+ # Don't bother trying to grow the left recursion
307
+ # if it's failing straight away (thus there is no seed)
308
+ if ans and lr
309
+ return grow_lr(rule, nil, start_pos, m)
310
+ else
311
+ return ans
312
+ end
313
+
314
+ return ans
315
+ end
316
+ end
317
+
318
+ def grow_lr(rule, args, start_pos, m)
319
+ while true
320
+ @pos = start_pos
321
+ @result = m.result
322
+
323
+ if args
324
+ ans = __send__ rule, *args
325
+ else
326
+ ans = __send__ rule
327
+ end
328
+ return nil unless ans
329
+
330
+ break if @pos <= m.pos
331
+
332
+ m.move! ans, @pos, @result
333
+ end
334
+
335
+ @result = m.result
336
+ @pos = m.pos
337
+ return m.ans
338
+ end
339
+
340
+ class RuleInfo
341
+ def initialize(name, rendered)
342
+ @name = name
343
+ @rendered = rendered
344
+ end
345
+
346
+ attr_reader :name, :rendered
347
+ end
348
+
349
+ def self.rule_info(name, rendered)
350
+ RuleInfo.new(name, rendered)
351
+ end
352
+
353
+
354
+ # :startdoc:
355
+
356
+
357
+ attr_accessor :result
358
+
359
+ private
360
+
361
+ def strip_chars string, chars
362
+ string[chars, string.length - chars * 2]
363
+ end
364
+
365
+
366
+ # :stopdoc:
367
+ def setup_foreign_grammar; end
368
+
369
+ # id = < /[a-z][a-z_]*/i > { text }
370
+ def _id
371
+
372
+ _save = self.pos
373
+ while true # sequence
374
+ _text_start = self.pos
375
+ _tmp = scan(/\A(?i-mx:[a-z][a-z_]*)/)
376
+ if _tmp
377
+ text = get_text(_text_start)
378
+ end
379
+ unless _tmp
380
+ self.pos = _save
381
+ break
382
+ end
383
+ @result = begin; text ; end
384
+ _tmp = true
385
+ unless _tmp
386
+ self.pos = _save
387
+ end
388
+ break
389
+ end # end sequence
390
+
391
+ set_failed_rule :_id unless _tmp
392
+ return _tmp
393
+ end
394
+
395
+ # ids = (ids:i1 - "," - ids:i2 { i1 + i2 } | id:i { [i] })
396
+ def _ids
397
+
398
+ _save = self.pos
399
+ while true # choice
400
+
401
+ _save1 = self.pos
402
+ while true # sequence
403
+ _tmp = apply(:_ids)
404
+ i1 = @result
405
+ unless _tmp
406
+ self.pos = _save1
407
+ break
408
+ end
409
+ _tmp = apply(:__hyphen_)
410
+ unless _tmp
411
+ self.pos = _save1
412
+ break
413
+ end
414
+ _tmp = match_string(",")
415
+ unless _tmp
416
+ self.pos = _save1
417
+ break
418
+ end
419
+ _tmp = apply(:__hyphen_)
420
+ unless _tmp
421
+ self.pos = _save1
422
+ break
423
+ end
424
+ _tmp = apply(:_ids)
425
+ i2 = @result
426
+ unless _tmp
427
+ self.pos = _save1
428
+ break
429
+ end
430
+ @result = begin; i1 + i2 ; end
431
+ _tmp = true
432
+ unless _tmp
433
+ self.pos = _save1
434
+ end
435
+ break
436
+ end # end sequence
437
+
438
+ break if _tmp
439
+ self.pos = _save
440
+
441
+ _save2 = self.pos
442
+ while true # sequence
443
+ _tmp = apply(:_id)
444
+ i = @result
445
+ unless _tmp
446
+ self.pos = _save2
447
+ break
448
+ end
449
+ @result = begin; [i] ; end
450
+ _tmp = true
451
+ unless _tmp
452
+ self.pos = _save2
453
+ end
454
+ break
455
+ end # end sequence
456
+
457
+ break if _tmp
458
+ self.pos = _save
459
+ break
460
+ end # end choice
461
+
462
+ set_failed_rule :_ids unless _tmp
463
+ return _tmp
464
+ end
465
+
466
+ # item = (attribute | attributes | element)
467
+ def _item
468
+
469
+ _save = self.pos
470
+ while true # choice
471
+ _tmp = apply(:_attribute)
472
+ break if _tmp
473
+ self.pos = _save
474
+ _tmp = apply(:_attributes)
475
+ break if _tmp
476
+ self.pos = _save
477
+ _tmp = apply(:_element)
478
+ break if _tmp
479
+ self.pos = _save
480
+ break
481
+ end # end choice
482
+
483
+ set_failed_rule :_item unless _tmp
484
+ return _tmp
485
+ end
486
+
487
+ # items = (items:i1 items:i2 { i1 + i2 } | item:i { (i.is_a? Array) ? i : [i] })
488
+ def _items
489
+
490
+ _save = self.pos
491
+ while true # choice
492
+
493
+ _save1 = self.pos
494
+ while true # sequence
495
+ _tmp = apply(:_items)
496
+ i1 = @result
497
+ unless _tmp
498
+ self.pos = _save1
499
+ break
500
+ end
501
+ _tmp = apply(:_items)
502
+ i2 = @result
503
+ unless _tmp
504
+ self.pos = _save1
505
+ break
506
+ end
507
+ @result = begin; i1 + i2 ; end
508
+ _tmp = true
509
+ unless _tmp
510
+ self.pos = _save1
511
+ end
512
+ break
513
+ end # end sequence
514
+
515
+ break if _tmp
516
+ self.pos = _save
517
+
518
+ _save2 = self.pos
519
+ while true # sequence
520
+ _tmp = apply(:_item)
521
+ i = @result
522
+ unless _tmp
523
+ self.pos = _save2
524
+ break
525
+ end
526
+ @result = begin; (i.is_a? Array) ? i : [i] ; end
527
+ _tmp = true
528
+ unless _tmp
529
+ self.pos = _save2
530
+ end
531
+ break
532
+ end # end sequence
533
+
534
+ break if _tmp
535
+ self.pos = _save
536
+ break
537
+ end # end choice
538
+
539
+ set_failed_rule :_items unless _tmp
540
+ return _tmp
541
+ end
542
+
543
+ # contents = items?:i { i.to_a }
544
+ def _contents
545
+
546
+ _save = self.pos
547
+ while true # sequence
548
+ _save1 = self.pos
549
+ _tmp = apply(:_items)
550
+ @result = nil unless _tmp
551
+ unless _tmp
552
+ _tmp = true
553
+ self.pos = _save1
554
+ end
555
+ i = @result
556
+ unless _tmp
557
+ self.pos = _save
558
+ break
559
+ end
560
+ @result = begin; i.to_a ; end
561
+ _tmp = true
562
+ unless _tmp
563
+ self.pos = _save
564
+ end
565
+ break
566
+ end # end sequence
567
+
568
+ set_failed_rule :_contents unless _tmp
569
+ return _tmp
570
+ end
571
+
572
+ # attr = - id:n - "=" - val:v - eol { Attribute.new n, *v }
573
+ def _attr
574
+
575
+ _save = self.pos
576
+ while true # sequence
577
+ _tmp = apply(:__hyphen_)
578
+ unless _tmp
579
+ self.pos = _save
580
+ break
581
+ end
582
+ _tmp = apply(:_id)
583
+ n = @result
584
+ unless _tmp
585
+ self.pos = _save
586
+ break
587
+ end
588
+ _tmp = apply(:__hyphen_)
589
+ unless _tmp
590
+ self.pos = _save
591
+ break
592
+ end
593
+ _tmp = match_string("=")
594
+ unless _tmp
595
+ self.pos = _save
596
+ break
597
+ end
598
+ _tmp = apply(:__hyphen_)
599
+ unless _tmp
600
+ self.pos = _save
601
+ break
602
+ end
603
+ _tmp = apply(:_val)
604
+ v = @result
605
+ unless _tmp
606
+ self.pos = _save
607
+ break
608
+ end
609
+ _tmp = apply(:__hyphen_)
610
+ unless _tmp
611
+ self.pos = _save
612
+ break
613
+ end
614
+ _tmp = apply(:_eol)
615
+ unless _tmp
616
+ self.pos = _save
617
+ break
618
+ end
619
+ @result = begin; Attribute.new n, *v ; end
620
+ _tmp = true
621
+ unless _tmp
622
+ self.pos = _save
623
+ end
624
+ break
625
+ end # end sequence
626
+
627
+ set_failed_rule :_attr unless _tmp
628
+ return _tmp
629
+ end
630
+
631
+ # multiple_attrs = - ids:n - "=" - vals:v - eol { n.reduce(Array.new) do |attrs, name| value = v.shift or [nil] attrs << Attribute.new(name, *value) end }
632
+ def _multiple_attrs
633
+
634
+ _save = self.pos
635
+ while true # sequence
636
+ _tmp = apply(:__hyphen_)
637
+ unless _tmp
638
+ self.pos = _save
639
+ break
640
+ end
641
+ _tmp = apply(:_ids)
642
+ n = @result
643
+ unless _tmp
644
+ self.pos = _save
645
+ break
646
+ end
647
+ _tmp = apply(:__hyphen_)
648
+ unless _tmp
649
+ self.pos = _save
650
+ break
651
+ end
652
+ _tmp = match_string("=")
653
+ unless _tmp
654
+ self.pos = _save
655
+ break
656
+ end
657
+ _tmp = apply(:__hyphen_)
658
+ unless _tmp
659
+ self.pos = _save
660
+ break
661
+ end
662
+ _tmp = apply(:_vals)
663
+ v = @result
664
+ unless _tmp
665
+ self.pos = _save
666
+ break
667
+ end
668
+ _tmp = apply(:__hyphen_)
669
+ unless _tmp
670
+ self.pos = _save
671
+ break
672
+ end
673
+ _tmp = apply(:_eol)
674
+ unless _tmp
675
+ self.pos = _save
676
+ break
677
+ end
678
+ @result = begin; n.reduce(Array.new) do |attrs, name|
679
+ value = v.shift or [nil]
680
+ attrs << Attribute.new(name, *value)
681
+ end ; end
682
+ _tmp = true
683
+ unless _tmp
684
+ self.pos = _save
685
+ end
686
+ break
687
+ end # end sequence
688
+
689
+ set_failed_rule :_multiple_attrs unless _tmp
690
+ return _tmp
691
+ end
692
+
693
+ # attribute = blk_lines attr:a blk_lines { a }
694
+ def _attribute
695
+
696
+ _save = self.pos
697
+ while true # sequence
698
+ _tmp = apply(:_blk_lines)
699
+ unless _tmp
700
+ self.pos = _save
701
+ break
702
+ end
703
+ _tmp = apply(:_attr)
704
+ a = @result
705
+ unless _tmp
706
+ self.pos = _save
707
+ break
708
+ end
709
+ _tmp = apply(:_blk_lines)
710
+ unless _tmp
711
+ self.pos = _save
712
+ break
713
+ end
714
+ @result = begin; a ; end
715
+ _tmp = true
716
+ unless _tmp
717
+ self.pos = _save
718
+ end
719
+ break
720
+ end # end sequence
721
+
722
+ set_failed_rule :_attribute unless _tmp
723
+ return _tmp
724
+ end
725
+
726
+ # attributes = blk_lines multiple_attrs:a blk_lines { a }
727
+ def _attributes
728
+
729
+ _save = self.pos
730
+ while true # sequence
731
+ _tmp = apply(:_blk_lines)
732
+ unless _tmp
733
+ self.pos = _save
734
+ break
735
+ end
736
+ _tmp = apply(:_multiple_attrs)
737
+ a = @result
738
+ unless _tmp
739
+ self.pos = _save
740
+ break
741
+ end
742
+ _tmp = apply(:_blk_lines)
743
+ unless _tmp
744
+ self.pos = _save
745
+ break
746
+ end
747
+ @result = begin; a ; end
748
+ _tmp = true
749
+ unless _tmp
750
+ self.pos = _save
751
+ end
752
+ break
753
+ end # end sequence
754
+
755
+ set_failed_rule :_attributes unless _tmp
756
+ return _tmp
757
+ end
758
+
759
+ # code = < /<<.*?>>/m > { [strip_chars(text, 2), {:code => true}] }
760
+ def _code
761
+
762
+ _save = self.pos
763
+ while true # sequence
764
+ _text_start = self.pos
765
+ _tmp = scan(/\A(?m-ix:<<.*?>>)/)
766
+ if _tmp
767
+ text = get_text(_text_start)
768
+ end
769
+ unless _tmp
770
+ self.pos = _save
771
+ break
772
+ end
773
+ @result = begin; [strip_chars(text, 2), {:code => true}] ; end
774
+ _tmp = true
775
+ unless _tmp
776
+ self.pos = _save
777
+ end
778
+ break
779
+ end # end sequence
780
+
781
+ set_failed_rule :_code unless _tmp
782
+ return _tmp
783
+ end
784
+
785
+ # in_brackets = < /\(.*?\)/m > { [strip_chars(text, 1)] }
786
+ def _in_brackets
787
+
788
+ _save = self.pos
789
+ while true # sequence
790
+ _text_start = self.pos
791
+ _tmp = scan(/\A(?m-ix:\(.*?\))/)
792
+ if _tmp
793
+ text = get_text(_text_start)
794
+ end
795
+ unless _tmp
796
+ self.pos = _save
797
+ break
798
+ end
799
+ @result = begin; [strip_chars(text, 1)] ; end
800
+ _tmp = true
801
+ unless _tmp
802
+ self.pos = _save
803
+ end
804
+ break
805
+ end # end sequence
806
+
807
+ set_failed_rule :_in_brackets unless _tmp
808
+ return _tmp
809
+ end
810
+
811
+ # in_quotes = < /".*?"/m > { [strip_chars(text, 1)] }
812
+ def _in_quotes
813
+
814
+ _save = self.pos
815
+ while true # sequence
816
+ _text_start = self.pos
817
+ _tmp = scan(/\A(?m-ix:".*?")/)
818
+ if _tmp
819
+ text = get_text(_text_start)
820
+ end
821
+ unless _tmp
822
+ self.pos = _save
823
+ break
824
+ end
825
+ @result = begin; [strip_chars(text, 1)] ; end
826
+ _tmp = true
827
+ unless _tmp
828
+ self.pos = _save
829
+ end
830
+ break
831
+ end # end sequence
832
+
833
+ set_failed_rule :_in_quotes unless _tmp
834
+ return _tmp
835
+ end
836
+
837
+ # raw = < /.*/ > { [text.strip] }
838
+ def _raw
839
+
840
+ _save = self.pos
841
+ while true # sequence
842
+ _text_start = self.pos
843
+ _tmp = scan(/\A(?-mix:.*)/)
844
+ if _tmp
845
+ text = get_text(_text_start)
846
+ end
847
+ unless _tmp
848
+ self.pos = _save
849
+ break
850
+ end
851
+ @result = begin; [text.strip] ; end
852
+ _tmp = true
853
+ unless _tmp
854
+ self.pos = _save
855
+ end
856
+ break
857
+ end # end sequence
858
+
859
+ set_failed_rule :_raw unless _tmp
860
+ return _tmp
861
+ end
862
+
863
+ # escaped = (in_quotes:s1 escaped:s2 { s1[0] += '"' + s2[0] ; s1 } | in_quotes)
864
+ def _escaped
865
+
866
+ _save = self.pos
867
+ while true # choice
868
+
869
+ _save1 = self.pos
870
+ while true # sequence
871
+ _tmp = apply(:_in_quotes)
872
+ s1 = @result
873
+ unless _tmp
874
+ self.pos = _save1
875
+ break
876
+ end
877
+ _tmp = apply(:_escaped)
878
+ s2 = @result
879
+ unless _tmp
880
+ self.pos = _save1
881
+ break
882
+ end
883
+ @result = begin; s1[0] += '"' + s2[0] ; s1 ; end
884
+ _tmp = true
885
+ unless _tmp
886
+ self.pos = _save1
887
+ end
888
+ break
889
+ end # end sequence
890
+
891
+ break if _tmp
892
+ self.pos = _save
893
+ _tmp = apply(:_in_quotes)
894
+ break if _tmp
895
+ self.pos = _save
896
+ break
897
+ end # end choice
898
+
899
+ set_failed_rule :_escaped unless _tmp
900
+ return _tmp
901
+ end
902
+
903
+ # i18n = "_" - (in_brackets | in_quotes):s { [s[0], {:translatable => true}] }
904
+ def _i18n
905
+
906
+ _save = self.pos
907
+ while true # sequence
908
+ _tmp = match_string("_")
909
+ unless _tmp
910
+ self.pos = _save
911
+ break
912
+ end
913
+ _tmp = apply(:__hyphen_)
914
+ unless _tmp
915
+ self.pos = _save
916
+ break
917
+ end
918
+
919
+ _save1 = self.pos
920
+ while true # choice
921
+ _tmp = apply(:_in_brackets)
922
+ break if _tmp
923
+ self.pos = _save1
924
+ _tmp = apply(:_in_quotes)
925
+ break if _tmp
926
+ self.pos = _save1
927
+ break
928
+ end # end choice
929
+
930
+ s = @result
931
+ unless _tmp
932
+ self.pos = _save
933
+ break
934
+ end
935
+ @result = begin; [s[0], {:translatable => true}] ; end
936
+ _tmp = true
937
+ unless _tmp
938
+ self.pos = _save
939
+ end
940
+ break
941
+ end # end sequence
942
+
943
+ set_failed_rule :_i18n unless _tmp
944
+ return _tmp
945
+ end
946
+
947
+ # val = (val:v1 - "+" sp_lf val:v2 { v1[0] += v2[0] ; v1 } | escaped | i18n | code | in_brackets | in_quotes | raw)
948
+ def _val
949
+
950
+ _save = self.pos
951
+ while true # choice
952
+
953
+ _save1 = self.pos
954
+ while true # sequence
955
+ _tmp = apply(:_val)
956
+ v1 = @result
957
+ unless _tmp
958
+ self.pos = _save1
959
+ break
960
+ end
961
+ _tmp = apply(:__hyphen_)
962
+ unless _tmp
963
+ self.pos = _save1
964
+ break
965
+ end
966
+ _tmp = match_string("+")
967
+ unless _tmp
968
+ self.pos = _save1
969
+ break
970
+ end
971
+ _tmp = apply(:_sp_lf)
972
+ unless _tmp
973
+ self.pos = _save1
974
+ break
975
+ end
976
+ _tmp = apply(:_val)
977
+ v2 = @result
978
+ unless _tmp
979
+ self.pos = _save1
980
+ break
981
+ end
982
+ @result = begin; v1[0] += v2[0] ; v1 ; end
983
+ _tmp = true
984
+ unless _tmp
985
+ self.pos = _save1
986
+ end
987
+ break
988
+ end # end sequence
989
+
990
+ break if _tmp
991
+ self.pos = _save
992
+ _tmp = apply(:_escaped)
993
+ break if _tmp
994
+ self.pos = _save
995
+ _tmp = apply(:_i18n)
996
+ break if _tmp
997
+ self.pos = _save
998
+ _tmp = apply(:_code)
999
+ break if _tmp
1000
+ self.pos = _save
1001
+ _tmp = apply(:_in_brackets)
1002
+ break if _tmp
1003
+ self.pos = _save
1004
+ _tmp = apply(:_in_quotes)
1005
+ break if _tmp
1006
+ self.pos = _save
1007
+ _tmp = apply(:_raw)
1008
+ break if _tmp
1009
+ self.pos = _save
1010
+ break
1011
+ end # end choice
1012
+
1013
+ set_failed_rule :_val unless _tmp
1014
+ return _tmp
1015
+ end
1016
+
1017
+ # vals = (vals:v1 - "," - vals:v2 { v1 + v2 } | val:v { [v] })
1018
+ def _vals
1019
+
1020
+ _save = self.pos
1021
+ while true # choice
1022
+
1023
+ _save1 = self.pos
1024
+ while true # sequence
1025
+ _tmp = apply(:_vals)
1026
+ v1 = @result
1027
+ unless _tmp
1028
+ self.pos = _save1
1029
+ break
1030
+ end
1031
+ _tmp = apply(:__hyphen_)
1032
+ unless _tmp
1033
+ self.pos = _save1
1034
+ break
1035
+ end
1036
+ _tmp = match_string(",")
1037
+ unless _tmp
1038
+ self.pos = _save1
1039
+ break
1040
+ end
1041
+ _tmp = apply(:__hyphen_)
1042
+ unless _tmp
1043
+ self.pos = _save1
1044
+ break
1045
+ end
1046
+ _tmp = apply(:_vals)
1047
+ v2 = @result
1048
+ unless _tmp
1049
+ self.pos = _save1
1050
+ break
1051
+ end
1052
+ @result = begin; v1 + v2 ; end
1053
+ _tmp = true
1054
+ unless _tmp
1055
+ self.pos = _save1
1056
+ end
1057
+ break
1058
+ end # end sequence
1059
+
1060
+ break if _tmp
1061
+ self.pos = _save
1062
+
1063
+ _save2 = self.pos
1064
+ while true # sequence
1065
+ _tmp = apply(:_val)
1066
+ v = @result
1067
+ unless _tmp
1068
+ self.pos = _save2
1069
+ break
1070
+ end
1071
+ @result = begin; [v] ; end
1072
+ _tmp = true
1073
+ unless _tmp
1074
+ self.pos = _save2
1075
+ end
1076
+ break
1077
+ end # end sequence
1078
+
1079
+ break if _tmp
1080
+ self.pos = _save
1081
+ break
1082
+ end # end choice
1083
+
1084
+ set_failed_rule :_vals unless _tmp
1085
+ return _tmp
1086
+ end
1087
+
1088
+ # amendment = - amending_tag:n - eol contents:c - closing_tag(n) - eol { Element.new(n, :amendment => true).push *c }
1089
+ def _amendment
1090
+
1091
+ _save = self.pos
1092
+ while true # sequence
1093
+ _tmp = apply(:__hyphen_)
1094
+ unless _tmp
1095
+ self.pos = _save
1096
+ break
1097
+ end
1098
+ _tmp = apply(:_amending_tag)
1099
+ n = @result
1100
+ unless _tmp
1101
+ self.pos = _save
1102
+ break
1103
+ end
1104
+ _tmp = apply(:__hyphen_)
1105
+ unless _tmp
1106
+ self.pos = _save
1107
+ break
1108
+ end
1109
+ _tmp = apply(:_eol)
1110
+ unless _tmp
1111
+ self.pos = _save
1112
+ break
1113
+ end
1114
+ _tmp = apply(:_contents)
1115
+ c = @result
1116
+ unless _tmp
1117
+ self.pos = _save
1118
+ break
1119
+ end
1120
+ _tmp = apply(:__hyphen_)
1121
+ unless _tmp
1122
+ self.pos = _save
1123
+ break
1124
+ end
1125
+ _tmp = apply_with_args(:_closing_tag, n)
1126
+ unless _tmp
1127
+ self.pos = _save
1128
+ break
1129
+ end
1130
+ _tmp = apply(:__hyphen_)
1131
+ unless _tmp
1132
+ self.pos = _save
1133
+ break
1134
+ end
1135
+ _tmp = apply(:_eol)
1136
+ unless _tmp
1137
+ self.pos = _save
1138
+ break
1139
+ end
1140
+ @result = begin; Element.new(n, :amendment => true).push *c ; end
1141
+ _tmp = true
1142
+ unless _tmp
1143
+ self.pos = _save
1144
+ end
1145
+ break
1146
+ end # end sequence
1147
+
1148
+ set_failed_rule :_amendment unless _tmp
1149
+ return _tmp
1150
+ end
1151
+
1152
+ # regular = - opening_tag:n - eol contents:c - closing_tag(n) - eol { Element.new(n).push *c }
1153
+ def _regular
1154
+
1155
+ _save = self.pos
1156
+ while true # sequence
1157
+ _tmp = apply(:__hyphen_)
1158
+ unless _tmp
1159
+ self.pos = _save
1160
+ break
1161
+ end
1162
+ _tmp = apply(:_opening_tag)
1163
+ n = @result
1164
+ unless _tmp
1165
+ self.pos = _save
1166
+ break
1167
+ end
1168
+ _tmp = apply(:__hyphen_)
1169
+ unless _tmp
1170
+ self.pos = _save
1171
+ break
1172
+ end
1173
+ _tmp = apply(:_eol)
1174
+ unless _tmp
1175
+ self.pos = _save
1176
+ break
1177
+ end
1178
+ _tmp = apply(:_contents)
1179
+ c = @result
1180
+ unless _tmp
1181
+ self.pos = _save
1182
+ break
1183
+ end
1184
+ _tmp = apply(:__hyphen_)
1185
+ unless _tmp
1186
+ self.pos = _save
1187
+ break
1188
+ end
1189
+ _tmp = apply_with_args(:_closing_tag, n)
1190
+ unless _tmp
1191
+ self.pos = _save
1192
+ break
1193
+ end
1194
+ _tmp = apply(:__hyphen_)
1195
+ unless _tmp
1196
+ self.pos = _save
1197
+ break
1198
+ end
1199
+ _tmp = apply(:_eol)
1200
+ unless _tmp
1201
+ self.pos = _save
1202
+ break
1203
+ end
1204
+ @result = begin; Element.new(n).push *c ; end
1205
+ _tmp = true
1206
+ unless _tmp
1207
+ self.pos = _save
1208
+ end
1209
+ break
1210
+ end # end sequence
1211
+
1212
+ set_failed_rule :_regular unless _tmp
1213
+ return _tmp
1214
+ end
1215
+
1216
+ # element = blk_lines (amendment | regular):e blk_lines { e }
1217
+ def _element
1218
+
1219
+ _save = self.pos
1220
+ while true # sequence
1221
+ _tmp = apply(:_blk_lines)
1222
+ unless _tmp
1223
+ self.pos = _save
1224
+ break
1225
+ end
1226
+
1227
+ _save1 = self.pos
1228
+ while true # choice
1229
+ _tmp = apply(:_amendment)
1230
+ break if _tmp
1231
+ self.pos = _save1
1232
+ _tmp = apply(:_regular)
1233
+ break if _tmp
1234
+ self.pos = _save1
1235
+ break
1236
+ end # end choice
1237
+
1238
+ e = @result
1239
+ unless _tmp
1240
+ self.pos = _save
1241
+ break
1242
+ end
1243
+ _tmp = apply(:_blk_lines)
1244
+ unless _tmp
1245
+ self.pos = _save
1246
+ break
1247
+ end
1248
+ @result = begin; e ; end
1249
+ _tmp = true
1250
+ unless _tmp
1251
+ self.pos = _save
1252
+ end
1253
+ break
1254
+ end # end sequence
1255
+
1256
+ set_failed_rule :_element unless _tmp
1257
+ return _tmp
1258
+ end
1259
+
1260
+ # amending_tag = "[+" id:n "]" { n }
1261
+ def _amending_tag
1262
+
1263
+ _save = self.pos
1264
+ while true # sequence
1265
+ _tmp = match_string("[+")
1266
+ unless _tmp
1267
+ self.pos = _save
1268
+ break
1269
+ end
1270
+ _tmp = apply(:_id)
1271
+ n = @result
1272
+ unless _tmp
1273
+ self.pos = _save
1274
+ break
1275
+ end
1276
+ _tmp = match_string("]")
1277
+ unless _tmp
1278
+ self.pos = _save
1279
+ break
1280
+ end
1281
+ @result = begin; n ; end
1282
+ _tmp = true
1283
+ unless _tmp
1284
+ self.pos = _save
1285
+ end
1286
+ break
1287
+ end # end sequence
1288
+
1289
+ set_failed_rule :_amending_tag unless _tmp
1290
+ return _tmp
1291
+ end
1292
+
1293
+ # closing_tag = "[/" id:n "]" &{ n == m }
1294
+ def _closing_tag(m)
1295
+
1296
+ _save = self.pos
1297
+ while true # sequence
1298
+ _tmp = match_string("[/")
1299
+ unless _tmp
1300
+ self.pos = _save
1301
+ break
1302
+ end
1303
+ _tmp = apply(:_id)
1304
+ n = @result
1305
+ unless _tmp
1306
+ self.pos = _save
1307
+ break
1308
+ end
1309
+ _tmp = match_string("]")
1310
+ unless _tmp
1311
+ self.pos = _save
1312
+ break
1313
+ end
1314
+ _save1 = self.pos
1315
+ _tmp = begin; n == m ; end
1316
+ self.pos = _save1
1317
+ unless _tmp
1318
+ self.pos = _save
1319
+ end
1320
+ break
1321
+ end # end sequence
1322
+
1323
+ set_failed_rule :_closing_tag unless _tmp
1324
+ return _tmp
1325
+ end
1326
+
1327
+ # opening_tag = "[" id:n "]" { n }
1328
+ def _opening_tag
1329
+
1330
+ _save = self.pos
1331
+ while true # sequence
1332
+ _tmp = match_string("[")
1333
+ unless _tmp
1334
+ self.pos = _save
1335
+ break
1336
+ end
1337
+ _tmp = apply(:_id)
1338
+ n = @result
1339
+ unless _tmp
1340
+ self.pos = _save
1341
+ break
1342
+ end
1343
+ _tmp = match_string("]")
1344
+ unless _tmp
1345
+ self.pos = _save
1346
+ break
1347
+ end
1348
+ @result = begin; n ; end
1349
+ _tmp = true
1350
+ unless _tmp
1351
+ self.pos = _save
1352
+ end
1353
+ break
1354
+ end # end sequence
1355
+
1356
+ set_failed_rule :_opening_tag unless _tmp
1357
+ return _tmp
1358
+ end
1359
+
1360
+ # eof = !.
1361
+ def _eof
1362
+ _save = self.pos
1363
+ _tmp = get_byte
1364
+ _tmp = _tmp ? nil : true
1365
+ self.pos = _save
1366
+ set_failed_rule :_eof unless _tmp
1367
+ return _tmp
1368
+ end
1369
+
1370
+ # eol = ("
1371
+ def _eol
1372
+
1373
+ _save = self.pos
1374
+ while true # choice
1375
+ _tmp = match_string("\r\n")
1376
+ break if _tmp
1377
+ self.pos = _save
1378
+ _tmp = match_string("\n")
1379
+ break if _tmp
1380
+ self.pos = _save
1381
+ break
1382
+ end # end choice
1383
+
1384
+ set_failed_rule :_eol unless _tmp
1385
+ return _tmp
1386
+ end
1387
+
1388
+ # sp = (" " | "\t")
1389
+ def _sp
1390
+
1391
+ _save = self.pos
1392
+ while true # choice
1393
+ _tmp = match_string(" ")
1394
+ break if _tmp
1395
+ self.pos = _save
1396
+ _tmp = match_string("\t")
1397
+ break if _tmp
1398
+ self.pos = _save
1399
+ break
1400
+ end # end choice
1401
+
1402
+ set_failed_rule :_sp unless _tmp
1403
+ return _tmp
1404
+ end
1405
+
1406
+ # - = sp*
1407
+ def __hyphen_
1408
+ while true
1409
+ _tmp = apply(:_sp)
1410
+ break unless _tmp
1411
+ end
1412
+ _tmp = true
1413
+ set_failed_rule :__hyphen_ unless _tmp
1414
+ return _tmp
1415
+ end
1416
+
1417
+ # sp_lf = (sp | eol)*
1418
+ def _sp_lf
1419
+ while true
1420
+
1421
+ _save1 = self.pos
1422
+ while true # choice
1423
+ _tmp = apply(:_sp)
1424
+ break if _tmp
1425
+ self.pos = _save1
1426
+ _tmp = apply(:_eol)
1427
+ break if _tmp
1428
+ self.pos = _save1
1429
+ break
1430
+ end # end choice
1431
+
1432
+ break unless _tmp
1433
+ end
1434
+ _tmp = true
1435
+ set_failed_rule :_sp_lf unless _tmp
1436
+ return _tmp
1437
+ end
1438
+
1439
+ # blk_lines = (- eol)*
1440
+ def _blk_lines
1441
+ while true
1442
+
1443
+ _save1 = self.pos
1444
+ while true # sequence
1445
+ _tmp = apply(:__hyphen_)
1446
+ unless _tmp
1447
+ self.pos = _save1
1448
+ break
1449
+ end
1450
+ _tmp = apply(:_eol)
1451
+ unless _tmp
1452
+ self.pos = _save1
1453
+ end
1454
+ break
1455
+ end # end sequence
1456
+
1457
+ break unless _tmp
1458
+ end
1459
+ _tmp = true
1460
+ set_failed_rule :_blk_lines unless _tmp
1461
+ return _tmp
1462
+ end
1463
+
1464
+ # root = contents:c { Root.new.push *c }
1465
+ def _root
1466
+
1467
+ _save = self.pos
1468
+ while true # sequence
1469
+ _tmp = apply(:_contents)
1470
+ c = @result
1471
+ unless _tmp
1472
+ self.pos = _save
1473
+ break
1474
+ end
1475
+ @result = begin; Root.new.push *c ; end
1476
+ _tmp = true
1477
+ unless _tmp
1478
+ self.pos = _save
1479
+ end
1480
+ break
1481
+ end # end sequence
1482
+
1483
+ set_failed_rule :_root unless _tmp
1484
+ return _tmp
1485
+ end
1486
+
1487
+ Rules = {}
1488
+ Rules[:_id] = rule_info("id", "< /[a-z][a-z_]*/i > { text }")
1489
+ Rules[:_ids] = rule_info("ids", "(ids:i1 - \",\" - ids:i2 { i1 + i2 } | id:i { [i] })")
1490
+ Rules[:_item] = rule_info("item", "(attribute | attributes | element)")
1491
+ Rules[:_items] = rule_info("items", "(items:i1 items:i2 { i1 + i2 } | item:i { (i.is_a? Array) ? i : [i] })")
1492
+ Rules[:_contents] = rule_info("contents", "items?:i { i.to_a }")
1493
+ Rules[:_attr] = rule_info("attr", "- id:n - \"=\" - val:v - eol { Attribute.new n, *v }")
1494
+ Rules[:_multiple_attrs] = rule_info("multiple_attrs", "- ids:n - \"=\" - vals:v - eol { n.reduce(Array.new) do |attrs, name| value = v.shift or [nil] attrs << Attribute.new(name, *value) end }")
1495
+ Rules[:_attribute] = rule_info("attribute", "blk_lines attr:a blk_lines { a }")
1496
+ Rules[:_attributes] = rule_info("attributes", "blk_lines multiple_attrs:a blk_lines { a }")
1497
+ Rules[:_code] = rule_info("code", "< /<<.*?>>/m > { [strip_chars(text, 2), {:code => true}] }")
1498
+ Rules[:_in_brackets] = rule_info("in_brackets", "< /\\(.*?\\)/m > { [strip_chars(text, 1)] }")
1499
+ Rules[:_in_quotes] = rule_info("in_quotes", "< /\".*?\"/m > { [strip_chars(text, 1)] }")
1500
+ Rules[:_raw] = rule_info("raw", "< /.*/ > { [text.strip] }")
1501
+ Rules[:_escaped] = rule_info("escaped", "(in_quotes:s1 escaped:s2 { s1[0] += '\"' + s2[0] ; s1 } | in_quotes)")
1502
+ Rules[:_i18n] = rule_info("i18n", "\"_\" - (in_brackets | in_quotes):s { [s[0], {:translatable => true}] }")
1503
+ Rules[:_val] = rule_info("val", "(val:v1 - \"+\" sp_lf val:v2 { v1[0] += v2[0] ; v1 } | escaped | i18n | code | in_brackets | in_quotes | raw)")
1504
+ Rules[:_vals] = rule_info("vals", "(vals:v1 - \",\" - vals:v2 { v1 + v2 } | val:v { [v] })")
1505
+ Rules[:_amendment] = rule_info("amendment", "- amending_tag:n - eol contents:c - closing_tag(n) - eol { Element.new(n, :amendment => true).push *c }")
1506
+ Rules[:_regular] = rule_info("regular", "- opening_tag:n - eol contents:c - closing_tag(n) - eol { Element.new(n).push *c }")
1507
+ Rules[:_element] = rule_info("element", "blk_lines (amendment | regular):e blk_lines { e }")
1508
+ Rules[:_amending_tag] = rule_info("amending_tag", "\"[+\" id:n \"]\" { n }")
1509
+ Rules[:_closing_tag] = rule_info("closing_tag", "\"[/\" id:n \"]\" &{ n == m }")
1510
+ Rules[:_opening_tag] = rule_info("opening_tag", "\"[\" id:n \"]\" { n }")
1511
+ Rules[:_eof] = rule_info("eof", "!.")
1512
+ Rules[:_eol] = rule_info("eol", "(\"
1513
+ Rules[:_sp] = rule_info("sp", "(\" \" | \"\\t\")")
1514
+ Rules[:__hyphen_] = rule_info("-", "sp*")
1515
+ Rules[:_sp_lf] = rule_info("sp_lf", "(sp | eol)*")
1516
+ Rules[:_blk_lines] = rule_info("blk_lines", "(- eol)*")
1517
+ Rules[:_root] = rule_info("root", "contents:c { Root.new.push *c }")
1518
+ # :startdoc:
1519
+ end
1520
+
1521
+ end