module ChunkyPNG::Canvas::PNGDecoding
The PNGDecoding
contains methods for decoding PNG datastreams to create a Canvas
object. The datastream can be provided as filename, string or IO stream.
Overview of the decoding process:
-
The optional PLTE and tRNS chunk are decoded for the color palette of the original image.
-
The contents of the IDAT chunks is combined, and uncompressed using Inflate decompression to the image pixelstream.
-
Based on the color mode, width and height of the original image, which is read from the PNG header (IHDR chunk), the amount of bytes per line is determined.
-
For every line of pixels in the encoded image, the original byte values are restored by unapplying the milter method for that line.
-
The read bytes are unfiltered given by the filter function specified by the first byte of the line.
-
The unfiltered pixelstream are is into colored pixels, using the color mode.
-
All lines combined to form the original image.
For interlaced images, the original image was split into 7 subimages. These images get decoded just like the process above (from step 3), and get combined to form the original images.
@see ChunkyPNG::Canvas::PNGEncoding
@see www.w3.org/TR/PNG/ The W3C PNG format specification
Public Instance Methods
Decodes a canvas from a PNG encoded pixelstream, using a given width, height, color mode and interlacing mode. @param [String] stream The pixelstream to read from. @param [Integer] width The width of the image. @param [Integer] height The height of the image. @param [Integer] color_mode The color mode of the encoded pixelstream. @param [Integer] depth The bit depth of the pixel samples. @param [Integer] interlace The interlace method of the encoded pixelstream. @param [ChunkyPNG::Palette] decoding_palette The palette to use to decode colors. @param [Integer] transparent_color The color that should be considered fully transparent. @return [ChunkyPNG::Canvas] The decoded Canvas
instance.
# File lib/chunky_png/canvas/png_decoding.rb 93 def decode_png_pixelstream(stream, width, height, color_mode, depth, interlace, decoding_palette, transparent_color) 94 raise ChunkyPNG::ExpectationFailed, "This palette is not suitable for decoding!" if decoding_palette && !decoding_palette.can_decode? 95 96 image = case interlace 97 when ChunkyPNG::INTERLACING_NONE then decode_png_without_interlacing(stream, width, height, color_mode, depth, decoding_palette) 98 when ChunkyPNG::INTERLACING_ADAM7 then decode_png_with_adam7_interlacing(stream, width, height, color_mode, depth, decoding_palette) 99 else raise ChunkyPNG::NotSupported, "Don't know how the handle interlacing method #{interlace}!" 100 end 101 102 image.pixels.map! { |c| c == transparent_color ? ChunkyPNG::Color::TRANSPARENT : c } if transparent_color 103 image 104 end
Decodes a Canvas
from a PNG encoded string. @param [String] str The string to read from. @return [ChunkyPNG::Canvas] The canvas decoded from the PNG encoded string.
# File lib/chunky_png/canvas/png_decoding.rb 33 def from_blob(str) 34 from_datastream(ChunkyPNG::Datastream.from_blob(str)) 35 end
Decodes the Canvas
from a PNG datastream instance. @param [ChunkyPNG::Datastream] ds The datastream to decode. @return [ChunkyPNG::Canvas] The canvas decoded from the PNG datastream.
# File lib/chunky_png/canvas/png_decoding.rb 58 def from_datastream(ds) 59 width = ds.header_chunk.width 60 height = ds.header_chunk.height 61 color_mode = ds.header_chunk.color 62 interlace = ds.header_chunk.interlace 63 depth = ds.header_chunk.depth 64 65 if width == 0 || height == 0 66 raise ExpectationFailed, "Invalid image size, width: #{width}, height: #{height}" 67 end 68 69 decoding_palette, transparent_color = nil, nil 70 case color_mode 71 when ChunkyPNG::COLOR_INDEXED 72 decoding_palette = ChunkyPNG::Palette.from_chunks(ds.palette_chunk, ds.transparency_chunk) 73 when ChunkyPNG::COLOR_TRUECOLOR 74 transparent_color = ds.transparency_chunk.truecolor_entry(depth) if ds.transparency_chunk 75 when ChunkyPNG::COLOR_GRAYSCALE 76 transparent_color = ds.transparency_chunk.grayscale_entry(depth) if ds.transparency_chunk 77 end 78 79 decode_png_pixelstream(ds.imagedata, width, height, color_mode, depth, interlace, decoding_palette, transparent_color) 80 end
Decodes a Canvas
from a PNG encoded file. @param [String] filename The file to read from. @return [ChunkyPNG::Canvas] The canvas decoded from the PNG file.
# File lib/chunky_png/canvas/png_decoding.rb 42 def from_file(filename) 43 from_datastream(ChunkyPNG::Datastream.from_file(filename)) 44 end
Decodes a Canvas
from a PNG encoded stream. @param [IO, read] io The stream to read from. @return [ChunkyPNG::Canvas] The canvas decoded from the PNG stream.
# File lib/chunky_png/canvas/png_decoding.rb 49 def from_io(io) 50 from_datastream(ChunkyPNG::Datastream.from_io(io)) 51 end
Protected Instance Methods
Extract a bit from a byte on a given index. @param [Integer] byte The byte (0..255) value to extract a bit from. @param [Integer] index The index within the byte. This should be 0..7;
the value will be modded by 8 to enforce this.
@return [Integer] Either 1 or 0.
# File lib/chunky_png/canvas/png_decoding.rb 166 def decode_png_extract_1bit_value(byte, index) 167 bitshift = 7 - (index & 0x07) 168 (byte & (0x01 << bitshift)) >> bitshift 169 end
Extract 2 consecutive bits from a byte. @param [Integer] byte The byte (0..255) value to extract a 2 bit value from. @param [Integer] index The index within the byte. This should be either 0, 1, 2, or 3;
the value will be modded by 4 to enforce this.
@return [Integer] The extracted 2 bit value (0..3)
# File lib/chunky_png/canvas/png_decoding.rb 156 def decode_png_extract_2bit_value(byte, index) 157 bitshift = 6 - ((index & 0x03) << 1) 158 (byte & (0x03 << bitshift)) >> bitshift 159 end
Extract 4 consecutive bits from a byte. @param [Integer] byte The byte (0..255) value to extract a 4 bit value from. @param [Integer] index The index within the byte. This should be either 0 or 2;
the value will be modded by 2 to enforce this.
@return [Integer] The extracted 4bit value (0..15)
# File lib/chunky_png/canvas/png_decoding.rb 147 def decode_png_extract_4bit_value(byte, index) 148 index & 0x01 == 0 ? ((byte & 0xf0) >> 4) : (byte & 0x0f) 149 end
Decodes a single PNG image pass width a given width, height and color mode, to a Canvas
, starting at the given position in the stream.
A non-interlaced image only consists of one pass, while an Adam7 image consists of 7 passes that must be combined after decoding.
@param stream (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param width (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param height (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param color_mode (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param [Integer] start_pos The position in the pixel stream to start reading. @param [ChunkyPNG::Palette] decoding_palette The palette to use to decode colors. @return (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
)
# File lib/chunky_png/canvas/png_decoding.rb 381 def decode_png_image_pass(stream, width, height, color_mode, depth, start_pos, decoding_palette) 382 pixels = [] 383 if width > 0 && height > 0 384 385 stream << ChunkyPNG::EXTRA_BYTE if color_mode == ChunkyPNG::COLOR_TRUECOLOR 386 pixel_decoder = decode_png_pixels_from_scanline_method(color_mode, depth) 387 line_length = ChunkyPNG::Color.scanline_bytesize(color_mode, depth, width) 388 pixel_size = ChunkyPNG::Color.pixel_bytesize(color_mode, depth) 389 390 raise ChunkyPNG::ExpectationFailed, "Invalid stream length!" unless stream.bytesize - start_pos >= ChunkyPNG::Color.pass_bytesize(color_mode, depth, width, height) 391 392 pos, prev_pos = start_pos, nil 393 for _ in 0...height do 394 decode_png_str_scanline(stream, pos, prev_pos, line_length, pixel_size) 395 pixels.concat(send(pixel_decoder, stream, pos, width, decoding_palette)) 396 397 prev_pos = pos 398 pos += line_length + 1 399 end 400 end 401 402 new(width, height, pixels) 403 end
Decodes a scanline of a 16-bit, grayscale image into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 345 def decode_png_pixels_from_scanline_grayscale_16bit(stream, pos, width, _decoding_palette) 346 values = stream.unpack("@#{pos + 1}n#{width}") 347 values.map { |value| ChunkyPNG::Color.grayscale(decode_png_resample_16bit_value(value)) } 348 end
Decodes a scanline of a 1-bit, grayscale image into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 308 def decode_png_pixels_from_scanline_grayscale_1bit(stream, pos, width, _decoding_palette) 309 (0...width).map do |index| 310 value = decode_png_extract_1bit_value(stream.getbyte(pos + 1 + (index >> 3)), index) 311 value == 1 ? ChunkyPNG::Color::WHITE : ChunkyPNG::Color::BLACK 312 end 313 end
Decodes a scanline of a 2-bit, grayscale image into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 318 def decode_png_pixels_from_scanline_grayscale_2bit(stream, pos, width, _decoding_palette) 319 (0...width).map do |index| 320 value = decode_png_extract_2bit_value(stream.getbyte(pos + 1 + (index >> 2)), index) 321 ChunkyPNG::Color.grayscale(decode_png_resample_2bit_value(value)) 322 end 323 end
Decodes a scanline of a 4-bit, grayscale image into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 328 def decode_png_pixels_from_scanline_grayscale_4bit(stream, pos, width, _decoding_palette) 329 (0...width).map do |index| 330 value = decode_png_extract_4bit_value(stream.getbyte(pos + 1 + (index >> 1)), index) 331 ChunkyPNG::Color.grayscale(decode_png_resample_4bit_value(value)) 332 end 333 end
Decodes a scanline of an 8-bit, grayscale image into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 338 def decode_png_pixels_from_scanline_grayscale_8bit(stream, pos, width, _decoding_palette) 339 (1..width).map { |i| ChunkyPNG::Color.grayscale(stream.getbyte(pos + i)) } 340 end
Decodes a scanline of a 16-bit, grayscale image with transparency into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 297 def decode_png_pixels_from_scanline_grayscale_alpha_16bit(stream, pos, width, _decoding_palette) 298 pixels = [] 299 stream.unpack("@#{pos + 1}n#{width * 2}").each_slice(2) do |g, a| 300 pixels << ChunkyPNG::Color.grayscale_alpha(decode_png_resample_16bit_value(g), decode_png_resample_16bit_value(a)) 301 end 302 pixels 303 end
Decodes a scanline of an 8-bit, grayscale image with transparency into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 290 def decode_png_pixels_from_scanline_grayscale_alpha_8bit(stream, pos, width, _decoding_palette) 291 (0...width).map { |i| ChunkyPNG::Color.grayscale_alpha(stream.getbyte(pos + (i * 2) + 1), stream.getbyte(pos + (i * 2) + 2)) } 292 end
Decodes a scanline of a 1-bit, indexed image into a row of pixels. @param [String] stream The stream to decode from. @param [Integer] pos The position in the stream on which the scanline starts (including the filter byte). @param [Integer] width The width in pixels of the scanline. @param [ChunkyPNG::Palette] decoding_palette The palette to use to decode colors. @return [Array<Integer>] An array of decoded pixels.
# File lib/chunky_png/canvas/png_decoding.rb 212 def decode_png_pixels_from_scanline_indexed_1bit(stream, pos, width, decoding_palette) 213 (0...width).map do |index| 214 palette_pos = decode_png_extract_1bit_value(stream.getbyte(pos + 1 + (index >> 3)), index) 215 decoding_palette[palette_pos] 216 end 217 end
Decodes a scanline of a 2-bit, indexed image into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 222 def decode_png_pixels_from_scanline_indexed_2bit(stream, pos, width, decoding_palette) 223 (0...width).map do |index| 224 palette_pos = decode_png_extract_2bit_value(stream.getbyte(pos + 1 + (index >> 2)), index) 225 decoding_palette[palette_pos] 226 end 227 end
Decodes a scanline of a 4-bit, indexed image into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 232 def decode_png_pixels_from_scanline_indexed_4bit(stream, pos, width, decoding_palette) 233 (0...width).map do |index| 234 palette_pos = decode_png_extract_4bit_value(stream.getbyte(pos + 1 + (index >> 1)), index) 235 decoding_palette[palette_pos] 236 end 237 end
Decodes a scanline of a 8-bit, indexed image into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 242 def decode_png_pixels_from_scanline_indexed_8bit(stream, pos, width, decoding_palette) 243 (1..width).map { |i| decoding_palette[stream.getbyte(pos + i)] } 244 end
Returns the method name to use to decode scanlines into pixels. @param [Integer] color_mode The color mode of the image. @param [Integer] depth The bit depth of the image. @return [Symbol] The method name to use for decoding, to be called on the canvas class. @raise [ChunkyPNG::NotSupported] when the color_mode and/or bit depth is not supported.
# File lib/chunky_png/canvas/png_decoding.rb 355 def decode_png_pixels_from_scanline_method(color_mode, depth) 356 decoder_method = case color_mode 357 when ChunkyPNG::COLOR_TRUECOLOR then :"decode_png_pixels_from_scanline_truecolor_#{depth}bit" 358 when ChunkyPNG::COLOR_TRUECOLOR_ALPHA then :"decode_png_pixels_from_scanline_truecolor_alpha_#{depth}bit" 359 when ChunkyPNG::COLOR_INDEXED then :"decode_png_pixels_from_scanline_indexed_#{depth}bit" 360 when ChunkyPNG::COLOR_GRAYSCALE then :"decode_png_pixels_from_scanline_grayscale_#{depth}bit" 361 when ChunkyPNG::COLOR_GRAYSCALE_ALPHA then :"decode_png_pixels_from_scanline_grayscale_alpha_#{depth}bit" 362 end 363 364 raise ChunkyPNG::NotSupported, "No decoder found for color mode #{color_mode} and #{depth}-bit depth!" unless respond_to?(decoder_method, true) 365 decoder_method 366 end
Decodes a scanline of a 16-bit, true color image into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 279 def decode_png_pixels_from_scanline_truecolor_16bit(stream, pos, width, _decoding_palette) 280 pixels = [] 281 stream.unpack("@#{pos + 1}n#{width * 3}").each_slice(3) do |r, g, b| 282 pixels << ChunkyPNG::Color.rgb(decode_png_resample_16bit_value(r), decode_png_resample_16bit_value(g), decode_png_resample_16bit_value(b)) 283 end 284 pixels 285 end
Decodes a scanline of an 8-bit, true color image into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 272 def decode_png_pixels_from_scanline_truecolor_8bit(stream, pos, width, _decoding_palette) 273 stream.unpack("@#{pos + 1}" << ("NX" * width)).map { |c| c | 0x000000ff } 274 end
Decodes a scanline of a 16-bit, true color image with transparency into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 256 def decode_png_pixels_from_scanline_truecolor_alpha_16bit(stream, pos, width, _decoding_palette) 257 pixels = [] 258 stream.unpack("@#{pos + 1}n#{width * 4}").each_slice(4) do |r, g, b, a| 259 pixels << ChunkyPNG::Color.rgba( 260 decode_png_resample_16bit_value(r), 261 decode_png_resample_16bit_value(g), 262 decode_png_resample_16bit_value(b), 263 decode_png_resample_16bit_value(a), 264 ) 265 end 266 pixels 267 end
Decodes a scanline of an 8-bit, true color image with transparency into a row of pixels. @params (see decode_png_pixels_from_scanline_indexed_1bit
) @return (see decode_png_pixels_from_scanline_indexed_1bit
)
# File lib/chunky_png/canvas/png_decoding.rb 249 def decode_png_pixels_from_scanline_truecolor_alpha_8bit(stream, pos, width, _decoding_palette) 250 stream.unpack("@#{pos + 1}N#{width}") 251 end
Resamples a 16 bit value to an 8 bit value. This will discard some color information. @param [Integer] value The 16 bit value to resample. @return [Integer] The 8 bit resampled value
# File lib/chunky_png/canvas/png_decoding.rb 174 def decode_png_resample_16bit_value(value) 175 value >> 8 176 end
Resamples a 1 bit value to an 8 bit value. @param [Integer] value The 1 bit value to resample. @return [Integer] The 8 bit resampled value
# File lib/chunky_png/canvas/png_decoding.rb 202 def decode_png_resample_1bit_value(value) 203 value == 0x01 ? 0xff : 0x00 204 end
Resamples a 2 bit value to an 8 bit value. @param [Integer] value The 2 bit value to resample. @return [Integer] The 8 bit resampled value.
# File lib/chunky_png/canvas/png_decoding.rb 195 def decode_png_resample_2bit_value(value) 196 value << 6 | value << 4 | value << 2 | value 197 end
Resamples a 4 bit value to an 8 bit value. @param [Integer] value The 4 bit value to resample. @return [Integer] The 8 bit resampled value.
# File lib/chunky_png/canvas/png_decoding.rb 188 def decode_png_resample_4bit_value(value) 189 value << 4 | value 190 end
No-op - available for completeness sake only @param [Integer] value The 8 bit value to resample. @return [Integer] The 8 bit resampled value
# File lib/chunky_png/canvas/png_decoding.rb 181 def decode_png_resample_8bit_value(value) 182 value 183 end
Decodes a scanline if it was encoded using filtering.
It will extract the filtering method from the first byte of the scanline, and uses the method to change the subsequent bytes to unfiltered values. This will modify the pixelstream.
The bytes of the scanline can then be used to construct pixels, based on the color mode..
@param [String] stream The pixelstream to undo the filtering in. @param [Integer] pos The starting position of the scanline to decode. @param [Integer, nil] prev_pos The starting position of the previously decoded scanline, or nil
if this is the first scanline of the image.
@param [Integer] line_length The number of bytes in the scanline, discounting the filter method byte. @param [Integer] pixel_size The number of bytes used per pixel, based on the color mode. @return [void]
# File lib/chunky_png/canvas/png_decoding.rb 419 def decode_png_str_scanline(stream, pos, prev_pos, line_length, pixel_size) 420 case stream.getbyte(pos) 421 when ChunkyPNG::FILTER_NONE then # rubocop:disable Lint/EmptyWhen # no-op 422 when ChunkyPNG::FILTER_SUB then decode_png_str_scanline_sub(stream, pos, prev_pos, line_length, pixel_size) 423 when ChunkyPNG::FILTER_UP then decode_png_str_scanline_up(stream, pos, prev_pos, line_length, pixel_size) 424 when ChunkyPNG::FILTER_AVERAGE then decode_png_str_scanline_average(stream, pos, prev_pos, line_length, pixel_size) 425 when ChunkyPNG::FILTER_PAETH then decode_png_str_scanline_paeth(stream, pos, prev_pos, line_length, pixel_size) 426 else raise ChunkyPNG::NotSupported, "Unknown filter type: #{stream.getbyte(pos)}!" 427 end 428 end
Decodes a scanline in a pixelstream that was encoded using AVERAGE filtering. This will change the pixelstream to have unfiltered values. @params (see decode_png_str_scanline
) @return [void]
# File lib/chunky_png/canvas/png_decoding.rb 462 def decode_png_str_scanline_average(stream, pos, prev_pos, line_length, pixel_size) 463 for i in 1..line_length do 464 a = i > pixel_size ? stream.getbyte(pos + i - pixel_size) : 0 465 b = prev_pos ? stream.getbyte(prev_pos + i) : 0 466 stream.setbyte(pos + i, (stream.getbyte(pos + i) + ((a + b) >> 1)) & 0xff) 467 end 468 end
Decodes a scanline in a pixelstream that was encoded using PAETH filtering. This will change the pixelstream to have unfiltered values. @params (see decode_png_str_scanline
) @return [void]
# File lib/chunky_png/canvas/png_decoding.rb 474 def decode_png_str_scanline_paeth(stream, pos, prev_pos, line_length, pixel_size) 475 for i in 1..line_length do 476 cur_pos = pos + i 477 a = i > pixel_size ? stream.getbyte(cur_pos - pixel_size) : 0 478 b = prev_pos ? stream.getbyte(prev_pos + i) : 0 479 c = prev_pos && i > pixel_size ? stream.getbyte(prev_pos + i - pixel_size) : 0 480 p = a + b - c 481 pa = (p - a).abs 482 pb = (p - b).abs 483 pc = (p - c).abs 484 pr = if pa <= pb 485 pa <= pc ? a : c 486 else 487 pb <= pc ? b : c 488 end 489 490 stream.setbyte(cur_pos, (stream.getbyte(cur_pos) + pr) & 0xff) 491 end 492 end
Decodes a scanline in a pixelstream that was encoded using SUB filtering. This will change the pixelstream to have unfiltered values. @params (see decode_png_str_scanline
) @return [void]
# File lib/chunky_png/canvas/png_decoding.rb 441 def decode_png_str_scanline_sub(stream, pos, prev_pos, line_length, pixel_size) 442 for i in 1..line_length do 443 stream.setbyte(pos + i, (stream.getbyte(pos + i) + (i > pixel_size ? stream.getbyte(pos + i - pixel_size) : 0)) & 0xff) 444 end 445 end
Decodes a scanline that wasn't encoded using filtering. This is a no-op. @params (see decode_png_str_scanline
) @return [void]
# File lib/chunky_png/canvas/png_decoding.rb 433 def decode_png_str_scanline_sub_none(stream, pos, prev_pos, line_length, pixel_size) 434 # noop - this method shouldn't get called. 435 end
Decodes a scanline in a pixelstream that was encoded using UP filtering. This will change the pixelstream to have unfiltered values. @params (see decode_png_str_scanline
) @return [void]
# File lib/chunky_png/canvas/png_decoding.rb 451 def decode_png_str_scanline_up(stream, pos, prev_pos, line_length, pixel_size) 452 for i in 1..line_length do 453 up = prev_pos ? stream.getbyte(prev_pos + i) : 0 454 stream.setbyte(pos + i, (stream.getbyte(pos + i) + up) & 0xff) 455 end 456 end
Decodes a canvas from a Adam 7 interlaced PNG encoded pixelstream, using a given width, height and color mode. @param stream (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param width (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param height (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param color_mode (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param depth (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param [ChunkyPNG::Palette] decoding_palette The palette to use to decode colors. @return (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
)
# File lib/chunky_png/canvas/png_decoding.rb 130 def decode_png_with_adam7_interlacing(stream, width, height, color_mode, depth, decoding_palette) 131 canvas = new(width, height) 132 start_pos = 0 133 for pass in 0...7 134 sm_width, sm_height = adam7_pass_size(pass, width, height) 135 sm = decode_png_image_pass(stream, sm_width, sm_height, color_mode, depth, start_pos, decoding_palette) 136 adam7_merge_pass(pass, canvas, sm) 137 start_pos += ChunkyPNG::Color.pass_bytesize(color_mode, depth, sm_width, sm_height) 138 end 139 canvas 140 end
Decodes a canvas from a non-interlaced PNG encoded pixelstream, using a given width, height and color mode. @param stream (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param width (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param height (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param color_mode (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param depth (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
) @param [ChunkyPNG::Palette] decoding_palette The palette to use to decode colors. @return (see ChunkyPNG::Canvas::PNGDecoding#decode_png_pixelstream
)
# File lib/chunky_png/canvas/png_decoding.rb 117 def decode_png_without_interlacing(stream, width, height, color_mode, depth, decoding_palette) 118 decode_png_image_pass(stream, width, height, color_mode, depth, 0, decoding_palette) 119 end