graffik 0.0.1

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.
@@ -0,0 +1,20 @@
1
+ Graffik
2
+ =======
3
+
4
+ Graffik is a fast, light-weight image manipulation library.
5
+
6
+ Example
7
+ -------
8
+
9
+ Graffic::Image('photo.jpg') do |img|
10
+ img.thumbnail(500) do |resized|
11
+ resized.write('thumbnail.jpg')
12
+ end
13
+ end
14
+
15
+ Requirements
16
+ ------------
17
+
18
+ * [FreeImage][1]
19
+
20
+ [1]: http://freeimage.sourceforge.net/ "FreeImage"
@@ -0,0 +1,14 @@
1
+ begin
2
+ require 'jeweler'
3
+ Jeweler::Tasks.new do |gemspec|
4
+ gemspec.name = "graffik"
5
+ gemspec.summary = "Graffik is a fast, light-weight image manipulation library."
6
+ gemspec.description = "Graffik is a Ruby wrapper for the FreeImage library."
7
+ gemspec.email = "jeremy@jeremyboles.com"
8
+ gemspec.homepage = "http://github.com/jeremyboles/Graffik"
9
+ gemspec.authors = ["Jeremy Boles"]
10
+ gemspec.files.exclude '.DS_Store', '.gitignore'
11
+ end
12
+ rescue LoadError
13
+ puts "Jeweler not available. Install it with: gem install jeweler"
14
+ end
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.0.1
@@ -0,0 +1,14 @@
1
+ # Loads mkmf which is used to make makefiles for Ruby extensions
2
+ require 'mkmf'
3
+
4
+ # Add FreeImage
5
+ $LIBS << "-lfreeimage"
6
+
7
+ # Give it a name
8
+ extension_name = 'graffik'
9
+
10
+ # The destination
11
+ dir_config(extension_name)
12
+
13
+ # Do the work
14
+ create_makefile(extension_name)
@@ -0,0 +1,248 @@
1
+ // Include the Ruby headers
2
+ #include "ruby.h"
3
+ #include "freeimage.h"
4
+
5
+ static VALUE rb_mGraffik;
6
+ static VALUE rb_cImage;
7
+
8
+ FIBITMAP *get_instance_image(VALUE self) {
9
+ FIBITMAP *image; // Place to store the image
10
+ Data_Get_Struct(self, FIBITMAP, image); // Load the image data from the instance
11
+
12
+ // Throw error if the image has already been closed
13
+ if (!image) {
14
+ rb_raise(rb_eTypeError, "Image has already been closed");
15
+ }
16
+
17
+ return image;
18
+ }
19
+
20
+ VALUE rb_graffik_close(VALUE self) {
21
+ FIBITMAP *image = get_instance_image(self);
22
+ FreeImage_Unload(image); // Free the image from memory
23
+ DATA_PTR(self) = NULL; // Release the data for Ruby
24
+ return Qnil; // Return nil back
25
+ }
26
+
27
+ VALUE rb_graffik_crop(VALUE self, VALUE rb_left, VALUE rb_top, VALUE rb_right, VALUE rb_bottom) {
28
+ // Convert Ruby numbers to C numbers
29
+ int top = FIX2INT(rb_top), right = FIX2INT(rb_right), bottom = FIX2INT(rb_bottom), left = FIX2INT(rb_left);
30
+ // Load our image and specifiy where to put the copy
31
+ FIBITMAP *image = get_instance_image(self);
32
+ // Crop the image
33
+ FIBITMAP *cropped = FreeImage_Copy(image, left, top, right, bottom);
34
+ // Create a new instance for Ruby
35
+ VALUE instance = Data_Wrap_Struct(CLASS_OF(self), NULL, NULL, cropped);
36
+ rb_iv_set(instance, "@file_type", rb_iv_get(self, "@file_type"));
37
+
38
+ // If a block is given, yield to it, if not, return the instance
39
+ if (rb_block_given_p()) {
40
+ return rb_ensure(rb_yield, instance, rb_graffik_close, instance);
41
+ } else {
42
+ return instance;
43
+ }
44
+ }
45
+
46
+ VALUE rb_graffik_cropped_thumbnail(VALUE self, VALUE rb_size) {
47
+ // Convert the Ruby numbers to C numbers
48
+ int size = FIX2INT(rb_size);
49
+ // Load our image
50
+ FIBITMAP *image = get_instance_image(self);
51
+ // Get dimensions
52
+ int width = FreeImage_GetWidth(image), height = FreeImage_GetHeight(image);
53
+ int left = 0, top = 0, right = width, bottom = height;
54
+ int half = (width - height) / 2;
55
+
56
+ if (width > height) {
57
+ left = half;
58
+ right = half + height;
59
+ }
60
+
61
+ if (height > width) {
62
+ top = half;
63
+ bottom = half + width;
64
+ }
65
+
66
+ // Crop the image
67
+ FIBITMAP *cropped = FreeImage_Copy(image, left, top, right, bottom);
68
+ // Resize the image
69
+ FIBITMAP *thumbnail = FreeImage_MakeThumbnail(cropped, size, TRUE);
70
+ // Create a new instance for Ruby
71
+ VALUE instance = Data_Wrap_Struct(CLASS_OF(self), NULL, NULL, thumbnail);
72
+ rb_iv_set(instance, "@file_type", rb_iv_get(self, "@file_type"));
73
+
74
+ // If a block is given, yield to it, if not, return the instance
75
+ if (rb_block_given_p()) {
76
+ return rb_ensure(rb_yield, instance, rb_graffik_close, instance);
77
+ } else {
78
+ return instance;
79
+ }
80
+ }
81
+
82
+ VALUE rb_graffik_from_memory(VALUE self, VALUE rb_data) {
83
+ FREE_IMAGE_FORMAT fif = FIF_UNKNOWN;
84
+ Check_Type(rb_data, T_STRING);
85
+
86
+ // Get info about our in-memory image
87
+ BYTE *data_ptr = (BYTE *) RSTRING_PTR(rb_data);
88
+ DWORD data_length = RSTRING_LEN(rb_data);
89
+
90
+ // Open up the memory stream
91
+ FIMEMORY *stream = FreeImage_OpenMemory(data_ptr, data_length);
92
+
93
+ // Make sure the stream was open
94
+ if (stream == NULL) {
95
+ rb_raise(rb_eTypeError, "Unable to read image from memory");
96
+ }
97
+
98
+ fif = FreeImage_GetFileTypeFromMemory(stream, 0);
99
+ if ((fif != FIF_UNKNOWN) && FreeImage_FIFSupportsReading(fif)) {
100
+ int flags = ((fif == FIF_JPEG) ? JPEG_ACCURATE : 0);
101
+ // Load the image from disk
102
+ FIBITMAP *image = FreeImage_LoadFromMemory(fif, stream, flags);
103
+ // Release memory
104
+ FreeImage_CloseMemory(stream);
105
+ // Develop an instance for Ruby
106
+ VALUE instance = Data_Wrap_Struct(self, NULL, NULL, image);
107
+ // Store the image type as a FixNum
108
+ rb_iv_set(instance, "@file_type", INT2FIX(fif));
109
+
110
+ // If a block is given, yield to it, if not, return the instance
111
+ if (rb_block_given_p()) {
112
+ return rb_ensure(rb_yield, instance, rb_graffik_close, instance);
113
+ } else {
114
+ return instance;
115
+ }
116
+ }
117
+
118
+ // If we couldn't load it, throw and error
119
+ rb_raise(rb_eTypeError, "Unknown file format");
120
+ }
121
+
122
+ VALUE rb_graffik_height(VALUE self) {
123
+ FIBITMAP *image = get_instance_image(self);
124
+ int height = FreeImage_GetHeight(image); // Height from FreeImage
125
+
126
+ return INT2FIX(height);
127
+ }
128
+
129
+ VALUE rb_graffik_open(VALUE self, VALUE rb_filename) {
130
+ char *filename = STR2CSTR(rb_filename);
131
+ FREE_IMAGE_FORMAT fif = FIF_UNKNOWN;
132
+
133
+ // Try various methods to thet the image format
134
+ fif = FreeImage_GetFileType(filename, 0);
135
+ if (fif == FIF_UNKNOWN) {
136
+ fif = FreeImage_GetFIFFromFilename(filename);
137
+ }
138
+
139
+ if ((fif != FIF_UNKNOWN) && FreeImage_FIFSupportsReading(fif)) {
140
+ int flags = ((fif == FIF_JPEG) ? JPEG_ACCURATE : 0);
141
+ // Load the image from disk
142
+ FIBITMAP *image = FreeImage_Load(fif, filename, flags);
143
+ // Develop an instance for Ruby
144
+ VALUE instance = Data_Wrap_Struct(self, NULL, NULL, image);
145
+ // Store the image type as a FixNum
146
+ rb_iv_set(instance, "@file_type", INT2FIX(fif));
147
+
148
+ // If a block is given, yield to it, if not, return the instance
149
+ if (rb_block_given_p()) {
150
+ return rb_ensure(rb_yield, instance, rb_graffik_close, instance);
151
+ } else {
152
+ return instance;
153
+ }
154
+ }
155
+
156
+ // If we couldn't load it, throw and error
157
+ rb_raise(rb_eTypeError, "Unknown file format");
158
+ }
159
+
160
+ VALUE rb_graffik_resize(VALUE self, VALUE rb_width, VALUE rb_height) {
161
+ // Convert the Ruby numbers to C numbers
162
+ int width = FIX2INT(rb_width), height = FIX2INT(rb_height);
163
+ // Load our image
164
+ FIBITMAP *image = get_instance_image(self);
165
+ // Resize the image
166
+ FIBITMAP *resized = FreeImage_Rescale(image, width, height, FILTER_CATMULLROM);
167
+ // Create a new instance for Ruby
168
+ VALUE instance = Data_Wrap_Struct(CLASS_OF(self), NULL, NULL, resized);
169
+ rb_iv_set(instance, "@file_type", rb_iv_get(self, "@file_type"));
170
+
171
+ // If a block is given, yield to it, if not, return the instance
172
+ if (rb_block_given_p()) {
173
+ return rb_ensure(rb_yield, instance, rb_graffik_close, instance);
174
+ } else {
175
+ return instance;
176
+ }
177
+ }
178
+
179
+ VALUE rb_graffik_thumbnail(VALUE self, VALUE rb_size) {
180
+ // Convert the Ruby numbers to C numbers
181
+ int size = FIX2INT(rb_size);
182
+ // Load our image
183
+ FIBITMAP *image = get_instance_image(self);
184
+ // Resize the image
185
+ FIBITMAP *thumbnail = FreeImage_MakeThumbnail(image, size, TRUE);
186
+ // Create a new instance for Ruby
187
+ VALUE instance = Data_Wrap_Struct(CLASS_OF(self), NULL, NULL, thumbnail);
188
+ rb_iv_set(instance, "@file_type", rb_iv_get(self, "@file_type"));
189
+
190
+ // If a block is given, yield to it, if not, return the instance
191
+ if (rb_block_given_p()) {
192
+ return rb_ensure(rb_yield, instance, rb_graffik_close, instance);
193
+ } else {
194
+ return instance;
195
+ }
196
+ }
197
+
198
+ VALUE rb_graffik_width(VALUE self) {
199
+ FIBITMAP *image = get_instance_image(self);
200
+ int width = FreeImage_GetWidth(image); // Width from FreeImage
201
+
202
+ return INT2FIX(width);
203
+ }
204
+
205
+ VALUE rb_graffik_write(VALUE self, VALUE rb_filename) {
206
+ char *filename = STR2CSTR(rb_filename);
207
+ FREE_IMAGE_FORMAT fif = FIF_UNKNOWN;
208
+
209
+ // Try various methods to get the image format
210
+ fif = FreeImage_GetFIFFromFilename(filename);
211
+ if (fif == FIF_UNKNOWN) {
212
+ fif = FIX2INT(rb_iv_get(self, "@file_type"));
213
+ }
214
+
215
+ if ((fif != FIF_UNKNOWN) && FreeImage_FIFSupportsWriting(fif)) {
216
+ int flags = fif == FIF_JPEG ? JPEG_QUALITYSUPERB : 0;
217
+ // Load the image from the instance
218
+ FIBITMAP *image = get_instance_image(self);
219
+
220
+ // Return Ruby objects for the write status from FreeImage
221
+ return FreeImage_Save(fif, image, filename, flags) ? Qtrue : Qfalse;
222
+ }
223
+
224
+ rb_raise(rb_eTypeError, "Unknown file format");
225
+ }
226
+
227
+ // Intialize extension
228
+ void Init_graffik() {
229
+ // Define the Graffik module
230
+ rb_mGraffik = rb_define_module("Graffik");
231
+
232
+ // Image class
233
+ rb_cImage = rb_define_class_under(rb_mGraffik, "Image", rb_cObject);
234
+
235
+ // Image class methods
236
+ rb_define_singleton_method(rb_cImage, "open", rb_graffik_open, 1);
237
+ rb_define_singleton_method(rb_cImage, "from_memory", rb_graffik_from_memory, 1);
238
+
239
+ // Image instance methods
240
+ rb_define_method(rb_cImage, "crop", rb_graffik_crop, 4);
241
+ rb_define_method(rb_cImage, "cropped_thumbnail", rb_graffik_cropped_thumbnail, 1);
242
+ rb_define_method(rb_cImage, "close", rb_graffik_close, 0);
243
+ rb_define_method(rb_cImage, "height", rb_graffik_height, 0);
244
+ rb_define_method(rb_cImage, "resize", rb_graffik_resize, 2);
245
+ rb_define_method(rb_cImage, "thumbnail", rb_graffik_thumbnail, 1);
246
+ rb_define_method(rb_cImage, "width", rb_graffik_width, 0);
247
+ rb_define_method(rb_cImage, "write", rb_graffik_write, 1);
248
+ }
@@ -0,0 +1,43 @@
1
+ # Generated by jeweler
2
+ # DO NOT EDIT THIS FILE DIRECTLY
3
+ # Instead, edit Jeweler::Tasks in Rakefile, and run the gemspec command
4
+ # -*- encoding: utf-8 -*-
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = %q{graffik}
8
+ s.version = "0.0.1"
9
+
10
+ s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
+ s.authors = ["Jeremy Boles"]
12
+ s.date = %q{2010-06-01}
13
+ s.description = %q{Graffik is a Ruby wrapper for the FreeImage library.}
14
+ s.email = %q{jeremy@jeremyboles.com}
15
+ s.extensions = ["ext/graffik/extconf.rb"]
16
+ s.extra_rdoc_files = [
17
+ "README.markdown"
18
+ ]
19
+ s.files = [
20
+ "README.markdown",
21
+ "Rakefile",
22
+ "VERSION",
23
+ "ext/graffik/extconf.rb",
24
+ "ext/graffik/graffik.c",
25
+ "graffik.gemspec"
26
+ ]
27
+ s.homepage = %q{http://github.com/jeremyboles/Graffik}
28
+ s.rdoc_options = ["--charset=UTF-8"]
29
+ s.require_paths = ["lib"]
30
+ s.rubygems_version = %q{1.3.7}
31
+ s.summary = %q{Graffik is a fast, light-weight image manipulation library.}
32
+
33
+ if s.respond_to? :specification_version then
34
+ current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
35
+ s.specification_version = 3
36
+
37
+ if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
38
+ else
39
+ end
40
+ else
41
+ end
42
+ end
43
+
metadata ADDED
@@ -0,0 +1,72 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: graffik
3
+ version: !ruby/object:Gem::Version
4
+ hash: 29
5
+ prerelease: false
6
+ segments:
7
+ - 0
8
+ - 0
9
+ - 1
10
+ version: 0.0.1
11
+ platform: ruby
12
+ authors:
13
+ - Jeremy Boles
14
+ autorequire:
15
+ bindir: bin
16
+ cert_chain: []
17
+
18
+ date: 2010-06-01 00:00:00 -05:00
19
+ default_executable:
20
+ dependencies: []
21
+
22
+ description: Graffik is a Ruby wrapper for the FreeImage library.
23
+ email: jeremy@jeremyboles.com
24
+ executables: []
25
+
26
+ extensions:
27
+ - ext/graffik/extconf.rb
28
+ extra_rdoc_files:
29
+ - README.markdown
30
+ files:
31
+ - README.markdown
32
+ - Rakefile
33
+ - VERSION
34
+ - ext/graffik/extconf.rb
35
+ - ext/graffik/graffik.c
36
+ - graffik.gemspec
37
+ has_rdoc: true
38
+ homepage: http://github.com/jeremyboles/Graffik
39
+ licenses: []
40
+
41
+ post_install_message:
42
+ rdoc_options:
43
+ - --charset=UTF-8
44
+ require_paths:
45
+ - lib
46
+ required_ruby_version: !ruby/object:Gem::Requirement
47
+ none: false
48
+ requirements:
49
+ - - ">="
50
+ - !ruby/object:Gem::Version
51
+ hash: 3
52
+ segments:
53
+ - 0
54
+ version: "0"
55
+ required_rubygems_version: !ruby/object:Gem::Requirement
56
+ none: false
57
+ requirements:
58
+ - - ">="
59
+ - !ruby/object:Gem::Version
60
+ hash: 3
61
+ segments:
62
+ - 0
63
+ version: "0"
64
+ requirements: []
65
+
66
+ rubyforge_project:
67
+ rubygems_version: 1.3.7
68
+ signing_key:
69
+ specification_version: 3
70
+ summary: Graffik is a fast, light-weight image manipulation library.
71
+ test_files: []
72
+