distorted-jekyll 0.5.2 → 0.5.7
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/LICENSE +661 -0
- data/README.md +6 -10
- data/lib/distorted-jekyll.rb +79 -0
- data/lib/distorted-jekyll/13th-style.rb +58 -0
- data/lib/distorted-jekyll/_config_default.yml +79 -0
- data/lib/distorted-jekyll/blocks.rb +16 -0
- data/lib/distorted-jekyll/error_code.rb +24 -0
- data/lib/distorted-jekyll/floor.rb +148 -0
- data/lib/distorted-jekyll/injection_of_love.rb +305 -0
- data/lib/distorted-jekyll/invoker.rb +400 -0
- data/lib/distorted-jekyll/molecule/abstract.rb +238 -0
- data/lib/distorted-jekyll/molecule/font.rb +29 -0
- data/lib/distorted-jekyll/molecule/image.rb +105 -0
- data/lib/distorted-jekyll/molecule/last-resort.rb +54 -0
- data/lib/distorted-jekyll/molecule/pdf.rb +88 -0
- data/lib/distorted-jekyll/molecule/svg.rb +59 -0
- data/lib/distorted-jekyll/molecule/text.rb +74 -0
- data/lib/distorted-jekyll/molecule/video.rb +43 -0
- data/lib/distorted-jekyll/monkey_business/jekyll/cleaner.rb +54 -0
- data/lib/distorted-jekyll/static/font.rb +42 -0
- data/lib/distorted-jekyll/static/image.rb +55 -0
- data/lib/distorted-jekyll/static/lastresort.rb +28 -0
- data/lib/distorted-jekyll/static/pdf.rb +53 -0
- data/lib/distorted-jekyll/static/state.rb +141 -0
- data/lib/distorted-jekyll/static/svg.rb +52 -0
- data/lib/distorted-jekyll/static/text.rb +57 -0
- data/lib/distorted-jekyll/static/video.rb +90 -0
- data/lib/distorted-jekyll/template/13th-style.css +78 -0
- data/lib/distorted-jekyll/template/error_code.liquid +3 -0
- data/lib/distorted-jekyll/template/font.liquid +32 -0
- data/lib/distorted-jekyll/template/image.liquid +32 -0
- data/lib/distorted-jekyll/template/lastresort.liquid +20 -0
- data/lib/distorted-jekyll/template/pdf.liquid +14 -0
- data/lib/distorted-jekyll/template/svg.liquid +32 -0
- data/lib/distorted-jekyll/template/text.liquid +32 -0
- data/lib/distorted-jekyll/template/video.liquid +11 -0
- metadata +41 -6
@@ -0,0 +1,59 @@
|
|
1
|
+
require 'set'
|
2
|
+
|
3
|
+
require 'distorted/svg'
|
4
|
+
require 'distorted-jekyll/static/svg'
|
5
|
+
|
6
|
+
module Jekyll
|
7
|
+
module DistorteD
|
8
|
+
module Molecule
|
9
|
+
module SVG
|
10
|
+
|
11
|
+
# Reference these instead of reassigning them. Consistency is mandatory.
|
12
|
+
MEDIA_TYPE = Cooltrainer::DistorteD::SVG::MEDIA_TYPE
|
13
|
+
SUB_TYPE = Cooltrainer::DistorteD::SVG::SUB_TYPE
|
14
|
+
MIME_TYPES = Cooltrainer::DistorteD::SVG::MIME_TYPES
|
15
|
+
|
16
|
+
ATTRS = Cooltrainer::DistorteD::SVG::ATTRS
|
17
|
+
ATTRS_DEFAULT = Cooltrainer::DistorteD::SVG::ATTRS_DEFAULT
|
18
|
+
ATTRS_VALUES = Cooltrainer::DistorteD::SVG::ATTRS_VALUES
|
19
|
+
|
20
|
+
|
21
|
+
def render_to_output_buffer(context, output)
|
22
|
+
super
|
23
|
+
begin
|
24
|
+
# Liquid doesn't seem able to reference symbolic keys,
|
25
|
+
# so convert everything to string for template.
|
26
|
+
# Not stripping :full tags like Image because all of our
|
27
|
+
# SVG variations will be full-res for now.
|
28
|
+
filez = files.map{ |f|
|
29
|
+
f.transform_values(&:to_s).transform_keys(&:to_s)
|
30
|
+
}
|
31
|
+
output << parse_template.render({
|
32
|
+
'name' => @name,
|
33
|
+
'path' => @dd_dest,
|
34
|
+
'alt' => attr_value(:alt),
|
35
|
+
'title' => attr_value(:title),
|
36
|
+
'href' => attr_value(:href),
|
37
|
+
'caption' => attr_value(:caption),
|
38
|
+
'loading' => attr_value(:loading),
|
39
|
+
'sources' => filez,
|
40
|
+
'fallback_img' => @name,
|
41
|
+
})
|
42
|
+
rescue Liquid::SyntaxError => l
|
43
|
+
unless Jekyll.env == 'production'.freeze
|
44
|
+
output << parse_template(name: 'error_code'.freeze).render({
|
45
|
+
'message' => l.message,
|
46
|
+
})
|
47
|
+
end
|
48
|
+
end
|
49
|
+
output
|
50
|
+
end
|
51
|
+
|
52
|
+
def static_file(*args)
|
53
|
+
Jekyll::DistorteD::Static::SVG.new(*args)
|
54
|
+
end
|
55
|
+
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
@@ -0,0 +1,74 @@
|
|
1
|
+
require 'set'
|
2
|
+
|
3
|
+
require 'distorted/text'
|
4
|
+
require 'distorted-jekyll/static/text'
|
5
|
+
|
6
|
+
module Jekyll
|
7
|
+
module DistorteD
|
8
|
+
module Molecule
|
9
|
+
module Text
|
10
|
+
|
11
|
+
DRIVER = Cooltrainer::DistorteD::Text
|
12
|
+
|
13
|
+
MEDIA_TYPE = DRIVER::MEDIA_TYPE
|
14
|
+
MIME_TYPES = DRIVER::MIME_TYPES
|
15
|
+
|
16
|
+
ATTRS = DRIVER::ATTRS
|
17
|
+
ATTRS_DEFAULT = DRIVER::ATTRS_DEFAULT
|
18
|
+
ATTRS_VALUES = DRIVER::ATTRS_VALUES
|
19
|
+
|
20
|
+
|
21
|
+
def render_to_output_buffer(context, output)
|
22
|
+
super
|
23
|
+
begin
|
24
|
+
filez = files.keep_if{ |f|
|
25
|
+
# Strip out all non-displayable media-types, e.g. the actual text/whatever.
|
26
|
+
f.key?(:type) && f&.dig(:type)&.media_type == 'image'.freeze
|
27
|
+
}.keep_if{ |f|
|
28
|
+
# Strip out full-size images (will have `nil`) — only display thumbnail vers
|
29
|
+
f.key?(:width) or f.key?(:height)
|
30
|
+
}.map{ |f|
|
31
|
+
# Stringify to make Liquid happy
|
32
|
+
f.transform_values(&:to_s).transform_keys(&:to_s)
|
33
|
+
}
|
34
|
+
output << parse_template.render({
|
35
|
+
'name' => @name,
|
36
|
+
'path' => @dd_dest,
|
37
|
+
'alt' => attr_value(:alt),
|
38
|
+
'title' => attr_value(:title),
|
39
|
+
'sources' => filez,
|
40
|
+
'fallback_img' => fallback_img,
|
41
|
+
})
|
42
|
+
rescue Liquid::SyntaxError => l
|
43
|
+
unless Jekyll.env == 'production'.freeze
|
44
|
+
output << parse_template(name: 'error_code'.freeze).render({
|
45
|
+
'message' => l.message,
|
46
|
+
})
|
47
|
+
end
|
48
|
+
end
|
49
|
+
output
|
50
|
+
end
|
51
|
+
|
52
|
+
# Return the filename of the most-compatible output image
|
53
|
+
# for use as the fallback <img> tag inside our <picture>.
|
54
|
+
def fallback_img
|
55
|
+
best_ver = nil
|
56
|
+
files.keep_if{|f| f.key?(:type) && f&.dig(:type)&.media_type == 'image'.freeze}.each{ |f|
|
57
|
+
# PNG > WebP
|
58
|
+
if f&.dig(:type)&.sub_type == 'png'.freeze || best_ver.nil?
|
59
|
+
best_ver = f
|
60
|
+
end
|
61
|
+
}
|
62
|
+
# Return the filename of the biggest matched variation,
|
63
|
+
# otherwise use the original filename.
|
64
|
+
best_ver&.dig(:name) || @name
|
65
|
+
end
|
66
|
+
|
67
|
+
def static_file(*args)
|
68
|
+
Jekyll::DistorteD::Static::Text.new(*args)
|
69
|
+
end
|
70
|
+
|
71
|
+
end # Text
|
72
|
+
end # Molecule
|
73
|
+
end # DistorteD
|
74
|
+
end # Jekyll
|
@@ -0,0 +1,43 @@
|
|
1
|
+
require 'distorted/video'
|
2
|
+
require 'distorted-jekyll/static/video'
|
3
|
+
|
4
|
+
module Jekyll
|
5
|
+
module DistorteD
|
6
|
+
module Molecule
|
7
|
+
module Video
|
8
|
+
|
9
|
+
# Reference these instead of reassigning them. Consistency is mandatory.
|
10
|
+
MEDIA_TYPE = Cooltrainer::DistorteD::Video::MEDIA_TYPE
|
11
|
+
MIME_TYPES = Cooltrainer::DistorteD::Video::MIME_TYPES
|
12
|
+
|
13
|
+
ATTRS = Cooltrainer::DistorteD::Video::ATTRS
|
14
|
+
ATTRS_DEFAULT = Cooltrainer::DistorteD::Video::ATTRS_DEFAULT
|
15
|
+
ATTRS_VALUES = Cooltrainer::DistorteD::Video::ATTRS_VALUES
|
16
|
+
|
17
|
+
def render_to_output_buffer(context, output)
|
18
|
+
super
|
19
|
+
begin
|
20
|
+
output << parse_template.render({
|
21
|
+
'name' => @name,
|
22
|
+
'basename' => File.basename(@name, '.*'),
|
23
|
+
'path' => @url,
|
24
|
+
'caption' => attr_value(:caption),
|
25
|
+
})
|
26
|
+
rescue Liquid::SyntaxError => l
|
27
|
+
unless Jekyll.env == 'production'.freeze
|
28
|
+
output << parse_template(name: 'error_code'.freeze).render({
|
29
|
+
'message' => l.message,
|
30
|
+
})
|
31
|
+
end
|
32
|
+
end
|
33
|
+
output
|
34
|
+
end
|
35
|
+
|
36
|
+
def static_file(*args)
|
37
|
+
Jekyll::DistorteD::Static::Video.new(*args)
|
38
|
+
end
|
39
|
+
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
@@ -0,0 +1,54 @@
|
|
1
|
+
require 'set'
|
2
|
+
|
3
|
+
module Jekyll
|
4
|
+
# Handles the cleanup of a site's destination before it is built or re-built.
|
5
|
+
class Cleaner
|
6
|
+
|
7
|
+
# Private: The list of files to be created when site is built.
|
8
|
+
#
|
9
|
+
# Returns a Set with the file paths
|
10
|
+
#
|
11
|
+
# Monkey-patch this to look for DD's unique `destinations` which is similar
|
12
|
+
# to the original `destination` method except it returns a Set of destination
|
13
|
+
# paths instead of a single destination path.
|
14
|
+
# Do the patch with `define_method` instead of just `def` because the block's
|
15
|
+
# closure of the local scope lets it carry a binding to the original overriden
|
16
|
+
# method which I use to bail out iff the monkey-patch fails.
|
17
|
+
# This is an attempt to avoid breaking future Jekyll versions as much as
|
18
|
+
# possible, since any Exception in the monkey-patched code will just cause
|
19
|
+
# the original Jekyll implementation to be called instead.
|
20
|
+
# The new worst case scenario is slow site builds due to media variation generation!
|
21
|
+
#
|
22
|
+
# If a StaticFile responds to `destinations` then use it and merge the result.
|
23
|
+
# I'm defining my own separate method for multi-destinations for now,
|
24
|
+
# but I also considered just overriding `destination` to return the Set and
|
25
|
+
# then doing this as a one-liner that handles either case (single or
|
26
|
+
# multiple destinations) with `files.merge(Set[*(item.destination(site.dest))])`.
|
27
|
+
# This is the safer choice though since we avoid changing the outout type of the
|
28
|
+
# regular `:destination` method.
|
29
|
+
the_old_new_thing = instance_method(:new_files)
|
30
|
+
define_method(:new_files) do
|
31
|
+
begin
|
32
|
+
@new_files ||= Set.new.tap do |files|
|
33
|
+
site.each_site_file { |item|
|
34
|
+
if item.respond_to?(:destinations)
|
35
|
+
files.merge(item.destinations(site.dest))
|
36
|
+
elsif item.respond_to?(:destination)
|
37
|
+
files << item.destination(site.dest)
|
38
|
+
else
|
39
|
+
# Something unrelated has gone wrong for us to end up sending
|
40
|
+
# `destination` to something that doesn't respond to it.
|
41
|
+
# We should fall back to the original implementation of `new_files`
|
42
|
+
# in this case so the failure doesn't appear to be here.
|
43
|
+
the_old_new_thing.bind(self).()
|
44
|
+
end
|
45
|
+
}
|
46
|
+
end
|
47
|
+
rescue RuntimeError => e
|
48
|
+
Jekyll.logger.warn('DistorteD', "Monkey-patching Jekyll::Cleaner#new_files failed: #{e.message}")
|
49
|
+
Jekyll.logger.debug('DistorteD', "Monkey-patched Jekyll::Cleaner#new_files backtrace: #{e.backtrace}")
|
50
|
+
the_old_new_thing.bind(self).()
|
51
|
+
end
|
52
|
+
end
|
53
|
+
end # Cleaner
|
54
|
+
end # Jekyll
|
@@ -0,0 +1,42 @@
|
|
1
|
+
require 'fileutils'
|
2
|
+
require 'set'
|
3
|
+
|
4
|
+
require 'distorted/font'
|
5
|
+
require 'distorted-jekyll/static/text'
|
6
|
+
|
7
|
+
module Jekyll
|
8
|
+
module DistorteD
|
9
|
+
module Static
|
10
|
+
class Font < Text
|
11
|
+
|
12
|
+
DRIVER = Cooltrainer::DistorteD::Font
|
13
|
+
|
14
|
+
MEDIA_TYPE = DRIVER::MEDIA_TYPE
|
15
|
+
MIME_TYPES = DRIVER::MIME_TYPES
|
16
|
+
|
17
|
+
ATTRS = DRIVER::ATTRS
|
18
|
+
ATTRS_DEFAULT = DRIVER::ATTRS_DEFAULT
|
19
|
+
ATTRS_VALUES = DRIVER::ATTRS_VALUES
|
20
|
+
|
21
|
+
|
22
|
+
# dest: String realpath to `_site` directory
|
23
|
+
def write(dest)
|
24
|
+
orig_dest = destination(dest)
|
25
|
+
|
26
|
+
return false if !modified?
|
27
|
+
self.class.mtimes[path] = mtime
|
28
|
+
|
29
|
+
@distorted = DRIVER.new(
|
30
|
+
path,
|
31
|
+
demo: attr_value(:title),
|
32
|
+
)
|
33
|
+
FileUtils.cp(path, File.join(dd_dest(dest), @name))
|
34
|
+
|
35
|
+
super
|
36
|
+
|
37
|
+
end
|
38
|
+
|
39
|
+
end # Text
|
40
|
+
end # Static
|
41
|
+
end # DistorteD
|
42
|
+
end # Jekyll
|
@@ -0,0 +1,55 @@
|
|
1
|
+
require 'fileutils'
|
2
|
+
require 'set'
|
3
|
+
|
4
|
+
require 'distorted/image'
|
5
|
+
require 'distorted-jekyll/static/state'
|
6
|
+
|
7
|
+
module Jekyll
|
8
|
+
module DistorteD
|
9
|
+
module Static
|
10
|
+
class Image < Jekyll::DistorteD::Static::State
|
11
|
+
|
12
|
+
DRIVER = Cooltrainer::DistorteD::Image
|
13
|
+
|
14
|
+
MEDIA_TYPE = DRIVER::MEDIA_TYPE
|
15
|
+
MIME_TYPES = DRIVER::MIME_TYPES
|
16
|
+
|
17
|
+
ATTRS = DRIVER::ATTRS
|
18
|
+
ATTRS_DEFAULT = DRIVER::ATTRS_DEFAULT
|
19
|
+
ATTRS_VALUES = DRIVER::ATTRS_VALUES
|
20
|
+
|
21
|
+
|
22
|
+
# dest: string realpath to `_site_` directory
|
23
|
+
def write(dest)
|
24
|
+
return false if File.exist?(path) && !modified?
|
25
|
+
self.class.mtimes[path] = mtime
|
26
|
+
|
27
|
+
# Create any directories to the depth of the intended destination.
|
28
|
+
FileUtils.mkdir_p(dd_dest(dest))
|
29
|
+
|
30
|
+
unless defined? @distorted
|
31
|
+
@distorted = DRIVER.new(path)
|
32
|
+
end
|
33
|
+
|
34
|
+
Jekyll.logger.debug(@tag_name, "Rotating #{@name} if tagged.")
|
35
|
+
@distorted.rotate(angle: :auto)
|
36
|
+
|
37
|
+
# Save every desired variation of this image.
|
38
|
+
# This will be a Set of Hashes each describing the name, type,
|
39
|
+
# dimensions, attributes, etc of each output variation we want.
|
40
|
+
# Full-size outputs will have the special tag `:full`.
|
41
|
+
for variation in files
|
42
|
+
if DRIVER::MIME_TYPES.include?(variation&.dig(:type))
|
43
|
+
filename = File.join(dd_dest(dest), variation&.dig(:name) || @name)
|
44
|
+
Jekyll.logger.debug('DistorteD Writing:', filename)
|
45
|
+
@distorted.save(filename, width: variation&.dig(:width), crop: variation&.dig(:crop))
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
true
|
50
|
+
end
|
51
|
+
|
52
|
+
end # Image
|
53
|
+
end # Static
|
54
|
+
end # DistorteD
|
55
|
+
end # Jekyll
|
@@ -0,0 +1,28 @@
|
|
1
|
+
require 'fileutils'
|
2
|
+
require 'set'
|
3
|
+
|
4
|
+
require 'distorted-jekyll/static/state'
|
5
|
+
|
6
|
+
module Jekyll
|
7
|
+
module DistorteD
|
8
|
+
module Static
|
9
|
+
class LastResort < Jekyll::DistorteD::Static::State
|
10
|
+
|
11
|
+
# dest: string realpath to `_site_` directory
|
12
|
+
def write(dest)
|
13
|
+
return false if File.exist?(path) && !modified?
|
14
|
+
self.class.mtimes[path] = mtime
|
15
|
+
|
16
|
+
# Create any directories to the depth of the intended destination.
|
17
|
+
FileUtils.mkdir_p(dd_dest(dest))
|
18
|
+
|
19
|
+
Jekyll.logger.debug(@tag_name, "Copying #{@name} to #{dd_dest(dest)}")
|
20
|
+
FileUtils.cp(path, File.join(dd_dest(dest), @name))
|
21
|
+
|
22
|
+
true
|
23
|
+
end
|
24
|
+
|
25
|
+
end # Image
|
26
|
+
end # Static
|
27
|
+
end # DistorteD
|
28
|
+
end # Jekyll
|
@@ -0,0 +1,53 @@
|
|
1
|
+
require 'fileutils'
|
2
|
+
require 'set'
|
3
|
+
|
4
|
+
require 'distorted/pdf'
|
5
|
+
require 'distorted-jekyll/static/pdf'
|
6
|
+
|
7
|
+
|
8
|
+
module Jekyll
|
9
|
+
module DistorteD
|
10
|
+
module Static
|
11
|
+
class PDF < Jekyll::DistorteD::Static::State
|
12
|
+
|
13
|
+
DRIVER = Cooltrainer::DistorteD::PDF
|
14
|
+
|
15
|
+
MEDIA_TYPE = DRIVER::MEDIA_TYPE
|
16
|
+
SUB_TYPE = DRIVER::SUB_TYPE
|
17
|
+
MIME_TYPES = DRIVER::MIME_TYPES
|
18
|
+
|
19
|
+
ATTRS = DRIVER::ATTRS
|
20
|
+
ATTRS_DEFAULT = DRIVER::ATTRS_DEFAULT
|
21
|
+
ATTRS_VALUES = DRIVER::ATTRS_VALUES
|
22
|
+
|
23
|
+
|
24
|
+
# dest: string realpath to `_site_` directory
|
25
|
+
def write(dest)
|
26
|
+
return false if File.exist?(path) && !modified?
|
27
|
+
self.class.mtimes[path] = mtime
|
28
|
+
|
29
|
+
# Create any directories to the depth of the intended destination.
|
30
|
+
FileUtils.mkdir_p(dd_dest(dest))
|
31
|
+
|
32
|
+
for variation in files
|
33
|
+
if DRIVER::MIME_TYPES.include?(variation[:type])
|
34
|
+
pdf_dest_path = File.join(dd_dest(dest), variation[:name])
|
35
|
+
|
36
|
+
if true # TODO: Make this configurable
|
37
|
+
Jekyll.logger.debug(@tag_name, "Optimizing #{@name} and copying to #{dd_dest(dest)}")
|
38
|
+
# TODO: Make optimizations/plugins configurable
|
39
|
+
DRIVER::optimize(path, pdf_dest_path)
|
40
|
+
else
|
41
|
+
Jekyll.logger.debug(@tag_name, "Copying #{@name} to #{dd_dest(dest)}")
|
42
|
+
FileUtils.cp(path, pdf_dest_path)
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
true
|
48
|
+
end
|
49
|
+
|
50
|
+
end # PDF
|
51
|
+
end # Static
|
52
|
+
end # DistorteD
|
53
|
+
end # Jekyll
|
@@ -0,0 +1,141 @@
|
|
1
|
+
require 'set'
|
2
|
+
|
3
|
+
require 'distorted-jekyll/molecule/abstract'
|
4
|
+
|
5
|
+
|
6
|
+
module Jekyll
|
7
|
+
module DistorteD
|
8
|
+
module Static
|
9
|
+
class State < Jekyll::StaticFile
|
10
|
+
|
11
|
+
include Jekyll::DistorteD::Molecule::Abstract
|
12
|
+
|
13
|
+
def initialize(
|
14
|
+
site,
|
15
|
+
base,
|
16
|
+
dir,
|
17
|
+
name,
|
18
|
+
mime,
|
19
|
+
attrs,
|
20
|
+
dd_dest,
|
21
|
+
url,
|
22
|
+
collection: nil
|
23
|
+
)
|
24
|
+
# e.g. 'DistorteD::Static::Image' or 'DistorteD::Static::Video'
|
25
|
+
@tag_name = self.class.name.split('::').drop(1).join('::').to_sym.freeze
|
26
|
+
|
27
|
+
# String path to Jekyll site root
|
28
|
+
@base = base
|
29
|
+
|
30
|
+
# String container dir (under `base`) of original file
|
31
|
+
@dir = dir
|
32
|
+
|
33
|
+
# String filename of original file
|
34
|
+
@name = name
|
35
|
+
|
36
|
+
# Union Set of MIME::Types between the original media file
|
37
|
+
# and the plugged MediaMolecule.
|
38
|
+
@mime = mime
|
39
|
+
|
40
|
+
# Attributes provided to our Liquid tag
|
41
|
+
@attrs = attrs
|
42
|
+
|
43
|
+
# String path to media generation output dir
|
44
|
+
# under Site.dest (which is currently unknown)
|
45
|
+
@dd_dest = dd_dest
|
46
|
+
|
47
|
+
# String destination URL for the post/page on which the media appears.
|
48
|
+
@url = url
|
49
|
+
|
50
|
+
# Hello yes
|
51
|
+
Jekyll.logger.debug(@tag_name, "#{base}/#{dir}/#{name} -> #{url}})")
|
52
|
+
|
53
|
+
# Construct Jekyll::StaticFile with only the args it takes:
|
54
|
+
super(
|
55
|
+
site,
|
56
|
+
base,
|
57
|
+
dir,
|
58
|
+
name,
|
59
|
+
)
|
60
|
+
end
|
61
|
+
|
62
|
+
def basename
|
63
|
+
File.basename(@name, '.*')
|
64
|
+
end
|
65
|
+
|
66
|
+
def extname
|
67
|
+
File.extname(@name)
|
68
|
+
end
|
69
|
+
|
70
|
+
# Returns the to-be-written path of a single standard StaticFile.
|
71
|
+
# The value returned by this method is only the 'main' or 'original'
|
72
|
+
# (even if modified somehow) file and does not include the
|
73
|
+
# path/filenames of any variations.
|
74
|
+
# This method will be called by jekyll/lib/cleaner#new_files
|
75
|
+
# to generate the list of files that need to be build or rebuilt
|
76
|
+
# for a site. For this reason, this method shouldn't do any kind
|
77
|
+
# of checking the real filesystem, since e.g. its URL-based
|
78
|
+
# destdir might not exist yet if the Site.dest is completely blank.
|
79
|
+
def destination(dest)
|
80
|
+
File.join(dest, @dd_dest, @name)
|
81
|
+
end
|
82
|
+
|
83
|
+
# Return the absolute path to the top-level destination directory
|
84
|
+
# of the currently-working media. This will usually be the same path
|
85
|
+
# as the Jekyll post/page's generated HTML output.
|
86
|
+
def dd_dest(dest)
|
87
|
+
File.join(dest, @dd_dest)
|
88
|
+
end
|
89
|
+
|
90
|
+
# This method will be called by our monkey-patched Jekyll::Cleaner#new_files
|
91
|
+
# in place of the single-destination method usually used.
|
92
|
+
# This allows us to tell Jekyll about more than a single file
|
93
|
+
# that should be kept when regenerating the site.
|
94
|
+
# This makes DistorteD fast!
|
95
|
+
def destinations(dest)
|
96
|
+
# TODO: Make outputting the original file optional. Will need to change
|
97
|
+
# templates, `modified?`s, and `generate`s to do that.
|
98
|
+
filenames.map{|f| File.join(dd_dest(dest), f)} << destination(dest)
|
99
|
+
end
|
100
|
+
|
101
|
+
# HACK HACK HACK
|
102
|
+
# Jekyll does not pass this method a site.dest like it does write() and
|
103
|
+
# others, but I want to be able to short-circuit here if all the
|
104
|
+
# to-be-generated files already exist.
|
105
|
+
def modified?
|
106
|
+
# Assume modified for the sake of freshness :)
|
107
|
+
modified = true
|
108
|
+
|
109
|
+
site_dest = Jekyll::DistorteD::Floor::config(:destination).to_s
|
110
|
+
if Dir.exist?(site_dest)
|
111
|
+
|
112
|
+
dd_dest = dd_dest(site_dest)
|
113
|
+
if Dir.exist?(dd_dest)
|
114
|
+
|
115
|
+
# TODO: Make outputting the original file conditional.
|
116
|
+
# Doing that will require changing the default href handling
|
117
|
+
# in the template, Jekyll::DistorteD::Static::State.destinations,
|
118
|
+
# as well as Cooltrainer::DistorteD::Image.generate
|
119
|
+
wanted_files = Set[@name].merge(filenames)
|
120
|
+
extant_files = Dir.entries(dd_dest).to_set
|
121
|
+
|
122
|
+
# TODO: Make this smarter. It's not enough that all the generated
|
123
|
+
# filenames should exist. Try a few more ways to detect subtler
|
124
|
+
# "changes to the source file since generation of variations.
|
125
|
+
if wanted_files.subset?(extant_files)
|
126
|
+
Jekyll.logger.debug(@name, "All variations present: #{wanted_files}")
|
127
|
+
modified = false
|
128
|
+
else
|
129
|
+
Jekyll.logger.debug(@name, "Missing variations: #{wanted_files - extant_files}")
|
130
|
+
end
|
131
|
+
|
132
|
+
end # dd_dest.exists?
|
133
|
+
end # site_dest.exists?
|
134
|
+
Jekyll.logger.debug("#{@name} modified?", modified)
|
135
|
+
return modified
|
136
|
+
end
|
137
|
+
|
138
|
+
end # state
|
139
|
+
end # Static
|
140
|
+
end # DistorteD
|
141
|
+
end # Jekyll
|