review 5.1.1 → 5.4.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (114) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/ruby-tex.yml +6 -2
  3. data/.github/workflows/ruby-win.yml +6 -2
  4. data/.github/workflows/ruby.yml +6 -2
  5. data/.rubocop.yml +5 -319
  6. data/NEWS.ja.md +149 -0
  7. data/NEWS.md +149 -1
  8. data/README.md +9 -8
  9. data/bin/review +1 -1
  10. data/bin/review-catalog-converter +15 -15
  11. data/bin/review-check +7 -7
  12. data/bin/review-compile +14 -23
  13. data/bin/review-index +1 -1
  14. data/bin/review-preproc +29 -35
  15. data/bin/review-validate +2 -2
  16. data/doc/config.yml.sample +9 -1
  17. data/doc/config.yml.sample-simple +1 -1
  18. data/doc/format.ja.md +29 -3
  19. data/doc/format.md +32 -3
  20. data/doc/writing_vertical.ja.md +6 -0
  21. data/lib/review/book/base.rb +3 -3
  22. data/lib/review/book/book_unit.rb +13 -3
  23. data/lib/review/book/chapter.rb +1 -1
  24. data/lib/review/book/index.rb +7 -4
  25. data/lib/review/book/part.rb +12 -13
  26. data/lib/review/book/volume.rb +1 -1
  27. data/lib/review/builder.rb +92 -65
  28. data/lib/review/catalog.rb +6 -5
  29. data/lib/review/compiler.rb +76 -57
  30. data/lib/review/configure.rb +5 -2
  31. data/lib/review/epub2html.rb +12 -12
  32. data/lib/review/epubmaker/content.rb +1 -1
  33. data/lib/review/epubmaker/epubcommon.rb +47 -45
  34. data/lib/review/epubmaker/epubv2.rb +2 -1
  35. data/lib/review/epubmaker/epubv3.rb +5 -4
  36. data/lib/review/epubmaker/producer.rb +6 -7
  37. data/lib/review/epubmaker/reviewheaderlistener.rb +1 -1
  38. data/lib/review/epubmaker.rb +56 -67
  39. data/lib/review/exception.rb +7 -0
  40. data/lib/review/extentions/string.rb +1 -1
  41. data/lib/review/htmlbuilder.rb +90 -34
  42. data/lib/review/htmlutils.rb +17 -17
  43. data/lib/review/i18n.rb +3 -3
  44. data/lib/review/i18n.yml +6 -0
  45. data/lib/review/idgxmlbuilder.rb +61 -39
  46. data/lib/review/idgxmlmaker.rb +27 -26
  47. data/lib/review/img_math.rb +12 -18
  48. data/lib/review/index_builder.rb +94 -53
  49. data/lib/review/init.rb +4 -4
  50. data/lib/review/latexbuilder.rb +84 -76
  51. data/lib/review/lineinput.rb +3 -3
  52. data/lib/review/location.rb +1 -1
  53. data/lib/review/loggable.rb +27 -0
  54. data/lib/review/logger.rb +69 -21
  55. data/lib/review/makerhelper.rb +8 -4
  56. data/lib/review/markdownbuilder.rb +21 -12
  57. data/lib/review/pdfmaker.rb +63 -42
  58. data/lib/review/plaintextbuilder.rb +16 -15
  59. data/lib/review/preprocessor/directive.rb +35 -0
  60. data/lib/review/preprocessor/line.rb +34 -0
  61. data/lib/review/preprocessor/repository.rb +177 -0
  62. data/lib/review/preprocessor.rb +94 -296
  63. data/lib/review/rstbuilder.rb +12 -3
  64. data/lib/review/template.rb +5 -1
  65. data/lib/review/textmaker.rb +32 -31
  66. data/lib/review/textutils.rb +5 -6
  67. data/lib/review/tocprinter.rb +12 -7
  68. data/lib/review/topbuilder.rb +96 -19
  69. data/lib/review/update.rb +16 -8
  70. data/lib/review/version.rb +1 -1
  71. data/lib/review/volumeprinter.rb +9 -9
  72. data/lib/review/webmaker.rb +45 -46
  73. data/lib/review/webtocprinter.rb +10 -10
  74. data/lib/review/yamlloader.rb +35 -2
  75. data/review.gemspec +2 -1
  76. data/samples/sample-book/src/config.yml +0 -1
  77. data/samples/sample-book/src/lib/tasks/review.rake +3 -1
  78. data/samples/sample-book/src/lib/tasks/z01_copy_sty.rake +2 -1
  79. data/samples/syntax-book/ch02.re +9 -0
  80. data/samples/syntax-book/lib/tasks/z01_copy_sty.rake +2 -1
  81. data/templates/html/_titlepage.html.erb +9 -17
  82. data/templates/latex/config.erb +3 -0
  83. data/templates/latex/review-jlreq/review-base.sty +4 -5
  84. data/templates/latex/review-jlreq/review-jlreq.cls +39 -5
  85. data/templates/latex/review-jsbook/review-base.sty +9 -3
  86. data/templates/latex/review-jsbook/review-jsbook.cls +32 -5
  87. data/templates/opf/opf_manifest_epubv2.opf.erb +1 -1
  88. data/templates/opf/opf_manifest_epubv3.opf.erb +1 -1
  89. data/test/assets/syntax_book_index_detail.txt +10 -8
  90. data/test/assets/test_template.tex +4 -1
  91. data/test/assets/test_template_backmatter.tex +4 -1
  92. data/test/book_test_helper.rb +10 -10
  93. data/test/test_book_chapter.rb +25 -2
  94. data/test/test_builder.rb +10 -8
  95. data/test/test_epub3maker.rb +3 -3
  96. data/test/test_epubmaker.rb +27 -37
  97. data/test/test_epubmaker_cmd.rb +14 -3
  98. data/test/test_htmlbuilder.rb +111 -31
  99. data/test/test_idgxmlbuilder.rb +41 -33
  100. data/test/test_idgxmlmaker_cmd.rb +1 -1
  101. data/test/test_img_math.rb +11 -2
  102. data/test/test_index.rb +30 -4
  103. data/test/test_latexbuilder.rb +46 -25
  104. data/test/test_latexbuilder_v2.rb +18 -10
  105. data/test/test_markdownbuilder.rb +13 -0
  106. data/test/test_pdfmaker.rb +19 -0
  107. data/test/test_pdfmaker_cmd.rb +10 -10
  108. data/test/test_plaintextbuilder.rb +46 -22
  109. data/test/test_preprocessor.rb +188 -1
  110. data/test/test_rstbuilder.rb +13 -0
  111. data/test/test_textmaker_cmd.rb +1 -1
  112. data/test/test_topbuilder.rb +195 -29
  113. data/test/test_yamlloader.rb +28 -42
  114. metadata +11 -6
@@ -1,4 +1,4 @@
1
- # Copyright (c) 2008-2020 Minero Aoki, Kenshi Muto, Masayoshi Takahashi,
1
+ # Copyright (c) 2008-2021 Minero Aoki, Kenshi Muto, Masayoshi Takahashi,
2
2
  # KADO Masanori
3
3
  #
4
4
  # This program is free software.
@@ -13,7 +13,8 @@ require 'review/sec_counter'
13
13
 
14
14
  module ReVIEW
15
15
  class IndexBuilder < Builder
16
- attr_reader :list_index, :table_index, :equation_index, :footnote_index,
16
+ attr_reader :list_index, :table_index, :equation_index,
17
+ :footnote_index, :endnote_index,
17
18
  :numberless_image_index, :image_index, :icon_index, :indepimage_index,
18
19
  :headline_index, :column_index, :bibpaper_index
19
20
 
@@ -24,9 +25,9 @@ module ReVIEW
24
25
  def check_id(id)
25
26
  if id
26
27
  if id =~ %r![#%\\{}\[\]~/$'"|*?&<>`\s]!
27
- warn "deprecated ID: `#{$&}` in `#{id}`"
28
+ warn "deprecated ID: `#{$&}` in `#{id}`", location: location
28
29
  elsif id.start_with?('.')
29
- warn "deprecated ID: `#{id}` begins from `.`"
30
+ warn "deprecated ID: `#{id}` begins from `.`", location: location
30
31
  end
31
32
  end
32
33
  end
@@ -51,14 +52,18 @@ module ReVIEW
51
52
  end
52
53
 
53
54
  def builder_init_file
54
- @sec_counter = SecCounter.new(5, @chapter)
55
-
55
+ super
56
56
  @headline_stack = []
57
+ @crossref = {
58
+ footnote: {},
59
+ endnote: {}
60
+ }
57
61
 
58
62
  @list_index = ReVIEW::Book::ListIndex.new
59
63
  @table_index = ReVIEW::Book::TableIndex.new
60
64
  @equation_index = ReVIEW::Book::EquationIndex.new
61
65
  @footnote_index = ReVIEW::Book::FootnoteIndex.new
66
+ @endnote_index = ReVIEW::Book::EndnoteIndex.new
62
67
  @headline_index = ReVIEW::Book::HeadlineIndex.new(@chapter)
63
68
  @column_index = ReVIEW::Book::ColumnIndex.new
64
69
  @chapter_index = ReVIEW::Book::ChapterIndex.new
@@ -74,6 +79,14 @@ module ReVIEW
74
79
  private :builder_init_file
75
80
 
76
81
  def result
82
+ %i[footnote endnote].each do |name|
83
+ @crossref[name].each_pair do |k, v|
84
+ if v == 0
85
+ warn "#{@chapter.basename}: #{name} ID #{k} is not referred."
86
+ end
87
+ end
88
+ end
89
+
77
90
  nil
78
91
  end
79
92
 
@@ -88,11 +101,7 @@ module ReVIEW
88
101
 
89
102
  cursor = level - 2
90
103
 
91
- if label
92
- @headline_stack[cursor] = label
93
- else
94
- @headline_stack[cursor] = caption
95
- end
104
+ @headline_stack[cursor] = (label || caption)
96
105
  if @headline_stack.size > cursor + 1
97
106
  @headline_stack = @headline_stack.take(cursor + 1)
98
107
  end
@@ -101,6 +110,7 @@ module ReVIEW
101
110
 
102
111
  item = ReVIEW::Book::Index::Item.new(item_id, @sec_counter.number_list, caption)
103
112
  @headline_index.add_item(item)
113
+ compile_inline(caption)
104
114
  end
105
115
 
106
116
  def nonum_begin(level, label, caption)
@@ -109,11 +119,7 @@ module ReVIEW
109
119
 
110
120
  cursor = level - 2
111
121
 
112
- if label
113
- @headline_stack[cursor] = label
114
- else
115
- @headline_stack[cursor] = caption
116
- end
122
+ @headline_stack[cursor] = (label || caption)
117
123
  if @headline_stack.size > cursor + 1
118
124
  @headline_stack = @headline_stack.take(cursor + 1)
119
125
  end
@@ -133,11 +139,7 @@ module ReVIEW
133
139
 
134
140
  cursor = level - 2
135
141
 
136
- if label
137
- @headline_stack[cursor] = label
138
- else
139
- @headline_stack[cursor] = caption
140
- end
142
+ @headline_stack[cursor] = (label || caption)
141
143
  if @headline_stack.size > cursor + 1
142
144
  @headline_stack = @headline_stack.take(cursor + 1)
143
145
  end
@@ -157,11 +159,7 @@ module ReVIEW
157
159
 
158
160
  cursor = level - 2
159
161
 
160
- if label
161
- @headline_stack[cursor] = label
162
- else
163
- @headline_stack[cursor] = caption
164
- end
162
+ @headline_stack[cursor] = (label || caption)
165
163
  if @headline_stack.size > cursor + 1
166
164
  @headline_stack = @headline_stack.take(cursor + 1)
167
165
  end
@@ -248,56 +246,73 @@ module ReVIEW
248
246
 
249
247
  alias_method :lead, :read
250
248
 
251
- def list(_lines, id, _caption, _lang = nil)
249
+ def list(lines, id, caption, _lang = nil)
252
250
  check_id(id)
253
251
  item = ReVIEW::Book::Index::Item.new(id, @list_index.size + 1)
254
252
  @list_index.add_item(item)
253
+ compile_inline(caption)
254
+ lines.each { |line| compile_inline(line) }
255
255
  end
256
256
 
257
- def source(_lines, _caption = nil, _lang = nil)
257
+ def source(lines, caption = nil, _lang = nil)
258
+ compile_inline(caption)
259
+ lines.each { |line| compile_inline(line) }
258
260
  end
259
261
 
260
- def listnum(_lines, id, _caption, _lang = nil)
262
+ def listnum(lines, id, caption, _lang = nil)
261
263
  check_id(id)
262
264
  item = ReVIEW::Book::Index::Item.new(id, @list_index.size + 1)
263
265
  @list_index.add_item(item)
266
+ compile_inline(caption)
267
+ lines.each { |line| compile_inline(line) }
264
268
  end
265
269
 
266
- def emlist(lines, caption = nil, lang = nil)
270
+ def emlist(lines, caption = nil, _lang = nil)
271
+ compile_inline(caption)
272
+ lines.each { |line| compile_inline(line) }
267
273
  end
268
274
 
269
- def emlistnum(lines, caption = nil, lang = nil)
275
+ def emlistnum(lines, caption = nil, _lang = nil)
276
+ compile_inline(caption)
277
+ lines.each { |line| compile_inline(line) }
270
278
  end
271
279
 
272
280
  def cmd(lines, caption = nil)
281
+ compile_inline(caption)
282
+ lines.each { |line| compile_inline(line) }
273
283
  end
274
284
 
275
285
  def quote(lines)
286
+ lines.each { |line| compile_inline(line) }
276
287
  end
277
288
 
278
289
  def image(_lines, id, caption, _metric = nil)
279
290
  check_id(id)
280
291
  item = ReVIEW::Book::Index::Item.new(id, @image_index.size + 1, caption)
281
292
  @image_index.add_item(item)
293
+ compile_inline(caption)
282
294
  end
283
295
 
284
- def table(_lines, id = nil, caption = nil)
296
+ def table(lines, id = nil, caption = nil)
285
297
  check_id(id)
286
298
  if id
287
299
  item = ReVIEW::Book::Index::Item.new(id, @table_index.size + 1, caption)
288
300
  @table_index.add_item(item)
289
301
  end
302
+ compile_inline(caption)
303
+ lines.each { |line| compile_inline(line) }
290
304
  end
291
305
 
292
- def emtable(_lines, _caption = nil)
306
+ def emtable(_lines, caption = nil)
293
307
  # item = ReVIEW::Book::TableIndex::Item.new(id, @table_index.size + 1)
294
308
  # @table_index << item
309
+ compile_inline(caption)
295
310
  end
296
311
 
297
312
  def comment(lines, comment = nil)
298
313
  end
299
314
 
300
- def imgtable(_lines, id, _caption = nil, _metric = nil)
315
+ def imgtable(_lines, id, caption = nil, _metric = nil)
301
316
  check_id(id)
302
317
  item = ReVIEW::Book::Index::Item.new(id, @table_index.size + 1)
303
318
  @table_index.add_item(item)
@@ -305,24 +320,37 @@ module ReVIEW
305
320
  ## to find image path
306
321
  item = ReVIEW::Book::Index::Item.new(id, @indepimage_index.size + 1)
307
322
  @indepimage_index.add_item(item)
323
+ compile_inline(caption)
308
324
  end
309
325
 
310
326
  def footnote(id, str)
311
327
  check_id(id)
328
+ @crossref[:footnote][id] ||= 0
312
329
  item = ReVIEW::Book::Index::Item.new(id, @footnote_index.size + 1, str)
313
330
  @footnote_index.add_item(item)
331
+ compile_inline(str)
332
+ end
333
+
334
+ def endnote(id, str)
335
+ check_id(id)
336
+ @crossref[:endnote][id] ||= 0
337
+ item = ReVIEW::Book::Index::Item.new(id, @endnote_index.size + 1, str)
338
+ @endnote_index.add_item(item)
339
+ compile_inline(str)
314
340
  end
315
341
 
316
- def indepimage(_lines, id, _caption = '', _metric = nil)
342
+ def indepimage(_lines, id, caption = '', _metric = nil)
317
343
  check_id(id)
318
344
  item = ReVIEW::Book::Index::Item.new(id, @indepimage_index.size + 1)
319
345
  @indepimage_index.add_item(item)
346
+ compile_inline(caption)
320
347
  end
321
348
 
322
- def numberlessimage(_lines, id, _caption = '', _metric = nil)
349
+ def numberlessimage(_lines, id, caption = '', _metric = nil)
323
350
  check_id(id)
324
351
  item = ReVIEW::Book::Index::Item.new(id, @indepimage_index.size + 1)
325
352
  @indepimage_index.add_item(item)
353
+ compile_inline(caption)
326
354
  end
327
355
 
328
356
  def hr
@@ -335,10 +363,12 @@ module ReVIEW
335
363
  def blankline
336
364
  end
337
365
 
338
- def flushright(_lines)
366
+ def flushright(lines)
367
+ lines.each { |line| compile_inline(line) }
339
368
  end
340
369
 
341
370
  def centering(lines)
371
+ lines.each { |line| compile_inline(line) }
342
372
  end
343
373
 
344
374
  def olnum(_num)
@@ -347,12 +377,16 @@ module ReVIEW
347
377
  def pagebreak
348
378
  end
349
379
 
350
- def bpo(_lines)
380
+ def bpo(lines)
381
+ lines.each { |line| compile_inline(line) }
351
382
  end
352
383
 
353
384
  def noindent
354
385
  end
355
386
 
387
+ def printendnotes
388
+ end
389
+
356
390
  def compile_inline(s)
357
391
  @compiler.text(s)
358
392
  end
@@ -389,7 +423,13 @@ module ReVIEW
389
423
  ''
390
424
  end
391
425
 
392
- def inline_fn(_id)
426
+ def inline_fn(id)
427
+ @crossref[:footnote][id] = @crossref[:footnote][id] ? @crossref[:footnote][id] + 1 : 1
428
+ ''
429
+ end
430
+
431
+ def inline_endnote(id)
432
+ @crossref[:endnote][id] = @crossref[:endnote][id] ? @crossref[:endnote][id] + 1 : 1
393
433
  ''
394
434
  end
395
435
 
@@ -465,10 +505,12 @@ module ReVIEW
465
505
  ''
466
506
  end
467
507
 
468
- def bibpaper(_lines, id, caption)
508
+ def bibpaper(lines, id, caption)
469
509
  check_id(id)
470
510
  item = ReVIEW::Book::Index::Item.new(id, @bibpaper_index.size + 1, caption)
471
511
  @bibpaper_index.add_item(item)
512
+ compile_inline(caption)
513
+ lines.each { |line| compile_inline(line) }
472
514
  end
473
515
 
474
516
  def inline_hd(_id)
@@ -598,25 +640,18 @@ module ReVIEW
598
640
  ''
599
641
  end
600
642
 
601
- def warn(msg)
602
- @logger.warn "#{@location}: #{msg}"
603
- end
604
-
605
- def error(msg = '(no message)')
606
- if msg =~ /builder does not support command/
607
- # ignore
608
- return
609
- end
610
-
611
- super
643
+ ## override
644
+ def error(msg = nil)
645
+ # ignore in indexing
612
646
  end
613
647
 
614
- def texequation(_lines, id = nil, _caption = '')
648
+ def texequation(_lines, id = nil, caption = '')
615
649
  check_id(id)
616
650
  if id
617
651
  item = ReVIEW::Book::Index::Item.new(id, @equation_index.size + 1)
618
652
  @equation_index.add_item(item)
619
653
  end
654
+ compile_inline(caption)
620
655
  end
621
656
 
622
657
  def get_chap(_chapter = nil)
@@ -627,10 +662,16 @@ module ReVIEW
627
662
  ''
628
663
  end
629
664
 
630
- def captionblock(_type, _lines, _caption, _specialstyle = nil)
665
+ def captionblock(_type, lines, caption, _specialstyle = nil)
666
+ compile_inline(caption)
667
+ lines.each { |line| compile_inline(line) }
631
668
  ''
632
669
  end
633
670
 
671
+ def graph(lines, id, _command, caption = '')
672
+ image(lines, id, caption)
673
+ end
674
+
634
675
  def tsize(_str)
635
676
  ''
636
677
  end
data/lib/review/init.rb CHANGED
@@ -179,12 +179,12 @@ EOS
179
179
  content = content.split("\n").delete_if { |l| l.strip.start_with?('#') || l.strip.empty? }.join("\n")
180
180
  end
181
181
 
182
- File.open(File.join(dir, 'config.yml'), 'w') { |f| f.write content }
182
+ File.write(File.join(dir, 'config.yml'), content)
183
183
  if @webui && !@web_result[2].empty?
184
184
  File.open(File.join(dir, 'config-ebook.yml'), 'w') do |f|
185
185
  f.puts <<EOT
186
186
  # for ebook PDF
187
- # REVIEW_CONFIG_FILE=config.yml rake pdf
187
+ # REVIEW_CONFIG_FILE=config-ebook.yml rake pdf
188
188
  inherit: ["config.yml"]
189
189
  # bookname: book-ebook
190
190
  texdocumentclass: ["#{@web_result[0]}", "#{@web_result[2]}"]
@@ -257,7 +257,7 @@ EOS
257
257
  exit 1
258
258
  end
259
259
 
260
- if filename =~ %r{\Ahttps?://}
260
+ if %r{\Ahttps?://}.match?(filename)
261
261
  begin
262
262
  @logger.info "Downloading from #{filename}"
263
263
  zipdata = Net::HTTP.get(URI.parse(filename))
@@ -334,7 +334,7 @@ EOS
334
334
  # validation
335
335
  if @web_result
336
336
  @web_result.each do |s|
337
- if s !~ /\A[a-z0-9=_,.-]*\Z/i
337
+ unless /\A[a-z0-9=_,.-]*\Z/i.match?(s)
338
338
  @web_result = nil
339
339
  break
340
340
  end