PDA

View Full Version : lots of stickers on Photo - efficient way?




IDMah
Feb 1, 2012, 09:39 PM
Hi all..

I want to put a whole lot - 20-70 small images / let's call them stickers on an image. I can do it now by adding UIImageViews. but 20-70 of them per image(s) means well 40 images X 70 = "C. load of Views" .. seems a little crazy. I had planned to store the co-ordinates in an array (and dynamically sticker them) but but still a lot of information.. I know that as soon as I leave the view I can de-alloc them but..

Is there an easier/more efficient way to overlay a bunch of "stickers"/small images on an image ??? to complicate; I also need to keep the original image clean.

Would saving an image copy be worth the memory hogging ??? and the coding efforts???

thanks
Ian

ps. Any help appreciated.. sorry if this seems a dumb question...
trying to code better than 1984 days...



robbieduncan
Feb 2, 2012, 05:29 AM
Copy the image into memory and actually composite the "stickers" onto the image?

You can get a CGGraphicsContext to draw into using CoreGraphics. I'd recommend the UIGraphicsBeginImageContextWithOptions (http://developer.apple.com/library/ios/documentation/uikit/reference/UIKitFunctionReference/Reference/reference.html#//apple_ref/c/func/UIGraphicsBeginImageContextWithOptions) function with the size of the initial image followed by UIGraphicsGetCurrentContext (http://developer.apple.com/library/ios/documentation/uikit/reference/UIKitFunctionReference/Reference/reference.html#//apple_ref/c/func/UIGraphicsGetCurrentContext) to get a CGContextRef to draw in. Now composite the images using drawAtPoint: (http://developer.apple.com/library/ios/documentation/uikit/reference/UIImage_Class/Reference/Reference.html#//apple_ref/occ/instm/UIImage/drawAtPoint:). Note this automatically handles the flipped coordinate system: if you use low-level CG to draw you will have to handle this. You can then turn the CGGraphicsContext into a CGImageRef with CGBitmapContextCreateImage (http://developer.apple.com/library/ios/DOCUMENTATION/GraphicsImaging/Reference/CGBitmapContext/Reference/reference.html#//apple_ref/c/func/CGBitmapContextCreateImage) which you can then turn into a UIImage with initWithCGImage: (http://developer.apple.com/library/ios/documentation/uikit/reference/UIImage_Class/Reference/Reference.html#//apple_ref/occ/instm/UIImage/initWithCGImage:). Note there is a shortcut for getting the image from a context: the UIGraphicsGetImageFromCurrentImageContext (http://developer.apple.com/library/ios/documentation/uikit/reference/UIKitFunctionReference/Reference/reference.html#//apple_ref/c/func/UIGraphicsGetImageFromCurrentImageContext) function.

As an annoying meerkat might say: simples!

ArtOfWarfare
Feb 2, 2012, 05:55 AM
I don't see the issue.

Just throw all the stickers and coordinates into core data.

dantastic
Feb 2, 2012, 06:19 AM
I'll say it somewhat depends on what else is going to happen in the view.

The option to first draw a background image and then draw small imageViews wherever needed may not be a huge problem, as long as the stickers aren't too big & overlap several times.

When you print out image views like that each and every image need to be drawn every time. But if nothing is happening after the image has been drawn once then this won't be a problem. up to 100 views won't be any problem. The advantage of this is that you can move or animate individual stickers.

On the other hand if you are running your memory a bit 'peaked' already or if the image need to be animated or otherwise redrawn then you have to go with Duncan's suggestion. The advantage here is a better memory footprint.

You will be able to create a context and then in an autoreleasepool allocate and draw image by image thereby saving memory.

IDMah
Feb 4, 2012, 02:37 PM
Thanks gang!!!

Worked like a dream ..

used this.

UIImage* uiimage = aStampImage;

CGSize mysize = uiimage.size;

UIGraphicsBeginImageContext(mysize);

CGPoint stampPos;

for (int i=40; i>0; i--) {

// random for test purposes // <---- I just like double //'s shrug..
stampPos.x = random()% (NSInteger)(bounds.size.width);
stampPos.y = random()% (NSInteger)(bounds.size.height);

// Draw image in Rectangle //
[uiimage drawInRect:CGRectMake(stampPos.x,stampPos.y, mysize.width/7, mysize.height/6)];

}
UIImage* blendedImage = UIGraphicsGetImageFromCurrentImageContext();

UIGraphicsEndImageContext();

// Make an UIImageView From blendedImage //
UIImageView *stickerOverlay = [[UIImageView alloc]
initWithImage:blendedImage];

[blendedImage release];
[stampOverlay setFrame:CGRectMake(0,0,bounds.size.width,bounds.size.height)];
[stampOverlay setAlpha:.90];
// Add the many stickers to image View //
[self addSubview:stickerOverlay];
[stampOverlay release];


I think this is leakless. .. maybe ?
thanks again.
Ian

jnoxx
Feb 4, 2012, 03:19 PM
If you're not sure about leaks, press command+Shift+B, this will trigger an analyze build from Xcode itself, which whill show you potential memory leaks. if it doesn't recognize any there. try profiling your app, press the "Run" button in Xcode 4 for a while and keep mouse clicked and then select Profile, and you should use your app, and see if any leaks come up ;)