loading and saving jpegs and pngs

BlitzMax Forums/BlitzMax Programming/loading and saving jpegs and pngs

Robert Cummings(Posted 2005) [#1]
Hi there,

I want to keep my download sizes really small and I have 2 800x600 pngs. The upper png layer will have an alpha channel too.

I was thinking: why not make a small utility that takes the lower layer png and compresses it to jpg, then takes the upper layer png and splits it into 2 jpeg files: one for the alpha channel and one for the image.

This only needs to be on the pc (the standalone utility).

Then when my game looks for a level, it finds the 3 jpegs and recombines them in memory to be two images, one with an alpha channel. This would need to be cross platform (done in memory).

Do you think this is feasible?

Any other ideas? The goal is to reduce download sizes.


Robert Cummings(Posted 2005) [#2]
There will be probably 50 levels like this, so it's really worth trying to nail.


taxlerendiosk(Posted 2005) [#3]
Does using JPEG with alpha ever work? I'm presuming you'd do that layer as monochrome and convert white into full alpha and black into no alpha, or vice-versa. But wouldn't it even then have nasty artifacting? You may have to compress the alpha layer as a PNG.


ImaginaryHuman(Posted 2005) [#4]
It sounds entirely possible.

You will get the loss of detail with jpeg, but saving the alpha as grayscale jpeg will cut down some size and then you can just convert the greyscale RGBA data into 256 levels of gray and combine it with your image.


taxlerendiosk(Posted 2005) [#5]
Well with JPEG the problem is usually more like added detail instead of loss, nasty blocks of graininess. I suppose it really depends what your alpha map is like, if it is very complicated JPEG would be fine, but if >90% of it is one extreme or the other then PNG would probably be better.


Robert Cummings(Posted 2005) [#6]
Hi lads,

I've done an experiment with photoshop - we're looking at 60k for 3 jpgs verses 500k for 2 png's tightly compressed with png gauntlet or png crush.

File sizes are a bit of a problem as I've been told to keep it circa 10-15 meg when I spoke to the distributors.

As I have photoshop I think it will be fairly easy to make a batch action that'll do the job for me so that's no worry...

The real problem is: how do I take a greyscale alpha image, a solid image and recombine them in memory so drawimage actually draws it with alpha?


taxlerendiosk(Posted 2005) [#7]
Something like this (untested):
For y = 0 To PixmapHeight(ImagePixmap)-1
	For x = 0 To PixmapWidth(ImagePixmap)-1
		Color = ReadPixel(ImagePixmap,x,y) & $FFFFFF ' RGB from original image
		AlphaValue = ReadPixel(AlphaPixmap,x,y) & $FF ' Only taking one channel
		WritePixel ImagePixmap, Color | (AlphaValue Shl 24)
	Next
Next



Robert Cummings(Posted 2005) [#8]
Thanks :) is that the fastest I can do it? just curious... as it will be performed on load and so I want to keep the speed up.


taxlerendiosk(Posted 2005) [#9]
I suppose you could use byte pointers to the actual pixel data rather than doing it through function calls... other than that, not that I'm aware of.


ImaginaryHuman(Posted 2005) [#10]
You're entirely assuming there that the pixel format is ARGB which is not necessarily true. On my Mac I usually work in RGBA and OpenGL seems to consider RGBA as fairly standard. You would possibly want to do a ConvertPixmap() to change the format first, or at least to ensure it is the right format.


Robert Cummings(Posted 2005) [#11]
Confused now. So openGL is different from DX and Mac is different to pc?


ImaginaryHuman(Posted 2005) [#12]
Well, all I know is that OpenGL doesn't necessarily assume that the data will be in ARGB format, it has to be specified. I don't know if it has a default, or if its possible to not define the mode that textures are stored in. I just don't think you should be assuming that ARGB is standard everywhere. Are you sure that BlitzMax is going to load the image as ARGB?


xlsior(Posted 2005) [#13]
Are you sure that BlitzMax is going to load the image as ARGB?


Might want to check out the 'pixmapformat' command:


Function PixmapFormat( pixmap:TPixmap ) Get pixmap format
Returns: The format of the pixels stored in pixmap

The returned value will be one of:

Format Description
PF_RGB888 24 bit big endian RGB
PF_BGR888 24 bit little endian RGB
PF_RGBA8888 32 bit big endian RGB with alpha
PF_BGRA8888 32 bit big endian RGB with alpha



which should tell you the format your particular system stores this info in...

What I did in my crossfading/black & white fading routines (see code archives), was to convert the image to a known format first, do my thing, and convert it back when done:



Since you want to use Alpha info, you would probably want to check for/switch to PF_RGBA8888 instead... And I suppose you could gain some speed by not doing an actual conversion, but actually having several copies of your routines to pick from depending on the input format.


Robert Cummings(Posted 2005) [#14]
Thanks for that, I think you're really helpful! This is valuable information.