#!/usr/bin/perl use CGI::Carp qw(fatalsToBrowser); use Image::Magick; use Digest::MD5(md5_hex); # last update 2011/12/08 19:02 # @author yunoki # -------------------------------------------------------------- # # -------------------------------------------------------------- # mode # fit : 縦横、広い方にあわせてリサイズ # fill : 縦横、広い方にあわせてリサイズ、不足分は白で埋める # crop : 縦横、狭い方にあわせて正方形で繰り抜き # max : 縦横サイズ以内に収める # -------------------------------------------------------------- # size # 320x240 のように表記 # 60x60 → 60 でもOK # 60x60+90 右へ90度回転 # 60x60-90 左へ90度回転 # 初期設定 my $base_dir = '../../../../../home2/www/narikiri'; my $cache_dir = '../../../../../home2/www/narikiri/_cache_dir'; # my $base_dir = '../../_home2_narikiri_'; # my $cache_dir = '../../_home2_narikiri_/_cache_dir'; my $notfound = 'notfound.gif'; #my $water_mark = 'wm.png'; # クエリーの解析 my $q = $ENV{'QUERY_STRING'}; my ( $mode, $size, $path ) = $q =~ m|(\w+)\/([0-9x@]+)\/(.*)|; $path = '' if ( $path =~ /\.\.\// ); # security my ( $size, $angle ) = split( /\@/, $size ); $size = sprintf( '%dx%d', $size, $size ) if ( $size !~ /x/ ); my $file_path = sprintf( '%s/%s.jpg', $base_dir, $path ); $q = md5_hex($q); my $cache_path = sprintf( '%s/%s.jpg', $cache_dir, $q ); mkdir( $cache_dir, 0755 ); # エラーチェック if ( !-e $file_path ) { $file_path = $notfound; unlink "$cache_path"; } # キャッシュを優先表示 if ( -e $cache_path ) { if ( ( stat $cache_path )[9] > ( stat $file_path )[9] ) { img_output($cache_path); } else { unlink "$cache_path"; } } my $image = Image::Magick->new; $image->Set( size => $size ); $image->Read($file_path); if ( $mode eq 'fit' ) { $image->Scale( geometry => $size ); } elsif ( $mode eq 'fill' ) { my $image_base = Image::Magick->new; $image_base->Set( size => $size ); $image_base->Read('XC:#ffffff'); $image->Scale( geometry => $size ); $image->Set( size => $size ); $image_base->Composite( image => $image, compose => 'Over', gravity => 'Center' ); $image = $image_base; } elsif ( $mode eq 'crop' ) { my ( $width, $height ) = $image->Get( 'width', 'height' ); my $thin = ( $width < $height ) ? $width : $height; my ( $x, $y ) = split( /x/, $size ); $width *= $x / $thin; $height *= $y / $thin; my $left = ( $width - $x ) / 2; my $top = ( $height - $y ) / 2; $image->Scale( geometry => $width ); $image->Crop( geometry => "$size+$left+$top" ); } elsif ( $mode eq 'max' ) { my ( $width, $height ) = $image->Get( 'width', 'height' ); my ( $x, $y ) = split( /x/, $size ); my ( $w, $h ) = fitSize( $width, $height, $x, $y ); $image->Scale( geometry => sprintf( '%dx%d', $w, $h ) ); } # ブラウザに出力 if ( $file_path eq $notfound ) { print "Content-Type: image/jpeg\n\n"; binmode STDOUT; $image->Write("jpeg:-"); } else { $image->Rotate( degrees => $angle ); if ($water_mark && $size >= 100 ) { my $image_wm = Image::Magick->new; $image_wm->Read($water_mark); $image->Composite( image => $image_wm, compose => 'Over', gravity=> 'NorthWest',opacity=>'20%'); } $image->Comment('kddi_copyright=on,copy="NO"'); # $image->Comment('kddi_copyright=on'); # $image->Comment('copy=no'); $image->Write("$cache_path"); img_output($cache_path); } # サブルーチン sub img_output { my $path = shift; print "x-jphone-copyright: no-store,no-transfer,no-peripheral\n"; print "Content-Type: image/jpeg\n\n"; binmode STDOUT; open( IMG, "$path" ); binmode IMG; print ; close(IMG); exit; } sub fitSize { my ( $obj_w, $obj_h, $frame_w, $frame_h ) = @_; return 0 if ( !$obj_w * $obj_h * $frame_w * $frame_h ); my $scale_w = $frame_w / $obj_w; if ( $scale_w < 1 ) { # > $obj_w *= $scale_w; $obj_h *= $scale_w; } my $scale_h = $frame_h / $obj_h; if ( $scale_h < 1 ) { # > $obj_w *= $scale_h; $obj_h *= $scale_h; } $obj_w, $obj_h; } 1;