PHP 上級試験範囲 グラフィックスまとめ

# HTMLページへの画像埋め込み

- 画像が埋めこまれているHTMLページをwebブラウザに表示しようとすると、webブラウザからwebサーバへ、HTMLページそのものに対するリクエストと、画像に対するリクエストの両方が送信される。

- webサーバからwebブラウザへ送信されるレスポンスは、**レスポンスヘッダ**と**レスポンスボディ**の2つの部分で構成されている。
レスポンスヘッダには`「Content-Type」`というヘッダが含まれている。
webブラウザはこのヘッダにより、レスポンスボディに含まれるデータの種別を判別している。
レスポンスボディ部分に含まれるデータは、HTMLファイルや画像ファイルそのものを指す。

- HTMLページ内に`<img src ="test.php" />`のような記述をし、画像を生成するPHPスクリプトが実行できる。

```php:test.php
header('Content-Type: image/jpg');
readfile('/tmp/test.jpg');
```

- HTMLページ内に`<img src ="test.php?text=OK" />`のような記述をし、「OK」というテキストが描画された画像を生成するPHPスクリプトを実行することができる。

- HTMLページ内に`<img src ="buttons/ok.png" />`のような記述をし、「OK.png」がwebサーバに存在しない場合のみ、その画像を生成するPHPスクリプトを実行することができる。

# グラフィックスの基本概念

- 画像内の色の情報は、パレットに記録されている。
パレットとは画像内の色情報の配列で、RBG（赤、青、緑）をそれぞれ0（暗い）～255（明るい）の256段階で表したもの。

- 画像は`jpg`や`png`など、さまざまなファイルフォーマットで保存、送信することができる。
なかには、`gif`のように1ファイルあたり最大256色までしか記録できないという制限があるものもある。

- [アンチエイリアス](http://e-words.jp/w/%E3%82%A2%E3%83%B3%E3%83%81%E3%82%A8%E3%82%A4%E3%83%AA%E3%82%A2%E3%82%B9.html)を有効にすると、ジャギーを目立たなくすることができる。

- アルファチャネルとは、透明度を表す情報のことである。


# GD拡張モジュール

### GD拡張モジュールの確認とインストール

GDモジュールが使用できるかどうかは、phpのphpinfo()で確認することができる。

```php:php
phpinfo();
```
gdと書いてある欄が表示されていて`GD Support`が`enable`になっていれば使用することができる。
ない場合はインストール。

■インストール

phpのバージョン確認

```
php -v
```

PHPのバージョンに合った、GDをインストール

```
yum list | grep gd
sudo yum install php72-php-gd.x86_64 --enablerepo=remi
```
インストール先が想定と違うので、インストール先のパスを確認し、シンボリックリンクを作成

```
rpm -ql php72-php-gd.x86_64
/opt/remi/php72/root/usr/lib64/php/modules/gd.so

ln -s /opt/remi/php54/root/usr/lib72/php/modules/gd.so /usr/lib64/php/modules/gd.so
```
php.iniのgdに`extension=gd.so`記述を追加し、apacheを再起動

```
sudo vi /etc/php.ini 

service httpd restart
```

インストール完了。

### GD拡張モジュールについて

`GD`は、オープンソースの画像処理ライブラリ。
GDを使用すると、画像ファイルの読み書き、ボタンやグラフの描画、サムネイルの作成などの画像処理をプログラム上から行える。
`GD拡張モジュール`は、GDをPHPから扱えるようにする拡張モジュールである。

* GDが作成する画像の種類には、`パレット形式の画像`と`フルカラー画像`の2種類がある。

| パレット形式の画像|フルカラー画像|
|:-----------------|:------------------|
| 各ピクセルはパレットの色番号を持つ（256色）|各ピクセルは赤・緑・青の情報を持つ。（色数無制限）|

* GDの図形描画関数は、画像の左上を(0, 0)とする座標を使用して、描画位置を指定する。

* GDは、点、直線、短形、円、多角形などの図形を描画するための関数を提供している。
これらの関数の第1引数に`画像リソース`を与えることで、その画像に図形の描画を行うことができる。
画像リソースは、GD上で操作している画像を指し示すものであり、既存の画像ファイルを読み込んで作成するか、または画像ファイルを読み込まずメモリ上に新規に作成する。
画像リソースはPHPのオブジェクトとは異なるものである。

* 以下でGDの機能のサポート状況を調べることができる。

```php:php
var_dump(gd_info());

// 結果
array(13) {
  ["GD Version"]=>
  string(5) "2.2.5"
  ["FreeType Support"]=>
  bool(true)
  ["FreeType Linkage"]=>
  string(13) "with freetype"
  ["GIF Read Support"]=>
  bool(true)
  ["GIF Create Support"]=>
  bool(true)
  ["JPEG Support"]=>
  bool(true)
  ["PNG Support"]=>
  bool(true)
  ["WBMP Support"]=>
  bool(true)
  ["XPM Support"]=>
  bool(true)
  ["XBM Support"]=>
  bool(true)
  ["WebP Support"]=>
  bool(true)
  ["BMP Support"]=>
  bool(true)
  ["JIS-mapped Japanese Font Support"]=>
  bool(false)
}
```

* `ImageTypes()`を使用すると、現在の動作環境でサポートされるファイルフォーマットを調べることができる。
ImageTypesの返り値は、サポートされるファイルフォーマットに対応するビットフィールド（IMG_GIF、IMG_PNG、IMG_JPEGなどの論理和）。
サポートされるファイルフォーマットを調べる方法は以下。

```php:php
if (ImageTypes() & IMG_GIF) {
    echo 'GIFがサポートされています。';
}

// 結果：GIFがサポートされています。
```
* `ImageCreateFromGIF()`、`ImageCreateFromPNG()`、`ImageCreateFromJPEG()`は、それぞれ既存のフォーマットファイルから画像データを読み取ることで、画像リソースを作成し、その画像リソースを返す。

```php:php
$file = 'img/test.jpg';
$res = ImageCreateFromJPEG($file);

var_dump($res);

// 結果：resource(185) of type (gd)

```

* 画像リソースは、`ImageCreate()`、`ImageCreateTrueColor()`で画像の幅・高さを指定して新規に作成することができる。
ImageCreate()は、パレット形式の画像を新規作成し、画像リソースを返す。
ImageCreateTrueColor()は、パレット形式の画像を新規作成し、画像リソースを返す。

```php:php
$width = 300;
$height = 200;
$res = ImageCreate($width, $height);

var_dump($res);

// 結果：resource(184) of type (gd)
```

* ImageCreate()を使用して作成したパレット形式の画像の場合、その画像リソースに対して`ImageColorAllocate()`で最初に作成した色が、その画像の背景色となる。


■背景色の設定

```php:php
$width = 300;
$height = 200;
$res = ImageCreate($width, $height);
$color = ImageColorAllocate($res, 255, 0, 0);
```

* `ImageGIF()`、`ImagePNG()`、`ImageJPEG()`などの関数を使用した場合、対応するContent-Typeヘッダが自動的に出力されるわけではない。
`header()`を使用して明示的に送信する必要がある。

* スクリプト内で作成された画像リソースは、そのスクリプトの実行が終わると自動的に破棄される。

* `ImageSetPixel()`は、点を描画する関数である。

* `ImageLine()`は、直線を描画する関数である。
※曲線を描画する関数は存在しない。

* `ImageDashedLine()`は、破線を描画する関数である。

* `ImageRectangle()`は短形（四角形）を描画する関数である。

* `ImageFilledRectangle()`は、内部を塗りつぶした短形（四角形）を描画する関数である。

* GDには三角形を描画する関数はない。

* `ImagePolygon()`は、多角形（ポリゴン）を描画する関数である。

* `ImageFilledPolygon()`は、内部を塗りつぶした多角形（ポリゴン）を描画する関数である。

* `ImageEllipse()`は、楕円を描画する関数である。

* `ImageFilledArc()`は、内部が塗りつぶされた楕円を描画する関数である。

* `ImageFill()`は、塗りつぶしを行う関数である。

* `ImageFillToBorder()`は、特定の色で囲まれた部分の塗りつぶしを行う関数である。
塗りつぶしのパターンを指定することはできないため、縞模様や網目模様に塗りつぶしを行うことはできない。

* グラデーションがかかった画像をImageFill()で塗りつぶすと、塗りつぶし開始位置と同色の部分だけが塗りつぶされるので、グラデーション全体を塗りつぶすことはできない。

* `ImageRotaete()`は画像の回転を行う関数である。
第一引数の画像リソースは変更されず、回転を行った新しい画像リソースを返す。
第二引数に正の値を指定すれば反時計回りに、負の値を指定すれば時計回りに回転させることができる。
回転の中心座標を指定することはできない。回転の中心座標は、画像の中央となる。
回転によって元画像の辺を超える場合は、回転先の画像を収めるのに必要なだけ幅・高さが拡大される。
拡大によって生じた領域は第三引数に指定した色で塗りつぶされる。

* `ImageString()`は組み込みのフォントを使用して文字列を描画する関数である。
ImageString()は、日本語を含むマルチバイト文字には対応していない。
そのため日本語を描画することができない。

* `ImageTTFText()`は、TrueTypeフォントを使用して文字列を描画する関数である。
デフォルトでは、ImageTTFText()はアンチエイリアスを使用して描画を行う。
アンチエイリアスを無効にするには、第六引数の描画色に負数を指定する。

* `ImageTTFBBox()`は、指定した文字列を描画する際に必要となる領域（バウンディングボックス）の頂点4点の座標配列で返す。文字列や四角形を描画する関数ではない。

* `ImageSx()`は画像の幅、`ImageSy()`は画像の高さを求める関数である。

* `ImageCopyresized()`、`ImageCopyResampled()`は、画像のコピーと拡大・縮小を行う関数である。
ImageCopyResampled()は、GDバージョン2.x以降で使用することができる。
ImageCopyResized()よりも処理に時間がかかるが、リサンプリング（マージされるピクセルの色の平均を取る処理）を行うことで、品質の高い拡大・縮小を行うことができる。

* ImageCreate()で作成したパレット形式の画像には、256色までしか使用できないという制限がある。
リサンプリングの際にはより多くの色が必要になることがあるため、リサンプリングによって256色以上の色が
必要になった場合は必要な色の割り当てができなくなる。したがって、リサンプリングをする際は、ImageCreateTrueColor()を使用してフルカラー画像のリソースを作成するようにする。

* 画像リソースがパレット形式の画像化フルカラー画像化どうかを確認するには、`ImagelsTrueColor()`を使用する。フルカラーの場合は、`true`を返す。

* フルカラー画像におけるアルファチャネルのビット数は7ビットである。

* `ImageTrueColorToPalette()`は、フルカラー画像をパレット形式の画像に変換する。

* 画像内の位置を指定して、その位置の色を調べるには、`ImageColorAt()`を使用する。

* `ImageColorsForIndex()`は、ImageColorAt()が返した値をRGB値およびアルファチャネル値を含む配列に変換する。

* GDにおけるアルファチャネル値は、128段階の設定が可能。
10進数では0～127の範囲となる、
数字が大きいほど透明度が大きくなる。半透明の場合は、アルファチャネル値に127の約半分の63を指定する。

* `ImageColorResolveAlpha()`は、アルファチャネル値（透明度）を含む色を作成する。

* `ImageAlphaBlending()`は、イメージのブレンドモードを設定する。

* フルカラー画像のデフォルトのブレンドモードはtrue（アルファブレンディングが有効）。
* これは、色のアルファチャネルを反映した描画が行われる。ImageAlphaBlending()を使用することで、アルファブレンディングを一時的に無効にしたり、再び有効に戻したりすることができる。

### 参照

徹底攻略 PHP5 技術者認定 [上級] 試験問題集 [PJ0-200]対応