bindery 2.0.0 → 2.1.0

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.
@@ -19,18 +19,22 @@ module Bindery
19
19
  def chapter(title, filename, options={}, &block)
20
20
  div('chapter', title, filename, options, &block)
21
21
  end
22
-
22
+
23
23
  def section(title, filename, options={}, &block)
24
24
  div('section', title, filename, options, &block)
25
25
  end
26
-
26
+
27
27
  def part(title, filename, options={}, &block)
28
28
  div('part', title, filename, options, &block)
29
29
  end
30
-
30
+
31
31
  def appendix(title, filename, options={}, &block)
32
32
  div('appendix', title, filename, options, &block)
33
33
  end
34
-
34
+
35
+ def index(title, filename, options={}, &block)
36
+ div('index', title, filename, options, &block)
37
+ end
38
+
35
39
  end
36
40
  end
@@ -6,14 +6,14 @@ module Bindery
6
6
  attr_accessor :options
7
7
 
8
8
  include ContentMethods
9
-
9
+
10
10
  def initialize(div_type, title, file, options)
11
11
  self.div_type = div_type
12
12
  self.title = title
13
13
  self.file = file
14
14
  self.options = options
15
15
  end
16
-
16
+
17
17
  def valid?
18
18
  true
19
19
  # ??? title specified? Is this required by the spec? Think about
@@ -25,17 +25,17 @@ module Bindery
25
25
  # chapters that would break up the text flow?
26
26
  # file exists, readable
27
27
  # file content properly formed? Does that matter? Can we
28
- # verify it?
28
+ # verify it?
29
29
  end
30
30
 
31
31
  def divisions
32
32
  @divisions ||= []
33
33
  end
34
-
34
+
35
35
  def body_only?
36
36
  options.fetch(:body_only, true)
37
37
  end
38
-
38
+
39
39
  def include_images?
40
40
  options.fetch(:include_images, true)
41
41
  end
@@ -2,10 +2,11 @@ require 'builder'
2
2
  require 'zip'
3
3
  require 'bindery/extensions/zip_file'
4
4
  require 'nokogiri'
5
+ require 'uri'
5
6
 
6
7
  module Bindery
7
8
  module Formats
8
-
9
+
9
10
  # Builds an EPUB book file from the book description.
10
11
  #
11
12
  # The {EPUB Wikipedia entry}[http://en.wikipedia.org/wiki/EPUB] provides a nice, concise overview of the EPUB format.
@@ -20,25 +21,25 @@ module Bindery
20
21
  # * Details of the format of other files allowed in EPUB documents are found in
21
22
  # {Open Publication Structure (OPS) 2.0.1 - Recommended Specification}[http://idpf.org/epub/20/spec/OPS_2.0.1_draft.htm].
22
23
  class Epub
23
-
24
+
24
25
  MimeTypes = {
25
26
  '.jpg' => 'image/jpeg',
26
27
  '.png' => 'image/png',
27
28
  '.gif' => 'image/gif',
28
29
  }
29
-
30
+
30
31
  class ManifestEntry < Struct.new(:file_name, :xml_id, :mime_type)
31
32
  end
32
-
33
+
33
34
  attr_accessor :book, :manifest_entries
34
-
35
+
35
36
  def initialize(book)
36
37
  self.book = book
37
38
  book.extend BookMethods
38
39
  book.divisions.each{|division| division.extend DivisionMethods}
39
40
  self.manifest_entries = []
40
41
  end
41
-
42
+
42
43
  def generate
43
44
  File.delete(book.epub_output_file) if File.exist?(book.epub_output_file)
44
45
  Zip::ZipFile.open(book.epub_output_file, Zip::ZipFile::CREATE) do |zipfile|
@@ -46,12 +47,12 @@ module Bindery
46
47
  zipfile.write_uncompressed_file 'mimetype', mimetype
47
48
  zipfile.mkdir 'META-INF'
48
49
  zipfile.write_file 'META-INF/container.xml', container
49
-
50
+
50
51
  # also frontmatter, backmatter
51
52
  book.divisions.each do |division|
52
53
  write_division(division, zipfile)
53
54
  end
54
-
55
+
55
56
  zipfile.mkdir 'css'
56
57
  zipfile.write_file 'css/book.css', stylesheet
57
58
 
@@ -59,13 +60,13 @@ module Bindery
59
60
  zipfile.write_file 'book.ncx', ncx
60
61
  end
61
62
  end
62
-
63
+
63
64
  def mimetype
64
65
  # the mimetype file must be the first file in the archive
65
66
  # it must be ASCII, uncompressed, and unencrypted
66
67
  'application/epub+zip'
67
68
  end
68
-
69
+
69
70
  def container
70
71
  %q{|<?xml version="1.0" encoding="UTF-8" ?>
71
72
  |<container version="1.0" xmlns="urn:oasis:names:tc:opendocument:xmlns:container">
@@ -75,23 +76,23 @@ module Bindery
75
76
  |</container>
76
77
  |}.strip_margin
77
78
  end
78
-
79
+
79
80
  def opf
80
81
  xm = Builder::XmlMarkup.new(:indent => 2)
81
82
  xm.instruct!
82
83
  xm.package('version'=>'2.0', 'xmlns'=>'http://www.idpf.org/2007/opf', 'unique-identifier'=>'BookId') {
83
-
84
+
84
85
  xm.metadata('xmlns:dc'=>'http://purl.org/dc/elements/1.1/', 'xmlns:opf'=>'http://www.idpf.org/2007/opf') {
85
86
  # required elements
86
87
  xm.dc :title, book.full_title
87
88
  xm.dc :language, book.language
88
89
  xm.dc :identifier, book.url, ident_options('opf:scheme'=>'URL') if book.url
89
- xm.dc :identifier, book.isbn, ident_options('opf:scheme'=>'ISBN') if book.isbn
90
-
90
+ xm.dc :identifier, book.isbn, ident_options('opf:scheme'=>'ISBN') if book.isbn
91
+
91
92
  # optional elements
92
93
  xm.dc :creator, book.author, 'opf:role'=>'aut' if book.author
93
94
  }
94
-
95
+
95
96
  xm.manifest {
96
97
  book.divisions.each{|division| division.write_item(xm)}
97
98
  # also frontmatter, backmatter
@@ -102,17 +103,17 @@ module Bindery
102
103
  # xm.item 'id'=>'myfont', 'href'=>'css/myfont.otf', 'media-type'=>'application/x-font-opentype'
103
104
  xm.item 'id'=>'ncx', 'href'=>'book.ncx', 'media-type'=>'application/x-dtbncx+xml'
104
105
  }
105
-
106
+
106
107
  xm.spine('toc'=>'ncx') {
107
108
  book.divisions.each{|division| division.write_itemref(xm)}
108
109
  }
109
-
110
+
110
111
  # xm.guide {
111
112
  # xm.reference 'type'='loi', 'title'=>'List of Illustrations', 'href'=>'appendix.html#figures'
112
113
  # }
113
114
  }
114
115
  end
115
-
116
+
116
117
  def ncx
117
118
  xm = Builder::XmlMarkup.new(:indent => 2)
118
119
  xm.instruct!
@@ -124,18 +125,18 @@ module Bindery
124
125
  xm.meta 'name'=>'dtb:totalPageCount', 'content'=>0
125
126
  xm.meta 'name'=>'dtb:maxPageNumber', 'content'=>0
126
127
  }
127
-
128
+
128
129
  xm.docTitle {
129
130
  xm.text book.full_title
130
131
  }
131
-
132
+
132
133
  xm.docAuthor {
133
134
  xm.text book.author
134
135
  }
135
-
136
+
136
137
  xm.navMap {
137
138
  play_order = 0
138
-
139
+
139
140
  # also frontmatter, backmatter
140
141
  book.divisions.each do |division|
141
142
  play_order += 1
@@ -174,7 +175,7 @@ module Bindery
174
175
  write_division(div, zipfile)
175
176
  end
176
177
  end
177
-
178
+
178
179
  def include_images(doc, zipfile)
179
180
  # TODO: where else can images appear? Style sheets?
180
181
  zipfile.mkdir('images') unless zip_dir_exists?(zipfile, 'images')
@@ -195,12 +196,12 @@ module Bindery
195
196
  end
196
197
  end
197
198
  end
198
-
199
+
199
200
  def add_manifest_entry(file_name)
200
201
  xml_id, ext = File.base_parts(file_name.gsub('/', '-'))
201
202
  manifest_entries << ManifestEntry.new(file_name, xml_id, MimeTypes[ext])
202
203
  end
203
-
204
+
204
205
  def cover
205
206
  xm = Builder::XmlMarkup.new(:indent => 2)
206
207
  xm.instruct!
@@ -223,7 +224,7 @@ module Bindery
223
224
  }
224
225
  }
225
226
  end
226
-
227
+
227
228
  def stylesheet
228
229
  # This is a start, but needs work.
229
230
  %q{|@page {
@@ -257,7 +258,7 @@ module Bindery
257
258
  |h3.section_title {text-align: center;}
258
259
  |}.strip_margin
259
260
  end
260
-
261
+
261
262
  def ident_options(opts)
262
263
  if book.isbn
263
264
  return opts.merge('id'=>'BookId') if opts['opf:scheme'] == 'ISBN'
@@ -266,18 +267,19 @@ module Bindery
266
267
  end
267
268
  opts
268
269
  end
269
-
270
+
270
271
  def zip_dir_exists?(zipfile, dirname)
271
272
  dirname = "#{dirname}/" unless dirname =~ %r{/$}
272
273
  zipfile.entries.any?{|e| e.directory? && e.name == dirname}
273
274
  end
274
-
275
+
275
276
  def zip_file_exists?(zipfile, filename)
276
277
  zipfile.entries.any?{|e| e.name == filename}
277
278
  end
278
-
279
+
279
280
  def make_image_file_name(zipfile, url)
280
- stem, ext = File.base_parts(url)
281
+ uri = URI(url)
282
+ stem, ext = File.base_parts(uri.path)
281
283
  filename = "images/#{stem}#{ext}"
282
284
  n = 0
283
285
  while zip_file_exists?(zipfile, filename)
@@ -286,31 +288,31 @@ module Bindery
286
288
  end
287
289
  filename
288
290
  end
289
-
291
+
290
292
  module BookMethods
291
293
  def epub_output_file
292
294
  @epub_output_file ||= "#{output}.epub"
293
295
  end
294
-
296
+
295
297
  def depth
296
298
  (divisions.map(&:depth) + [0]).max
297
299
  end
298
-
300
+
299
301
  def ident
300
302
  isbn || url
301
303
  end
302
304
  end
303
-
305
+
304
306
  module DivisionMethods
305
307
 
306
308
  def self.extended(obj)
307
309
  obj.divisions.each{|division| division.extend DivisionMethods}
308
310
  end
309
-
311
+
310
312
  def epub_id
311
313
  @epub_id ||= File.stemname(file)
312
314
  end
313
-
315
+
314
316
  def epub_output_file
315
317
  @epub_output_file ||= "#{epub_id}.xhtml"
316
318
  end
@@ -346,14 +348,14 @@ module Bindery
346
348
  end
347
349
 
348
350
  end
349
-
351
+
350
352
  module MetadataMethods
351
353
  def to_xml(builder)
352
354
  builder.meta(options.merge(:name => name, :content => value))
353
355
  %{<dc:#{name}>#{value}</dc:#{name}>}
354
356
  end
355
357
  end
356
-
358
+
357
359
  module DublinMetadataMethods
358
360
  def to_xml(builder)
359
361
  builder.dc name, value, options
@@ -1,3 +1,3 @@
1
1
  module Bindery
2
- VERSION = "2.0.0"
2
+ VERSION = "2.1.0"
3
3
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: bindery
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.0.0
4
+ version: 2.1.0
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2014-12-16 00:00:00.000000000 Z
12
+ date: 2016-06-02 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: builder
@@ -173,7 +173,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
173
173
  version: '0'
174
174
  segments:
175
175
  - 0
176
- hash: -394401607600380017
176
+ hash: 4117656268896811284
177
177
  requirements: []
178
178
  rubyforge_project: bindery
179
179
  rubygems_version: 1.8.23