web-dev-qa-db-ja.com

PHPページを画像として返します

画像ファイル(正確には.jpeg)を読み取って、ページ出力に「エコー」しようとしていますが、画像を表示しています...

私のindex.phpには次のような画像リンクがあります:

<img src='test.php?image=1234.jpeg' />

そして私のPHPスクリプトは基本的にこれを行います:

1)1234.jpegを読む2)ファイルの内容をエコーする... 3)出力をmimeタイプで戻す必要があると感じているが、ここで迷子になる

これを理解したら、入力されたファイル名をすべて削除し、イメージIDに置き換えます。

不明な場合、または詳細が必要な場合は、返信してください。

60
MichaelICE

PHPマニュアルには この例

<?php
// open the file in a binary mode
$name = './img/ok.png';
$fp = fopen($name, 'rb');

// send the right headers
header("Content-Type: image/png");
header("Content-Length: " . filesize($name));

// dump the picture and stop the script
fpassthru($fp);
exit;
?>

重要な点は、Content-Typeヘッダーを送信する必要があることです。また、<?php ... ?>タグの前後にファイルに余分な空白(改行など)を含めないように注意する必要があります。

コメントで示唆されているように、?>タグを省略することにより、スクリプトの最後に余分な空白が含まれる危険を回避できます。

<?php
$name = './img/ok.png';
$fp = fopen($name, 'rb');

header("Content-Type: image/png");
header("Content-Length: " . filesize($name));

fpassthru($fp);

スクリプトの上部の空白を慎重に避ける必要があります。空白の特に扱いにくい形式の1つは、 TF-8 BOM です。それを避けるには、スクリプトを「ANSI」(メモ帳)、「ASCII」、または「署名なしのUTF-8」(Emacs)などとして保存してください。

105
Martin Geisler

readfile()はこのタスクを実行するためにも一般的に使用され、fpassthru()を使用するよりも優れたソリューションのようです。

私にとってはうまく機能し、 ドキュメント によれば、メモリの問題は発生しません。

動作中の私の例を次に示します。

$file_out = "myDirectory/myImage.gif"; // The image to return

if (file_exists($file_out)) {

    //Set the content-type header as appropriate
    $image_info = getimagesize($file_out);
    switch ($image_info[2]) {
        case IMAGETYPE_JPEG:
            header("Content-Type: image/jpeg");
            break;
        case IMAGETYPE_GIF:
            header("Content-Type: image/gif");
            break;
        case IMAGETYPE_PNG:
            header("Content-Type: image/png");
            break;
       default:
            header($_SERVER["SERVER_PROTOCOL"] . " 500 Internal Server Error");
            break;
    }

    // Set the content-length header
    header('Content-Length: ' . filesize($file_out));

    // Write the image bytes to the client
    readfile($file_out);

}
else { // Image file not found

    header($_SERVER["SERVER_PROTOCOL"] . " 404 Not Found");

}
20

これは動作するはずです。遅いかもしれません。

$img = imagecreatefromjpeg($filename);
header("Content-Type: image/jpg");
imagejpeg($img);
imagedestroy($img);
4
Drew LeSueur

Content-Lengthなしで作業しました。多分リモート画像ファイルの理由の仕事

// open the file in a binary mode
$name = 'https://www.example.com/image_file.jpg';
$fp = fopen($name, 'rb');

// send the right headers
header('Cache-Control: no-cache, no-store, max-age=0, must-revalidate');
header('Expires: January 01, 2013'); // Date in the past
header('Pragma: no-cache');
header("Content-Type: image/jpg");
/* header("Content-Length: " . filesize($name)); */

// dump the picture and stop the script
fpassthru($fp);
exit;
2
Berk