oily_png 0.3.0 → 1.0.0.beta1

Sign up to get free protection for your applications and to get access to all the features.
data/.gitignore CHANGED
@@ -4,6 +4,7 @@ Makefile
4
4
  *.o
5
5
  *.rbc
6
6
  /.bundle/
7
+ Gemfile.lock
7
8
  /pkg
8
9
  oily_png-*.gem
9
10
  .DS_Store
data/.infinity_test CHANGED
@@ -6,4 +6,18 @@ infinity_test do
6
6
  environment.system('bundle install')
7
7
  environment.system('rake compile')
8
8
  end
9
+
10
+ after(:each_ruby) do |environment|
11
+ environment.system("rake clean_and_clobber_without_verbose")
12
+ end
13
+
14
+ heuristics do
15
+ add("^ext/*/(.*)\.c") do |file|
16
+ run :all => :tests
17
+ end
18
+
19
+ add("^ext/*/(.*)\.h") do |file|
20
+ run :all => :tests
21
+ end
22
+ end
9
23
  end
data/Rakefile CHANGED
@@ -1,19 +1,9 @@
1
- require 'rubygems'
2
- require 'bundler'
3
-
4
- Bundler.setup
5
-
6
1
  Dir['tasks/*.rake'].each { |file| load(file) }
7
2
 
8
3
  require 'rake/extensiontask'
9
4
 
10
- def gemspec
11
- @clean_gemspec ||= eval(File.read(File.expand_path('../oily_png.gemspec', __FILE__)))
12
- end
13
-
14
- GithubGem::RakeTasks.new(:gem)
15
-
16
- Rake::ExtensionTask.new('oily_png', gemspec) do |ext|
5
+ gem_management_tasks = GithubGem::RakeTasks.new(:gem)
6
+ Rake::ExtensionTask.new('oily_png', gem_management_tasks.gemspec) do |ext|
17
7
  ext.lib_dir = File.join('lib', 'oily_png')
18
8
  end
19
9
 
@@ -17,14 +17,15 @@
17
17
  #define OILY_PNG_FILTER_AVERAGE 3
18
18
  #define OILY_PNG_FILTER_PAETH 4
19
19
 
20
- // Type definitions
21
- #define PIXEL unsigned int // Pixels use 32 bits unsigned integers
22
- #define BYTE unsigned char // Bytes use 8 bits unsigned integers
23
-
20
+ // Macro to surpress warnings about unused parameters.
24
21
  #define UNUSED_PARAMETER(param) (void) param
25
22
 
26
- #include <png_decoding.h>
27
- #include <png_encoding.h>
23
+ // Type definitions
24
+ typedef unsigned int PIXEL; // Pixels use 32 bits unsigned integers
25
+ typedef unsigned char BYTE; // Bytes use 8 bits unsigned integers
26
+
27
+ #include "png_decoding.h"
28
+ #include "png_encoding.h"
28
29
 
29
30
 
30
31
  /*
@@ -1,4 +1,9 @@
1
- #include <oily_png_ext.h>
1
+ #include "oily_png_ext.h"
2
+
3
+
4
+ /////////////////////////////////////////////////////////////////////
5
+ // UNFILTERING SCANLINES
6
+ /////////////////////////////////////////////////////////////////////
2
7
 
3
8
 
4
9
  // Decodes a SUB filtered scanline at the given position in the byte array
@@ -48,6 +53,11 @@ void oily_png_decode_filter_paeth(BYTE* bytes, long pos, long line_size, char pi
48
53
  }
49
54
  }
50
55
 
56
+ /////////////////////////////////////////////////////////////////////
57
+ // BIT HANDLING
58
+ /////////////////////////////////////////////////////////////////////
59
+
60
+
51
61
  BYTE oily_png_extract_1bit_element(BYTE* bytes, long start, long x) {
52
62
  BYTE byte = bytes[start + 1 + (x >> 3)];
53
63
  char bitshift = 7 - (x & (BYTE) 0x07);
@@ -100,152 +110,210 @@ BYTE oily_png_resample_4bit_element(BYTE* bytes, long start, long x) {
100
110
  }
101
111
  }
102
112
 
113
+ /////////////////////////////////////////////////////////////////////
114
+ // PIXEL DECODING SCANLINES
115
+ /////////////////////////////////////////////////////////////////////
103
116
 
104
- PIXEL oily_png_decode_pixel_indexed_8bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
105
- return (PIXEL) NUM2UINT(rb_funcall(decoding_palette, rb_intern("[]"), 1, INT2FIX(bytes[start + 1 + x])));
106
- }
107
117
 
108
- PIXEL oily_png_decode_pixel_indexed_4bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
109
- return (PIXEL) NUM2UINT(rb_funcall(decoding_palette, rb_intern("[]"), 1, INT2FIX(oily_png_extract_4bit_element(bytes, start, x))));
118
+ void oily_png_decode_scanline_grayscale_1bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
119
+ UNUSED_PARAMETER(decoding_palette);
120
+ long x;
121
+ for (x = 0; x < width; x++) {
122
+ ADD_PIXEL_FROM_RGBA(pixels,
123
+ oily_png_resample_1bit_element(bytes, start, x),
124
+ oily_png_resample_1bit_element(bytes, start, x),
125
+ oily_png_resample_1bit_element(bytes, start, x),
126
+ 0xff);
127
+ }
110
128
  }
111
129
 
112
- PIXEL oily_png_decode_pixel_indexed_2bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
113
- return (PIXEL) NUM2UINT(rb_funcall(decoding_palette, rb_intern("[]"), 1, INT2FIX(oily_png_extract_2bit_element(bytes, start, x))));
130
+ void oily_png_decode_scanline_grayscale_2bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
131
+ UNUSED_PARAMETER(decoding_palette);
132
+ long x;
133
+ for (x = 0; x < width; x++) {
134
+ ADD_PIXEL_FROM_RGBA(pixels,
135
+ oily_png_resample_2bit_element(bytes, start, x),
136
+ oily_png_resample_2bit_element(bytes, start, x),
137
+ oily_png_resample_2bit_element(bytes, start, x),
138
+ 0xff);
139
+ }
114
140
  }
115
141
 
116
- PIXEL oily_png_decode_pixel_indexed_1bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
117
- return (PIXEL) NUM2UINT(rb_funcall(decoding_palette, rb_intern("[]"), 1, INT2FIX(oily_png_extract_1bit_element(bytes, start, x))));
142
+ void oily_png_decode_scanline_grayscale_4bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
143
+ UNUSED_PARAMETER(decoding_palette);
144
+ long x;
145
+ for (x = 0; x < width; x++) {
146
+ ADD_PIXEL_FROM_RGBA(pixels,
147
+ oily_png_resample_4bit_element(bytes, start, x),
148
+ oily_png_resample_4bit_element(bytes, start, x),
149
+ oily_png_resample_4bit_element(bytes, start, x),
150
+ 0xff);
151
+ }
118
152
  }
119
153
 
120
-
121
- PIXEL oily_png_decode_pixel_grayscale_8bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
154
+ void oily_png_decode_scanline_grayscale_8bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
122
155
  UNUSED_PARAMETER(decoding_palette);
123
- return BUILD_PIXEL( bytes[start + 1 + x],
124
- bytes[start + 1 + x],
125
- bytes[start + 1 + x],
126
- 0xff);
156
+ long x;
157
+ for (x = 0; x < width; x++) {
158
+ ADD_PIXEL_FROM_RGBA(pixels,
159
+ bytes[start + 1 + x],
160
+ bytes[start + 1 + x],
161
+ bytes[start + 1 + x],
162
+ 0xff);
163
+ }
127
164
  }
128
165
 
129
- PIXEL oily_png_decode_pixel_grayscale_1bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
166
+ void oily_png_decode_scanline_grayscale_16bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
130
167
  UNUSED_PARAMETER(decoding_palette);
131
- return BUILD_PIXEL( oily_png_resample_1bit_element(bytes, start, x),
132
- oily_png_resample_1bit_element(bytes, start, x),
133
- oily_png_resample_1bit_element(bytes, start, x),
134
- 0xff);
168
+ long x;
169
+ for (x = 0; x < width; x++) {
170
+ ADD_PIXEL_FROM_RGBA(pixels,
171
+ bytes[start + 1 + (x * 2)],
172
+ bytes[start + 1 + (x * 2)],
173
+ bytes[start + 1 + (x * 2)],
174
+ 0xff);
175
+ }
135
176
  }
136
177
 
137
- PIXEL oily_png_decode_pixel_grayscale_2bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
178
+ void oily_png_decode_scanline_grayscale_alpha_8bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
138
179
  UNUSED_PARAMETER(decoding_palette);
139
- return BUILD_PIXEL( oily_png_resample_2bit_element(bytes, start, x),
140
- oily_png_resample_2bit_element(bytes, start, x),
141
- oily_png_resample_2bit_element(bytes, start, x),
142
- 0xff);
180
+ long x;
181
+ for (x = 0; x < width; x++) {
182
+ ADD_PIXEL_FROM_RGBA(pixels,
183
+ bytes[start + 1 + (x * 2) + 0],
184
+ bytes[start + 1 + (x * 2) + 0],
185
+ bytes[start + 1 + (x * 2) + 0],
186
+ bytes[start + 1 + (x * 2) + 1]);
187
+ }
143
188
  }
144
189
 
145
- PIXEL oily_png_decode_pixel_grayscale_4bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
190
+ void oily_png_decode_scanline_grayscale_alpha_16bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
146
191
  UNUSED_PARAMETER(decoding_palette);
147
- return BUILD_PIXEL( oily_png_resample_4bit_element(bytes, start, x),
148
- oily_png_resample_4bit_element(bytes, start, x),
149
- oily_png_resample_4bit_element(bytes, start, x),
150
- 0xff);
192
+ long x;
193
+ for (x = 0; x < width; x++) {
194
+ ADD_PIXEL_FROM_RGBA(pixels,
195
+ bytes[start + 1 + (x * 4) + 0],
196
+ bytes[start + 1 + (x * 4) + 0],
197
+ bytes[start + 1 + (x * 4) + 0],
198
+ bytes[start + 1 + (x * 4) + 2]);
199
+ }
151
200
  }
152
201
 
153
- PIXEL oily_png_decode_pixel_truecolor_8bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
154
- UNUSED_PARAMETER(decoding_palette);
155
- return BUILD_PIXEL( bytes[start + 1 + (x * 3) + 0],
156
- bytes[start + 1 + (x * 3) + 1],
157
- bytes[start + 1 + (x * 3) + 2],
158
- 0xff);
202
+ void oily_png_decode_scanline_indexed_1bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
203
+ long x;
204
+ for (x = 0; x < width; x++) {
205
+ ADD_PIXEL_FROM_PALLETE(pixels, decoding_palette, oily_png_extract_1bit_element(bytes, start, x));
206
+ }
159
207
  }
160
208
 
161
- PIXEL oily_png_decode_pixel_grayscale_alpha_8bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
162
- UNUSED_PARAMETER(decoding_palette);
163
- return BUILD_PIXEL( bytes[start + 1 + (x * 2) + 0],
164
- bytes[start + 1 + (x * 2) + 0],
165
- bytes[start + 1 + (x * 2) + 0],
166
- bytes[start + 1 + (x * 2) + 1]);
209
+ void oily_png_decode_scanline_indexed_2bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
210
+ long x;
211
+ for (x = 0; x < width; x++) {
212
+ ADD_PIXEL_FROM_PALLETE(pixels, decoding_palette, oily_png_extract_2bit_element(bytes, start, x));
213
+ }
167
214
  }
168
215
 
169
- PIXEL oily_png_decode_pixel_truecolor_alpha_8bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
170
- UNUSED_PARAMETER(decoding_palette);
171
- return BUILD_PIXEL( bytes[start + 1 + (x * 4) + 0],
172
- bytes[start + 1 + (x * 4) + 1],
173
- bytes[start + 1 + (x * 4) + 2],
174
- bytes[start + 1 + (x * 4) + 3]);
216
+ void oily_png_decode_scanline_indexed_4bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
217
+ long x;
218
+ for (x = 0; x < width; x++) {
219
+ ADD_PIXEL_FROM_PALLETE(pixels, decoding_palette, oily_png_extract_4bit_element(bytes, start, x));
220
+ }
175
221
  }
176
222
 
177
- PIXEL oily_png_decode_pixel_grayscale_16bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
178
- UNUSED_PARAMETER(decoding_palette);
179
- return BUILD_PIXEL( bytes[start + 1 + (x * 2)],
180
- bytes[start + 1 + (x * 2)],
181
- bytes[start + 1 + (x * 2)],
182
- 0xff);
223
+ void oily_png_decode_scanline_indexed_8bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
224
+ long x;
225
+ for (x = 0; x < width; x++) {
226
+ ADD_PIXEL_FROM_PALLETE(pixels, decoding_palette, bytes[start + 1 + x]);
227
+ }
183
228
  }
184
229
 
185
- PIXEL oily_png_decode_pixel_truecolor_16bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
230
+ void oily_png_decode_scanline_truecolor_8bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
186
231
  UNUSED_PARAMETER(decoding_palette);
187
- return BUILD_PIXEL( bytes[start + 1 + (x * 6) + 0],
188
- bytes[start + 1 + (x * 6) + 2],
189
- bytes[start + 1 + (x * 6) + 4],
190
- 0xff);
232
+ long x;
233
+ for (x = 0; x < width; x++) {
234
+ ADD_PIXEL_FROM_RGBA(pixels,
235
+ bytes[start + 1 + (x * 3) + 0],
236
+ bytes[start + 1 + (x * 3) + 1],
237
+ bytes[start + 1 + (x * 3) + 2],
238
+ 0xff);
239
+ }
191
240
  }
192
241
 
193
- PIXEL oily_png_decode_pixel_grayscale_alpha_16bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
242
+ void oily_png_decode_scanline_truecolor_16bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
194
243
  UNUSED_PARAMETER(decoding_palette);
195
- return BUILD_PIXEL( bytes[start + 1 + (x * 4) + 0],
196
- bytes[start + 1 + (x * 4) + 0],
197
- bytes[start + 1 + (x * 4) + 0],
198
- bytes[start + 1 + (x * 4) + 2]);
244
+ long x;
245
+ for (x = 0; x < width; x++) {
246
+ ADD_PIXEL_FROM_RGBA(pixels,
247
+ bytes[start + 1 + (x * 6) + 0],
248
+ bytes[start + 1 + (x * 6) + 2],
249
+ bytes[start + 1 + (x * 6) + 4],
250
+ 0xff);
251
+ }
199
252
  }
200
253
 
201
- PIXEL oily_png_decode_pixel_truecolor_alpha_16bit(BYTE* bytes, long start, long x, VALUE decoding_palette) {
254
+ void oily_png_decode_scanline_truecolor_alpha_8bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
202
255
  UNUSED_PARAMETER(decoding_palette);
203
- return BUILD_PIXEL( bytes[start + 1 + (x * 8) + 0],
204
- bytes[start + 1 + (x * 8) + 2],
205
- bytes[start + 1 + (x * 8) + 4],
206
- bytes[start + 1 + (x * 8) + 6]);
256
+ long x;
257
+ for (x = 0; x < width; x++) {
258
+ ADD_PIXEL_FROM_RGBA(pixels,
259
+ bytes[start + 1 + (x * 4) + 0],
260
+ bytes[start + 1 + (x * 4) + 1],
261
+ bytes[start + 1 + (x * 4) + 2],
262
+ bytes[start + 1 + (x * 4) + 3]);
263
+ }
207
264
  }
208
265
 
266
+ void oily_png_decode_scanline_truecolor_alpha_16bit(VALUE pixels, BYTE* bytes, long start, long width, VALUE decoding_palette) {
267
+ UNUSED_PARAMETER(decoding_palette);
268
+ long x;
269
+ for (x = 0; x < width; x++) {
270
+ ADD_PIXEL_FROM_RGBA(pixels,
271
+ bytes[start + 1 + (x * 8) + 0],
272
+ bytes[start + 1 + (x * 8) + 2],
273
+ bytes[start + 1 + (x * 8) + 4],
274
+ bytes[start + 1 + (x * 8) + 6]);
275
+ }
276
+ }
209
277
 
210
- pixel_decoder_func oily_png_decode_pixel_func(int color_mode, int bit_depth) {
278
+ scanline_decoder_func oily_png_decode_scanline_func(int color_mode, int bit_depth) {
211
279
  switch (color_mode) {
212
280
  case OILY_PNG_COLOR_GRAYSCALE:
213
281
  switch (bit_depth) {
214
- case 1: return &oily_png_decode_pixel_grayscale_1bit;
215
- case 2: return &oily_png_decode_pixel_grayscale_2bit;
216
- case 4: return &oily_png_decode_pixel_grayscale_4bit;
217
- case 8: return &oily_png_decode_pixel_grayscale_8bit;
218
- case 16: return &oily_png_decode_pixel_grayscale_16bit;
282
+ case 1: return &oily_png_decode_scanline_grayscale_1bit;
283
+ case 2: return &oily_png_decode_scanline_grayscale_2bit;
284
+ case 4: return &oily_png_decode_scanline_grayscale_4bit;
285
+ case 8: return &oily_png_decode_scanline_grayscale_8bit;
286
+ case 16: return &oily_png_decode_scanline_grayscale_16bit;
219
287
  default: return NULL;
220
288
  }
221
289
 
222
290
  case OILY_PNG_COLOR_TRUECOLOR:
223
291
  switch (bit_depth) {
224
- case 8: return &oily_png_decode_pixel_truecolor_8bit;
225
- case 16: return &oily_png_decode_pixel_truecolor_16bit;
292
+ case 8: return &oily_png_decode_scanline_truecolor_8bit;
293
+ case 16: return &oily_png_decode_scanline_truecolor_16bit;
226
294
  default: return NULL;
227
295
  }
228
296
 
229
297
  case OILY_PNG_COLOR_INDEXED:
230
298
  switch (bit_depth) {
231
- case 1: return &oily_png_decode_pixel_indexed_1bit;
232
- case 2: return &oily_png_decode_pixel_indexed_2bit;
233
- case 4: return &oily_png_decode_pixel_indexed_4bit;
234
- case 8: return &oily_png_decode_pixel_indexed_8bit;
299
+ case 1: return &oily_png_decode_scanline_indexed_1bit;
300
+ case 2: return &oily_png_decode_scanline_indexed_2bit;
301
+ case 4: return &oily_png_decode_scanline_indexed_4bit;
302
+ case 8: return &oily_png_decode_scanline_indexed_8bit;
235
303
  default: return NULL;
236
304
  }
237
305
 
238
- case OILY_PNG_COLOR_GRAYSCALE_ALPHA:
306
+ case OILY_PNG_COLOR_GRAYSCALE_ALPHA:
239
307
  switch (bit_depth) {
240
- case 8: return &oily_png_decode_pixel_grayscale_alpha_8bit;
241
- case 16: return &oily_png_decode_pixel_grayscale_alpha_16bit;
308
+ case 8: return &oily_png_decode_scanline_grayscale_alpha_8bit;
309
+ case 16: return &oily_png_decode_scanline_grayscale_alpha_16bit;
242
310
  default: return NULL;
243
311
  }
244
312
 
245
313
  case OILY_PNG_COLOR_TRUECOLOR_ALPHA:
246
314
  switch (bit_depth) {
247
- case 8: return &oily_png_decode_pixel_truecolor_alpha_8bit;
248
- case 16: return &oily_png_decode_pixel_truecolor_alpha_16bit;
315
+ case 8: return &oily_png_decode_scanline_truecolor_alpha_8bit;
316
+ case 16: return &oily_png_decode_scanline_truecolor_alpha_16bit;
249
317
  default: return NULL;
250
318
  }
251
319
 
@@ -253,6 +321,22 @@ pixel_decoder_func oily_png_decode_pixel_func(int color_mode, int bit_depth) {
253
321
  }
254
322
  }
255
323
 
324
+ /////////////////////////////////////////////////////////////////////
325
+ // DECODING AN IMAGE PASS
326
+ /////////////////////////////////////////////////////////////////////
327
+
328
+ VALUE oily_png_decode_palette(VALUE self) {
329
+ VALUE palette_instance = rb_funcall(self, rb_intern("decoding_palette"), 0);
330
+ if (palette_instance != Qnil) {
331
+ VALUE decoding_map = rb_iv_get(palette_instance, "@decoding_map");
332
+ if (rb_funcall(decoding_map, rb_intern("kind_of?"), 1, rb_cArray) == Qtrue) {
333
+ return decoding_map;
334
+ }
335
+ }
336
+ rb_raise(rb_eRuntimeError, "Could not retrieve a decoding palette for this image!");
337
+ }
338
+
339
+
256
340
  VALUE oily_png_decode_png_image_pass(VALUE self, VALUE stream, VALUE width, VALUE height, VALUE color_mode, VALUE depth, VALUE start_pos) {
257
341
 
258
342
  VALUE pixels = rb_ary_new();
@@ -276,20 +360,16 @@ VALUE oily_png_decode_png_image_pass(VALUE self, VALUE stream, VALUE width, VALU
276
360
  // Get the decoding palette for indexed images.
277
361
  VALUE decoding_palette = Qnil;
278
362
  if (FIX2INT(color_mode) == OILY_PNG_COLOR_INDEXED) {
279
- decoding_palette = rb_funcall(self, rb_intern("decoding_palette"), 0);
280
- }
363
+ decoding_palette = oily_png_decode_palette(self);
364
+ }
281
365
 
282
- // Select the pixel decoder function for this color mode.
283
- PIXEL (*pixel_decoder)(BYTE*, long, long, VALUE) = NULL;
284
- pixel_decoder = oily_png_decode_pixel_func(FIX2INT(color_mode), FIX2INT(depth));
285
-
286
- if (pixel_decoder == NULL) {
366
+ // Select the scanline decoder function for this color mode and bit depth.
367
+ scanline_decoder_func scanline_decoder = oily_png_decode_scanline_func(FIX2INT(color_mode), FIX2INT(depth));
368
+ if (scanline_decoder == NULL) {
287
369
  rb_raise(rb_eRuntimeError, "No decoder for color mode %d and bit depth %d", FIX2INT(color_mode), FIX2INT(depth));
288
370
  }
289
371
 
290
- long y, x, line_start;
291
- PIXEL pixel;
292
-
372
+ long y, line_start;
293
373
  for (y = 0; y < FIX2LONG(height); y++) {
294
374
  line_start = y * line_size;
295
375
 
@@ -305,12 +385,7 @@ VALUE oily_png_decode_png_image_pass(VALUE self, VALUE stream, VALUE width, VALU
305
385
 
306
386
  // Set the filter byte to 0 because the bytearray is now unfiltered.
307
387
  bytes[line_start] = OILY_PNG_FILTER_NONE;
308
-
309
- // Now, iterate over all bytes in this line and convert them into pixels
310
- for (x = 0; x < FIX2LONG(width); x++) {
311
- pixel = pixel_decoder(bytes, line_start, x, decoding_palette);
312
- rb_ary_store(pixels, FIX2LONG(width) * y + x, UINT2NUM(pixel));
313
- }
388
+ scanline_decoder(pixels, bytes, line_start, FIX2LONG(width), decoding_palette);
314
389
  }
315
390
  }
316
391
 
@@ -1,12 +1,21 @@
1
1
  #ifndef PNG_DECODING_H
2
2
  #define PNG_DECODING_H
3
3
 
4
- #define BUILD_PIXEL(r, g, b, a) (((PIXEL) r << 24) + ((PIXEL) g << 16) + ((PIXEL) b << 8) + (PIXEL) a)
4
+ #define BUILD_PIXEL(r, g, b, a) (((PIXEL) (r) << 24) + ((PIXEL) (g) << 16) + ((PIXEL) (b) << 8) + (PIXEL) (a))
5
5
  #define UNFILTER_BYTE(byte, adjustment) byte = (BYTE) (((byte) + (adjustment)) & 0x000000ff)
6
6
 
7
- typedef PIXEL(*pixel_decoder_func)(BYTE*, long, long, VALUE);
7
+ #define ADD_PIXEL_FROM_PALLETE(pixels, decoding_palette, palette_entry) \
8
+ if (RARRAY_LEN(decoding_palette) > (palette_entry)) { \
9
+ rb_ary_push(pixels, rb_ary_entry(decoding_palette, (palette_entry))); \
10
+ } else { \
11
+ rb_raise(rb_eRuntimeError, "The decoding palette does not have %d entries!", (palette_entry)); \
12
+ }
13
+
14
+ #define ADD_PIXEL_FROM_RGBA(pixels, r, g, b, a) rb_ary_push(pixels, UINT2NUM(BUILD_PIXEL(r,g,b,a)));
8
15
 
9
16
 
17
+ typedef void(*scanline_decoder_func)(VALUE, BYTE*, long, long, VALUE);
18
+
10
19
  /*
11
20
  Decodes an image pass from the given byte stream at the given position.
12
21
  A normal PNG will only have one pass that consumes the entire stream, while an
@@ -1,4 +1,4 @@
1
- #include <oily_png_ext.h>
1
+ #include "oily_png_ext.h"
2
2
 
3
3
  ///// Scanline filtering functions //////////////////////////////////////////
4
4
 
@@ -47,7 +47,52 @@ void oily_png_encode_filter_paeth(BYTE* bytes, long pos, long line_size, char pi
47
47
  ///// Scanline encoding functions //////////////////////////////////////////
48
48
 
49
49
  // Assume R == G == B. ChunkyPNG uses the B byte fot performance reasons.
50
- // We'll uses the same to reomain compatible with ChunkyPNG.
50
+ // We'll uses the same to remain compatible with ChunkyPNG.
51
+ void oily_png_encode_scanline_grayscale_1bit(BYTE* bytes, VALUE pixels, long y, long width, VALUE encoding_palette) {
52
+ UNUSED_PARAMETER(encoding_palette);
53
+ long x; BYTE p1, p2, p3, p4, p5, p6, p7, p8;
54
+ for (x = 0; x < width; x += 8) {
55
+ p1 = (x + 0 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 0))) >> 7);
56
+ p2 = (x + 1 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 1))) >> 7);
57
+ p3 = (x + 2 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 2))) >> 7);
58
+ p4 = (x + 3 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 3))) >> 7);
59
+ p5 = (x + 4 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 4))) >> 7);
60
+ p6 = (x + 5 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 5))) >> 7);
61
+ p7 = (x + 6 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 6))) >> 7);
62
+ p8 = (x + 7 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 7))) >> 7);
63
+ bytes[x >> 3] = (BYTE) ((p1 << 7) | (p2 << 6) | (p3 << 5) | (p4 << 4) | (p5 << 3) | (p6 << 2) | (p7 << 1) | (p8));
64
+ }
65
+ }
66
+
67
+
68
+ // Assume R == G == B. ChunkyPNG uses the B byte fot performance reasons.
69
+ // We'll uses the same to remain compatible with ChunkyPNG.
70
+ void oily_png_encode_scanline_grayscale_2bit(BYTE* bytes, VALUE pixels, long y, long width, VALUE encoding_palette) {
71
+ UNUSED_PARAMETER(encoding_palette);
72
+ long x; BYTE p1, p2, p3, p4;
73
+ for (x = 0; x < width; x += 4) {
74
+ p1 = (x + 0 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 0))) >> 6);
75
+ p2 = (x + 1 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 1))) >> 6);
76
+ p3 = (x + 2 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 2))) >> 6);
77
+ p4 = (x + 3 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 3))) >> 6);
78
+ bytes[x >> 2] = (BYTE) ((p1 << 6) | (p2 << 4) | (p3 << 2) | (p4));
79
+ }
80
+ }
81
+
82
+ // Assume R == G == B. ChunkyPNG uses the B byte fot performance reasons.
83
+ // We'll uses the same to remain compatible with ChunkyPNG.
84
+ void oily_png_encode_scanline_grayscale_4bit(BYTE* bytes, VALUE pixels, long y, long width, VALUE encoding_palette) {
85
+ UNUSED_PARAMETER(encoding_palette);
86
+ long x; BYTE p1, p2;
87
+ for (x = 0; x < width; x += 2) {
88
+ p1 = (x + 0 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 0))) >> 4);
89
+ p2 = (x + 1 >= width) ? 0 : (B_BYTE(NUM2UINT(rb_ary_entry(pixels, y * width + x + 1))) >> 4);
90
+ bytes[x >> 1] = (BYTE) ((p1 << 4) | (p2));
91
+ }
92
+ }
93
+
94
+ // Assume R == G == B. ChunkyPNG uses the B byte fot performance reasons.
95
+ // We'll uses the same to remain compatible with ChunkyPNG.
51
96
  void oily_png_encode_scanline_grayscale_8bit(BYTE* bytes, VALUE pixels, long y, long width, VALUE encoding_palette) {
52
97
  UNUSED_PARAMETER(encoding_palette);
53
98
  long x; PIXEL pixel;
@@ -58,7 +103,7 @@ void oily_png_encode_scanline_grayscale_8bit(BYTE* bytes, VALUE pixels, long y,
58
103
  }
59
104
 
60
105
  // Assume R == G == B. ChunkyPNG uses the B byte fot performance reasons.
61
- // We'll uses the same to reomain compatible with ChunkyPNG.
106
+ // We'll uses the same to remain compatible with ChunkyPNG.
62
107
  void oily_png_encode_scanline_grayscale_alpha_8bit(BYTE* bytes, VALUE pixels, long y, long width, VALUE encoding_palette) {
63
108
  UNUSED_PARAMETER(encoding_palette);
64
109
  long x; PIXEL pixel;
@@ -72,7 +117,7 @@ void oily_png_encode_scanline_grayscale_alpha_8bit(BYTE* bytes, VALUE pixels, lo
72
117
  void oily_png_encode_scanline_indexed_8bit(BYTE* bytes, VALUE pixels, long y, long width, VALUE encoding_palette) {
73
118
  long x;
74
119
  for (x = 0; x < width; x++) {
75
- bytes[x] = (BYTE) NUM2UINT(rb_funcall(encoding_palette, rb_intern("index"), 1, rb_ary_entry(pixels, y * width + x)));
120
+ bytes[x] = ENCODING_PALETTE_INDEX(encoding_palette, pixels, width, y, x);
76
121
  }
77
122
  }
78
123
 
@@ -141,6 +186,9 @@ scanline_encoder_func oily_png_encode_scanline_func(char color_mode, char bit_de
141
186
  case OILY_PNG_COLOR_GRAYSCALE:
142
187
  switch (bit_depth) {
143
188
  case 8: return &oily_png_encode_scanline_grayscale_8bit;
189
+ case 4: return &oily_png_encode_scanline_grayscale_4bit;
190
+ case 2: return &oily_png_encode_scanline_grayscale_2bit;
191
+ case 1: return &oily_png_encode_scanline_grayscale_1bit;
144
192
  default: return NULL;
145
193
  }
146
194
 
@@ -175,6 +223,21 @@ scanline_encoder_func oily_png_encode_scanline_func(char color_mode, char bit_de
175
223
  }
176
224
  }
177
225
 
226
+ /////////////////////////////////////////////////////////////////////
227
+ // ENCODING AN IMAGE PASS
228
+ /////////////////////////////////////////////////////////////////////
229
+
230
+ VALUE oily_png_encode_palette(VALUE self) {
231
+ VALUE palette_instance = rb_funcall(self, rb_intern("encoding_palette"), 0);
232
+ if (palette_instance != Qnil) {
233
+ VALUE encoding_map = rb_iv_get(palette_instance, "@encoding_map");
234
+ if (rb_funcall(encoding_map, rb_intern("kind_of?"), 1, rb_cHash) == Qtrue) {
235
+ return encoding_map;
236
+ }
237
+ }
238
+ rb_raise(rb_eRuntimeError, "Could not retrieve a decoding palette for this image!");
239
+ }
240
+
178
241
  VALUE oily_png_encode_png_image_pass_to_stream(VALUE self, VALUE stream, VALUE color_mode, VALUE bit_depth, VALUE filtering) {
179
242
 
180
243
  UNUSED_PARAMETER(bit_depth);
@@ -192,7 +255,7 @@ VALUE oily_png_encode_png_image_pass_to_stream(VALUE self, VALUE stream, VALUE c
192
255
  // Get the encoding palette if we're encoding to an indexed bytestream.
193
256
  VALUE encoding_palette = Qnil;
194
257
  if (FIX2INT(color_mode) == OILY_PNG_COLOR_INDEXED) {
195
- encoding_palette = rb_funcall(self, rb_intern("encoding_palette"), 0);
258
+ encoding_palette = oily_png_encode_palette(self);
196
259
  }
197
260
 
198
261
  char pixel_size = oily_png_pixel_bytesize(FIX2INT(color_mode), depth);
@@ -203,8 +266,7 @@ VALUE oily_png_encode_png_image_pass_to_stream(VALUE self, VALUE stream, VALUE c
203
266
  BYTE* bytes = ALLOCA_N(BYTE, pass_size);
204
267
 
205
268
  // Get the scanline encoder function.
206
- void (*scanline_encoder)(BYTE*, VALUE, long, long, VALUE) = NULL;
207
- scanline_encoder = oily_png_encode_scanline_func(FIX2INT(color_mode), depth);
269
+ scanline_encoder_func scanline_encoder = oily_png_encode_scanline_func(FIX2INT(color_mode), depth);
208
270
  if (scanline_encoder == NULL) {
209
271
  rb_raise(rb_eRuntimeError, "No encoder for color mode %d and bit depth %d", FIX2INT(color_mode), depth);
210
272
  }
@@ -7,7 +7,7 @@
7
7
  #define A_BYTE(pixel) ((BYTE) (((pixel) & (PIXEL) 0x000000ff)))
8
8
 
9
9
  #define FILTER_BYTE(byte, adjustment) byte = (BYTE) (((byte) - (adjustment)) & 0x000000ff)
10
- #define ENCODING_PALETTE_INDEX(encoding_palette, pixels, width, y, x) ((x < width) ? ((BYTE) NUM2UINT(rb_funcall(encoding_palette, rb_intern("index"), 1, rb_ary_entry(pixels, y * width + x)))) : 0)
10
+ #define ENCODING_PALETTE_INDEX(encoding_palette, pixels, width, y, x) (((x) < (width)) ? ((BYTE) NUM2UINT(rb_hash_aref(encoding_palette, rb_ary_entry(pixels, (y) * (width) + (x))))) : 0)
11
11
 
12
12
  typedef void(*scanline_encoder_func)(BYTE*, VALUE, long, long, VALUE);
13
13
 
@@ -0,0 +1,9 @@
1
+ require 'chunky_png'
2
+ require 'oily_png/oily_png'
3
+
4
+ module OilyPNG
5
+ class Canvas < ChunkyPNG::Canvas
6
+ extend OilyPNG::PNGDecoding
7
+ include OilyPNG::PNGEncoding
8
+ end
9
+ end
data/lib/oily_png.rb CHANGED
@@ -2,13 +2,12 @@ require 'chunky_png'
2
2
 
3
3
  module OilyPNG
4
4
 
5
- VERSION = "0.3.0"
5
+ VERSION = "1.0.0.beta1"
6
6
 
7
7
  def self.included(base)
8
8
  base::Canvas.send(:extend, OilyPNG::PNGDecoding)
9
9
  base::Canvas.send(:include, OilyPNG::PNGEncoding)
10
10
  end
11
-
12
11
  end
13
12
 
14
13
  require 'oily_png/oily_png'
data/oily_png.gemspec CHANGED
@@ -4,8 +4,8 @@ Gem::Specification.new do |s|
4
4
 
5
5
  # Do not change the version and date fields by hand. This will be done
6
6
  # automatically by the gem release script.
7
- s.version = "0.3.0"
8
- s.date = "2010-12-12"
7
+ s.version = "1.0.0.beta1"
8
+ s.date = "2011-01-24"
9
9
 
10
10
  s.summary = "Native mixin to speed up ChunkyPNG"
11
11
  s.description = <<-EOT
@@ -19,7 +19,7 @@ Gem::Specification.new do |s|
19
19
  s.extensions = ["ext/oily_png/extconf.rb"]
20
20
  s.require_paths = ["lib", "ext"]
21
21
 
22
- s.add_runtime_dependency('chunky_png', '~> 0.12')
22
+ s.add_runtime_dependency('chunky_png', '~> 1.0.0.beta1')
23
23
 
24
24
  s.add_development_dependency('rake')
25
25
  s.add_development_dependency('rake-compiler')
@@ -30,6 +30,6 @@ Gem::Specification.new do |s|
30
30
 
31
31
  # Do not change the files and test_files fields by hand. This will be done
32
32
  # automatically by the gem release script.
33
- s.files = %w(.gitignore .infinity_test Gemfile Gemfile.lock LICENSE README.rdoc Rakefile ext/oily_png/extconf.rb ext/oily_png/oily_png_ext.c ext/oily_png/oily_png_ext.h ext/oily_png/png_decoding.c ext/oily_png/png_decoding.h ext/oily_png/png_encoding.c ext/oily_png/png_encoding.h lib/oily_png.rb oily_png.gemspec spec/decoding_spec.rb spec/encoding_spec.rb spec/resources/basi0g01.png spec/resources/basi0g02.png spec/resources/basi0g04.png spec/resources/basi0g08.png spec/resources/basi0g16.png spec/resources/basi2c08.png spec/resources/basi2c16.png spec/resources/basi3p01.png spec/resources/basi3p02.png spec/resources/basi3p04.png spec/resources/basi3p08.png spec/resources/basi4a08.png spec/resources/basi4a16.png spec/resources/basi6a08.png spec/resources/basi6a16.png spec/resources/basn0g01.png spec/resources/basn0g02.png spec/resources/basn0g04.png spec/resources/basn0g08.png spec/resources/basn0g16.png spec/resources/basn2c08.png spec/resources/basn2c16.png spec/resources/basn3p01.png spec/resources/basn3p02.png spec/resources/basn3p04.png spec/resources/basn3p08.png spec/resources/basn4a08.png spec/resources/basn4a16.png spec/resources/basn6a08.png spec/resources/basn6a16.png spec/resources/gray.png spec/resources/interlaced.png spec/resources/nonsquare.png spec/resources/s01i3p01.png spec/resources/s01n3p01.png spec/resources/s02i3p01.png spec/resources/s02n3p01.png spec/resources/s03i3p01.png spec/resources/s03n3p01.png spec/resources/s04i3p01.png spec/resources/s04n3p01.png spec/resources/s05i3p02.png spec/resources/s05n3p02.png spec/resources/s06i3p02.png spec/resources/s06n3p02.png spec/resources/s07i3p02.png spec/resources/s07n3p02.png spec/resources/s08i3p02.png spec/resources/s08n3p02.png spec/resources/s09i3p02.png spec/resources/s09n3p02.png spec/resources/s32i3p04.png spec/resources/s32n3p04.png spec/resources/s33i3p04.png spec/resources/s33n3p04.png spec/resources/s34i3p04.png spec/resources/s34n3p04.png spec/resources/s35i3p04.png spec/resources/s35n3p04.png spec/resources/s36i3p04.png spec/resources/s36n3p04.png spec/resources/s37i3p04.png spec/resources/s37n3p04.png spec/resources/s38i3p04.png spec/resources/s38n3p04.png spec/resources/s39i3p04.png spec/resources/s39n3p04.png spec/resources/s40i3p04.png spec/resources/s40n3p04.png spec/resources/square.png spec/spec_helper.rb tasks/github-gem.rake tasks/testing.rake)
33
+ s.files = %w(.gitignore .infinity_test Gemfile LICENSE README.rdoc Rakefile ext/oily_png/extconf.rb ext/oily_png/oily_png_ext.c ext/oily_png/oily_png_ext.h ext/oily_png/png_decoding.c ext/oily_png/png_decoding.h ext/oily_png/png_encoding.c ext/oily_png/png_encoding.h lib/oily_png.rb lib/oily_png/canvas.rb oily_png.gemspec spec/decoding_spec.rb spec/encoding_spec.rb spec/resources/basi0g01.png spec/resources/basi0g02.png spec/resources/basi0g04.png spec/resources/basi0g08.png spec/resources/basi0g16.png spec/resources/basi2c08.png spec/resources/basi2c16.png spec/resources/basi3p01.png spec/resources/basi3p02.png spec/resources/basi3p04.png spec/resources/basi3p08.png spec/resources/basi4a08.png spec/resources/basi4a16.png spec/resources/basi6a08.png spec/resources/basi6a16.png spec/resources/basn0g01.png spec/resources/basn0g02.png spec/resources/basn0g04.png spec/resources/basn0g08.png spec/resources/basn0g16.png spec/resources/basn2c08.png spec/resources/basn2c16.png spec/resources/basn3p01.png spec/resources/basn3p02.png spec/resources/basn3p04.png spec/resources/basn3p08.png spec/resources/basn4a08.png spec/resources/basn4a16.png spec/resources/basn6a08.png spec/resources/basn6a16.png spec/resources/gray.png spec/resources/interlaced.png spec/resources/nonsquare.png spec/resources/s01i3p01.png spec/resources/s01n3p01.png spec/resources/s02i3p01.png spec/resources/s02n3p01.png spec/resources/s03i3p01.png spec/resources/s03n3p01.png spec/resources/s04i3p01.png spec/resources/s04n3p01.png spec/resources/s05i3p02.png spec/resources/s05n3p02.png spec/resources/s06i3p02.png spec/resources/s06n3p02.png spec/resources/s07i3p02.png spec/resources/s07n3p02.png spec/resources/s08i3p02.png spec/resources/s08n3p02.png spec/resources/s09i3p02.png spec/resources/s09n3p02.png spec/resources/s32i3p04.png spec/resources/s32n3p04.png spec/resources/s33i3p04.png spec/resources/s33n3p04.png spec/resources/s34i3p04.png spec/resources/s34n3p04.png spec/resources/s35i3p04.png spec/resources/s35n3p04.png spec/resources/s36i3p04.png spec/resources/s36n3p04.png spec/resources/s37i3p04.png spec/resources/s37n3p04.png spec/resources/s38i3p04.png spec/resources/s38n3p04.png spec/resources/s39i3p04.png spec/resources/s39n3p04.png spec/resources/s40i3p04.png spec/resources/s40n3p04.png spec/resources/square.png spec/spec_helper.rb tasks/github-gem.rake tasks/testing.rake)
34
34
  s.test_files = %w(spec/decoding_spec.rb spec/encoding_spec.rb)
35
35
  end
@@ -2,49 +2,65 @@ require 'spec_helper'
2
2
 
3
3
  describe OilyPNG::PNGEncoding do
4
4
 
5
- context 'encoding different color modes' do
5
+ context 'encoding different color settings without palette' do
6
6
  before do
7
7
  @canvas = ChunkyPNG::Canvas.from_file(resource_file('gray.png'))
8
8
  @oily_canvas = OilyPNG::Canvas.from_canvas(@canvas)
9
9
  end
10
10
 
11
- it "should encode an image using grayscale correctly" do
12
- @oily_canvas.send(:encode_png_image_pass_to_stream, stream1 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_GRAYSCALE, 8, ChunkyPNG::FILTER_NONE)
11
+ it "should encode an image using 8-bit grayscale correctly" do
13
12
  @canvas.send(:encode_png_image_pass_to_stream, stream2 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_GRAYSCALE, 8, ChunkyPNG::FILTER_NONE)
13
+ @oily_canvas.send(:encode_png_image_pass_to_stream, stream1 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_GRAYSCALE, 8, ChunkyPNG::FILTER_NONE)
14
+ stream1.should == stream2
15
+ end
16
+
17
+ it "should encode an image using 4-bit grayscale correctly" do
18
+ @canvas.send(:encode_png_image_pass_to_stream, stream2 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_GRAYSCALE, 4, ChunkyPNG::FILTER_NONE)
19
+ @oily_canvas.send(:encode_png_image_pass_to_stream, stream1 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_GRAYSCALE, 4, ChunkyPNG::FILTER_NONE)
20
+ stream1.should == stream2
21
+ end
22
+
23
+ it "should encode an image using 2-bit grayscale correctly" do
24
+ @canvas.send(:encode_png_image_pass_to_stream, stream2 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_GRAYSCALE, 2, ChunkyPNG::FILTER_NONE)
25
+ @oily_canvas.send(:encode_png_image_pass_to_stream, stream1 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_GRAYSCALE, 2, ChunkyPNG::FILTER_NONE)
14
26
  stream1.should == stream2
15
27
  end
16
28
 
17
- it "should encode an image using grayscale alpha correctly" do
29
+ it "should encode an image using 1-bit grayscale correctly" do
30
+ @canvas.send(:encode_png_image_pass_to_stream, stream2 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_GRAYSCALE, 1, ChunkyPNG::FILTER_NONE)
31
+ @oily_canvas.send(:encode_png_image_pass_to_stream, stream1 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_GRAYSCALE, 1, ChunkyPNG::FILTER_NONE)
32
+ stream1.should == stream2
33
+ end
34
+
35
+ it "should encode an image using 8-bit grayscale alpha correctly" do
18
36
  @oily_canvas.send(:encode_png_image_pass_to_stream, stream1 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_GRAYSCALE_ALPHA, 8, ChunkyPNG::FILTER_NONE)
19
37
  @canvas.send(:encode_png_image_pass_to_stream, stream2 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_GRAYSCALE_ALPHA, 8, ChunkyPNG::FILTER_NONE)
20
38
  stream1.should == stream2
21
39
  end
22
40
 
23
- it "should encode an image using truecolor correctly" do
41
+ it "should encode an image using 8-bit truecolor correctly" do
24
42
  @oily_canvas.send(:encode_png_image_pass_to_stream, stream1 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_TRUECOLOR, 8, ChunkyPNG::FILTER_NONE)
25
43
  @canvas.send(:encode_png_image_pass_to_stream, stream2 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_TRUECOLOR, 8, ChunkyPNG::FILTER_NONE)
26
44
  stream1.should == stream2
27
45
  end
28
46
 
29
- it "should encode an image using truecolor alpha correctly" do
47
+ it "should encode an image using 8-bit truecolor alpha correctly" do
30
48
  @oily_canvas.send(:encode_png_image_pass_to_stream, stream1 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_TRUECOLOR_ALPHA, 8, ChunkyPNG::FILTER_NONE)
31
49
  @canvas.send(:encode_png_image_pass_to_stream, stream2 = ChunkyPNG::Datastream.empty_bytearray, ChunkyPNG::COLOR_TRUECOLOR_ALPHA, 8, ChunkyPNG::FILTER_NONE)
32
50
  stream1.should == stream2
33
51
  end
34
-
35
52
  end
36
-
37
- context 'encoding with palette images' do
53
+
54
+ context 'encoding with paletted images using different bitrates' do
38
55
  before do
39
56
  @canvas = ChunkyPNG::Canvas.from_file(resource_file('gray.png'))
40
57
  @oily_canvas = OilyPNG::Canvas.from_canvas(@canvas)
41
58
 
42
- @palette_mock = mock('Palette')
43
- @palette_mock.stub(:index).with(an_instance_of(Fixnum)).and_return(0x01)
44
- @palette_mock.stub(:index).with(nil).and_return(0)
45
-
46
- @canvas.stub(:encoding_palette).and_return(@palette_mock)
47
- @oily_canvas.stub(:encoding_palette).and_return(@palette_mock)
59
+ @canvas.encoding_palette = @canvas.palette
60
+ @canvas.encoding_palette.to_plte_chunk
61
+
62
+ @oily_canvas.encoding_palette = @oily_canvas.palette
63
+ @oily_canvas.encoding_palette.to_plte_chunk
48
64
  end
49
65
 
50
66
  it "should encode an image using 8-bit indexed colors correctly" do
data/spec/spec_helper.rb CHANGED
@@ -1,19 +1,7 @@
1
1
  require 'rubygems'
2
- require 'bundler'
3
-
4
- Bundler.setup
5
-
6
- require 'rspec'
2
+ require 'bundler/setup'
7
3
  require 'chunky_png'
8
- require 'oily_png/oily_png'
9
-
10
-
11
- module OilyPNG
12
- class Canvas < ChunkyPNG::Canvas
13
- extend OilyPNG::PNGDecoding
14
- include OilyPNG::PNGEncoding
15
- end
16
- end
4
+ require 'oily_png/canvas'
17
5
 
18
6
  module ResourceHelper
19
7
  def resource_files
@@ -220,7 +220,7 @@ module GithubGem
220
220
 
221
221
  def check_version_task
222
222
  raise "#{ENV['VERSION']} is not a valid version number!" if ENV['VERSION'] && !Gem::Version.correct?(ENV['VERSION'])
223
- proposed_version = Gem::Version.new(ENV['VERSION'].dup || gemspec.version)
223
+ proposed_version = Gem::Version.new((ENV['VERSION'] || gemspec.version).dup)
224
224
  raise "This version (#{proposed_version}) is not higher than the highest tagged version (#{newest_version})" if newest_version >= proposed_version
225
225
  end
226
226
 
@@ -339,22 +339,26 @@ module GithubGem
339
339
 
340
340
  # Updates the tasks file using the latest file found on Github
341
341
  def update_tasks_task
342
- require 'net/http'
343
-
344
- server = 'github.com'
345
- path = '/wvanbergen/github-gem/raw/master/tasks/github-gem.rake'
342
+ require 'net/https'
343
+ require 'uri'
344
+
345
+ uri = URI.parse('https://github.com/wvanbergen/github-gem/raw/master/tasks/github-gem.rake')
346
+ http = Net::HTTP.new(uri.host, uri.port)
347
+ http.use_ssl = true
348
+ http.verify_mode = OpenSSL::SSL::VERIFY_NONE
349
+ response = http.request(Net::HTTP::Get.new(uri.path))
346
350
 
347
- Net::HTTP.start(server) do |http|
348
- response = http.get(path)
351
+ if Net::HTTPSuccess === response
349
352
  open(__FILE__, "w") { |file| file.write(response.body) }
350
- end
351
-
352
- relative_file = File.expand_path(__FILE__).sub(%r[^#{@root_dir}/], '')
353
- if `#{git} ls-files -m #{relative_file}`.split("\n").any?
354
- sh git, 'add', relative_file
355
- sh git, 'commit', '-m', "Updated to latest gem release management tasks."
353
+ relative_file = File.expand_path(__FILE__).sub(%r[^#{@root_dir}/], '')
354
+ if `#{git} ls-files -m #{relative_file}`.split("\n").any?
355
+ sh git, 'add', relative_file
356
+ sh git, 'commit', '-m', "Updated to latest gem release management tasks."
357
+ else
358
+ puts "Release managament tasks already are at the latest version."
359
+ end
356
360
  else
357
- puts "Release managament tasks already are at the latest version."
361
+ raise "Download failed with HTTP status #{response.code}!"
358
362
  end
359
363
  end
360
364
  end
data/tasks/testing.rake CHANGED
@@ -1,8 +1,6 @@
1
1
  task(:verify, :png_file) do |task, args|
2
2
  require 'rubygems'
3
- require 'bundler'
4
- Bundler.setup
5
-
3
+ require 'bundler/setup'
6
4
  require 'chunky_png'
7
5
  require 'oily_png/oily_png_ext'
8
6
 
metadata CHANGED
@@ -1,12 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: oily_png
3
3
  version: !ruby/object:Gem::Version
4
- prerelease: false
4
+ prerelease: true
5
5
  segments:
6
+ - 1
6
7
  - 0
7
- - 3
8
8
  - 0
9
- version: 0.3.0
9
+ - beta1
10
+ version: 1.0.0.beta1
10
11
  platform: ruby
11
12
  authors:
12
13
  - Willem van Bergen
@@ -14,25 +15,28 @@ autorequire:
14
15
  bindir: bin
15
16
  cert_chain: []
16
17
 
17
- date: 2010-12-12 00:00:00 -05:00
18
+ date: 2011-01-24 00:00:00 -05:00
18
19
  default_executable:
19
20
  dependencies:
20
21
  - !ruby/object:Gem::Dependency
21
22
  name: chunky_png
23
+ prerelease: false
22
24
  requirement: &id001 !ruby/object:Gem::Requirement
23
25
  none: false
24
26
  requirements:
25
27
  - - ~>
26
28
  - !ruby/object:Gem::Version
27
29
  segments:
30
+ - 1
28
31
  - 0
29
- - 12
30
- version: "0.12"
32
+ - 0
33
+ - beta1
34
+ version: 1.0.0.beta1
31
35
  type: :runtime
32
- prerelease: false
33
36
  version_requirements: *id001
34
37
  - !ruby/object:Gem::Dependency
35
38
  name: rake
39
+ prerelease: false
36
40
  requirement: &id002 !ruby/object:Gem::Requirement
37
41
  none: false
38
42
  requirements:
@@ -42,10 +46,10 @@ dependencies:
42
46
  - 0
43
47
  version: "0"
44
48
  type: :development
45
- prerelease: false
46
49
  version_requirements: *id002
47
50
  - !ruby/object:Gem::Dependency
48
51
  name: rake-compiler
52
+ prerelease: false
49
53
  requirement: &id003 !ruby/object:Gem::Requirement
50
54
  none: false
51
55
  requirements:
@@ -55,10 +59,10 @@ dependencies:
55
59
  - 0
56
60
  version: "0"
57
61
  type: :development
58
- prerelease: false
59
62
  version_requirements: *id003
60
63
  - !ruby/object:Gem::Dependency
61
64
  name: rspec
65
+ prerelease: false
62
66
  requirement: &id004 !ruby/object:Gem::Requirement
63
67
  none: false
64
68
  requirements:
@@ -68,7 +72,6 @@ dependencies:
68
72
  - 2
69
73
  version: "2"
70
74
  type: :development
71
- prerelease: false
72
75
  version_requirements: *id004
73
76
  description: " This Ruby C extenstion defines a module that can be included into ChunkyPNG to improve its speed.\n"
74
77
  email:
@@ -83,7 +86,6 @@ files:
83
86
  - .gitignore
84
87
  - .infinity_test
85
88
  - Gemfile
86
- - Gemfile.lock
87
89
  - LICENSE
88
90
  - README.rdoc
89
91
  - Rakefile
@@ -95,6 +97,7 @@ files:
95
97
  - ext/oily_png/png_encoding.c
96
98
  - ext/oily_png/png_encoding.h
97
99
  - lib/oily_png.rb
100
+ - lib/oily_png/canvas.rb
98
101
  - oily_png.gemspec
99
102
  - spec/decoding_spec.rb
100
103
  - spec/encoding_spec.rb
@@ -191,19 +194,19 @@ required_ruby_version: !ruby/object:Gem::Requirement
191
194
  requirements:
192
195
  - - ">="
193
196
  - !ruby/object:Gem::Version
194
- hash: -4404807782310531361
195
197
  segments:
196
198
  - 0
197
199
  version: "0"
198
200
  required_rubygems_version: !ruby/object:Gem::Requirement
199
201
  none: false
200
202
  requirements:
201
- - - ">="
203
+ - - ">"
202
204
  - !ruby/object:Gem::Version
203
- hash: -4404807782310531361
204
205
  segments:
205
- - 0
206
- version: "0"
206
+ - 1
207
+ - 3
208
+ - 1
209
+ version: 1.3.1
207
210
  requirements: []
208
211
 
209
212
  rubyforge_project: oily_png
data/Gemfile.lock DELETED
@@ -1,32 +0,0 @@
1
- PATH
2
- remote: .
3
- specs:
4
- oily_png (0.3.0)
5
- chunky_png (~> 0.12)
6
-
7
- GEM
8
- remote: http://rubygems.org/
9
- specs:
10
- chunky_png (0.12.0)
11
- diff-lcs (1.1.2)
12
- rake (0.8.7)
13
- rake-compiler (0.7.5)
14
- rake
15
- rspec (2.2.0)
16
- rspec-core (~> 2.2)
17
- rspec-expectations (~> 2.2)
18
- rspec-mocks (~> 2.2)
19
- rspec-core (2.2.1)
20
- rspec-expectations (2.2.0)
21
- diff-lcs (~> 1.1.2)
22
- rspec-mocks (2.2.0)
23
-
24
- PLATFORMS
25
- ruby
26
-
27
- DEPENDENCIES
28
- chunky_png (~> 0.12)
29
- oily_png!
30
- rake
31
- rake-compiler
32
- rspec (~> 2)