source: branches/version-2_12-dev/data/include/image_converter.inc @ 21441

Revision 21441, 8.3 KB checked in by Seasoft, 12 years ago (diff)

#1613 (ソース整形・ソースコメントの改善)

  • Zend Framework PHP 標準コーディング規約への準拠を高めた
  • Property svn:eol-style set to LF
  • Property svn:keywords set to Id
Line 
1<?php
2/**
3 * 画像ファイルの変換を行う
4 */
5class ImageConverter {
6    var $outputImageDir;         // 変換後の画像の保存先
7    var $outputImageType;        // 変換後の画像の形式
8    var $outputImageWidth;       // 変換後の画像の横幅
9    var $outputImageHeight;      // 変換後の画像の高さ
10    var $outputImageFileSize;    // 変換後の画像のファイルサイズ
11
12    // コンストラクタ
13    function ImageConverter() {
14        $this->outputImageDir    = realpath(realpath(dirname(__FILE__)));
15        $this->outputImageType   = 'jpg';
16        $this->outputImageWidth  = 320;
17        $this->outputImageHeight = NULL;
18        $this->outputFileSize    = 20000;
19    }
20
21    // 変換実行
22    function execute($inputImagePath) {
23        // 前処理
24        $filestat         = @stat($inputImagePath);
25        $imagesize        = getimagesize($inputImagePath);
26        $inputImageWidth  = $imagesize[0];
27        $inputImageHeight = $imagesize[1];
28        $inputImageType   = $imagesize[2];
29
30        // 今回実行用の一時変数をセット
31        $output_image_width = $this->outputImageWidth;
32        $output_image_height = is_null($this->outputImageHeight)
33            ? $inputImageHeight * ($output_image_width / $inputImageWidth)
34            : $this->outputImageHeight;
35        // GIF 画像は縮小後も GIF 画像で出力する。旧機種対応などで、機種用の画像形式に変換したい場合、expr3 に固定する。
36        $output_image_type = $inputImageType == IMAGETYPE_GIF ? 'gif' : $this->outputImageType;
37
38        $outputImageName  = sha1($inputImagePath . '_' . $this->outputImageWidth . '_' . $this->outputFileSize . '_' . $filestat['mtime']) . '.' . $output_image_type;
39        $outputImagePath  = $this->outputImageDir . '/' . $outputImageName;
40
41        if ($inputImageWidth <= $output_image_width) {
42            if ($inputImageHeight <= $output_image_height) {
43                $output_image_width  = $inputImageWidth;
44                $output_image_height = $inputImageHeight;
45            } else {
46                $output_image_width = $inputImageWidth * ($output_image_height / $inputImageHeight);
47            }
48        } else {
49            if ($inputImageHeight <= $output_image_height) {
50                $output_image_height = $inputImageHeight * ($output_image_width / $inputImageWidth);
51            } else {
52                if ($output_image_width / $inputImageWidth < $output_image_height / $inputImageHeight) {
53                    $output_image_height = $inputImageHeight * ($output_image_width / $inputImageWidth);
54                } else {
55                    $output_image_width = $inputImageWidth * ($output_image_height / $inputImageHeight);
56                }
57            }
58        }
59
60        // ファイルが存在するか確認し、存在しない場合のみ作成する
61        if (file_exists($outputImagePath)) {
62            $info['convert'] = FALSE;
63        } else {
64            // 元ファイル作成
65            switch ($inputImageType) {
66                case IMAGETYPE_GIF:
67                    $tempImage = imagecreatefromgif($inputImagePath);
68                    $arrTransparentColor = $this->getTransparentColor($tempImage);
69                    if (!empty($arrTransparentColor)) {
70                        imagecolortransparent($tempImage, $arrTransparentColor);
71                    }
72                    break;
73
74                case IMAGETYPE_JPEG:
75                    $tempImage = imagecreatefromjpeg($inputImagePath);
76                    break;
77
78                case IMAGETYPE_PNG:
79                    $tempImage = imagecreatefrompng($inputImagePath);
80                    break;
81
82                case IMAGETYPE_WBMP:
83                    $tempImage = imagecreatefromwbmp($inputImagePath);
84                    break;
85            }
86
87            if (!$tempImage) {
88                return false;
89            }
90
91            $scale = 1.0;
92            $outputImagePathTemp = $outputImagePath . '.tmp-' . rand();
93            do {
94                // 空ファイル作成
95                if ($output_image_type == 'gif') {
96                    // 縮小時のノイズ防止のためインデックスカラーで処理する。特に透過色を扱う上で重要。
97                    $outputImage = ImageCreate($output_image_width * $scale, $output_image_height * $scale);
98                } else {
99                    $outputImage = ImageCreateTruecolor($output_image_width * $scale, $output_image_height * $scale);
100                }
101
102                ImageCopyResampled($outputImage, $tempImage, 0, 0, 0, 0, $output_image_width * $scale, $output_image_height * $scale, $inputImageWidth, $inputImageHeight);
103
104                // ファイル出力
105
106                @unlink($outputImagePathTemp);
107
108                switch ($output_image_type) {
109                    case 'gif':
110                        if (!empty($arrTransparentColor)) {
111                            $transparent_color_id = imagecolorexact($outputImage, $arrTransparentColor['red'], $arrTransparentColor['green'], $arrTransparentColor['blue']);
112                            imagecolortransparent($outputImage, $transparent_color_id);
113                        }
114                        imagegif($outputImage, $outputImagePathTemp);
115                        break;
116
117                    case 'jpg':
118                        $quality = 75;
119                        // 表示可能なファイルサイズ以下になるまで、10%ずつクオリティを調整する
120                        do {
121                            @unlink($outputImagePathTemp);
122                            imagejpeg($outputImage, $outputImagePathTemp, $quality);
123                            $quality -= 10;
124                            clearstatcache();
125                        } while (filesize($outputImagePathTemp) > $this->outputFileSize && $quality > 0);
126                        break;
127
128                    case 'png':
129                        imagepng($outputImage, $outputImagePathTemp);
130                        break;
131
132                    case 'bmp':
133                        imagewbmp($outputImage, $outputImagePathTemp);
134                        break;
135
136                    default:
137                        GC_Utils_Ex::gfPrintLog('不正な画像タイプ: ');
138                        break;
139                }
140
141                // メモリ開放
142                imagedestroy($outputImage);
143
144                $scale -= 0.1;
145                clearstatcache();
146            } while (filesize($outputImagePathTemp) > $this->outputFileSize && $scale >= 0.5);
147
148            rename($outputImagePathTemp, $outputImagePath);
149
150            // メモリ開放
151            imagedestroy($tempImage);
152
153            $info['convert'] = TRUE;
154        }
155
156        $info['outputImagePath']  = $outputImagePath;
157        $info['outputImageName']  = $outputImageName;
158        return $info;
159
160    }
161
162    // Setter
163    function setOutputDir($outputDir)   { $this->outputImageDir   = $outputDir;  }
164    function setImageType($imageType)   { $this->outputImageType  = $imageType;  }
165    function setImageWidth($imageWidth) { $this->outputImageWidth = $imageWidth; }
166    function setImageHeight($imageHeight) { $this->outputImageHeight = $imageHeight; }
167    function setFileSize($fileSize)     { $this->outputFileSize   = $fileSize;   }
168
169    // Getter
170    function getOutputDir()   { return $this->outputDir;         }
171    function getImageType()   { return $this->outputImageType;   }
172    function getImageWidth()  { return $this->outputImageWidth;  }
173    function getImageHeight() { return $this->outputImageHeight; }
174
175    /*
176     * PrivateMethod
177     */
178    function beforeExecute() {
179    }
180
181    /**
182     * 透過GIFの色情報を返す
183     *
184     * @access private
185     * @param resource $image imagecreatetruecolor() のような画像作成関数が返す画像リソース。
186     * @return array 色情報
187     */
188    function getTransparentColor($image) {
189        $max_x = imagesx($image) - 1;
190        $max_y = imagesy($image) - 1;
191        for ($x = 0; $x <= $max_x; $x++) {
192            for ($y = 0; $y <= $max_y; $y++) {
193                $color_index = imagecolorat($image, $x, $y);
194                $arrColors = imagecolorsforindex($image, $color_index);
195                if ($arrColors['alpha'] !== 0) {
196                    return $arrColors;
197                }
198            }
199        }
200        return array();
201    }
202}
Note: See TracBrowser for help on using the repository browser.