CGImageRef consumes lot of memory

1.1k views Asked by At

I am creating blur image for one of my apps screen, for this i am using following code


UIGraphicsBeginImageContext(self.view.bounds.size);
[self.view.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();

CIContext *context = [CIContext contextWithOptions:nil];
CIImage *inputImage = [CIImage imageWithCGImage:image.CGImage];


CIFilter *filter = [CIFilter filterWithName:@"CIGaussianBlur"];
[filter setValue:inputImage forKey:kCIInputImageKey];
[filter setValue:[NSNumber numberWithFloat:5] forKey:@"inputRadius"];
CIImage *result = [filter valueForKey:kCIOutputImageKey];

CGImageRef cgImage = [context createCGImage:result fromRect:[inputImage extent]];

blurrImage = [UIImage imageWithCGImage:cgImage];
  self.blurrImageView.image = blurrImage;
  CGImageRelease(cgImage);


form the above code i am getting the correct blur image, but the problem is at CGImageRef cgImage = [context createCGImage:result fromRect:[inputImage extent]]; at this line.

upto this line memory usage showing is normal, but after this line memory usage is increased abnormally high,

hear is the screenchot of memory usage shown before the execution. memory usage is keep on increasing along the execution of this method , this is before

enter image description here

and this after execution of the line CGImageRef cgImage = [context createCGImage:result fromRect:[inputImage extent]];

enter image description here

is this is common behaviour..? i searched answer but i didn't get, so any one faced the same problem please help me on this

one thing i am "not using ARC"

2

There are 2 answers

1
Rob On BEST ANSWER

I experience the same memory consumption problems with Core Image.

If you're looking for alternatives, in iOS 7, you can use UIImage+ImageEffects category, which is available as part of the iOS_UIImageEffects project at the WWDC 2013 sample code page. It provides a few new methods:

- (UIImage *)applyLightEffect;
- (UIImage *)applyExtraLightEffect;
- (UIImage *)applyDarkEffect;
- (UIImage *)applyTintEffectWithColor:(UIColor *)tintColor;
- (UIImage *)applyBlurWithRadius:(CGFloat)blurRadius tintColor:(UIColor *)tintColor saturationDeltaFactor:(CGFloat)saturationDeltaFactor maskImage:(UIImage *)maskImage;

These don't suffer from the memory consumption issues that you experience with Core Image. (Plus, it's a much faster blurring algorithm.)

This technique is illustrated in WWDC 2013 video Implementing Engaging UI on iOS.

4
Andrea On

The fact you are using a screenshot could vary the memory usage, on retina display could be more that normal device. The doubled is ok in my opinion because you have the original UIImage and the blur image living in memory, probably also the context will keep some memory. I make a guess:

  • You are using a lot of autoreleased object, they will stay in memory until the pool is drained, try to wrap the code in an autoreleaseblock


@autoreleasepool{
 UIGraphicsBeginImageContext(self.view.bounds.size);
[self.view.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();

CIContext *context = [CIContext contextWithOptions:nil];
CIImage *inputImage = [CIImage imageWithCGImage:image.CGImage];


CIFilter *filter = [CIFilter filterWithName:@"CIGaussianBlur"];
[filter setValue:inputImage forKey:kCIInputImageKey];
[filter setValue:[NSNumber numberWithFloat:5] forKey:@"inputRadius"];
CIImage *result = [filter valueForKey:kCIOutputImageKey];

CGImageRef cgImage = [context createCGImage:result fromRect:[inputImage extent]];

blurrImage = [UIImage imageWithCGImage:cgImage];
  self.blurrImageView.image = blurrImage;
  CGImageRelease(cgImage);
}