How do you create an RGBA image in Core Graphics?

I am trying to create an RGBA8 image from text for use as an OpenGL ES 2.0 texture.

+(UIImage *)imageFromText:(NSString *)text { UIFont *font = [UIFont systemFontOfSize:20.0]; CGSize size = [text sizeWithFont:font]; CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); CGContextRef contextRef = CGBitmapContextCreate (NULL, size.width, size.height, 8, 4*size.width, colorSpace, kCGImageAlphaLast ); CGColorSpaceRelease(colorSpace); UIGraphicsPushContext(contextRef); [text drawAtPoint:CGPointMake(0.0, 0.0) withFont:font]; UIImage *image = UIGraphicsGetImageFromCurrentImageContext(); UIGraphicsPopContext(); return image; } 

Unfortunately, there is no CGColorSpaceCreateDeviceRGBA , and CGColorSpaceCreateDeviceRGB results in the following error:

 CGBitmapContextCreate: unsupported parameter combination: 8 integer bits/component; 32 bits/pixel; 3-component color space; kCGImageAlphaLast; 448 bytes/row. 

What am I missing to create the right RGBA8 format that OpenGL needs here?

Update: I changed the last CGBitmapContextCreate parameter from kCGImageAlphaNone (which was when copying the code) to kCGImageAlphaLast , which is one of several options that I tried with an error.

Update 2: UIGraphicsGetImageFromCurrentImageContext() returns nil if the context was not created using UIGraphicsBeginImageContext() , so you need to extract the image in a different way: [UIImage imageWithCGImage:CGBitmapContextCreateImage(contextRef)] .

+7
source share
3 answers

The color space that you specify at creation time will not result in an error.

The reason you get this error is because you pointed 8 bits to the component, presumably 4 color components in the 4*size.width that you passed for bytesPerRow , but the bitmapInfo parameter kCGImageAlphaNone , kCGImageAlphaNone means only RGB , and not RGBA . If you want RGBA , most likely specify kCGImageAlphaLast kCGImageAlphaPremultipliedLast .

[EDIT] Sorry. I should have said kCGImageAlphaPremultipliedLast , not kCGImageAlphaLast .

So something like this:

 CGColorSpaceRef colorSpace = CGColorSpaceCreateWithName(kCGColorSpaceGenericRGB); CGContextRef contextRef = CGBitmapContextCreate(NULL, size.width, size.height, 8, 4 * size.width, colorSpace, kCGImageAlphaPremultipliedLast); 
+14
source

I was getting the same unsupported parameter combination error, although I used kCGImageAlphaPremultipliedLast . The question in my case was that the width I was getting was fractional. Turning it into an integer, passing int(width) to CGBitmapContextCreate, the problem is solved.

- Edit in response to Stephen's comment -

The problem with supplying a fractional width as the second argument is not that the CGBitmapContextCreate interprets it as such - as indicated, it receives an implicit expression without an unsigned integer type argument. Rather, this generates a mismatch in the bytes_per_row argument, since int (width * 4) does not match int (width) * 4. For example. if the width is 22.5, then the width is truncated to 22, but width * 4 evaluates to 90, not 88.

+1
source
  CGColorSpaceRef colorSpace = CGColorSpaceCreateWithName(kCGColorSpaceGenericRGB); CGBitmapInfo bitmapInfo = kCGImageAlphaPremultipliedFirst | kCGBitmapByteOrder32Little; CGContextRef theContext = CGBitmapContextCreate(NULL, imgSize.width, imgSize.height, 8, 4*imgSize.width, colorSpace, bitmapInfo); 
0
source

All Articles