iPhone CGContextRef CGBitmapContextCreate unsupported parameter combination
Asked Answered
K

5

10

In my application I need to resize and crop some images, stored locally and online. I am using Trevor Harmon's tutorial which implements UIImage+Resize.

On my iPhone 4(iOS 4.3.1) everything works OK, I have no problems. But on my iPhone 3G (iOS 3.2) the resizing and crop methods are not working for any picture (the locally stored ones are PNGs). This is the console output:

Tue Apr  5 02:34:44 Andreis-MacBook-Pro.local Puzzle[12453] <Error>: CGBitmapContextCreate:     unsupported parameter combination: 8 integer bits/component; 32 bits/pixel; 3-component color space; kCGImageAlphaLast; 288 bytes/row.
Tue Apr  5 02:34:44 Andreis-MacBook-Pro.local Puzzle[12453] <Error>: CGBitmapContextCreate: unsupported parameter combination: 8 integer bits/component; 32 bits/pixel; 3-component color space; kCGImageAlphaLast; 288 bytes/row.
Tue Apr  5 02:34:44 Andreis-MacBook-Pro.local Puzzle[12453] <Error>: CGBitmapContextCreate: unsupported parameter combination: 8 integer bits/component; 32 bits/pixel; 3-component color space; kCGImageAlphaLast; 288 bytes/row.
Tue Apr  5 02:34:44 Andreis-MacBook-Pro.local Puzzle[12453] <Error>: CGBitmapContextCreate: unsupported parameter combination: 8 integer bits/component; 32 bits/pixel; 3-component color space; kCGImageAlphaLast; 288 bytes/row.

This is the crop method

- (UIImage *)croppedImage:(CGRect)bounds 
{
    CGImageRef imageRef = CGImageCreateWithImageInRect([self CGImage], bounds);
    UIImage *croppedImage = [UIImage imageWithCGImage:imageRef];
    CGImageRelease(imageRef);
    return croppedImage;
}

The resize method is this:

- (UIImage *)resizedImage:(CGSize)newSize
            transform:(CGAffineTransform)transform
       drawTransposed:(BOOL)transpose
 interpolationQuality:(CGInterpolationQuality)quality 
{
    CGRect newRect = CGRectIntegral(CGRectMake(0, 0, newSize.width, newSize.height));
    CGRect transposedRect = CGRectMake(0, 0, newRect.size.height, newRect.size.width);
    CGImageRef imageRef = self.CGImage;

    CGContextRef bitmap = CGBitmapContextCreate(NULL,
                                            newRect.size.width,
                                            newRect.size.height,
                                            CGImageGetBitsPerComponent(imageRef),
                                            0,
                                            CGImageGetColorSpace(imageRef),
                                            CGImageGetBitmapInfo(imageRef));
    if(bitmap == nil)
        return nil;

    CGContextConcatCTM(bitmap, transform);

    CGContextSetInterpolationQuality(bitmap, quality);

    CGContextDrawImage(bitmap, transpose ? transposedRect : newRect, imageRef);

    CGImageRef newImageRef = CGBitmapContextCreateImage(bitmap);
    UIImage *newImage = [UIImage imageWithCGImage:newImageRef];

    CGContextRelease(bitmap);
    CGImageRelease(newImageRef);

    return newImage;
}

Can someone explain to me way I have this issue?

Thank you, Andrei

Knucklehead answered 4/4, 2011 at 23:44 Comment(0)
N
24

Replying here since I had the exact same pixel format when I got this error. I hope this answer helps someone.

The reason it was failing, in my case, was that kCGImageAlphaLast isn't a permitted value anymore on iOS 8, although it works well on iOS 7. The 32 pbb, 8 bpc combination only allows kCGImageAlphaNoneSkip* and kCGImageAlphaPremultiplied* for the Alpha Info. Apparently this was a problem always, but wasn't enforced before iOS 8. Here's my solution:

- (CGBitmapInfo)normalizeBitmapInfo:(CGBitmapInfo)oldBitmapInfo {
    //extract the alpha info by resetting everything else
    CGImageAlphaInfo alphaInfo = oldBitmapInfo & kCGBitmapAlphaInfoMask;

    //Since iOS8 it's not allowed anymore to create contexts with unmultiplied Alpha info
    if (alphaInfo == kCGImageAlphaLast) {
        alphaInfo = kCGImageAlphaPremultipliedLast;
    }
    if (alphaInfo == kCGImageAlphaFirst) {
        alphaInfo = kCGImageAlphaPremultipliedFirst;
    }

    //reset the bits
    CGBitmapInfo newBitmapInfo = oldBitmapInfo & ~kCGBitmapAlphaInfoMask;

    //set the bits to the new alphaInfo
    newBitmapInfo |= alphaInfo;

    return newBitmapInfo;
}

In my case the failing piece of code looked like this, where imageRef is a CGImageRef of a PNG loaded from the app bundle:

CGContextRef bitmap = CGBitmapContextCreate(NULL,
                                                newRect.size.width,
                                                newRect.size.height,
                                                CGImageGetBitsPerComponent(imageRef),
                                                0,
                                                CGImageGetColorSpace(imageRef),
                                                CGImageGetBitmapInfo(imageRef));

Sources: https://mcmap.net/q/540527/-cgbitmapcontextcreate-unsupported-parameter-combination

https://developer.apple.com/library/mac/DOCUMENTATION/GraphicsImaging/Conceptual/drawingwithquartz2d/dq_context/dq_context.html#//apple_ref/doc/uid/TP30001066-CH203-BCIBHHBB

Nabors answered 14/10, 2014 at 16:0 Comment(1)
For anyone using UIImage categories from Trevor Harmon's tutorial, the code OP is using, this is a sure way to fix it.Fenner
F
5

I figured out it's a problem with the color space. Just replace CGImageGetColorSpace(imageRef) with CGColorSpaceCreateDeviceRGB() . This works for me when trying to save image I got from AVCaptureSession. And don't forget to release it!

CGColorSpaceRef rgbColorSpace = CGColorSpaceCreateDeviceRGB();
CGContextRef bitmap = CGBitmapContextCreate(NULL,
                                            newRect.size.width,
                                            newRect.size.height,
                                            CGImageGetBitsPerComponent(imageRef),
                                            0,
                                            rgbColorSpace,//CGImageGetColorSpace(imageRef), sometimes contains unsupported colorspace
                                            bitmapInfo);
CGColorSpaceRelease(rgbColorSpace);
Foresaid answered 10/12, 2011 at 8:12 Comment(0)
N
3

Ok this may or may not help you (and i appreciate that this is an old post)

I was getting a similar problem because the width parameter (in your case newRect.size.width) had a decimal fraction component (eg 100.001 instead of 100.0). i typecast it to an integer and back, truncating the decimals component, and the problem went away. i am guessing there is a test to see that the number of bits per component x pixels etc adds up, and it can't deal with fractional pixels/points. you are welcome to use this method if it helps.

+(CGSize)  fixSize:(CGSize) forSize{
    NSInteger w = (NSInteger) forSize.width;
    NSInteger h = (NSInteger) forSize.height;
    return CGSizeMake(w, h);
}
New answered 23/10, 2011 at 20:30 Comment(1)
I was observing exactly the same error on iOS 6. This comment probably saved me a long topsy turvy ride.Balling
C
3

I had the same problem with iOS 5 simulator and the answers above didn't resolve my issue: images were not loaded and the console still reported the same errors.

I am using the very popular categories found here.

On this blog people are having the same issue(s). Matt's answer from November 22, 2011 helped me.

Cheers!

Confabulation answered 11/6, 2013 at 8:30 Comment(0)
H
0

I was seeing this issue in the simulator when switching from 5.1 to 6.1 for testing. Closing the simulator and opening it again seems to have removed the error.

Hopehopeful answered 17/8, 2013 at 18:37 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.