Simulator Rendering bug in Particles Code

Some of you may have found your way here from my chapter on particle systems in Advanced iPhone Projects. If you have tried out that code in the simulator, and you are running in Snow Leopard, you may have noticed that the buttons have groovy patterns on them for some inexplicable reason.

This is because I made a minor error in the code, one of the most common ones that should never happen, but tend to happen in cases like these where I am writing code for a book and so it doesnt get tested nearly as well as it should. (which is my fault :-) No, it is not the dreaded one-off error, but the rookie mistake of not initializing my buffers before using them. To try and justify: when working with images, it is not generally necessary to initiaize the buffers to anything and it usually is just a wast of cycles since you often just write over the whole thing anyway (so why do it twice?). That and I borrowed heavily from Apple’s sample code, and now I have learned my lesson (again :-)

In this case, because of the way I am drawing into the resulting CGContext, the old stuff not getting properly overwritten. (so it looks a bit like a multi texture, or an overlay)

The Badness can be seen here:

Screen shot 2010-01-01 at 11.21.18 AM

The buttons on the right are not supposed to have snowflakes in them.

Luckily, this render bug doesn’t really effect the actual functioning of the code, just the look of it, and just in the simulator. However, the fix is good to have in there even on your device, so.. here it is:

		memset(spriteData, 0, (width * height * 4));

It needs to go in the BBMaterialController.m file, in the loadTextureImage: materialKey: method, right after we malloc the buffer for the sprite image.

-(CGSize)loadTextureImage:(NSString*)imageName materialKey:(NSString*)materialKey
{
	.
	.
	.

	// you'll want to add code that checks the dimensions and takes appropriate action if they are not a power of 2.
	
	if(spriteImage) {
		// Allocated memory needed for the bitmap context
		spriteData = (GLubyte *) malloc(width * height * 4);

		// clear the memory
		memset(spriteData, 0, (width * height * 4)); // <----------- ADD THIS!

		// Uses the bitmatp creation function provided by the Core Graphics framework. 
		spriteContext = CGBitmapContextCreate(spriteData, width, height, 8, width * 4, CGImageGetColorSpace(spriteImage), kCGImageAlphaPremultipliedLast);
		// After you create the context, you can draw the sprite image to the context.
	.
	.
	.
}

Anyhow, there you go. Always initialize your variables :-) Once you have made this fix, you will be rewarded with a slightly less interesting, but correctly rendering app:

The Goodness:

Screen shot 2010-01-01 at 11.20.22 AM

This will also make the numbers on the bottom of the screen render properly as well, they were similarly being corrupted with bad starting data, so they were sometimes hard to read.

Cheers!
-B

This entry was posted in multitouch. Bookmark the permalink.

Leave a Reply