Ios 从图像文件确定颜色顺序

Ios 从图像文件确定颜色顺序,ios,cgimage,Ios,Cgimage,我的应用程序有几个部分基于的方法 我需要在某个位置查找颜色的图像可以来自相机、库、应用程序包,也可以来自应用程序中生成的图像。我刚刚遇到了一个频道顺序不同的问题(碰巧不同的频道是由应用程序生成并以jpeg格式保存以用于缓存的频道) 所以我的问题是,最好是使用链接作为起点,如何确定CG图像的颜色顺序?我肯定这在什么地方有记录,但在哪里 受此启发,我使用了一种名为+imageDump:的方法,从一幅图像中提取以下信息: CGImageGetHeight: 120 CGImageGetWidth:

我的应用程序有几个部分基于的方法

我需要在某个位置查找颜色的图像可以来自相机、库、应用程序包,也可以来自应用程序中生成的图像。我刚刚遇到了一个频道顺序不同的问题(碰巧不同的频道是由应用程序生成并以jpeg格式保存以用于缓存的频道)

所以我的问题是,最好是使用链接作为起点,如何确定CG图像的颜色顺序?我肯定这在什么地方有记录,但在哪里

受此启发,我使用了一种名为+imageDump:的方法,从一幅图像中提取以下信息:

CGImageGetHeight: 120
CGImageGetWidth:  120
CGImageGetColorSpace: <CGColorSpace 0x1c562050> (kCGColorSpaceDeviceRGB)
CGImageGetBitsPerPixel:     32
CGImageGetBitsPerComponent: 8
CGImageGetBytesPerRow:      480
CGImageGetBitmapInfo: 0x00002002
  kCGBitmapAlphaInfoMask     = YES
  kCGBitmapFloatComponents   = NO
  kCGBitmapByteOrderMask     = YES
  kCGBitmapByteOrderDefault  = NO
  kCGBitmapByteOrder16Little = NO
  kCGBitmapByteOrder32Little = YES
  kCGBitmapByteOrder16Big    = YES
  kCGBitmapByteOrder32Big    = NO
CGImageGetHeight:120
CGImageGetWidth:120
CGImageGetColorSpace:(kCGColorSpaceDeviceRGB)
CGImageGetBitsPerPixel:32
CGImageGetBitsPerComponent:8
CGImageGetBytesPerRow:480
CGImageGetBitmapInfo:0x000002
kCGBitmapAlphaInfoMask=是
kCGBitmapFloatComponents=否
kCGBitmapByteOrderMask=是
kCGBitmapByteOrderDefault=否
kCGBitmapByteOrder16Little=否
kCGBitmapByteOrder32Little=是
kCGBitmapByteOrder16Big=是
kCGBitmapByteOrder32Big=否
从另一幅图像中,通道顺序不同:

CGImageGetHeight: 120
CGImageGetWidth:  120
CGImageGetColorSpace: <CGColorSpace 0x1c562050> (kCGColorSpaceDeviceRGB)
CGImageGetBitsPerPixel:     32
CGImageGetBitsPerComponent: 8
CGImageGetBytesPerRow:      480
CGImageGetBitmapInfo: 0x00000001
  kCGBitmapAlphaInfoMask     = YES
  kCGBitmapFloatComponents   = NO
  kCGBitmapByteOrderMask     = NO
  kCGBitmapByteOrderDefault  = NO
  kCGBitmapByteOrder16Little = NO
  kCGBitmapByteOrder32Little = NO
  kCGBitmapByteOrder16Big    = NO
  kCGBitmapByteOrder32Big    = NO
CGImageGetHeight:120
CGImageGetWidth:120
CGImageGetColorSpace:(kCGColorSpaceDeviceRGB)
CGImageGetBitsPerPixel:32
CGImageGetBitsPerComponent:8
CGImageGetBytesPerRow:480
CGImageGetBitmapInfo:0x00000001
kCGBitmapAlphaInfoMask=是
kCGBitmapFloatComponents=否
kCGBitmapByteOrderMask=否
kCGBitmapByteOrderDefault=否
kCGBitmapByteOrder16Little=否
kCGBitmapByteOrder32Little=否
kCGBitmapByteOrder16Big=否
kCGBitmapByteOrder32Big=否

似乎这些信息以某种方式指定了通道顺序,但我不知道如何解释这些常量。还是我看错了?

您需要使用
CGImageGetAlphaInfo
CGImageGetBitmapInfo
CGImageGetBitsPerComponent
cgimagegetbitspexel
函数来确定数据的布局。这些值的组合将允许您确定有哪些组件、它们的大小和顺序。

我发布此答案主要是为了回答对我的问题的评论。以下是我使用的解决方案:

- (UIColor*)colorFromImage:(UIImage*)image sampledAtPoint:(CGPoint)p {
   // from http://stackoverflow.com/questions/144250/how-to-get-the-rgb-values-for-a-pixel-on-an-image-on-the-iphone
   //DLog(@"Image dump call from colorFromImage:sampledAtPoint:");
   //[Utilities imageDump:image];
   int radius = 3;
   CGImageRef cgImage = [image CGImage];
   CGDataProviderRef provider = CGImageGetDataProvider(cgImage);
   CFDataRef bitmapData = CGDataProviderCopyData(provider);
   const UInt8* data = CFDataGetBytePtr(bitmapData);
   size_t bytesPerRow = CGImageGetBytesPerRow(cgImage);
   size_t width = CGImageGetWidth(cgImage);
   size_t height = CGImageGetHeight(cgImage);
   CGBitmapInfo info = CGImageGetBitmapInfo(cgImage);

   long col = p.x*(width-1);
   long row = p.y*(height-1);
   long cnt = 0;long redval=0,greenval=0,blueval=0;
   for (int rrow = row - radius; rrow < row + radius; rrow++) {
      for (int ccol = col - radius; ccol < col + radius; ccol++) {
         if ((rrow >= 0) && (ccol >= 0)) {
            if ((rrow < height) && (ccol < width)) {
               const UInt8* pixel = data + rrow*bytesPerRow+ccol*4;
               int tempred,tempgreen,tempblue,tempalpha;
               if (info & kCGBitmapByteOrder32Little) {
                  tempred = pixel[2];
                  tempgreen = pixel[1];
                  tempblue = pixel[0];
                  tempalpha = pixel[3];
               } else {
                  tempred = pixel[0];
                  tempgreen = pixel[1];
                  tempblue = pixel[2];
                  tempalpha = pixel[3];
               }
               //DLog(@"%d %d %d %d",tempred,tempgreen,tempblue,tempalpha);
               if (tempalpha==255) {
                  redval += tempred;
                  greenval += tempgreen;
                  blueval += tempblue;
                  cnt++;
               }
            }
         }
      }
   }
   UIColor *returnColor = [UIColor colorWithRed:1.0f*redval/(cnt*255) green:1.0f*greenval/(cnt*255) blue:1.0f*blueval/(cnt*255) alpha:1.0];
   CFRelease(bitmapData);//take care of memory leak
   return returnColor;
}
-(UIColor*)colorFromImage:(UIImage*)图像采样点:(CGPoint)p{
//从http://stackoverflow.com/questions/144250/how-to-get-the-rgb-values-for-a-pixel-on-an-image-on-the-iphone
//DLog(@“来自colorFromImage:sampledAtPoint:的图像转储调用”);
//[实用程序映像转储:映像];
int半径=3;
CGImageRef cgImage=[图像cgImage];
CGDataProviderRef provider=CGImageGetDataProvider(cgImage);
CFDataRef bitmapData=CGDataProviderCopyData(提供程序);
const UInt8*data=CFDataGetBytePtr(位图数据);
大小\u t bytesPerRow=CGImageGetBytesPerRow(cgImage);
大小\u t宽度=CGImageGetWidth(cgImage);
尺寸高度=CGImageGetHeight(cgImage);
CGBitmapInfo info=CGImageGetBitmapInfo(cgImage);
长柱=p.x*(宽度-1);
长行=p.y*(高度-1);
长cnt=0;长redval=0,绿val=0,蓝val=0;
对于(int rrow=行-半径;rrow<行+半径;rrow++){
对于(int-ccol=col-radius;ccol=0)和&(ccol>=0)){
如果((箭头<高度)和&(ccol<宽度)){
常量UInt8*像素=数据+rrow*字节数+ccol*4;
int tempred、tempgreen、tempblue、tempalpha;
if(信息和kCGBitmapByteOrder32Little){
tempred=像素[2];
tempgreen=像素[1];
tempblue=像素[0];
tempalpha=像素[3];
}否则{
tempred=像素[0];
tempgreen=像素[1];
tempblue=像素[2];
tempalpha=像素[3];
}
//DLog(@“%d%d%d%d”、淡红色、淡绿色、淡蓝色、淡紫色);
如果(tempalpha==255){
redval+=tempred;
greenval+=tempgreen;
blueval+=tempblue;
cnt++;
}
}
}
}
}
UIColor*returnColor=[UIColor color withred:1.0f*redval/(cnt*255)greenval/(cnt*255)blue:1.0f*blueval/(cnt*255)alpha:1.0];
CFRelease(bitmapData);//注意内存泄漏
返回颜色;
}

我似乎记得这不是一个完整的解决方案,但就我自己的目的而言已经足够了。

对。我正在查看这些信息,我不知道如何解释它。我会用细节更新我的问题。你明白了吗?我不知道我的像素是ARGB、RGBA、RGB、BGR、BGRA等等。对不起,我已经很久没有参与这个项目了,我不记得我做了什么。不过,快速浏览一下引用了这篇堆栈溢出文章的代码。也许它会帮助你。仅供参考,我添加我自己的答案主要是为了回答您的问题。在确定是BGRA还是RGBA的if条件下,您有
信息和kCGBitmapByteOrder32Little
——您的意思是
(bitmapInfo和kCGBitmapByteOrderMask)==kCGBitmapByteOrder32Little
?没有变量名bitmapInfo。但是,有一个变量名info,类型为CGBitmapInfo。很抱歉,我在注释的第一个代码段中正确命名了它,但在第二个代码段中拼写错误。本应阅读:
(info&kCGBitmapByteOrderMask)==kCGBitmapByteOrder32Little)
——因此我的问题是,您是否需要在掩码上使用位运算符,然后将其与常量进行比较以检查条件?嗯,我不这么认为。我认为KCGBitMapByteOrder32小常量只能解析为一位。所以把它和任何东西联系起来只是一点点。我们只是检查位的值是多少。你的支票