gpt4 book ai didi

ios - 如何更改部分 UIImage 的颜色?

转载 作者:塔克拉玛干 更新时间:2023-11-02 21:11:34 25 4
gpt4 key购买 nike

我有一张灰度图像,我在该图像的某些部分应用了它的原始颜色,我已经实现了。现在我想改变我在图像中应用原始颜色的那部分的颜色

我有这个: Original Image

我想转换成这样: Result Image

CGImageRef imageRef = [image CGImage];
NSUInteger width = CGImageGetWidth(imageRef);
NSUInteger height = CGImageGetHeight(imageRef);

NSUInteger bytesPerPixel = 4;
NSUInteger bytesPerRow = bytesPerPixel * width;
NSUInteger bitsPerComponent = 8;

NSUInteger bytesCount = height * width * bytesPerPixel;

CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
unsigned char *rawData = (unsigned char *)calloc(bytesCount, sizeof(unsigned char));
CGContextRef context = CGBitmapContextCreate(rawData, width, height,
bitsPerComponent, bytesPerRow, colorSpace,
kCGImageAlphaPremultipliedLast | kCGBitmapByteOrder32Big);

CGContextDrawImage(context, CGRectMake(0, 0, width, height), imageRef);
CGContextRelease(context);

unsigned char *outputData = (unsigned char *)calloc(bytesCount, sizeof(unsigned char));

NSUInteger byteIndex = 0;
for (NSUInteger i=0; i<bytesCount / bytesPerPixel; ++i) {
CGFloat red = (CGFloat)rawData[byteIndex];
CGFloat green = (CGFloat)rawData[byteIndex+1];
CGFloat blue = (CGFloat)rawData[byteIndex+2];
CGFloat alpha = (CGFloat)rawData[byteIndex+3];

BOOL grayscale = red == green == blue;

if (!grayscale) {
// test for near values
CGFloat diff = MAX(ABS(red-green), MAX(ABS(red-blue), ABS(green-blue)));

static CGFloat allowedDifference = 100; // in range of 0-255

if (diff > allowedDifference) {

// CGFloat redTemp = 236;
// red = green;
// green = redTemp;
red = 236.0;
green = 17.0;
blue = 17.0;

}
}

outputData[byteIndex] = red;
outputData[byteIndex+1] = green;
outputData[byteIndex+2] = blue;
outputData[byteIndex+3] = alpha;

byteIndex += bytesPerPixel;
}

free(rawData);


CGDataProviderRef outputDataProvider = CGDataProviderCreateWithData(NULL,
outputData,
bytesCount,
NULL);
free(outputData);

CGImageRef outputImageRef = CGImageCreate(width,
height,
bitsPerComponent,
bytesPerPixel * 8,
bytesPerRow,
colorSpace,
kCGBitmapByteOrderDefault,
outputDataProvider,
NULL,NO,
kCGRenderingIntentDefault);


CGColorSpaceRelease(colorSpace);
CGDataProviderRelease(outputDataProvider);

UIImage *outputImage = [UIImage imageWithCGImage:outputImageRef];
CGImageRelease(outputImageRef);

我尝试了 bitmapcontext 和一切,但没有得到想要的结果。

有人知道吗?

最佳答案

您可以尝试使用 CGBitmapContextCreate 从图像中获取像素数据来创建颜色空间,然后通过 CGContextDrawImage 向其绘制图像。

其次,您将收到一个一维字节数组。像这样:[r1, g1, b1, a1, r2, g2, b2, a2, ...] 其中 r,g,b,a - 颜色分量,1,2 - nu。像素。

在此之后,您可以遍历数组并比较每个像素的颜色分量。由于您应该跳过灰度像素,因此您需要比较 rgb 参数,理论上它们必须相等,但您也可以支持一些小的几位数 +- 错误。

如果具体像素不是灰度,只需交换红色和绿色字节。

应该是要走的路。

更新示例:

UIImage *image = [UIImage imageNamed:@"qfjsc.png"];

CGImageRef imageRef = [image CGImage];
NSUInteger width = CGImageGetWidth(imageRef);
NSUInteger height = CGImageGetHeight(imageRef);

NSUInteger bytesPerPixel = 4;
NSUInteger bytesPerRow = bytesPerPixel * width;
NSUInteger bitsPerComponent = 8;

NSUInteger bytesCount = height * width * bytesPerPixel;

CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
unsigned char *rawData = (unsigned char *)calloc(bytesCount, sizeof(unsigned char));
CGContextRef context = CGBitmapContextCreate(rawData, width, height,
bitsPerComponent, bytesPerRow, colorSpace,
kCGImageAlphaPremultipliedLast | kCGBitmapByteOrder32Big);

CGContextDrawImage(context, CGRectMake(0, 0, width, height), imageRef);
CGContextRelease(context);

unsigned char *outputData = (unsigned char *)calloc(bytesCount, sizeof(unsigned char));

NSUInteger byteIndex = 0;
for (NSUInteger i=0; i<bytesCount / bytesPerPixel; ++i) {
CGFloat red = (CGFloat)rawData[byteIndex];
CGFloat green = (CGFloat)rawData[byteIndex+1];
CGFloat blue = (CGFloat)rawData[byteIndex+2];
CGFloat alpha = (CGFloat)rawData[byteIndex+3];

BOOL grayscale = red == green == blue;

if (!grayscale) {
// test for near values
CGFloat diff = MAX(ABS(red-green), MAX(ABS(red-blue), ABS(green-blue)));

static CGFloat allowedDifference = 50.0; // in range of 0-255

if (diff > allowedDifference) {

CGFloat redTemp = red;
red = green;
green = redTemp;

}
}

outputData[byteIndex] = red;
outputData[byteIndex+1] = green;
outputData[byteIndex+2] = blue;
outputData[byteIndex+3] = alpha;

byteIndex += bytesPerPixel;
}

free(rawData);


CGDataProviderRef outputDataProvider = CGDataProviderCreateWithData(NULL,
outputData,
bytesCount,
NULL);
free(outputData);

CGImageRef outputImageRef = CGImageCreate(width,
height,
bitsPerComponent,
bytesPerPixel * 8,
bytesPerRow,
colorSpace,
kCGBitmapByteOrderDefault,
outputDataProvider,
NULL,NO,
kCGRenderingIntentDefault);


CGColorSpaceRelease(colorSpace);
CGDataProviderRelease(outputDataProvider);

UIImage *outputImage = [UIImage imageWithCGImage:outputImageRef];
CGImageRelease(outputImageRef);

注意静态允许的差异变量。它允许您跳过几乎非灰度像素,但它们在 RGB 颜色空间中并且本质上几乎是灰度。

例子如下:

  1. 允许的差异 = 0 Allowed difference = 0
  2. 允许的差异 = 50 Allowed difference = 50

关于ios - 如何更改部分 UIImage 的颜色?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33521152/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com