Module: Cooltrainer::DistorteD::Technology::Vips
- Included in:
- Molecule::Image
- Defined in:
- lib/distorted/modular_technology/vips.rb,
lib/distorted/modular_technology/vips/foreign.rb
Defined Under Namespace
Constant Summary collapse
- TOP_LEVEL_LOADER =
All of the actual Loader/Saver classes we need to interact with will be tree children of one of these top-level class categories:
:VipsForeignLoad
- TOP_LEVEL_SAVER =
:VipsForeignSave
- G_TYPE_VALUES =
This has got to be built in to Ruby-GLib somewhere, right? Remove this if an FFI method is possible to get this mapping.
{ :gboolean => [false, true], :gchararray => String, :gdouble => Float, :gint => Integer, }
- VIPS_ALIASES =
Aliases we want to support for consistency and accessibility.
{ :Q => Set[:Q, :quality], :colours => Set[:colours, :colors], :centre => Set[:centre, :center], # America; FUCK YEAH! }
- VIPS_VALID =
GEnum valid values are detectable, but I don’t know how to do the same for the numeric parameters. Specify them here manually for now.
{ :"page-height" => (0..Vips::MAX_COORD), :"quant-table" => (0..8), :Q => (0..100), :colours => (2..256), :dither => (0.0..1.0), :compression => (0..9), :"alpha-q" => (0..100), :"reduction-effort" => (0..6), :kmin => (0..0x7FFFFFFF), # https://en.wikipedia.org/wiki/2,147,483,647 :kmax => (0..0x7FFFFFFF), :"tile-width" => (0..0x8000), # 32768 :"tile-height" => (0..0x8000), :xres => (0.001..1e+06), :yres => (0.001..1e+06), }
- VIPS_DEFAULT =
Same with default values for numeric parameters.
{ :Q => 75, :colours => 256, :compression => 6, :"alpha-q" => 100, :"reduction-effort" => 4, :kmin => 0x7FFFFFFF - 1, :kmax => 0x7FFFFFFF, :"tile-width" => 128, :"tile-height" => 128, :xres => 1, :yres => 1, }
- @@vips_foreign_types =
Store FFI results where possible to minimize memory churn ‘n’ general fragility.
- @@vips_foreign_suffixes =
- @@vips_foreign_options =
Constants included from Load
Load::LOWER_WORLD, Load::VIPS_LOADERS
Constants included from Save
Save::OUTER_LIMITS, Save::VIPS_SAVERS
Class Method Summary collapse
-
.vips_foreign_find_load_suffix(filename) ⇒ Object
Returns a String libvips Loader class name most appropriate for the given filename suffix.
-
.vips_get_options(nickname) ⇒ Object
Returns a Hash of Compound attributes supported by a given libvips Loader/Saver class.
-
.vips_get_suffixes(basename) ⇒ Object
Returns a Set of String filename suffixes supported by a tree of libvips loader/saver classes.
-
.vips_get_types(basename) ⇒ Object
Returns a Set of MIME::Types based on the “supported suffix” lists generated by libvips and our other functions here in this Module.
Methods included from Load
Class Method Details
.vips_foreign_find_load_suffix(filename) ⇒ Object
Returns a String libvips Loader class name most appropriate for the given filename suffix. This is a workaround for the fact that the built-in Vips::vips_foreign_find_load requires access of a real image file, and we are here talking only of hypothetical ones. See this method’s call site in ‘vips/load’ for more detailed comments on this.
irb(main):234:0> Vips::vips_filename_get_filename(‘fart.jpg’)
> #<FFI::Pointer address=0x0000561efe3d08e0>
irb(main):235:0> Vips::p2str(Vips::vips_filename_get_filename(‘fart.jpg’))
> “fart.jpg”
irb(main):236:0> File.extname(Vips::p2str(Vips::vips_filename_get_filename(‘fart.jpg’)))
> “.jpg”
irb(main):237:0> Vips::vips_foreign_find_save(File.extname(Vips::p2str(Vips::vips_filename_get_filename(‘fart.jpg’))))
> “VipsForeignSaveJpegFile”
Here are the available Operations I have on my laptop with libvips 8.8:
- okeeblow@emi#okeeblow
-
vips -l|grep VipsForeign|grep File
VipsForeignLoadPdfFile (pdfload), load PDF with libpoppler (.pdf), priority=0, is_a, get_flags, get_flags_filename, header, load
VipsForeignLoadSvgFile (svgload), load SVG with rsvg (.svg, .svgz, .svg.gz), priority=0, is_a, get_flags, get_flags_filename, header, load
VipsForeignLoadGifFile (gifload), load GIF with giflib (.gif), priority=0, is_a, get_flags, get_flags_filename, header, load
VipsForeignLoadJpegFile (jpegload), load jpeg from file (.jpg, .jpeg, .jpe), priority=50, is_a, get_flags, header, load
VipsForeignLoadWebpFile (webpload), load webp from file (.webp), priority=0, is_a, get_flags, get_flags_filename, header, load
VipsForeignLoadTiffFile (tiffload), load tiff from file (.tif, .tiff), priority=50, is_a, get_flags, get_flags_filename, header, load
VipsForeignLoadMagickFile (magickload), load file with ImageMagick, priority=-100, is_a, get_flags, get_flags_filename, header
VipsForeignSaveRadFile (radsave), save image to Radiance file (.hdr), priority=0, rgb
VipsForeignSaveDzFile (dzsave), save image to deepzoom file (.dz), priority=0, any
VipsForeignSavePngFile (pngsave), save image to png file (.png), priority=0, rgba
VipsForeignSaveJpegFile (jpegsave), save image to jpeg file (.jpg, .jpeg, .jpe), priority=0, rgb-cmyk
VipsForeignSaveWebpFile (webpsave), save image to webp file (.webp), priority=0, rgba-only
VipsForeignSaveTiffFile (tiffsave), save image to tiff file (.tif, .tiff), priority=0, any
VipsForeignSaveMagickFile (magicksave), save file with ImageMagick (.gif, .bmp), priority=-100, any
You can notice differences such as a ‘dzsave` and `radsave` but no `dzload` or `radload`. This is why we can’t assume that HAS_SAVER == HAS_LOADER across the board. Other differences are invisible here, like different formats supported silently by ‘magickload`, so that Operation is the catch-all fallback if we don’t have any better idea.
We can try taking a MIME::Type’s ‘sub_type`, capitalizing it, and trying to find a Loader Operation by that name. irb(main):254:0> MIME::Types::type_for(’.heif’).last.sub_type.capitalize
> “Heif”
irb(main):255:0> MIME::Types::type_for(‘.jpg’).last.sub_type.capitalize
> “Jpeg”
NOTE: I’m writing this on an old install that lacks HEIF support in its libvips 8.8 installation, so this failure to find ‘VipsForeignLoadHeifFile’ is expected and correct for me! It probably won’t fail for you in the future, but I want to make sure to include some example of varying library capability and not assume capabilities based on libvips version:
irb(main):257:0> GObject::g_type_from_name(“VipsForeignLoad#MIME::Types::type_for(‘.jpg’).last.sub_type.capitalizeFile”)
> 94691057380176
irb(main):258:0> GObject::g_type_from_name(“VipsForeignLoad#MIME::Types::type_for(‘.heif’).last.sub_type.capitalizeFile”)
> 0
154 155 156 157 158 |
# File 'lib/distorted/modular_technology/vips/foreign.rb', line 154 def self.vips_foreign_find_load_suffix(filename) suffix = File.extname(Vips::p2str(Vips::vips_filename_get_filename('fart.jpg'))) guessed_loader = "VipsForeignLoad#{CHECKING::YOU::OUT(suffix).first.sub_type.capitalize}File" return self::vips_foreign_valid_operation?(guessed_loader) ? guessed_loader : 'VipsForeignLoadMagickFile'.freeze end |
.vips_get_options(nickname) ⇒ Object
Returns a Hash of Compound attributes supported by a given libvips Loader/Saver class.
182 183 184 185 |
# File 'lib/distorted/modular_technology/vips/foreign.rb', line 182 def self.(nickname) return Hash if nickname.nil? @@vips_foreign_options[nickname.to_sym] ||= self::(nickname) end |
.vips_get_suffixes(basename) ⇒ Object
Returns a Set of String filename suffixes supported by a tree of libvips loader/saver classes.
The Array returned from self::vips_get_nickname_suffixes will be overloaded with all duplicate suffix possibilities for each Type according to libvips. e.g. This is unrelated to MIME::Type#preferred_extension!!
176 177 178 |
# File 'lib/distorted/modular_technology/vips/foreign.rb', line 176 def self.vips_get_suffixes(basename) @@vips_foreign_suffixes[basename.to_sym] ||= self::vips_get_suffixes_per_nickname(basename).values.each_with_object(Set[]) {|s,n| n.merge(s)} end |
.vips_get_types(basename) ⇒ Object
Returns a Set of MIME::Types based on the “supported suffix” lists generated by libvips and our other functions here in this Module.
163 164 165 166 167 |
# File 'lib/distorted/modular_technology/vips/foreign.rb', line 163 def self.vips_get_types(basename) @@vips_foreign_types[basename.to_sym] ||= self::vips_get_suffixes(basename).each_with_object(Set[]) { |suffix, types| types.merge(CHECKING::YOU::OUT(suffix)) } end |