问题
I am using Paperclip to attach image files to an object and all is well but I'd also like to mask (preferably only one of the image style – main_feature) the image upon upload. I'm able to save my masked image using masked_image.write('result.png')
but can't seem to get it to update the image attribute for Paperclip. With the following code I get this error:
No handler found for /var/folders/q1/xf59whv514lgw_xr10hb208m0000gn/T/gaither-nomask20130312-80235-yaj1s7.png PNG 1020x470 1020x470+0+0 DirectClass 8-bit
has_attached_file :image,
:styles =>{
:main_feature => "1020x470",
:top_feature => "345x159",
:smallest => "229x131"
},
:storage => :s3,
:s3_credentials => "#{Rails.root}/config/s3.yml",
:path => ":attachment/:id/:style.:extension",
:url => "/:id/:style/:basename.:extension",
:bucket => "bucketname"
after_image_post_process :post_process_image
def post_process_image
require 'rubygems'
require 'RMagick'
require "open-uri"
mask = Magick::ImageList.new
urlimage = open("http://bucket.s3.amazonaws.com/mask.png")
mask.from_blob(urlimage.read)
imgfile = Magick::Image.read(image.queued_for_write[:original].path).first
mask.matte = true
imgfile.matte = true
masked_image = imgfile.composite(mask, Magick::CenterGravity, Magick::CopyOpacityCompositeOp)
self.update_attribute(:image, masked_image)
end
回答1:
After a little trial and error, I ended up writing a Paperclip processor:
model:
:styles =>{
:main_feature => {:geometry => "1020x470", :processors => [:masker] },
:top_feature => "345x159",
:smallest => "229x131"
}
/lib/paperclip_processors/masker.rb:
module Paperclip
class Masker < Processor
def initialize file, options = {}, attachment = nil
super
@format = File.extname(@file.path)
@basename = File.basename(@file.path, @format)
end
def make
src = @file
dst = Tempfile.new([@basename, @format])
dst.binmode
begin
parameters = []
parameters << ':source'
parameters << ':mask'
parameters << '-alpha'
parameters << 'on'
parameters << '-compose'
parameters << 'CopyOpacity'
parameters << '-composite'
parameters << ':dest'
parameters = parameters.flatten.compact.join(" ").strip.squeeze(" ")
mask_path = File.expand_path('lib/paperclip_processors/mask.png')
success = Paperclip.run("convert", parameters, :source => "#{File.expand_path(src.path)}[0]", :mask => "#{mask_path}[0]", :dest => File.expand_path(dst.path))
rescue PaperclipCommandLineError => e
raise PaperclipError, "There was an error during the mask for #{@basename}" if @whiny
end
dst
end
end
end
来源:https://stackoverflow.com/questions/15365984/rmagick-mask-paperclip-image-attachment