Page 1 of 2 12 LastLast
Results 1 to 10 of 15

Thread: Image packer project

  1. #1

    Image packer project

    Hi guys :-)
    I am currently writing an image packer utility that uses freeimage for loading/saving graphic files.

    see screenshots of current version




    I have incorporated in my code an updated version of the TPartition class that Nitrogen wrote for his Font Studio (http://www.nitrogen.za.org/projectinfo.asp?id=12) (Thanks Nitrogen!!).

    I thought I'd share the updated TPartition unit here.

    I have replaced the corner constants with an enumerated type for specifying how to pack the rectangles, added a new option for packing rectangles as horizontal strips, made the Insert method return true or false and the rect as a var parameter, altered variable names, and altered the code formatting (easier to read in my opinion, no offense intended to Nitrogen).

    When my image packer is done, I will share it as well

    Again, lots of thanks to Nitrogen for sharing the original partition code :-)

    You can download the unit from here

    http://fpc4gp2x.eonclash.com/downloads/Partitions.pas

    I tried pasting it here but using the code and pascal both screwed up the formatting and some of the code

    This is how I use the unit:

    [pascal]
    Type
    {................................................. .............................}
    TRectangle = Class
    Rect : TRect;
    Name : AnsiString;
    FileName : AnsiString;
    Width,Height : Integer;
    Index : Integer;
    WasInserted : Boolean;
    End;
    {................................................. .............................}

    {................................................. .............................}
    <SNIP>
    {................................................. .............................}

    {................................................. .............................}
    Function CompareRectanglesByArea(a,b: Pointer): Integer;
    Begin
    Result := -1 * ((TRectangle(a).Width * TRectangle(a).Height) - (TRectangle(b).Width * TRectangle(b).Height));
    End;
    {................................................. .............................}

    {................................................. .............................}
    Function CompareRectanglesByIndex(a,b: Pointer): Integer;
    Begin
    Result := TRectangle(a).Index - TRectangle(b).Index;
    End;
    {................................................. .............................}

    {................................................. .............................}
    Procedure TForm_MainForm.PackRectangles(x,y,x2,y2: Integer; PackingMode: TPackingMode);
    Var
    Rectangle : TRectangle;
    i : Integer;
    Partition : TPartition;
    r : TRect;
    Begin
    If FRectangles.Count <= 0 Then Exit;
    Partition := TPartition.Create(x,y,x2,y2,PackingMode);

    If PackingMode <> ePackingMode_HorizontalStrips Then
    FRectangles.Sort(@CompareRectanglesByArea);
    For i := 0 To FRectangles.Count - 1 Do
    Begin
    Rectangle := TRectangle(FRectangles.Items[i]);
    Rectangle.WasInserted := False;
    If Partition.Insert(Rectangle.Width,Rectangle.Height, r) Then
    Begin
    Rectangle.WasInserted := True;
    Rectangle.Rect := r;
    End;
    End;

    If PackingMode <> ePackingMode_HorizontalStrips Then
    FRectangles.Sort(@CompareRectanglesByIndex);
    Partition.Free;
    For i := 0 To FRectangles.Count - 1 Do
    Begin
    Rectangle := TRectangle(FRectangles.Items[i]);
    If Rectangle.WasInserted Then
    StringGrid_ImagesToPack.Cells[1,i + 1] := ''
    Else
    StringGrid_ImagesToPack.Cells[1,i + 1] := 'X';
    End;
    End;
    {................................................. .............................}

    {................................................. .............................}
    [/pascal]

    FRectangles is a TList holding a number of the TRectangle classes that I want to pack.

    TRectangle.Rect is the rectangle where it was inserted, and TRectangle.WasInserted can be checked for to see if the rectangle was actually inserted.

    TRectangle.Index allows me to sort the list by area and then back to the original order.

    TRectangle.Width and TRectangle.Height is the width and height of this rectangle to be inserted.

    After packing the rectangles I am going through the list and updating a stringgrid showing if the rectangle was inserted or not, but you can do whatever you want with this information of course.

    I call the PackRectangles like so:
    [pascal]PackRectangles(0,0,FPackedImage.GetWidth,FPackedIm age.GetHeight,PackingMode);[/pascal]

    the first 4 parameters are the rectangle (top,left, bottom,right) where I want to attempt to pack the rectangles into; in this case the whole of the specified image dimensions, and the PackingMode is just one of the TPackingMode enums from the TPartition unit.

    cheers,
    Paul.

  2. #2

    Image packer project

    i don't understand what is a image packer, the ideia is put some images in a big one?
    From brazil (:

    Pascal pownz!

  3. #3

    Image packer project

    Hi arthurprs,
    yes an image packer is designed to pack multiple smaller images of any size into a larger image (usually with power of 2 dimensions).

    This is usually done for a number of reasons:

    a) save texture swapping
    b) allow non-power of 2 dimensioned images to be used when you may be limited to only power of 2 sized textures.

    This site gives examples and one reason (packing lightmaps using similar algorithm)
    (http://www.blackpawn.com/texts/lightmaps/default.html)

    I hope this helps :-)
    cheers,
    Paul

  4. #4

    Image packer project

    Quote Originally Posted by paul_nicholls
    Hi arthurprs,
    yes an image packer is designed to pack multiple smaller images of any size into a larger image (usually with power of 2 dimensions).

    This is usually done for a number of reasons:

    a) save texture swapping
    b) allow non-power of 2 dimensioned images to be used when you may be limited to only power of 2 sized textures.

    This site gives examples and one reason (packing lightmaps using similar algorithm)
    (http://www.blackpawn.com/texts/lightmaps/default.html)

    I hope this helps :-)
    cheers,
    Paul
    thx, talking about that, i need to implement pattern drawing on my framework, i will code something now ;P
    From brazil (:

    Pascal pownz!

  5. #5

    Image packer project

    Looks nice. Can you save the images to dds with mipmaps and compression?

  6. #6

    Image packer project

    Quote Originally Posted by Luuk van Venrooij
    Looks nice. Can you save the images to dds with mipmaps and compression?
    Not unless I get a 3rd party DDS writer, or create one myself.

    Currently, the image formats supported are the ones freeimage support:

    cheers,
    Paul

  7. #7

    Image packer project

    Quote Originally Posted by paul_nicholls
    Quote Originally Posted by Luuk van Venrooij
    Looks nice. Can you save the images to dds with mipmaps and compression?
    Not unless I get a 3rd party DDS writer, or create one myself.

    Currently, the image formats supported are the ones freeimage support:

    cheers,
    Paul
    http://imaginglib.sourceforge.net/index.php?page=about

    don't know if it support everything you want in dds, but supporting saving dds

    i use it in almost every project very powerfull library!
    From brazil (:

    Pascal pownz!

  8. #8

    Image packer project

    I also use it in my projects

  9. #9

    Image packer project

    Hi guys :-)
    I have uploaded a minimally working version of the Image Packer (http://fpc4gp2x.eonclash.com/downloads/Image Packer.7z) which includes the exe + source (Delphi 5 tested) + freeimage.dll.

    You can add images and pack them in one of two ways (best fit partitioning (sorted from largest to smallest) or as horizontal strips in the order they are specified.

    When images are imported, the program tries to guess what type they are; a single image, or an array of smaller images. This can be specified for each file at import time (or changed later by clicking on the Type column field for that image).

    After packing the images you can alter the names of each packed image rectangle.

    If any of the images couldn't be packed, their status will be a red cross instead of a green tick (images to pack grid)

    The final total packed image size can be altered if needed using preset width and height values or using custom width and height.

    You can export the packed image as BMP, PNG, or other image type (right click on packed image).
    You can export the packed image rectangles data as INI or XML files (right click on the packed images grid.

    A packed image file type will be created later on but for now this will do.

    I know it is a work-in-progress, so feedback is important :-)

    cheers,
    Paul

  10. #10

    Image packer project

    working nice here

    my sugestion are,

    default rect names = "(sourceimagename-extension)-#number"

    and guidelines like these blank lines
    From brazil (:

    Pascal pownz!

Page 1 of 2 12 LastLast

Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •