アレルギー性鼻炎しんどいです。今日はGDライブラリのお話。

風邪でだいぶしんどかったんですが、治ったと思ったら鼻が治らず・・・実はアレルギー性鼻炎なのです。去年の11月に耳がふさがった感じになって耳鼻科に行って初めて知った事実ですが・・・。なんのアレルギーなのかはさっぱり。たぶんホコリとかだと思います。



今日はImagickの合成をGDライブラリでやります。なかなか時間が取れなくて見本が出せないのが残念です。
時間ができたら合成した見本とか載せたいです。


さて、コードです。
実は合成するだけならImagickとやり方とかほとんど変わらないです。
GDライブラリの場合読み込むときにそれが何なのかによって指定する必要があります。
ImagickでのreadImageがImageCreateFrom〜〜に変わります。
まずjpg
$image = ImageCreateFromJPEG(ファイル場所/ファイル名.jpg);
そしてpng
$image = ImageCreateFromPNG(ファイル場所/ファイル名.png);
最後にgifです。
$image = ImageCreateFromGIF(ファイル場所/ファイル名.gif);

後はそんなに変わらない。
ImagickのcompositeImageがimagecopyに変わるだけ。
imagecopy($image,$image2,0,0,0,0,240,252 );
ただimagecopyの方がいろいろ指定できます。
3,4番目の数字が$imageのどこに置くか(x,y)を指定して、$image2の開始位置を5,6番目の数字で指定(x,y)し、7,8番目の数字の場所(x,y)までをコピーするという感じなのです。
なのでこういう感じにすると、
imagecopy($image,$image2,60,0,0,0,240,252 );
$image2が少し右に寄った状態で合成されます。
あとは画像として出力するだけ。


実はGDライブラリだとバイナリに変換できないのです。
DBに入れようと思うとファイル書き出しして読み込んでになります。
(間違ってたらすいません。)


なので後はファイル出力のみ・・かな?
これも拡張子によって
imagejpeg($image,"./ファイル場所/ファイル名.jpg");
imagepng($image,"./ファイル場所/ファイル名.png");
imagegif($image,"./ファイル場所/ファイル名.gif");
の3種類に分かれます。わかりやすくていいですよね。

後はお片付けします。
imagedestroy($image);
imagedestroy($image2);



私はImagick使いすぎてあまりGDライブラリを使ってないのですが、
GDライブラリは大量の画像処理の際の速度に思わず「はふん」ってなります。
Imagickだと結構な時間待つんですけど、GDライブラリは意外と早く終わります。

Imagickじゃなきゃできないことってありますけど、GDライブラリじゃないとできないこともあると思うので用途分けして使うのが一番です。
私は慣れてるからってついついなんでもかんでもImagickで合成しちゃうんですけどね・・・。サーバーの負荷を考えるとよろしくないですが。



というまだGDライブラリ初心者の話でした。




早く鼻炎をなんとかしないと!(`・ω・´)

アニメーションGIF合成のお話。

アニGIFを扱ったのがだいぶ前なので忘れてて今までファイル生成がうまくできなかったという・・・。
コメントってきちんと書いとくべきですよね・・・。
ついめんどくさくなってやらないことが多いので。
とりあえずなんとかできました。
すごくめんどくさい処理やってます。まずコードをごらんくだしあ。

//アニGIFを重ねるファイル。これはGIFでもjpgでもおk。
$image = new Imagick();
$image->readImage(ファイル先/ファイル名);
//今後の為にバイナリ保存。まぁ、もっかいreadImageでも別に悪くはないと思うんですけどなんとなく。
$binary = $image->getImagesBlob();
//今回の主役アニGIF君
$ani_image = new Imagick();
$ani_image->readImage($face_gif);

$max_frames = 0;
//まずこのアニGIFが何枚重なっているか調べます
foreach($ani_image as $img_ani){
  //フレーム数を取得
  $num = $img_ani->getNumberImages();
  if($num > $max_frames){
    //MAXフレーム数を取得
    $max_frames = $num;
  }
  unset($img_ani);
}

$i = 0;
foreach($ani_image as $img_ani){
 //アニGIFの枚数分合成
if($i >= $max_frames){
break;
}
 $img_ani->setImageIndex($i);
  if($i == 0){
    //アニGIFの1枚目だったら
    $pose_image->compositeImage ( $img_ani , imagick::COMPOSITE_OVER , 0 , 0 );
    //アニGIFの遅延設定
    $pose_image->setImageDelay(50);// アニメーションディレイの設定
    $pose_image->setImageIterations(0);// アニメーションループの設定(0だとループ設定)
  }else{
    //2枚目以降
    $avatar_b = new Imagick();
    //-- 画像を重ねていく
    $avatar_b->readImageBlob( $pose_binary );
    $avatar_b->compositeImage ( $img_ani , imagick::COMPOSITE_OVER , 0 , 0 );
    $avatar_b->setImageDelay(50);// アニメーションディレイの設定
    $pose_image->addImage($avatar_b);
    //使いまわすから消すらしい
    $avatar_b->destroy();
  }
  $pose_image->writeImages("./face_img/swf/{$i}.gif", true) ;
  $i++;
  unset($img_ani);
}
//最適化したい。
// 一度結果画像を書き出す
$file_name1 = "ファイル場所/ファイル名.gif.MIFF";
$file_name2 = "ファイル場所/ファイル名.gif";

$pose_image->writeImages($file_name1, true) ;
// Quantizeが使えないので保存ファイルをconvert +mapに通す
exec("/usr/local/bin/convert {$file_name1} -layers OptimizeTransparency +map {$file_name2}") ;
$pose_image->destroy();
//別ファイルにしたい時はこの下もいるかもです。
//特に問題なければ$file_name2の場所が完成品です
$pose_image = new Imagick();
$pose_image->readImage( $file_name2 );
unlink($file_name1);
unlink($file_name2);

$pose_image->writeImages("ファイル場所/ファイル名.gif", true) ;

とまぁ、ここまでがコードなわけですが、
素材画像は↓の2つで、

これがgifを合成するjpg画像。(22.7KB)


これがアニgif。(30.1KB)
この2つを合成していきます。

まず1コマ目を普通に合成。(これで48.4KB)

1枚目の上に2コマ目をjpgと合成した状態で重ねる。
(普通に2枚分のサイズなので96.8KBです)
もともと大きさが251×250のjpgを合成してますが、それがGIFに変わるのでサイズが・・・。
これを携帯で表示させようと思うとぎりぎりになります。

convert後の画像。これが一応完成品です。
画像によってサイズはいろいろ変わると思いますがこれは71.2KBになりました。
アニGIF自体2コマしかないので25KBしか減ってないですが、
もう少し容量の少ない画像で4コマ分合成をしてみると容量がだいぶ削れた・・・ハズ。
いろいろ試しながらやってみてください。私は必死にグーグル先生にお願いしてました。
これの難点はかならずファイル書き出しを行ってからconvertしなければいけないところ・・・。
あとconvertしても結構2枚目にゴミが残っていて、物によってはすごくクオリティが低く感じます・・。
できればファイル書き出しとかせずにクオリティを維持してやりたいですぉ・・。

今はImagick2.0なのでImagick3.0とかバージョンが上がったらいい感じになったりするのかしら。

PHPなう。

初めて知った言語はC言語ですが、ここ一年はPHPしかいじってないのでC言語はすっかり忘れました。

さて・・・PHPの何の話をしよう・・・。
正直自分もそんな高度な技術は知らないのでdate関数でいっか。

よくmktimeと一緒に使われるdate関数。
一年前PHP初心者な時はdate関数の有効活用とかできてなかったです。
ひと月分のデータを出すために末日を出そうとして

$year = date("Y");
$mon = date("m");
//2月末日を出す
$lasttime = mktime(0,0,0,3,0,$year);
$lastday = date("d",$lasttime);

こういうのはわかったんですが
なぜか年またぎの時に

$mon1 = $mon+1;
$year1 = $year;
if($mon1==13){
$mon1=1;
$year1 = $year+1;
}

こういうものや

if($mon==12){
//今月が12月
 $lasttime = mktime(0,0,0,1,0,$year+1);
}else{
//それ以外
 $lasttime = mktime(0,0,0,$mon+1,0,$year);
}
$lastday = date("d",$lasttime);

こんなif文書いたりしてました。今思えば何やってんだがな感じですが、難しく考えてしまうのでその当時は本気でこんなことしてました。ちなみに先頭に0のつく"Y-m-d"なのはsqlに投げるためです。

まぁ、今も結構適当にやっちゃってるんで後で見返すと「これは一体何がしたかったんだ?」ってことを思ったりします。あの頃はひと月っていう単位と格闘する日々でした・・・。(^_^;)



実は最近風邪っぴきなのです。寒くなったり暖かくなったりの連続だったので春だと思って薄着をして失敗しました・・。本格的に暖かくなってきたので早めに治したいです!(`・ω・´)

今日は普通の話。

昨日登録したんですが、4月23日の
Japan AWS User Group (JAWS-UG) - Osaka勉強会 第2回
http://atnd.org/events/14351
に行くことになりました。
ハンズオンのために小さいノートパソコンを買おうか悩み中です。

ノートパソコンを買って持って行く場合、腐女子と公言しているからには壁紙はBLじゃないとダメなのかしらとかちょっと思ってます。
18禁ゲームの壁紙とかじゃダメかな・・・。

ちなみにいきなり始めたブログですけど自己紹介が「腐女子です」しかないことに気づいたので腐女子です以外の簡単な自己紹介。


えっと・・・


好きなBLゲームは「王子さまLv1・1.5・2」です。「王子さまLv3」が出ると信じてLv2の最後に出たコードは未だに大切に持ってます。




初めてのエロゲは「魔彩子雀」っていう脱衣麻雀ゲームです。ググってもちゃんとした画像はそんなに出てこないです。
その時8インチフロッピーだったのか5.25インチフロッピーだったのかも思い出せないですし。まぁ、7歳の記憶なんてそんなもんです。

ということでした。
以上自己紹介終わり。

せっかくImagickの話をしたので。

私が最近よく使うのはこういう処理。知ってる人は知ってる処理だと思います。

$a_jpg="ファイル場所/ファイル名.jpg";
$b_gif="ファイル場所/ファイル名.gif";

$a_image = new Imagick();
$a_image->readImage($a_jpg);
$b_image = new Imagick();
$b_image->readImage($b_gif);

//画像合成($a_jpgや$b_gifは別にgifではなくてもjpgでもpngでもOKです。)0,0は数字を入れることで位置をずらして合成できます
$a_image->compositeImage ( $b_image , imagick::COMPOSITE_OVER , 0 , 0 );

//合成したものはjpgですよ!っていう宣言。拡張子をいろいろ混ぜて合成する時に必要だったり。
$a_image->setImageFormat('jpg');

//jpgだったら画質が変更できます。サイズを小さくしたい時は数字をいろいろ変えてください。
$a_image->setImageCompression(Imagick::COMPRESSION_JPEG);
$a_image->setImageCompressionQuality(80);

//バイナリ出力なのです。
$a_img = $a_image->getImageBlob();

//使い終わった$a_image、$b_imageはデストロイしましょう。エコのために!(?)
$a_image->destroy();
$b_image->destroy();

//ファイル生成
$fr = fopen("ファイル出力先場所/ファイル名.jpg","w");
fwrite($fr ,$a_img );
fclose($fr);

以上で終了です。
とりあえずImagickの画像合成ってこんな感じ〜みたいなコードでした。

はい、お待たせしました。画像を使った講義の時間です。
適当に作ったので白いギザギザはご愛嬌。


↑実際に使った画像。上を加工して使いました。下は背景の代わり。背景(jpg)→$a_image
加工すると↓こうなります。3つのパーツに分けてみた。

まずシエル君。(png)→$b_image

そしてセバスチャン(手なし)(png)→$c_image

セバスの手。(gif)→$d_image

そして上の通り(readImageとcompositeImageは画像枚数と合成回数分増えます。)に合成すると

こんな感じになります。

そしてセバスチャン(手なし)を合成する時に
$a_image->compositeImage ( $c_image , imagick::COMPOSITE_OVER , -43 , 0 );
セバスの手を合成する時に
$a_image->compositeImage ( $d_image , imagick::COMPOSITE_OVER , -35 , 0 );
とすると…

こんな感じでセバスチャンが寄って来た画像が合成できます!両方横向きだったらいい感じにくっつけるんですけどね…。

PHPカンファレンス関西

4月2日にPHPカンファレンス関西に参加してきました

カンファレンスや勉強会などは初めてだったので会場の人の多さにびっくりしました。
あとみなさんパソコン持ちだったのでそれが普通なのか〜と思いました。
セッションはクラウドスマートフォンなどの話題が多かったですが、
やはりドラ娘がとても印象的でしたww
是非次回はドラ男(ry

このパワポは懇親会LTで使ったものです。
せっかくパワポを作ってSlideShareに上げたので勢いでブログ始めてみました。
30分であわあわしながら作ったパワポでLTをさせて頂いたのですが、
お暇な方はよろしければちょっとのぞいて見てください。
ちなみに私は初LTだったのできちんと「真面目に」LTしました!パワポはともかく!

女性が少なくて少し心細かったです・・・。
もっと女性が増えたらいいなと思います!(`・ω・´)