Attachment_fu model With Custom Filename, Square Cropping.
이번 작업을 하면서 필요했던 부분.
Attachment_fu에서 저장되는 파일 명 변경과 함께, 특정 이미지를 골라서 정해준 위치에 맞게 Cropping을 하는 기능이 필요했다. Cropping 관련 메소드는 Kropper에서 빌려옴. ^^
class ArticleImage < ActiveRecord::Base
belongs_to :article
@@thumbs = {
:large => '180x180!',
:medium => '120x120!',
:small => '90x90!'
}
has_attachment :content_type => :image,
:storage => :file_system,
:max_size => 20.megabytes,
:path_prefix => "public/images/#{table_name}",
:resize_to => '600x400>',
:processor => "Rmagick",
:thumbnails => {
:large => '180x180!',
:medium => '120x120!',
:small => '90x90!'
}
validates_as_attachment
# Customizing Filename.
def full_filename(thumbnail = nil)
file_system_path = (thumbnail ? thumbnail_class : self).attachment_options[:path_prefix].to_s
@thumb = self.thumbnail unless (@thumb = thumbnail)
asset = self.parent_id.nil? ? self.id : self.parent_id
File.join(RAILS_ROOT, file_system_path, *partitioned_path(thumbnail_name_for(@thumb, asset)))
end
# Filename Customizing Method
def thumbnail_name_for(thumbnail = nil, asset = nil)
suffix = "_#{thumbnail}" unless thumbnail.blank?
extension = filename.scan(/\.\w+$/)
return "#{asset}#{suffix}#{extension}"
end
# crops the attached image according to the passed left, top, width, and height params.
# if resize_to_stencil is true, the image is resized to stencil_w x stencil_h.
# after cropping and resizing, the resulting image is saved back to disk.
# any thumbnail image the image may have is automatically updated.
def crop!( options = {} )
# setup the default params
options[:crop_left] ||= 0
options[:crop_top] ||= 0
options[:crop_width] ||= 100
options[:crop_height] ||= 100
options[:stencil_width] ||= 100
options[:stencil_height] ||= 100
options[:resize_to_stencil] ||= false
# passed params could be strings, so convert them to ints/booleans
crop_l = options[:crop_left].to_i
crop_t = options[:crop_top].to_i
crop_w = options[:crop_width].to_i
crop_h = options[:crop_height].to_i
stencil_w = options[:stencil_width].to_i
stencil_h = options[:stencil_height].to_i
resize_to_stencil = false if (options[:resize_to_stencil] == false) || (options[:resize_to_stencil] == "false")
resize_to_stencil = true if (options[:resize_to_stencil] == true) || (options[:resize_to_stencil] == "true")
# call the appropriate crop method for the image processor we're using with attachment_fu
if self.class.include?(Technoweenie::AttachmentFu::Processors::RmagickProcessor)
crop_with_rmagick! crop_l, crop_t, crop_w, crop_h, stencil_w, stencil_h, resize_to_stencil
else
raise "You're using an unsupported image processor."
end
end
private
def crop_with_rmagick!(crop_l, crop_t, crop_w, crop_h, stencil_w, stencil_h, resize_to_stencil)
# create a temporary cropped version of our image
cropped_img = nil
self.with_image do |img|
if (crop_w <= 0) || (crop_h <= 0) || (crop_l + crop_w <= 0) || (crop_t + crop_h <= 0) || (crop_l >= img.base_columns) || (crop_t >= img.base_rows)
raise InvalidCropRect
end
cropped_img = img.crop(crop_l, crop_t, crop_w, crop_h, true )
cropped_img.resize!(stencil_w, stencil_h) if resize_to_stencil
end
# write the cropped image to a temp file, which attachment_fu will use
# to replace the existing image file (and thumbnail, if any) on save
self.temp_path = write_to_temp_file(cropped_img.to_blob)
@@thumbs.each { |suffix, size| create_or_update_thumbnail(self.temp_path, suffix, *size) }
#callback_with_args :after_resize, cropped_img
end
end