[cl-pdf-devel] png image representation

Thibault Langlois tl at di.fc.ul.pt
Wed May 30 21:41:23 UTC 2007


On 5/30/07, iso at localhost.di.fc.ul.pt <iso at localhost.di.fc.ul.pt> wrote:
> > Hello,
> >
> > I would like to know what is the representation used in the data
> > slot of a PDF::PNG-IMAGE. My goal is to be able to use a png image
> > made with the imago package in a cl-pdf document.
> > In an IMAGO:RGB-IMAGE a slot (PIXELS) contains a bidimensional
> > array of (UNSIGNED-BYTE 32) that contains the image pixels.
> > I want to translate this representation into a representation
> > that can be used by cl-pdf.
> >
> > Thanks
> >
> > Thibault
>
> Maybe you don't need PNG for that. If you have a vector of pixel
> values, then just use something like this:
>
> (defun my-image (pixels width height)
>   (let ((image (make-instance 'pdf:image
>                  :color-space "DeviceCMYK"
>                  :filter nil
>                  :bits pixels
>                  :width width
>                  :height height)))
>     (pdf:add-images-to-page image)
>     (pdf:paint-image image)))
>

Each pixel in the imago format is a unsigned 32bits that
represents R, G, B and Alpha channel.

> This assumes that you want to use colour separations and that the
> dimensions of the pixel vector are (* width height 4). If you
> have a grayscale image, then use DeviceGray instead of DeviceCMYK. Of

Each pixel in the imago format is a unsigned 32bits that
represents R, G, B and Alpha channel.

> course, you can also use DeviceRGB (then the pixel vector should look
> like this: R00 G00 B00 R01 G01 B01 ..., where R01 is the Red value of
> the pixel at row 0 column 1).

I tried to follow your suggestion using a DeviceRGB.
First I got an error when the :bits argument is a vector of
bytes. Looking at the code it seems that this argument must
be a string (the data is passed to a pdf-stream and then to the
compress-pdf-stream function where compress-string is called).

So I converted each byte into a char to build a string. I do not
get any errors but the image does not appear in the document.

(defun image-example-1 (&optional (file #P"/home/tl/Desktop/ex.pdf"))
  (pdf:with-document ()
    (let* ((imago-image ;; Load an image as a imago:rgb-image
            (imago:read-png "/home/tl/Photos/lemon-slice.png"))
           (pdf-image ;; make a pdf-image using image data
            (make-instance 'pdf:image
                           :color-space "DeviceRGB"
                           :filter nil
                           :bits (string-of-bytes imago-image)
                           :width (imago:image-width imago-image)
                           :height (imago:image-height imago-image))))
      (pdf:with-page (:bounds (vector 0 0 400 300))
        (pdf:add-images-to-page pdf-image)
        (pdf:draw-image pdf-image 10 100 250 120 0 t)
        (pdf:write-document file)))))

The string-of-bytes function collect the r g b components and
build a string:
(defun string-of-bytes (imago-rgb-image)
  (let (color-values)
    (imago:do-image-pixels (imago-rgb-image c x y)
      (setq color-values
            (nconc color-values
                   (list (code-char (imago:color-red c))
                         (code-char (imago:color-green c))
                         (code-char (imago:color-blue c))))))
    (coerce color-values 'string)))

My first attempt was to make a vector:

(defun vector-of-bytes (imago-rgb-image)
  (let (color-values)
    (imago:do-image-pixels (imago-rgb-image c x y)
      (setq color-values
            (nconc color-values
                   (list (imago:color-red c)
                         (imago:color-green c)
                         (imago:color-blue c)))))
    (coerce color-values 'vector)))

Any help will be appreciated.

Thibault



More information about the cl-pdf-devel mailing list