Re: [GD-DEVEL] [proposal] Attach DIB section buffer to gdImage

[email protected] ("Pierre Joye")
Newsgroups php.gd.devel
Message-ID <[email protected]>
Hi Markus,

On Feb 13, 2008 3:46 PM, Markus Fleck-Graffe <[email protected]> wrote:
> Pierre Joye wrote:
> >>> I'm finishing the initial support of the new formats. The two most
> >>> important additions for you and other users are the true 8bit per
> >>> channel (alpha) and the contiguous buffer instead of per row
> >>> allocation. It will let you use a DIB/BMP (or any compatible buffer)
> >>> directly without any extra allocations or loop. It will require a lof
> >>> tests and work to get stable enough for 2.1.x :)
>
> There is this very powerful "iterator" abstraction used, for example,
> by the Fltk GUI toolkit, and by Python's "NumPy" matrix calculation
> library as well[1].
>
> It supports basically all kinds of contiguous buffer schemes (including
> the Windows DIB one), and has excellent performance characteristics.
>
> Basically, you store the following data for each image:
> - "topleft": a pointer to the memory location that stores the first
>    (top-left) pixel of the image
> - "buffer": a pointer to the (contiguous) memory buffer (which will
>    be used mainly just for eventually free()'ing the buffer)
> - "depth": pixel depth (in bytes, or maybe even in bits),
>    e.g. 3 (bytes) for plain 24-bit RGB, or 4 (bytes) for 32-bit RGBA
> - "w", "h": actual (logical) image width and height (in pixels)
> - "dy" byte offset to the next scan line (for "vertical" iteration)
> - "dx" byte offset to the next pixel (for "horizontal" iteration)
>
> Ideally, for a contiguous RGB(A) buffer, "dx" would be equal
> to "depth", "dy" would be equal to "width", and "topleft" would
> be equal to "buffer".
>
> Now:
> - if scanlines must be "padded" to satisfy some alignment constraints,
>    "dy" may be made larger than "width"
> - in case of "upside-down" storage (such as with Windows DIB bitmaps),
>    "dy" must be made negative, and the initial image pointer ("topleft")
>    must be calculated to point to the beginning of the "last" DIB
>    scanline in memory (which is actually the "topmost" scanline of
>    the corresponding image).
>
> The memory position of each pixel can then be calculated at any
> time, using either absolute or relative pointer arithmetics,
> based only on the above small (and fixed) set of metadata.

That's more or less what I'm doing except that the various
informations depend of the image format you use. I think adding such
internal structure can make GD flexible enough to work with almost
every system out there.  To full fill the needs, we also have to add
different alpha support:

 - level of transparency or opacity
 - pre multiplied alpha or not
 - rgba masks (obviously do not apply to gray level images)


> It is also possible to very efficiently (and safely) perform
> BITBLT-style operations using fast block copy operations, just by
> calculating the corresponding topleft/width/height/dx/dy values,
> for any rectangular region inside an image. (In fact, multiple
> overlapping images could even share the same data buffer,
> which may be useful e.g. for showing a scrollable rectangular
> clipped "view" of a larger image in a GUI toolkit, as Fltk can,
> or for processing very large 2D arrays or matrices, as NumPy can.)

You can copy only a row at a time using system fast block copy as soon
as the buffer are not contiguous.That's why I would love to have a
contiguous buffer, you don't need much offsets but stride. I have now
to take a look at these implementations, they seem to cover all we
need!

> Now the question is: are there any GD users who depend on the
> peculiarities and availability of the current tpixels array
> (probably for non-contiguous in-memory images whose buffers
> have not been created by GD itself)? Would it be an option
> to get rid of "tpixels" for GD 3.x, for the sake of
> significantly improving performance?

That's the second main reason behind the new formats, the first being
interoperability with other libraries or toolkits. Many users depend
on the presence of tpixel (and the palette buffers), I'm not sure we
gain much to remove it. But if we do, as you said, we can do it in
3.x.

Almost all new rendering functions will  work only in the new formats
and not with the current 31bit (7,8,8,8) format and with level of
opacity instead  of transparency as it is now (more logical and works
well with other toolkits).

Thanks for this post, it is really what we need to implement the best
possible solution in GD (or closed to the best :).

Cheers,
-- 
Pierre
http://blog.thepimp.net | http://www.libgd.org
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.