Capturing PNG stream with PHP output buffer - php
I am currently attempting to write a web service that generates a QR code for a given string. I am using PHP QR Code (http://phpqrcode.sourceforge.net/) to generate the QR code, like this:
QRcode::png('PHP QR Code :)');
Result: a PNG stream of the QR Code is displayed on the screen.
As this is a void function that outputs directly to the browser, this prevents me from properly returning the image.
I would like to capture the PNG stream with PHP's output buffer and have my web service return this captured image.
I have set up the following test code on a plain php page for testing purposes:
include('/vendor/phpqrcode/qrlib.php');
$scancode = "testcode";
ob_implicit_flush(false); //just in case
ob_start();
QRcode::png($scancode);
$output = ob_get_contents();
ob_end_clean();
echo "--" . $output . "--";
die();
However, when I run the code the buffer does not work as I had planned. No matter what I do, a broken image is always displayed as soon as I call the function. When I remove the output buffer code the QR code is rendered on the screen.
Why is some of my output not being captured?
Edit: related: phpqrcode library return image as a string
Remove header("content-type:image/png");
to get it worked with output buffering.
Later you can echo
header("content-type:image/png"); and your captured output to show the image
Related
PNG image required to be converted from JSON and email
So I have used a signature pad from another source and the pad works fine. When I submit the form, it saves the image as JSON code and this is useful as I need to store it within a database as well. However upon submission, I need to convert the code to png and email the image. This is the code I use to convert the code to image, $output2 is the JSON code from the signature capture, signature-to-image.php is the file actually converting the image: require_once 'signature-to-image.php'; $img = sigJsonToImage($output2); // Save to file imagepng($img); // Destroy the image in memory when complete - I destroy the image at the very end of the PHP file This code converts the code fine as I have tested it opening a header with just $img in it and the image appears fine. However when I try to add the png image to the body of the email, it just shows up as Resource id#7. I use the line of code below to send the image: $email_message .= "Signature: ".clean_string($img)."\n"; I am assuming I need to either embed the image within the body of the email (which I am unfamiliar with) or I need to send the image as an attachment (which I am also unfamiliar with). Am I correct in thinking this? which option is the better choice or is there a better alternative? So I write in the signature pad, it captures the signature and saves the image in JSON (as far as I am aware, I have zero experience using JSON) This is an example of the output I would receive: [{"lx":46,"ly":49,"mx":46,"my":48},{"lx":46,"ly":48,"mx":46,"my":49},{"lx":46,"ly":51,"mx":46,"my":48},{"lx":46,"ly":55,"mx":46,"my":51},{"lx":46,"ly":62,"mx":46,"my":55},{"lx":47,"ly":69,"mx":46,"my":62},{"lx":52,"ly":94,"mx":47,"my":69},{"lx":54,"ly":105,"mx":52,"my":94},{"lx":56,"ly":114,"mx":54,"my":105},{"lx":58,"ly":126,"mx":56,"my":114},{"lx":59,"ly":133,"mx":58,"my":126},{"lx":60,"ly":136,"mx":59,"my":133},{"lx":60,"ly":140,"mx":60,"my":136},{"lx":88,"ly":25,"mx":88,"my":24},{"lx":88,"ly":24,"mx":88,"my":25},{"lx":88,"ly":28,"mx":88,"my":24},{"lx":89,"ly":33,"mx":88,"my":28},{"lx":90,"ly":39,"mx":89,"my":33},{"lx":91,"ly":43,"mx":90,"my":39},{"lx":93,"ly":60,"mx":91,"my":43},{"lx":94,"ly":69,"mx":93,"my":60},{"lx":96,"ly":79,"mx":94,"my":69},{"lx":98,"ly":94,"mx":96,"my":79},{"lx":99,"ly":102,"mx":98,"my":94},{"lx":100,"ly":114,"mx":99,"my":102},{"lx":100,"ly":117,"mx":100,"my":114},{"lx":100,"ly":118,"mx":100,"my":117},{"lx":100,"ly":120,"mx":100,"my":118},{"lx":28,"ly":116,"mx":28,"my":115},{"lx":28,"ly":115,"mx":28,"my":116},{"lx":28,"ly":114,"mx":28,"my":115},{"lx":30,"ly":113,"mx":28,"my":114},{"lx":32,"ly":112,"mx":30,"my":113},{"lx":36,"ly":110,"mx":32,"my":112},{"lx":57,"ly":104,"mx":36,"my":110},{"lx":67,"ly":100,"mx":57,"my":104},{"lx":91,"ly":92,"mx":67,"my":100},{"lx":121,"ly":75,"mx":91,"my":92},{"lx":127,"ly":72,"mx":121,"my":75},{"lx":129,"ly":72,"mx":127,"my":72},{"lx":130,"ly":72,"mx":129,"my":72},{"lx":130,"ly":73,"mx":130,"my":72},{"lx":196,"ly":48,"mx":196,"my":47},{"lx":196,"ly":47,"mx":196,"my":48},{"lx":198,"ly":45,"mx":196,"my":47},{"lx":200,"ly":43,"mx":198,"my":45},{"lx":204,"ly":42,"mx":200,"my":43},{"lx":209,"ly":41,"mx":204,"my":42},{"lx":219,"ly":40,"mx":209,"my":41},{"lx":232,"ly":39,"mx":219,"my":40},{"lx":238,"ly":39,"mx":232,"my":39},{"lx":244,"ly":39,"mx":238,"my":39},{"lx":257,"ly":38,"mx":244,"my":39},{"lx":261,"ly":38,"mx":257,"my":38},{"lx":263,"ly":38,"mx":261,"my":38},{"lx":223,"ly":42,"mx":223,"my":41},{"lx":223,"ly":41,"mx":223,"my":42},{"lx":223,"ly":44,"mx":223,"my":41},{"lx":223,"ly":45,"mx":223,"my":44},{"lx":223,"ly":50,"mx":223,"my":45},{"lx":223,"ly":52,"mx":223,"my":50},{"lx":223,"ly":56,"mx":223,"my":52},{"lx":223,"ly":75,"mx":223,"my":56},{"lx":223,"ly":84,"mx":223,"my":75},{"lx":223,"ly":91,"mx":223,"my":84},{"lx":223,"ly":110,"mx":223,"my":91},{"lx":223,"ly":119,"mx":223,"my":110},{"lx":223,"ly":123,"mx":223,"my":119},{"lx":223,"ly":127,"mx":223,"my":123},{"lx":222,"ly":129,"mx":223,"my":127},{"lx":221,"ly":129,"mx":222,"my":129},{"lx":219,"ly":130,"mx":221,"my":129},{"lx":217,"ly":130,"mx":219,"my":130},{"lx":211,"ly":131,"mx":217,"my":130},{"lx":201,"ly":131,"mx":211,"my":131},{"lx":192,"ly":132,"mx":201,"my":131},{"lx":181,"ly":132,"mx":192,"my":132},{"lx":177,"ly":132,"mx":181,"my":132},{"lx":173,"ly":132,"mx":177,"my":132},{"lx":163,"ly":132,"mx":173,"my":132},{"lx":161,"ly":132,"mx":163,"my":132},{"lx":159,"ly":132,"mx":161,"my":132},{"lx":161,"ly":132,"mx":159,"my":132},{"lx":166,"ly":131,"mx":161,"my":132},{"lx":172,"ly":130,"mx":166,"my":131},{"lx":176,"ly":130,"mx":172,"my":130},{"lx":192,"ly":130,"mx":176,"my":130},{"lx":203,"ly":130,"mx":192,"my":130},{"lx":211,"ly":130,"mx":203,"my":130},{"lx":219,"ly":130,"mx":211,"my":130},{"lx":222,"ly":130,"mx":219,"my":130},{"lx":228,"ly":130,"mx":222,"my":130},{"lx":232,"ly":130,"mx":228,"my":130},{"lx":235,"ly":130,"mx":232,"my":130},{"lx":240,"ly":130,"mx":235,"my":130},{"lx":241,"ly":130,"mx":240,"my":130},{"lx":242,"ly":130,"mx":241,"my":130},{"lx":243,"ly":130,"mx":242,"my":130},{"lx":246,"ly":130,"mx":243,"my":130},{"lx":250,"ly":129,"mx":246,"my":130},{"lx":261,"ly":128,"mx":250,"my":129},{"lx":265,"ly":128,"mx":261,"my":128},{"lx":267,"ly":127,"mx":265,"my":128},{"lx":269,"ly":127,"mx":267,"my":127}]
How to use output buffering inside PHPUnit test?
I'm using PHPUnit to test a function which downloads a file. I want to test that the correct file is downloaded and so my idea was to check the output of the function. I'm trying to use output buffering: ob_start(); $viewer->downloadById($fileId); $output = ob_get_flush(); $this->assertEquals($expectedFileContents,$output); The test passes/fails when it should, which is good. My issue is that the contents of the output buffer is also printed to the console. How do I hide this?
Use ob_get_clean() instead of ob_get_flush(). The former will remove the buffer without printing it and return its contents. The latter will do the same and print the contents of the buffer.
Display png image from php on a certain position on a webpage
The code works fine if i display only image with the help of code. <?php // my code processing header("Content-type: image/png"); imagepng($base_image); ?> But if i use some other fields like echo some text or i want to put some buttons on my page. I get error, for code: <?php echo "hi"; ?> <?php // my code processing header("Content-type: image/png"); imagepng($base_image); ?> It gives me error : The displayed page contains some errors. Can someone please help me in this regard.
Any output before the Content-Type header will break your code. The browser does not know you are trying to serve it an image since it will have already defaulted to text/html by the time your image data turns up. If you want an image at a given point in your page, you will need to serve it as a separate object. The easiest way is to wrap it in an <img> tag e.g. <img src="myimage_generator.php" />
This answer is based off of another SO answer. Your problem is that you're trying to send header info after you already sent data to the browser, which is not possible. Even so you can't display an image on a page with it's data alone. You need to base64 encode the image data first. This way you can build a whole HTML page and place this image anywhere on it and position it with CSS. // Enable output buffering ob_start(); imagepng($base_image); // Capture the output $imagedata = ob_get_contents(); // Clear the output buffer ob_end_clean(); echo '<img src="data:image/png;base64,'.base64_encode($imagedata).'">';
PHP Debugging: How to view image resource information
I am debugging a PHP application that handles image resources. I would like to see the output ($dst_image as per the PHP manual's jargon), but the code is not in a place that I could simply output it to the browser. Would the best debugging procedure be to write $dst_image to a file, and to load that file in the browser? Any other ideas? Thanks.
See Example #1 and #2, imagejpeg will output the jpeg data. You need to do few tings: set headers for image header('Content-Type: image/jpeg'); output your image data Make sure you are not outputting any data except the image At the end you should end up with something like this: <?php // Get new dimensions // Resample // etc... // set header so browser can render image properly header('Content-Type: image/jpeg'); // Output imagejpeg($image, null, xxx); // [or] echo file_get_contents($pathToJpgImage); If you find your self in a situation where current request outputs data and you cannot output image... You can inject the base64 encoded image data into the HTML by using <img src="data:image/jpeg;base64,..." />. See php documentation on base64_encode for images.
Generating an image then sending it without first saving it as a file?
If I generate an image directly in a php script to be sent back to JS, is it mandatory to have this interoom step of saving the image to the file system ? I create an image using imagecreate() then imagecopyresized() then want to send the result as base64 wrapped in json (Later I will want an array of strings rather than just one). I couldn't find anything that base64_encode() would take in apart from the bytes from fread(). I find having to save to the file system wasteful and think there must be a better way! Thanks
You don't have to save the file at all. Simply use output buffering: ob_start(); imagepng($im); $pngData = ob_get_contents(); ob_end_clean(); echo base64_encode($pngData);
Just want to add; There's a function ob_get_clean() which executes both ob_get_contents() and ob_end_clean()