2011-01-21 6 views
2

이미지의 색상을 바꾸어 보았지만 투명도뿐만 아니라 모든 색상으로 처리하려고하기 때문에 필요한 방식으로 작동하지 않습니다.색상별로 UIImage를 분할하고 2 개의 이미지를 만듭니다.

내가 찾고있는 것은 이미지를 가져 와서 그 이미지에서 색상 (모든 순수한 검정색을 말함)을 분리하는 방법입니다. 그런 다음 분할 된 부분을 취해 투명한 배경과 분할 된 부분으로 새 이미지를 만듭니다.

(여기는 아이디어의 예일뿐입니다.이 페이지의 스크린 샷을 찍고 싶습니다. 모든 다른 색을 투명하게 만들고, 새 이미지를 라이브러리에 저장하거나 UIImageView에 저장하십시오.)

나는 CGImageCreateWithMaskingColors를 들여다 보았지만 투명 부분에 필요한 것을 수행하지 못하는 것 같아서 colorMasking 입력이 {Rmin, Rmax, Gmin, Gmax, Bmin , Bmax} 컬러 마스크를 사용합니다. 어떤 생각이나 입력이 좋을 것입니다.

답변

2

기본 바이트에 액세스하고 코드를 작성하여 직접 처리해야하는 것처럼 들립니다. CGImageGetDataProvider()을 사용하여 이미지의 데이터에 액세스 할 수 있지만 처리 방법을 알고있는 형식 일 수는 없습니다. 또는 처리 방법을 알고있는 특정 형식을 사용하여 새 CGContextRef을 새로 만든 다음 원본 이미지를 새 컨텍스트에 그려서 기본 데이터를 처리 할 수도 있습니다. 다음은 원하는 작업 (컴파일되지 않은 작업)에 대한 빠른 시도입니다.

- (UIImage *)imageWithBlackPixels:(UIImage *)image { 
    CGImageRef cgImage = image.CGImage; 
    // create a premultiplied ARGB context with 32bpp 
    CGColorSpaceRef colorspace = CGColorSpaceCreateDeviceRGB(); 
    size_t width = CGImageGetWidth(cgImage); 
    size_t height = CGImageGetHeight(cgImage); 
    size_t bpc = 8; // bits per component 
    size_t bpp = bpc * 4/8; // bytes per pixel 
    size_t bytesPerRow = bpp * width; 
    void *data = malloc(bytesPerRow * height); 
    CGBitmapInfo bitmapInfo = kCGImageAlphaPremultipliedFirst | kCGBitmapByteOrder32Host; 
    CGContextRef ctx = CGBitmapContextCreate(data, width, height, bpc, bytesPerRow, colorspace, bitmapInfo); 
    CGColorSpaceRelease(colorspace); 
    if (ctx == NULL) { 
     // couldn't create the context - double-check the parameters? 
     free(data); 
     return nil; 
    } 
    // draw the image into the context 
    CGContextDrawImage(ctx, CGRectMake(0, 0, width, height), cgImage); 
    // replace all non-black pixels with transparent 
    // preserve existing transparency on black pixels 
    for (size_t y = 0; y < height; y++) { 
     size_t rowStart = bytesPerRow * y; 
     for (size_t x = 0; x < width; x++) { 
      size_t pixelOffset = rowStart + x*bpp; 
      // check the RGB components of the pixel 
      if (data[pixelOffset+1] != 0 || data[pixelOffset+2] != 0 || data[pixelOffset+3] != 0) { 
       // this pixel contains non-black. zero it out 
       memset(&data[pixelOffset], 0, 4); 
      } 
     } 
    } 
    // create our new image and release the context data 
    CGImageRef newCGImage = CGBitmapContextCreateImage(ctx); 
    CGContextRelease(ctx); 
    free(data); 
    UIImage *newImage = [UIImage imageWithCGImage:newCGImage scale:image.scale orientation:image.imageOrientation]; 
    CGImageRelease(newCGImage); 
    return newImage; 
} 
+0

이 솔루션은 매우 근접해 있습니다. 내가 변경해야만했던 유일한 것은 무효화 된 char * 데이터에 대한 데이터입니다. 그래서 데이터의 int 값에 액세스 할 수 있습니다. 데이터가 argb가 아닌 rgba 값을 표시하므로 데이터 [pixelOffset + 3]을 데이터 [pixelOffset]로 만들었습니다. 그렇지 않으면 위대한 작품. 감사! – AtomRiot

+0

아, 코드를 컴파일하지 않을 때의 위험. RGBA라고 생각하는 이유는'kCGImageAlphaPremultipliedFirst'가 최하위 비트가 아닌 최상위 비트에 먼저 저장하기 때문입니다. Host를 사용하는 대신 명시 적으로 엔디안을 지정하면이 시점에서 좋은 생각 일 수 있습니다. –

관련 문제