RandomWhiteTrash
RandomWhiteTrash

Reputation: 4014

PDF to JPG Imagic page selection

Loads of answers on how to do it for a command line

convert /path/to/file/file.pdf[3] output.jpg

great... but what if I am using in memory processing, I am generating PDF with PDFlib and then output its buffer to a function that I want to generate jpg preview of selected page. How? My code :

    [...]
    $buf = $pdf->get_buffer();

    //$buff is just a PDF stored in a string now.

    $im = new Imagick();
    $im->readimageblob($buf);

    $im->setImageFormat("jpg");
    $im->setimagecompressionquality(60);

    $len = strlen($im);
    header("Content-type: image/jpeg");
    header("Content-Length: $len");      
    header("Content-Disposition: inline; filename=test.jpg");

    echo $im;

This creates a jpeg but always returns last page of the PDF. I want to be able to choose which one will be converted. Is it doable without saving temporary files and using command line (exec('convert /path/to/file/file.pdf[3] output.jpg')) syntax?

Let me add that I tried

    $im->readimageblob($buf[2]);

and it did not work :)

Upvotes: 2

Views: 5447

Answers (5)

I found solution. It is very simple.

1 step: save your pdf, load it and check out whether there are some pages, more than one

$pdf = __DIR__ . "/test.pdf";
$im = new Imagick($pdf);
$count_pages = $im->getNumberImages();

2 step: load exactly needed page. For example 1st page of pdf:

if ($count_pages > 1){
    $page = $pdf.'[0]';
    $im = new Imagick($pdf);
}

3 step: do all you want with this image!

Upvotes: 0

Adam
Adam

Reputation: 6117

I'm loading the PDF binary into memory from Amazon S3 and then selecting the specific page I want using setIteratorIndex() followed by getImage()

function get_image_from_pdf($pdf_bytes, $page_num){
    $im = new \Imagick();
    $im->setResolution(150, 150);
    $im->readImageBlob($pdf_bytes);
    $im->setIteratorIndex($page_num);
    $im = $im->getImage();
    $im->setImageFormat('png');
    return $im->getImageBlob();
}

Upvotes: 4

user3253797
user3253797

Reputation: 183

For the ones who is still searching for solution of reading specific page number from blob, please check this question Creating array populated by images from a PDF using PHP and ImageMagick

$img_array = array();
$im = new imagick();
$im->setResolution(150,150);
$im->readImageBlob($pdf_in);
$num_pages = $im->getNumberImages();
for($i = 0;$i < $num_pages; $i++) 
{
    $im->setIteratorIndex($i);
    $im->setImageFormat('jpeg');
    $img_array[$i] = $im->getImageBlob();
}
$im->destroy();

Upvotes: 5

John Smith
John Smith

Reputation: 721

version 3.0.1 being on the last image or first image in imagic object

$image_obj = new Imagick("test.pdf"); then you on last image in $image_obj

if you use

fp_pdf = fopen("test.pdf", 'rb');
$image_obj = new Imagick();
$image_obj -> readImageFile($fp_pdf);

then you on the first image in $image_obj

In second case to switch to last image you can do

fp_pdf = fopen("test.pdf", 'rb');
$image_obj = new Imagick();
$image_obj -> readImageFile($fp_pdf,2); // 2 can be any positive number?

then you on the last image in $image_obj

echo $image_obj->getNumberImages() // Returns the number of images in the object

then

   if ($image_obj->hadPreviousImage)
       $image_obj->previousImage() //Switch to the previous image in the object
    }

or

if ($image_obj->hasNextImage()) {
   $image_obj->nextImage())  //Switch to the next image in the object
}

e.g. if you have 6 images total and you need 4th then do from the end

$image_obj->previousImage()
$image_obj->previousImage()
$image_obj->setImageFormat("png");
header("Content-Type: image/png");
echo $image_obj;

EDIT: Another find is that you can

foreach($image_obj as $slides) {
    echo "<br>".$Obj_img->getImageWidth();
    //or wehatever you need to do.
}

EDIT 2: Very simple solution would be to use this function $image_obj->setIteratorIndex(4) count starts with zero.

Upvotes: 3

Michael Sallaway
Michael Sallaway

Reputation: 411

It's not good news unfortunately, but I can definitively say that, as of time of writing, the ImageMagick (and PHP libraries) don't support the page notation that you're trying to use. (For people from the future finding this: I'm checking php-imagick-3.0.1 and imagemagick-6.6.0.4).

I'm trying to do the exact same thing as you, and I've just spent the last few hours trawling through the source, trying to figure out what it does and how it gets the pages, and it looks like it simply won't use it when reading from a stream (ie. the readBlob() call).

As such, I'm just going to be putting it in a temporary file and reading it from there instead. Not as elegant, but it'll work.

Upvotes: 3

Related Questions