
PHPの画像アップロードが任意のフォームで、
・新規画像アップロード
・上書き画像アップロード
・画像削除
の編集しDBにファイル名を保存する機能がある。
画像アップロードあった場合に、画像のサイズを取得し、縦横どちらかが基準値により大きい場合、比率を保ったまま縮小する。
もくじ
php関連記事

PHPのmb_send_mailでメール送信時に、はしご高「髙」やたつさき「﨑」など旧漢字や丸数字の日本語文字化け対策をする

MySQL/MariaDBのデータをPHP側で暗号化・復号する

phpで10進数と16進数、2進数、8進数の変換と0埋め表記

WordPressの条件分岐タグでページを判別する

PHPでpreg_splitの文字化けを回避しながらテキストを改行ごとに区切ってHTMLメールをつくる

WordPressテーマアップロード時に「辿ったリンクは期限が切れています。 もう一度お試しください。」と表示される

PHPで画像アップロード時に比率を保ったまま縮小する

phpで郵便番号を正規表現で3桁・ハイフン・4桁で出力するfunction

phpで電話番号のハイフンを正規表現で出力するfunction
フォームのHTML
HTML
<form action="" method="post" enctype="multipart/form-data">
<div class="form-group">
<label for="image">画像</label>
<input type="file" name="image" id="image"
accept=".jpg,.gif,.png,image/gif,image/jpeg,image/png">
<div>ファイルサイズ10MB以内</div>
<div id="already" style="display: none;">
<img id="preview">
<a href="javascript:void(0)" id="imagedel">
<img src="/img/icon/batu.jpg">
</a>
</div>
<canvas id="trimed_image" style="display: none;"></canvas>
<input type="hidden" name="" id="imagedel_send" value="del">
<button type="submit">投稿する</button>
</div>
</form>
formタグには、ファイルアップロードがあるので、enctype="multipart/form-data"をつけます。ファイルアップロードがある場合は、これを付けないとファイルの送信ができません。
input type="file"には、accept=".jpg,.gif,.png,image/gif,image/jpeg,image/png"をつけています。
ユーザーが選択できるファイル形式を、あらかじめ選択しておくことができます。
img id="preview"は、既存の画像がある場合の表示と、canvas id="trimed_image"アップロードされたファイルのプレビュー用です。
id="imagedel"は、既存の画像がある場合に表示される、画像削除用ボタンです。
aタグのjavascript:void(0)については、下記で確認してください。

画像アップロード時にプレビューを表示する
jQueryで画像アップロード時にプレビューを表示する詳細は、下記を参照してください。

is_uploaded_fileで、アップロードがあったかの判別する
php
if (is_uploaded_file($_FILES['image']['tmp_name'])) {
//アップロードがあった処理
}elseif(isset($_POST["img_d"])){
//画像削除があった処理
}else{
//アップロードがなかった処理
}
is_uploaded_fileで、アップロードがあったかの判別します。
あった場合は、アップロードされた画像が最優先で利用されます。
アップロードがなく、画像の削除ボタンが押されたときは、DBの更新やファイルの削除処理なんかをしていきます。
アップロードファイルが正しいかチェックする
php
if(!isset($_FILES['image']['error']) || !is_int($_FILES['image']['error'])){
throw new ErrorException('パラメータが不正です');
}
// $_FILES['image']['error'] の値を確認
switch ($_FILES['image']['error']) {
case UPLOAD_ERR_OK: // OK
break;
case UPLOAD_ERR_NO_FILE: // ファイル未選択
throw new ErrorException('ファイルが選択されていません');
case UPLOAD_ERR_INI_SIZE: // php.ini定義の最大サイズ超過
case UPLOAD_ERR_FORM_SIZE: // フォーム定義の最大サイズ超過 (設定した場合のみ)
throw new ErrorException('ファイルサイズが大きすぎます');
default:
throw new ErrorException('その他のエラーが発生しました');
}
$_FILES['image']['error']のerrorの値を調べて、アップロードファイルが正しいかチェックします。
ファイルサイズの大きさをチェックする
php
if ($_FILES['image']['size'] > 10485760) {
throw new ErrorException('ファイルサイズが大きすぎます');
}
$_FILES['image']['size']の値を調べて、アップロードファイルのサイズが問題ないかをチェックします。
MIMEタイプに対応する拡張子をチェックする
php
if (!$ext = array_search(
mime_content_type($_FILES['image']['tmp_name']),
array(
'gif' => 'image/gif',
'jpg' => 'image/jpeg',
'png' => 'image/png',
),
true
)) {
throw new ErrorException('ファイル形式が不正です');
}
mime_content_typeでアップロードされたファイルのMIMEタイプをチェックします。
今回は画像のアップロードなので、このくらいで問題ないと思います。
アップロードされた画像のファイル名を変更する
php
$rename_org = TALK_PFX.$insct_id."-".$local_id;
$rename_org = $rename_org.".".$ext;
if (!move_uploaded_file(
$_FILES['image']['tmp_name'],
"./".UP_PATH_TALK.$rename_org
)
) {
throw new ErrorException('ファイル保存時にエラーが発生しました');
}
$fileimagename = $rename_org;
// ファイルのパーミッションを確実に0644に設定する
chmod("./".UP_PATH_TALK.$rename_org, 0644);
$rename_orgであらかじめファイルの命名規則を作成しておき、チェックした拡張子を、合わせます。
アップロードされたファイル名はそのまま使わないようにしましょう。
その後、move_uploaded_fileで、ファイルをコピーします。
さらに、そのファイルのパーミッションを0644に変更します。自分は読み書き、他の人は読み込みのみ可能な状態にします。
画像の縦横のサイズを取得して縮小後のサイズを計算するfunction
php
function ratio($w, $h){
$newwidth = 0; // 新しい横幅
$newheight = 0; // 新しい縦幅
$res_w = 800; // 最大横幅
$res_h = 800; // 最大縦幅
if ($w > $h) {
// 横長の画像は横のサイズを指定値にあわせる
$ratio = $h / $w;
$newwidth = $res_w;
$newheight = $res_w * $ratio;
} else {
// 縦長の画像は縦のサイズを指定値にあわせる
$ratio = $w / $h;
$newwidth = $res_h * $ratio;
$newheight = $res_h;
}
$rtn_wh = [
'width' => $newwidth,
'height' => $newheight,
];
return $rtn_wh;
}
縦横どちらか大きい方の辺に合わせて、反対の辺を縮小した際の比率を計算します。
画像をリサイズするfunction
php
function img_resize($url, $res_w, $res_h, $p_w, $p_h, $x, $y, $picturename){
list($w, $h, $type) = getimagesize($url);
switch($type){
case IMAGETYPE_JPEG:
$in = imagecreatefromjpeg($url);
break;
case IMAGETYPE_GIF:
$in = imagecreatefromgif($url);
break;
case IMAGETYPE_PNG:
$in = imagecreatefrompng($url);
break;
}
// コピー画像のリソース
$out = imagecreatetruecolor($res_w, $res_h);
imagealphablending($out, false);
imagesavealpha($out, true);
// リサイズ
ImageCopyResampled($out, $in, 0, 0, $x, $y, $res_w, $res_h, $p_w, $p_h);
imagepng($out, UP_PATH_TALK.$picturename);
imagedestroy($out);
imagedestroy($in);
}
ratio関数で、取得した比率を元に画像を縮小するfunctionです。
ここでも拡張子をチェックします。
画像の縦横のサイズを取得してリサイズする
php
list($wid, $hei, $type) = getimagesize("./".UP_PATH_TALK.$rename_org);
if($wid >= 800 || $hei >= 800){
$wh = ratio($wid, $hei);
img_resize(
"./".UP_PATH_TALK.$rename_org,
$wh['width'], $wh['height'],
$wid, $hei,
0, 0, $rename_org);
}
$image_change = true;
画像の縦横サイズを取得してから、必要ならratio関数と、img_resize関数を使って、辺の最大値より大きい場合に、画像をリサイズします。
リサイズをしてもしなくても、DBは更新するので$image_changeをtrueにします。
画像の削除をする場合
php
elseif(isset($_POST["img_d"])){
$fileimagename = "";
$image_change = true;
}
$fileimagenameがDBに入れるファイル名で値をブランクにし、DBは更新するので、$image_changeをtrueにします。
最終的なコード
HTML
//アップロードがあった
if (is_uploaded_file($_FILES['image']['tmp_name'])) {
$rename_org = TALK_PFX.$insct_id."-".$local_id;
if(!isset($_FILES['image']['error']) || !is_int($_FILES['image']['error'])){
throw new ErrorException('パラメータが不正です');
}
// $_FILES['image']['error'] の値を確認
switch ($_FILES['image']['error']) {
case UPLOAD_ERR_OK: // OK
break;
case UPLOAD_ERR_NO_FILE: // ファイル未選択
throw new ErrorException('ファイルが選択されていません');
case UPLOAD_ERR_INI_SIZE: // php.ini定義の最大サイズ超過
case UPLOAD_ERR_FORM_SIZE: // フォーム定義の最大サイズ超過 (設定した場合のみ)
throw new ErrorException('ファイルサイズが大きすぎます');
default:
throw new ErrorException('その他のエラーが発生しました');
}
// ここで定義するサイズ上限のオーバーチェック
if ($_FILES['image']['size'] > 10485760) {//
throw new ErrorException('ファイルサイズが大きすぎます');
}
if (!$ext = array_search(
mime_content_type($_FILES['image']['tmp_name']),
array(
'gif' => 'image/gif',
'jpg' => 'image/jpeg',
'png' => 'image/png',
),
true
)) {
throw new ErrorException('ファイル形式が不正です');
}
$rename_org = $rename_org.".".$ext;
if (!move_uploaded_file(
$_FILES['image']['tmp_name'],
"./".UP_PATH_TALK.$rename_org
)
) {
throw new ErrorException('ファイル保存時にエラーが発生しました');
}
$fileimagename = $rename_org;
// ファイルのパーミッションを確実に0644に設定する
chmod("./".UP_PATH_TALK.$rename_org, 0644);
list($wid, $hei, $type) = getimagesize("./".UP_PATH_TALK.$rename_org);
if($wid >= 800 || $hei >= 800){
$wh = ratio($wid, $hei);
img_resize(
"./".UP_PATH_TALK.$rename_org,
$wh['width'], $wh['height'],
$wid, $hei,
0, 0, $rename_org);
}
$image_change = true;
}elseif(isset($_POST["img_d"])){
$fileimagename = "";
$image_change = true;
}else{
$fileimagename = "";
}
検証中のため、漏れ等あるかもしれませんので、ご注意ください。


コメント