image_sorcery 1.0.7 → 1.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.
- data/README.markdown +27 -6
- data/lib/gm_support.rb +1 -1
- data/lib/image_sorcery.rb +67 -4
- metadata +28 -6
data/README.markdown
CHANGED
@@ -1,13 +1,13 @@
|
|
1
|
-
Image Sorcery allows you to leverage all three of ImageMagick's command line tools, [mogrify](http://www.imagemagick.org/script/mogrify.php), [convert](http://www.imagemagick.org/script/convert.php), and [identify](http://www.imagemagick.org/script/identify.php), for maximum magickal power and minimum memory consumption! It lets you use GraphicsMagick if that's
|
1
|
+
Image Sorcery allows you to leverage all three of ImageMagick's command line tools, [mogrify](http://www.imagemagick.org/script/mogrify.php), [convert](http://www.imagemagick.org/script/convert.php), and [identify](http://www.imagemagick.org/script/identify.php), for maximum magickal power and minimum memory consumption! It even lets you use GraphicsMagick, too, if that's your thing.
|
2
2
|
|
3
3
|
## Why?
|
4
4
|
|
5
|
-
At [Fol.io](http://fol.io), we
|
5
|
+
At [Fol.io](http://fol.io), we needed server-side image processing to work well and bend to our will. I wrote this because the ImageMagick libraries we tried suffered from at least one of two problems:
|
6
6
|
|
7
7
|
* Large memory consumption/leaking
|
8
|
-
* Didn't expose the entire ImageMagick
|
8
|
+
* Didn't expose the entire ImageMagick API
|
9
9
|
|
10
|
-
|
10
|
+
ImageSorcery doesn't try to be anything more than a wrapper that exposes the full ImageMagick and GraphicsMagick APIs. This makes it small and powerful, eliminating the above problems.
|
11
11
|
|
12
12
|
## Installation
|
13
13
|
|
@@ -15,17 +15,38 @@ Due to the way Image Sorcery was written, it manages to avoid both of these prob
|
|
15
15
|
|
16
16
|
## Code Examples
|
17
17
|
```ruby
|
18
|
-
image =
|
18
|
+
image = ImageSorcery.new("image.png")
|
19
19
|
image.identify # => "image.png PNG 500x500 500x500+0+0 8-bit DirectClass 236KB 0.010u 0:00.010\n"
|
20
20
|
image.manipulate!(scale: "50%") # => true
|
21
21
|
image.dimensions # => { x: 250, y: 250 }
|
22
22
|
image.convert("thumbnail.jpg", quality: 80, crop: "100x100>") # => true
|
23
23
|
```
|
24
|
+
|
25
|
+
```ruby
|
26
|
+
image = ImageSorcery.new("multi-page.pdf")
|
27
|
+
image.filename_changed? # => false
|
28
|
+
image.manipulate!(format: "png", layer: 0) # => true
|
29
|
+
image.filename_changed? # => true
|
30
|
+
image.file # => "multi-page.png"
|
31
|
+
```
|
32
|
+
|
33
|
+
```ruby
|
34
|
+
image = ImageSorcery.new("multi-page.pdf")
|
35
|
+
image.manipulate!(format: "png") # => true
|
36
|
+
image.filename_changed? # => true
|
37
|
+
|
38
|
+
# on ImageMagick it returns all layers as a single file
|
39
|
+
image.file # => "multi-page-*.png"
|
40
|
+
|
41
|
+
# on GrapicksMagick it returns only the fist layer
|
42
|
+
image.file # => "multi-page.png"
|
43
|
+
```
|
44
|
+
|
24
45
|
# Using GraphicsMagick
|
25
46
|
Assuming you have GraphicsMagick installed on your box:
|
26
47
|
|
27
48
|
```ruby
|
28
|
-
image =
|
49
|
+
image = ImageSorcery.gm("image.png")
|
29
50
|
# use as normal
|
30
51
|
```
|
31
52
|
|
data/lib/gm_support.rb
CHANGED
data/lib/image_sorcery.rb
CHANGED
@@ -1,6 +1,8 @@
|
|
1
1
|
require 'gm_support'
|
2
2
|
|
3
|
-
class
|
3
|
+
class ImageSorcery
|
4
|
+
attr_reader :file
|
5
|
+
|
4
6
|
def initialize(file)
|
5
7
|
@file = file
|
6
8
|
end
|
@@ -12,8 +14,10 @@ class Sorcery
|
|
12
14
|
tokens = ["mogrify"]
|
13
15
|
tokens << convert_to_arguments(args) if args
|
14
16
|
tokens << " '#{@file}#{"[#{args[:layer].to_s}]" if args[:layer]}'"
|
17
|
+
tokens << " -annotate #{args[:annotate].to_s}" if args[:annotate]
|
15
18
|
tokens = convert_to_command(tokens)
|
16
19
|
success = run(tokens)[1]
|
20
|
+
replace_file(args[:format].to_s.downcase, args[:layer]) if success && args[:format]
|
17
21
|
success
|
18
22
|
end
|
19
23
|
|
@@ -24,6 +28,7 @@ class Sorcery
|
|
24
28
|
tokens = ["convert"]
|
25
29
|
tokens << convert_to_arguments(args) if args
|
26
30
|
tokens << " '#{@file}#{"[#{args[:layer].to_s}]" if args[:layer]}'"
|
31
|
+
tokens << " -annotate #{args[:annotate].to_s}" if args[:annotate]
|
27
32
|
tokens << " #{output}"
|
28
33
|
tokens = convert_to_command(tokens)
|
29
34
|
success = run(tokens)[1]
|
@@ -46,19 +51,77 @@ class Sorcery
|
|
46
51
|
#
|
47
52
|
def dimensions
|
48
53
|
dimensions = identify(:layer => 0, :format => "%wx%h").chomp.split("x")
|
49
|
-
{ :x => dimensions[0],
|
50
|
-
:y => dimensions[1] }
|
54
|
+
{ :x => dimensions[0].to_i,
|
55
|
+
:y => dimensions[1].to_i }
|
56
|
+
end
|
57
|
+
|
58
|
+
# Returns the x dimension of an image as an integer
|
59
|
+
#
|
60
|
+
def width
|
61
|
+
dimensions()[:x]
|
62
|
+
end
|
63
|
+
|
64
|
+
# Returns the y dimension of an image as an integer
|
65
|
+
#
|
66
|
+
def height
|
67
|
+
dimensions()[:y]
|
68
|
+
end
|
69
|
+
|
70
|
+
# Runs ImageMagick's 'montage'.
|
71
|
+
# See http://www.imagemagick.org/script/montage.php
|
72
|
+
#
|
73
|
+
def montage(sources, args={})
|
74
|
+
tokens = ["montage"]
|
75
|
+
tokens << convert_to_arguments(args) if args
|
76
|
+
sources.each {|source| tokens << " '#{source}'" }
|
77
|
+
tokens << " '#{@file}'"
|
78
|
+
tokens = convert_to_command(tokens)
|
79
|
+
success = run(tokens)[1]
|
80
|
+
end
|
81
|
+
|
82
|
+
def filename_changed?
|
83
|
+
(@filename_changed)
|
51
84
|
end
|
52
85
|
|
53
86
|
private
|
54
87
|
|
88
|
+
# Replaces the old file (with the old file format) with the newly generated one.
|
89
|
+
# The old file will be deleted and $file will be reset.
|
90
|
+
# If ImageMagick generated more than one file, $file will have a "*", so that all files generated
|
91
|
+
# will be manipulated in the following steps.
|
92
|
+
def replace_file(format, layer)
|
93
|
+
return if File.extname(@file) == format
|
94
|
+
|
95
|
+
layer ||= 0
|
96
|
+
layer = layer.split(",").first if layer.is_a? String
|
97
|
+
|
98
|
+
File.delete @file
|
99
|
+
@filename_changed = true
|
100
|
+
|
101
|
+
path = File.join File.dirname(@file), File.basename(@file, File.extname(@file))
|
102
|
+
new_file = find_file path, format, layer
|
103
|
+
|
104
|
+
@file = new_file.call(path, format, "*") unless new_file.nil?
|
105
|
+
end
|
106
|
+
|
107
|
+
def find_file(path, format, layer)
|
108
|
+
possible_paths = [
|
109
|
+
Proc.new { |path, format, layer| "#{path}.#{format}" },
|
110
|
+
Proc.new { |path, format, layer| "#{path}-#{layer}.#{format}" },
|
111
|
+
Proc.new { |path, format, layer| "#{path}.#{format}.#{layer}" }
|
112
|
+
]
|
113
|
+
|
114
|
+
possible_paths.find { |possible_path| File.exists?(possible_path.call(path, format, layer)) }
|
115
|
+
end
|
116
|
+
|
55
117
|
def convert_to_command(tokens)
|
56
118
|
tokens[0] = prefix(tokens[0]) if respond_to? :prefix
|
57
119
|
tokens.flatten.join("")
|
58
120
|
end
|
59
121
|
|
60
122
|
def convert_to_arguments(args)
|
61
|
-
|
123
|
+
special_args = [:layer, :annotate]
|
124
|
+
args.reject {|k, v| special_args.include?(k) }.map {|k, v| " -#{k} '#{v}'"}
|
62
125
|
end
|
63
126
|
|
64
127
|
def run(cmds)
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: image_sorcery
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.0
|
4
|
+
version: 1.1.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -10,9 +10,31 @@ authors:
|
|
10
10
|
autorequire:
|
11
11
|
bindir: bin
|
12
12
|
cert_chain: []
|
13
|
-
date:
|
14
|
-
dependencies:
|
15
|
-
|
13
|
+
date: 2013-01-17 00:00:00.000000000Z
|
14
|
+
dependencies:
|
15
|
+
- !ruby/object:Gem::Dependency
|
16
|
+
name: rspec
|
17
|
+
requirement: &70278859175680 !ruby/object:Gem::Requirement
|
18
|
+
none: false
|
19
|
+
requirements:
|
20
|
+
- - ~>
|
21
|
+
- !ruby/object:Gem::Version
|
22
|
+
version: 2.12.0
|
23
|
+
type: :development
|
24
|
+
prerelease: false
|
25
|
+
version_requirements: *70278859175680
|
26
|
+
- !ruby/object:Gem::Dependency
|
27
|
+
name: rake
|
28
|
+
requirement: &70278859175200 !ruby/object:Gem::Requirement
|
29
|
+
none: false
|
30
|
+
requirements:
|
31
|
+
- - ~>
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: 10.0.2
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: *70278859175200
|
37
|
+
description: A ruby ImageMagick/GraphicsMagick library that doesn't suck
|
16
38
|
email:
|
17
39
|
- hello@ericrafaloff.com
|
18
40
|
- guy@musicglue.com
|
@@ -23,7 +45,7 @@ files:
|
|
23
45
|
- lib/gm_support.rb
|
24
46
|
- lib/image_sorcery.rb
|
25
47
|
- README.markdown
|
26
|
-
homepage: https://github.com/
|
48
|
+
homepage: https://github.com/EricR/image_sorcery
|
27
49
|
licenses: []
|
28
50
|
post_install_message:
|
29
51
|
rdoc_options: []
|
@@ -47,5 +69,5 @@ rubyforge_project:
|
|
47
69
|
rubygems_version: 1.8.10
|
48
70
|
signing_key:
|
49
71
|
specification_version: 3
|
50
|
-
summary: A ruby ImageMagick library that doesn't suck
|
72
|
+
summary: A ruby ImageMagick/GraphicsMagick library that doesn't suck
|
51
73
|
test_files: []
|