Skip to content

Commit

Permalink
Reorganize book structure. (#69)
Browse files Browse the repository at this point in the history
  • Loading branch information
fnando committed Jan 28, 2024
1 parent 0f0594b commit 048f714
Show file tree
Hide file tree
Showing 91 changed files with 802 additions and 332 deletions.
128 changes: 84 additions & 44 deletions README.md
Expand Up @@ -53,46 +53,51 @@ To create a new e-book, just run

This command creates a directory `mybook` with the following structure:

.
├── Gemfile
├── Gemfile.lock
├── Guardfile
├── config
│   ├── helper.rb
│   ├── kitabu.yml
│   └── locales
│   └── en.yml
├── fonts
├── images
│   ├── cover.png
│   ├── kitabu.svg
│   ├── markdown.svg
│   └── up.svg
├── templates
│   ├── epub
│   │   ├── cover.erb
│   │   ├── page.erb
│   │   └── toc.erb
│   ├── html
│   │   └── layout.erb
│   └── styles
│   ├── epub.css
│   ├── files
│   │   ├── normalize.css
│   │   ├── notes.css
│   │   └── toc.css
│   ├── html.css
│   ├── pdf.css
│   └── print.css
└── text
├── 01_Getting_Started.md
├── 02_Creating_Chapters.md
├── 03_Syntax_Highlighting.md.erb
├── 04_Dynamic_Content.md.erb
├── 05_Exporting_Files.md
└── 06_Changelog.md

11 directories, 27 files
```
.
├── Gemfile
├── Gemfile.lock
├── Guardfile
├── assets
│   ├── fonts
│   ├── images
│   │   ├── cover.png
│   │   ├── kitabu.svg
│   │   ├── markdown.svg
│   │   └── up.svg
│   ├── scripts
│   └── styles
│   ├── epub.css
│   ├── html.css
│   ├── pdf.css
│   ├── print.css
│   └── support
│   ├── kitabu.css
│   ├── normalize.css
│   ├── notes.css
│   └── toc.css
├── config
│   ├── helpers.rb
│   ├── kitabu.yml
│   └── locales
│   └── en.yml
├── templates
│   ├── epub
│   │   ├── cover.erb
│   │   ├── page.erb
│   │   └── toc.erb
│   └── html
│   └── layout.erb
└── text
├── 01_Getting_Started.md
├── 02_Creating_Chapters.md
├── 03_Syntax_Highlighting.md.erb
├── 04_Dynamic_Content.md.erb
├── 05_Exporting_Files.md
└── 06_Changelog.md
13 directories, 28 files
```

The `config/kitabu.yml` file holds some information about your book; so you'll
always change it.
Expand Down Expand Up @@ -193,7 +198,7 @@ be something like this:
<img src="images/myimage.png" />
```

You book's helpers can be added to `config/helper.rb`, as this file is loaded
You book's helpers can be added to `config/helpers.rb`, as this file is loaded
automatically by kitabu.

You can see available helpers on
Expand Down Expand Up @@ -254,11 +259,12 @@ end

### Using custom fonts

You can use custom fonts for your PDF. Just add them to the `fonts` directory
You can use custom fonts on your ebooks. Just add them to the `fonts` directory
(you can create this directory on your book's root directory if it doesn't
exist).

Then, on `templates/styles/pdf.css` you can add the `@font-face` declaration.
Then, on `assets/styles/support/fonts.css` you can add the `@font-face`
declaration.

```css
@font-face {
Expand All @@ -275,12 +281,46 @@ Finally, to use this font, do something like this:
}
```

Instead of doing the above manually, you can also use Prince's `--scanfonts`
option.

```console
$ prince --scanfonts assets/fonts/* > assets/styles/support/fonts.css
```

Just remember to replace the generated path to be something like `../../fonts`
instead.

> [!TIP]
>
> In most cases, it's easier to redefine `sans-serif`, `serif` and `monospace`
> fonts. To know more about how to do this, read Prince's
> [Redefining the generic font families](https://www.princexml.com/doc/styling/#redefining-the-generic-font-families)
> documentation.
If you're unsure if fonts are actually being used on PDF files, use the
environment variable `PRINCEOPT` to disable system fonts.

```console
$ PRINCEOPT='--no-system-fonts --debug --log output/prince.log' kitabu export --only pdf
=> e-book couldn't be exported

$ tail -n10 output/prince.log
Sat Jan 27 18:39:10 2024: debug: font request: Caslon, serif
Sat Jan 27 18:39:10 2024: warning: Ensure fonts are available on the system or load them via a @font-face rule.
Sat Jan 27 18:39:10 2024: warning: For more information see:
Sat Jan 27 18:39:10 2024: warning: https://www.princexml.com/doc/help-install/#missing-glyphs-or-fonts
Sat Jan 27 18:39:10 2024: internal error: Unable to find any available fonts.
Sat Jan 27 18:39:10 2024: finished: failure
Sat Jan 27 18:39:10 2024: ---- end
```

### Configuring Markdown

Kitabu uses [Redcarpet](https://github.com/vmg/redcarpet) as the Markdown
engine. You can override the default processor by setting
`Kitabu::Markdown.processor`. This can be done by adding something like the
following to `config/helper.rb`:
following to `config/helpers.rb`:

```ruby
Kitabu::Markdown.processor = Redcarpet::Markdown.new(
Expand Down
2 changes: 1 addition & 1 deletion lib/kitabu.rb
Expand Up @@ -33,6 +33,7 @@ module Kitabu
require "kitabu/version"
require "kitabu/generator"
require "kitabu/cli"
require "kitabu/css"
require "kitabu/markdown"
require "kitabu/source_list"
require "kitabu/exporter"
Expand All @@ -41,7 +42,6 @@ module Kitabu
require "kitabu/exporter/epub"
require "kitabu/exporter/mobi"
require "kitabu/exporter/pdf"
require "kitabu/exporter/css"
require "kitabu/footnotes/base"
require "kitabu/footnotes/html"
require "kitabu/footnotes/pdf"
Expand Down
56 changes: 56 additions & 0 deletions lib/kitabu/css.rb
@@ -0,0 +1,56 @@
# frozen_string_literal: true

module Kitabu
class CSS
def self.create_file(root_dir:, config:)
buffer = StringIO.new
buffer << accent_color(config:)
buffer << "\n\n"
buffer << syntax_highlight(config:)
buffer << "\n\n"
buffer << translations(config:)

support_dir = root_dir.join("assets/styles/support")

FileUtils.mkdir_p(support_dir)
support_dir.join("kitabu.css").open("w") do |file|
file << buffer.tap(&:rewind).read
end
end

def self.accent_color(config:)
accent_color = config.fetch(:css_accent_color, "#000")

<<~CSS
:root {
--accent-color: #{accent_color};
}
CSS
end

def self.syntax_highlight(config:)
Rouge::Theme.find(
config.fetch(:syntax_highlight_theme, :github)
).render(scope: ".highlight")
end

def self.translations(config:)
backend = I18n.backend.translations

translations =
backend.each_with_object([]) do |(lang, dict), buffer|
buffer << "html[lang='#{lang}'] {"

dict.each do |key, value|
next unless value.is_a?(String) && value.lines.count == 1

buffer << "--#{key.to_s.tr('_', '-')}-text: #{value.inspect};"
end

buffer << "}\n"
end

translations.join("\n")
end
end
end
2 changes: 1 addition & 1 deletion lib/kitabu/exporter.rb
Expand Up @@ -19,7 +19,7 @@ def ui
end

def export!
helper = root_dir.join("config/helper.rb")
helper = root_dir.join("config/helpers.rb")
load(helper) if helper.exist?

FileUtils.rm_rf root_dir.join("output").to_s
Expand Down
16 changes: 11 additions & 5 deletions lib/kitabu/exporter/base.rb
Expand Up @@ -2,6 +2,16 @@

module Kitabu
class Exporter
def self.load_translations(root_dir:)
I18n.load_path += Dir[
File.expand_path(File.join(__dir__, "../../../templates/en.yml")),
root_dir.join("config/locales/**/*.{yml,rb}").to_s
]

I18n.backend.reload!
I18n.backend.eager_load!
end

class Base
# The e-book directory.
#
Expand All @@ -12,11 +22,7 @@ class Base
attr_accessor :source

def self.export(root_dir)
I18n.backend.eager_load!
I18n.load_path += Dir[
root_dir.join("config/locales/**/*.{yml,rb}").to_s
]

Exporter.load_translations(root_dir:)
new(root_dir).export
end

Expand Down
18 changes: 0 additions & 18 deletions lib/kitabu/exporter/css.rb

This file was deleted.

22 changes: 12 additions & 10 deletions lib/kitabu/exporter/epub.rb
Expand Up @@ -42,16 +42,23 @@ def html
def export
super

copy_styles!
copy_images!
copy_assets

write_sections!
write_cover!
write_toc!

ignore_files = [
tmp_dir.join("assets/styles/html.css"),
tmp_dir.join("assets/styles/print.css"),
tmp_dir.join("assets/styles/pdf.css")
].map(&:to_s)

epub.files += [tmp_dir.join("cover.html"), tmp_dir.join("toc.html")]
epub.files += tmp_dir.glob("**/*").select do |entry|
!epub.files.include?(entry) && entry.file?
!epub.files.include?(entry) &&
entry.file? &&
!ignore_files.include?(entry.to_s)
end

epub.save(epub_path)
Expand All @@ -62,13 +69,8 @@ def export
false
end

def copy_styles!
copy_files("output/styles/epub.css", "output/epub/styles")
copy_files("output/styles/files/*.css", "output/epub/styles")
end

def copy_images!
copy_directory("output/images", "output/epub/images")
def copy_assets
copy_directory("output/assets", "output/epub/assets")
end

def write_toc!
Expand Down
24 changes: 9 additions & 15 deletions lib/kitabu/exporter/html.rb
Expand Up @@ -8,9 +8,8 @@ class HTML < Base
#
def export
super
copy_images!
copy_fonts!
export_stylesheets!
copy_assets
export_kitabu_css

File.open(root_dir.join("output/#{name}.html"), "w") do |file|
file << render_layout
Expand Down Expand Up @@ -97,22 +96,17 @@ def content
buffer.join
end

# Copy images
# Copy assets
#
private def copy_images!
copy_directory("images", "output/images")
private def copy_assets
copy_directory("assets", "output/assets")
end

# Copy font files
# Export css with utilities for syntax highlighting, translations, and
# accent color.
#
private def copy_fonts!
copy_directory("fonts", "output/fonts")
end

# Export all root stylesheets.
#
private def export_stylesheets!
Exporter::CSS.new(root_dir).export
private def export_kitabu_css
CSS.create_file(config:, root_dir:)
end
end
end
Expand Down
3 changes: 2 additions & 1 deletion lib/kitabu/exporter/pdf.rb
Expand Up @@ -7,6 +7,7 @@ def export
super
apply_footnotes!
args = Shellwords.split(ENV.fetch("PRINCEOPT", ""))
args += Array(config[:prince_args])

spawn_command(
["prince", *args, html_for_pdf.to_s, "-o", pdf_file.to_s]
Expand All @@ -29,7 +30,7 @@ def create_html_file(target, html, class_name)
html
.css("link[rel=stylesheet]")
.first
.set_attribute "href", "styles/#{class_name}.css"
.set_attribute "href", "assets/styles/#{class_name}.css"

File.open(target, "w") {|f| f << html.to_html }
end
Expand Down

0 comments on commit 048f714

Please sign in to comment.