2013-03-08 52 views
1

我正在使用[uiImage drawAtPoint]来绘制新图像。但事实证明,颜色变了。我的原始图像uiImage是红色,而生成的图像newImage是蓝色。这里是我的代码:UIImage字节顺序已更改

UIImage* uiImage = [UIHelper loadImage:fileName]; 
NSString *text = [ApplicationSettings instance].user.name; 
UIGraphicsBeginImageContext(uiImage.size); 
[uiImage drawAtPoint: CGPointZero]; 
[text drawAtPoint: CGPointMake(10, 10) withFont: [UIFont systemFontOfSize: 12]]; 
UIImage* newImage = UIGraphicsGetImageFromCurrentImageContext(); 
UIGraphicsEndImageContext(); 
return [Texture createTexture: newImage]; 

而且在[Texture createTexture]

+ (Texture*) createTextureWithImage:(UIImage*)image { 
    Texture* tex = [[[Texture alloc] init] autorelease]; 
    if ([tex loadImage:image]) 
     return tex; 
    else { 
     NSLog(@"Failed to load image %@", image); 
     return nil; 
    } 
} 

- (BOOL)loadImage:(UIImage *)image { 
    BOOL ret = NO; 

    if (image) { 
     // Get the inner CGImage from the UIImage wrapper 
     CGImageRef cgImage = image.CGImage; 

     // Get the image size 
     width = CGImageGetWidth(cgImage); 
     height = CGImageGetHeight(cgImage); 

     // Record the number of channels 
     channels = CGImageGetBitsPerPixel(cgImage)/CGImageGetBitsPerComponent(cgImage); 

     // Generate a CFData object from the CGImage object (a CFData object represents an area of memory) 
     CFDataRef imageData = CGDataProviderCopyData(CGImageGetDataProvider(cgImage)); 

     // Copy the image data for use by Open GL 
     ret = [self copyImageDataForOpenGL: imageData]; 
     CFRelease(imageData); 
    } 

    return ret; 
} 

而且在[texture copyImageDataForOpenGL]

- (BOOL)copyImageDataForOpenGL:(CFDataRef)imageData { 
    if (pngData) { 
     free(pngData); 
    } 

    pngData = (unsigned char*)malloc(width * height * channels); 
    const int rowSize = width * channels; 
    const unsigned char* pixels = (unsigned char*)CFDataGetBytePtr(imageData); 

    // Copy the row data from bottom to top 
    for (int i = 0; i < height; ++i) { 
     memcpy(pngData + rowSize * i, pixels + rowSize * (height - 1 - i), width * channels); 
    } 

    return YES; 
} 

我猜测,生成的图像采用RGB顺序,而原来使用倒序。这是因为白色和黑色的颜色保持不变。

编辑

我使用的OpenGL ES渲染这个纹理。

return [Texture createTexture: uiImage];而不是return [Texture createTexture: newImage]完美的作品,但我想画uiImage上的文字。

我测试过UIImageWriteToSavedPhotosAlbum(newImage, nil, nil, nil);,保存的图像是正确的。

我印的是CGImageGetBitmapInfo(uiImage.CGImage))CGImageGetBitmapInfo(newImage.CGImage),它们是不一样的!

+0

我推荐使用UIGraphicsBeginImageContextWithOptions(uiImage.size,NO,0.0);而不是UIGraphicsBeginImageContext(uiImage.size);以支持视网膜屏幕渲染。 但是,这不应该是您的图像渲染翻转颜色的原因。我希望稍后再深入研究一下 - 尽快写下来(只要尚未解决);)。 – Markus 2013-03-08 10:57:58

+0

@Markus它不能使用'UIGraphicsBeginImageContextWithOptions'。 – 2013-03-08 11:03:46

+0

你根本看不到任何图像?请尝试使用不透明YES而不是NO(第二参数),如果您不介意请分享结果。 – Markus 2013-03-08 13:22:40

回答

1

这是我的copyImageDataForOpenGL

- (BOOL)copyImageDataForOpenGL:(CGImageRef)image { 
    if (pngData) { 
     free(pngData); 
    } 

    pngData = (GLubyte*)malloc(width * height * channels); 
    const int rowSize = width * channels; 
    CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); 
    NSUInteger bytesPerPixel = channels; 
    NSUInteger bytesPerRow = bytesPerPixel * width; 
    NSUInteger bitsPerComponent = 8; 
    CGContextRef context = CGBitmapContextCreate(pngData, width, height, 
               bitsPerComponent, bytesPerRow, colorSpace, 
               kCGImageAlphaPremultipliedLast | kCGBitmapByteOrder32Big); 
    CGColorSpaceRelease(colorSpace); 
    CGContextClearRect(context, CGRectMake(0, 0, width, height)); 
    CGContextTranslateCTM(context, 0,0); 
    CGContextDrawImage(context, CGRectMake(0, 0, width, height), image); 

    [ARRenderer flipRGBData: pngData bytesPerRow:bytesPerRow height:height]; 
    return YES; 
} 

电流和正确的版本,其中[ARRenderer flipRGBData]被定义为

+ (void)flipRGBData:(GLubyte*)data bytesPerRow:(int)bytesPerRow height:(int)height { 
    GLubyte* swp = (GLubyte*)malloc(bytesPerRow); 
    for (int h = 0; h < height/2; h++) { 
     memcpy(swp, data + (height - 1 - h) * bytesPerRow, bytesPerRow); 
     memcpy(data + (height - 1 - h) * bytesPerRow, data + h * bytesPerRow, bytesPerRow); 
     memcpy(data + h * bytesPerRow, swp, bytesPerRow); 
    } 
    free(swp); 
}