Resizing images in MIDP 1.0

I’m curious if anyone has managed to solve the MIDP 1.0 issue with resizing game images to fit the screen. The only solution I’ve seen to date (see here) is extremely slow and rather wasteful.

I only ask because I have solved the problem, and want to know if anyone else independently developed the same solution. (Don’t worry, I’ll release it soon.) :slight_smile:

I have did somethting before, it was relatively succesful. The method at the link is not a proper scaling as it just kindly duplicates the pixels by drawing them over and over again by slighlty shifting. I cant expect any good view out of it. We are waiting to see yours or least main logic beind it which is more interesting than the application itself.
cheers

Oh fine. Don’t tell me then. :wink:

Ah well, it’s probably the same thing. The code can be found here:

http://java.dnsalias.com/blockattack/source/ImageUnpacker.java

The concept behind it is quite simple. Pixel data is stored in my own proprietary format (see here) that produces smaller files than PNGs, and relies on the JAR compression to reduce the file size even further. The pixel data is then reconstructed into an image by using Image.createImage(width, height), then painting 1 pixel rectangles of the proper color.

From there, resizing is a simple issue to solve. The simplest solution is to scale the size of the drawRect() calls to “stretch” the pixels. This is the algorithm I’m using at the moment. But since you have the pixel data, and a way of reconstructing an image from it, there’s nothing preventing the developer from using nice looking scaling filters.

So, is it the same? Different? Better? Worse? :slight_smile:

Well, if you have access to the pixel data, then resizing becomes a lot more feasible, and I’m not talking about resizing by doubling, tripling, etc. the size.
If you’re interested, you can try to use this code and fit it to the use of your own pixel format.

The biggest drawback with your method though, is that you can’t have any transparent pixels because Image.createImage(int,int) creates a fully opaque Image to begin with. The only way around this problem would be to write a png encoder so that you can take your format and transform it into a png that does support transparency.

shmoove

If you are using a midp1 device that doesn’t check the adler or crc32 checksums on png files, you could use a png that has an uncompressed zlib stream inside it, and Image.createImage(byte[]…).
You would then effectively have per-pixel access, the only cost would be a native mem copy during createImage(byte[]…)

If the phone did perform either the adler or crc32 checksums, I think you’d find the speed cost would be prohibitive, (not only would createImage have to check the crc’s, but your code would have to generate them).

:edit:

btw shmoove, the resizing code was a very generous gift! =)

[quote]Well, if you have access to the pixel data, then resizing becomes a lot more feasible, and I’m not talking about resizing by doubling, tripling, etc. the size.
If you’re interested, you can try to use this code and fit it to the use of your own pixel format.
[/quote]
Nice MIDP 2.0 code schmoove! Thanks for sharing that with everyone!

[quote]The biggest drawback with your method though, is that you can’t have any transparent pixels because Image.createImage(int,int) creates a fully opaque Image to begin with.
[/quote]
That’s a good point. Since my current game uses rectangular sprites, I’d forgotten all about mutable images being opaque.

[quote]The only way around this problem would be to write a png encoder so that you can take your format and transform it into a png that does support transparency.
[/quote]
Not to fear! There is another way! :slight_smile: What is needed is a “sliver” engine. The idea would be to scan the longest dimension into individual lines of pixels. By trimming the transparent area off of each line and saving the offset, you can draw the complete image on screen by looping through each sliver image. The method could be further optimized by grouping slivers that have the same length and offset.

Believe it or not, there is some precedent for such a design. Raycasting engines ala Wolf3D and Duke Nukem 3D make use of “scaled slivers” to produce 3D effects. The design is really an advanced form of 2D scaling for 3D effects that had been in use since the days of Pole Position. The primary difference in Raycasting was the addition of true spatial calculations (somewhat costly trig).

[quote]If you are using a midp1 device that doesn’t check the adler or crc32 checksums on png files, you could use a png that has an uncompressed zlib stream inside it, and Image.createImage(byte[]…).
You would then effectively have per-pixel access, the only cost would be a native mem copy during createImage(byte[]…)
[/quote]
Abuse, I’ve often heard talk of this method, but I’m curious if you’ve ever actually seen someone use it? I tried stripping down a PNG encoder about a year ago, and I was not pleased with the results. The encoder itself can easily take up as much space as an entire game, and is rather tricky to code and test.

A number of games I have ported have used it.
However, most have simply used it so they can access, and swap the palette for a png, I havn’t yet seen one that has used this method for manipulating the pixel data.

I have written a light-weight png encoder/decoder, it realy is quite easy - the png format lends itself quite well to a small implementation. (The only exception to this, is the use of 2 diffferent CRC methods - which is a right pain in the arse)
All in, its a few hundred lines.