diff graster/graster/lib/graster/image.rb @ 11:f952052e37b7

trying a fix.
author Robert McIntyre <rlm@mit.edu>
date Tue, 24 Aug 2010 19:06:45 -0400
parents
children
line wrap: on
line diff
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/graster/graster/lib/graster/image.rb	Tue Aug 24 19:06:45 2010 -0400
     1.3 @@ -0,0 +1,83 @@
     1.4 +class Graster
     1.5 +  class Image
     1.6 +    PROPS = [:filename,:size,:pixels]
     1.7 +
     1.8 +    def initialize(props)
     1.9 +      PROPS.each do |p|
    1.10 +        raise "required image property :#{p} missing" unless props[p]
    1.11 +        instance_variable_set "@#{p}", props[p]
    1.12 +      end
    1.13 +    end
    1.14 +
    1.15 +    PROPS.each{|p| attr_reader p }
    1.16 +
    1.17 +    def self.from_file pathname
    1.18 +      raise "file not found #{pathname}" unless File.exist? pathname
    1.19 +      img = Magick::Image.read(pathname)
    1.20 +      raise "bad image data in #{pathname}" unless img = img[0]
    1.21 +      new :filename => File.basename(pathname),
    1.22 +          :size => [img.columns,img.rows],
    1.23 +          :pixels => img.export_pixels(0,0,img.columns,img.rows,"I")
    1.24 +    end
    1.25 +
    1.26 +    # get pixel(s) from x,y coords
    1.27 +    # 0,0 is bottom,left
    1.28 +    # image[x,y] => pixel at x,y
    1.29 +    # image[y] => row at y
    1.30 +    def [] y, x=nil
    1.31 +      if x
    1.32 +        @pixels[(@size[1]-y)*@size[0]+x]
    1.33 +      else
    1.34 +        @pixels[(@size[1]-y)*@size[0],@size[0]]
    1.35 +      end
    1.36 +    end
    1.37 +
    1.38 +    def each_row &block
    1.39 +      @pixels.chars.each_slice(@size[0]).each_with_index &block
    1.40 +    end
    1.41 +
    1.42 +    # "encode" a float 0..1 to a pixel
    1.43 +    def self.f_to_pix f
    1.44 +      (f*65535).round
    1.45 +    end
    1.46 +
    1.47 +    # "decode" an encoded pixel to a float 0..1
    1.48 +    def self.pix_to_f pix
    1.49 +      pix/65535.0
    1.50 +    end
    1.51 +
    1.52 +
    1.53 +    # convert bitmap data to spans (or runs) of contiguous pixels
    1.54 +    # also invert the Y axis
    1.55 +    def build_spans on_range
    1.56 +      # TODO: rewrite in terms of each_row
    1.57 +      @spans = Array.new @size[1]
    1.58 +
    1.59 +      @size[1].times do |y|
    1.60 +        spans = []
    1.61 +        left = (@size[1]-y-1)*@size[0]
    1.62 +        start = nil
    1.63 +
    1.64 +        @size[0].times do |x|
    1.65 +          d = on_range.include?(@pixels[left+x])
    1.66 +
    1.67 +          if !start && d
    1.68 +            start = x
    1.69 +          elsif start && !d
    1.70 +            spans << [start, x]
    1.71 +            start = nil
    1.72 +          end
    1.73 +        end
    1.74 +
    1.75 +        spans << [start, @size[0]] if start
    1.76 +        @spans[y] = spans
    1.77 +      end
    1.78 +    end
    1.79 +
    1.80 +    attr_reader :spans
    1.81 +
    1.82 +    def hash
    1.83 +      [@pixels,@width,@height].hash
    1.84 +    end
    1.85 +  end
    1.86 +end
    1.87 \ No newline at end of file