CGImageCreateWithMaskingColors不适用于iOS7

我在iOS5和iOS6上开发了一个应用程序。 升级到XCode 5和iOS7后,我有一些新的bug。

主要的一点就是colorMasking不再有效。 完全相同的代码仍然编译和iOS6的手机上工作。 在iOS7上,蒙版颜色仍然存在。 我试图在Google上find答案,但还没有find答案。 这是一个iOS7的错误,还是有人知道一个更好的方法做色罩?

这里是代码:

- (UIImage*) processImage :(UIImage*) image { UIImage *inputImage = [UIImage imageWithData:UIImageJPEGRepresentation(image, 1.0)]; const float colorMasking[6]={100.0, 255.0, 0.0, 100.0, 100.0, 255.0}; CGImageRef imageRef = CGImageCreateWithMaskingColors(inputImage.CGImage, colorMasking); UIImage* finalImage = [UIImage imageWithCGImage:imageRef]; CGImageRelease(imageRef); return finalImage; } 

这里有几个StackOverflow的post,我发现,帮助我在iOS6中工作的第一个地方: 透明度iOS的 iOS颜色透明的UIImage

我偶然发现了CGImageCreateWithMaskingColorsUIImagePNGRepresentation一些奇怪的行为。 这可能会或可能不会涉及到您的问题。 我发现如果:

  1. 如果使用CGImageCreateWithMaskingColors并立即将该图像添加到图像视图,我可以看到透明度似乎已经正确应用;

  2. 但在iOS 7中,如果我那么:

    • CGImageCreateWithMaskingColors获取这个图像,并使用UIImagePNGRepresentation创build一个NSData ; 和

    • 如果使用imageWithData从该NSData重新加载图像,则生成的图像将不再具有透明度。

    为了证实这一点,如果我writeToFile这个NSData并检查保存的图像像Photoshop一样的工具,我可以确认该文件没有应用任何透明度。

    这只能在iOS 7中体现出来。在iOS 6中,这很好。

  3. 但是,如果我在第1步拍摄图像并通过drawInRect往返,则保存图像并随后加载的过程也可以正常进行。

以下代码说明了这个问题:

 - (UIImage*) processImage :(UIImage*) inputImage { const float colorMasking[6] = {255.0, 255.0, 255.0, 255.0, 255.0, 255.0}; CGImageRef imageRef = CGImageCreateWithMaskingColors(inputImage.CGImage, colorMasking); UIImage* finalImage = [UIImage imageWithCGImage:imageRef]; CGImageRelease(imageRef); // If I put this image in an image view, I see the transparency fine. self.imageView.image = finalImage; // this works // But if I save it to disk and the file does _not_ have any transparency NSString *documentsPath = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)[0]; NSString *pathWithoutTransparency = [documentsPath stringByAppendingPathComponent:@"image-but-no-transparency.png"]; NSData *data = UIImagePNGRepresentation(finalImage); [data writeToFile:pathWithoutTransparency atomically:YES]; // save it so I can check out the file in Photoshop // In iOS 7, the following imageview does not honor the transparency self.imageView2.image = [UIImage imageWithData:data]; // this does not work in iOS 7 // but, if I round-trip the original image through `drawInRect` one final time, // the transparency works UIGraphicsBeginImageContextWithOptions(finalImage.size, NO, 1.0); [finalImage drawInRect:CGRectMake(0, 0, finalImage.size.width, finalImage.size.height)]; UIImage *anotherRendition = UIGraphicsGetImageFromCurrentImageContext(); UIGraphicsEndImageContext(); data = UIImagePNGRepresentation(anotherRendition); NSString *pathWithTransparency = [documentsPath stringByAppendingPathComponent:@"image-with-transparancy.png"]; [data writeToFile:pathWithTransparency atomically:YES]; // But this image is fine self.imageView3.image = [UIImage imageWithContentsOfFile:pathWithTransparency]; // this does work return anotherRendition; } 

我正在加载一个JPEG,由于某种原因加载了一个alpha通道,这将无法正常工作时,所以这里我重新创buildCGImage忽略alpha通道。 可能有更好的方法做到这一点,但这个工程!

 - (UIImage *)imageWithChromaKeyMasking { const CGFloat colorMasking[6]={255.0,255.0,255.0,255.0,255.0,255.0}; CGImageRef oldImage = self.CGImage; CGBitmapInfo oldInfo = CGImageGetBitmapInfo(oldImage); CGBitmapInfo newInfo = (oldInfo & (UINT32_MAX ^ kCGBitmapAlphaInfoMask)) | kCGImageAlphaNoneSkipLast; CGDataProviderRef provider = CGImageGetDataProvider(oldImage); CGImageRef newImage = CGImageCreate(self.size.width, self.size.height, CGImageGetBitsPerComponent(oldImage), CGImageGetBitsPerPixel(oldImage), CGImageGetBytesPerRow(oldImage), CGImageGetColorSpace(oldImage), newInfo, provider, NULL, false, kCGRenderingIntentDefault); CGDataProviderRelease(provider); provider = NULL; CGImageRef im = CGImageCreateWithMaskingColors(newImage, colorMasking); UIImage *ret = [UIImage imageWithCGImage:im]; CGImageRelease(im); return ret; }