Archive for March, 2010

How to create square thumbnails using iPhone SDK / CG Quartz 2D

24.03.2010 19

Today I wrote a useful Objective-C method which uses Quartz 2D from the iPhone SDK to dynamically generate square thumbnails from any portfolio or landscape UIImage. I failed to find helpful results on Google for the various CGContextClipToRect/CGContextTranslateCTM/CGContextScaleCTM Quartz functions so after a lot of trial and error I managed to get the results I was after with a fairly efficient script – shown below.

So, if for example you want to get a 32×32 pixel square thumbnail, you can pass 32 as the ‘length’ parameter in the function below. For portfolio images the code will take a full square from the original image from the centre using the full width of your original portfolio image. Likewise, for a landscape image the script will use all the height available, clipping the right and left sides.

I think the most import thing I learned when writing this script is that when you call UIGraphicsBeginImageContext(CGSize) make sure that the size you pass in is the size you want your final image to be. Otherwise you end up having to call UIGraphicsEndImageContext() and UIGraphicsBeginImageContext() multiple times with different CGSize instances which I’m sure isn’t an optimised way to achieve the same results.

- (UIImage *)thumbWithSideOfLength:(float)length {

NSString *subdir = @”my/images/directory”;
NSString *filename = @”myOriginalImage.png”;
NSString *fullPathToThumbImage = [subdir stringByAppendingPathComponent:[NSString stringWithFormat:@"%dx%d%@",(int) length, (int) length,filename];
NSString *fullPathToMainImage = [subdir stringByAppendingPathComponent:filename];

UIImage *thumbnail;

NSFileManager *fileManager = [NSFileManager defaultManager];

if ([fileManager fileExistsAtPath:fullPathToThumbImage] == YES) {
thumbnail = [UIImage imageWithContentsOfFile:fullPathToThumbImage];

}
else {
//couldn’t find a previously created thumb image so create one first…
UIImage *mainImage = [UIImage imageWithContentsOfFile:fullPathToMainImage];

UIImageView *mainImageView = [[UIImageView alloc] initWithImage:mainImage];

BOOL widthGreaterThanHeight = (mainImage.size.width > mainImage.size.height);
float sideFull = (widthGreaterThanHeight) ? mainImage.size.height : mainImage.size.width;

CGRect clippedRect = CGRectMake(0, 0, sideFull, sideFull);

//creating a square context the size of the final image which we will then
// manipulate and transform before drawing in the original image
UIGraphicsBeginImageContext(CGSizeMake(length, length));
CGContextRef currentContext = UIGraphicsGetCurrentContext();

CGContextClipToRect( currentContext, clippedRect);

CGFloat scaleFactor = length/sideFull;

if (widthGreaterThanHeight) {
//a landscape image – make context shift the original image to the left when drawn into the context
CGContextTranslateCTM(currentContext, -((mainImage.size.width – sideFull) / 2) * scaleFactor, 0);

}
else {
//a portfolio image – make context shift the original image upwards when drawn into the context
CGContextTranslateCTM(currentContext, 0, -((mainImage.size.height – sideFull) / 2) * scaleFactor);

}
//this will automatically scale any CGImage down/up to the required thumbnail side (length) when the CGImage gets drawn into the context on the next line of code
CGContextScaleCTM(currentContext, scaleFactor, scaleFactor);

[mainImageView.layer renderInContext:currentContext];

thumbnail = UIGraphicsGetImageFromCurrentImageContext();

UIGraphicsEndImageContext();
NSData *imageData = UIImagePNGRepresentation(thumbnail);

[imageData writeToFile:fullPathToThumbImage atomically:YES];

thumbnail = [UIImage imageWithContentsOfFile:fullPathToThumbImage];
}
return thumbnail;
}

So if, for example your original image looked like this:

finn

Using the method above you could request a 100×100 pixel thumbnail which would result in this:

finn_thumb

Pitching the Microphone with Flash Player 10.1 Beta

11.03.2010 5

I’ve been lucky enough to get some Research & Development work in over the last few weeks. The latest batch of work has included some experimental stuff with the the new Microphone features introduced in Flash Player 10.1 which is currently in beta. You can download the required Flash Player here.

In the example below the app will automatically record your voice until you stop talking and will playback the sound bytes as Barry White or a Chipmunk (adjust using the slider).

Prior to Flash 10.1 you could manipulate the sound bytearray from an mp3 at runtime but you couldn’t access the native incoming microphone data. I can see this modification to the Flash Player leading to some really cool future games and apps.

In my example there’s currently no encoding to mp3. I just save the incoming sound byte arrays in memory. I think there may be as3 mp3 encoders already written if this was a project requirement.

Microphone Fun

Alternative content

Get Adobe Flash player

I’m also really intrigued by Didier Brun’s R&D work on voice recognition in Flash Player 10.1:

http://www.bytearray.org/?p=1151

http://vimeo.com/9780416

Looks like he’s really getting somewhere from those example videos. I guess one approach might be to render the sound data samples to bitmaps and run the sort of blend, colour threshold comparisons that you achieve with Flash WebCam motion detection.

Thanks to Andre Michelle’s shared work on pitching MP3s and Devon Wolfgang’s microphone code example I was able to get the above up and running.

Here’s the source :-)