From de19c24241628c79235e6938e485b1f4c70673d9 Mon Sep 17 00:00:00 2001 From: Martin Conte Mac Donell Date: Wed, 13 Feb 2013 21:55:26 -0300 Subject: [PATCH] [BUG] Fix invalid alpha on JPEG files --- SDWebImage/SDWebImageDecoder.m | 37 ++++++++++++++++++++++++++++++++-- 1 file changed, 35 insertions(+), 2 deletions(-) diff --git a/SDWebImage/SDWebImageDecoder.m b/SDWebImage/SDWebImageDecoder.m index 1b219c9..fe70fd9 100644 --- a/SDWebImage/SDWebImageDecoder.m +++ b/SDWebImage/SDWebImageDecoder.m @@ -18,8 +18,41 @@ CGSize imageSize = CGSizeMake(CGImageGetWidth(imageRef), CGImageGetHeight(imageRef)); CGRect imageRect = (CGRect){.origin = CGPointZero, .size = imageSize}; - CGColorSpaceRef colorSpace = CGImageGetColorSpace(imageRef); - CGContextRef context = CGBitmapContextCreate(NULL, imageSize.width, imageSize.height, CGImageGetBitsPerComponent(imageRef), CGImageGetBytesPerRow(imageRef), colorSpace, CGImageGetBitmapInfo(imageRef)); + CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); + CGBitmapInfo bitmapInfo = CGImageGetBitmapInfo(imageRef); + + int infoMask = (bitmapInfo & kCGBitmapAlphaInfoMask); + BOOL anyNonAlpha = (infoMask == kCGImageAlphaNone || + infoMask == kCGImageAlphaNoneSkipFirst || + infoMask == kCGImageAlphaNoneSkipLast); + + // CGBitmapContextCreate doesn't support kCGImageAlphaNone with RGB. + // https://developer.apple.com/library/mac/#qa/qa1037/_index.html + if (infoMask == kCGImageAlphaNone && CGColorSpaceGetNumberOfComponents(colorSpace) > 1) + { + // Unset the old alpha info. + bitmapInfo &= ~kCGBitmapAlphaInfoMask; + + // Set noneSkipFirst. + bitmapInfo |= kCGImageAlphaNoneSkipFirst; + } + // Some PNGs tell us they have alpha but only 3 components. Odd. + else if (!anyNonAlpha && CGColorSpaceGetNumberOfComponents(colorSpace) == 3) + { + // Unset the old alpha info. + bitmapInfo &= ~kCGBitmapAlphaInfoMask; + bitmapInfo |= kCGImageAlphaPremultipliedFirst; + } + + // It calculates the bytes-per-row based on the bitsPerComponent and width arguments. + CGContextRef context = CGBitmapContextCreate(NULL, + imageSize.width, + imageSize.height, + CGImageGetBitsPerComponent(imageRef), + 0, + colorSpace, + bitmapInfo); + CGColorSpaceRelease(colorSpace); // If failed, return undecompressed image if (!context) return image;