Class: Middleman::WebP::Converter
- Inherits:
-
Object
- Object
- Middleman::WebP::Converter
- Defined in:
- lib/middleman-webp/converter.rb
Overview
Handles finding image assets and running them through the conversion using external cwebp and gif2webp commandline tools
Constant Summary collapse
- SUFFIX_RE =
/(jpe?g|png|tiff?|gif)$/i
Instance Method Summary collapse
-
#change_percentage(src_size, dst_size) ⇒ Object
Calculate change percentage of converted file size.
- #convert ⇒ Object
- #convert_images(paths, &_after_conversion) ⇒ Object
- #destination_path(src_path) ⇒ Object
- #exec_convert_tool(src, dst) ⇒ Object
- #image_files ⇒ Object
-
#initialize(app, builder, options = {}) ⇒ Converter
constructor
A new instance of Converter.
-
#number_to_human_size(n) ⇒ Object
Output file size using most human friendly multiple of byte eg.
- #print_summary ⇒ Object
- #reject_file(file) ⇒ Object
-
#tool_for(file) ⇒ Object
Internal: Return proper tool command based on file type.
Constructor Details
Instance Method Details
#change_percentage(src_size, dst_size) ⇒ Object
Calculate change percentage of converted file size
src - File instance of the source dst - File instance of the destination
Examples
change_percentage(100, 75)
# => '25 %'
Returns percentage as string.
82 83 84 85 86 |
# File 'lib/middleman-webp/converter.rb', line 82 def change_percentage(src_size, dst_size) return '0 %' if src_size == 0 format('%g %%', format('%.2f', 100 - 100.0 * dst_size / src_size)) end |
#convert ⇒ Object
17 18 19 20 21 22 23 24 25 26 27 28 29 30 |
# File 'lib/middleman-webp/converter.rb', line 17 def convert @original_size = 0 @converted_size = 0 convert_images(image_files) do |src, dst| next reject_file(dst) if @options.allow_skip && dst.size >= src.size @original_size += src.size @converted_size += dst.size @builder.trigger :created, "#{dst.path} "\ "(#{change_percentage(src.size, dst.size)} smaller)" end print_summary end |
#convert_images(paths, &_after_conversion) ⇒ Object
32 33 34 35 36 37 38 39 40 41 42 43 44 45 |
# File 'lib/middleman-webp/converter.rb', line 32 def convert_images(paths, &_after_conversion) paths.each do |p| begin dst = destination_path(p) exec_convert_tool(p, dst) yield (src_file = File.new(p)), (dest_file = File.new(dst.to_s)) rescue StandardError => e @builder.trigger :error, "Converting #{p} failed", e.backtrace ensure src_file&.close dest_file&.close end end end |
#destination_path(src_path) ⇒ Object
88 89 90 91 92 93 94 95 |
# File 'lib/middleman-webp/converter.rb', line 88 def destination_path(src_path) dst_name = if @options.append_extension "#{src_path.basename}.webp" else src_path.basename.to_s.gsub(SUFFIX_RE, 'webp') end src_path.parent.join(dst_name) end |
#exec_convert_tool(src, dst) ⇒ Object
47 48 49 50 |
# File 'lib/middleman-webp/converter.rb', line 47 def exec_convert_tool(src, dst) cmd = "#{tool_for(src)} #{@options.for(src)} -quiet #{src} -o #{dst}" @builder.thor.run(cmd, verbose: @options.verbose, capture: true) end |
#image_files ⇒ Object
97 98 99 100 101 102 103 104 105 |
# File 'lib/middleman-webp/converter.rb', line 97 def image_files all = ::Middleman::Util.all_files_under(site_dir) images = all.select { |p| p.to_s =~ SUFFIX_RE } # Reject files matching possible ignore patterns @options.ignore.reduce(images) do |arr, matcher| arr.select { |path| !matcher.matches? path } end end |
#number_to_human_size(n) ⇒ Object
Output file size using most human friendly multiple of byte eg. MiB.
n - size in bytes
Examples
number_to_human_size(12345)
# => '12.06 KiB'
Returns string containing size and unit.
118 119 120 121 122 123 124 125 |
# File 'lib/middleman-webp/converter.rb', line 118 def number_to_human_size(n) return "#{n} B" if n <= 0 units = %w(B KiB MiB GiB TiB PiB) exponent = (Math.log(n) / Math.log(1024)).to_i format("%g #{units[exponent]}", format('%.2f', n.to_f / 1024**exponent)) end |
#print_summary ⇒ Object
64 65 66 67 68 69 |
# File 'lib/middleman-webp/converter.rb', line 64 def print_summary savings = @original_size - @converted_size @builder.trigger :webp, '', 'Total conversion savings: '\ "#{number_to_human_size(savings)} "\ "(#{change_percentage(@original_size, @converted_size)})" end |
#reject_file(file) ⇒ Object
59 60 61 62 |
# File 'lib/middleman-webp/converter.rb', line 59 def reject_file(file) @builder.trigger :deleted, "#{file.path} skipped" File.unlink(file) end |
#tool_for(file) ⇒ Object
Internal: Return proper tool command based on file type
file - Filename
55 56 57 |
# File 'lib/middleman-webp/converter.rb', line 55 def tool_for(file) file.to_s =~ /gif$/i ? 'gif2webp' : 'cwebp' end |