2009-08-26 18 views
2

Gibt es eine Möglichkeit, die Min Rechteckfläche zu erhalten, die alle nicht transparenten Teil eines UIImage enthält?iPhone-Ziel C: UIImage - Region of Interest

Lesen Pixel für Pixel, wo Alpha == 0 ... ist kein guter Weg, glaube ich.

Jeder bessere Weg?

Vielen Dank für

Antwort

0

Okay, hier ist meine hässliche Lösung für dieses Problem. Ich hoffe, es gibt einen besseren Weg, dies zu tun.

- (CGRect) getROIRect:(UIImage*)pImage { 

CGRect roiRect = {{0,0}, {0,0}}; 
int vMaxX = -999; 
int vMinX = 999; 
int vMaxY = -999; 
int vMinY = 999; 
int x,y; 

CGImageRef inImage = pImage.CGImage; 
// Create off screen bitmap context to draw the image into. Format ARGB is 4 bytes for each pixel: Alpa, Red, Green, Blue 
CGContextRef cgctx = [self createARGBBitmapContextFromImage:inImage]; 
if (cgctx == NULL) { return roiRect; /* error */ } 

size_t w = CGImageGetWidth(inImage); 
size_t h = CGImageGetHeight(inImage); 
CGRect rect = {{0,0},{w,h}}; 

// Draw the image to the bitmap context. Once we draw, the memory 
// allocated for the context for rendering will then contain the 
// raw image data in the specified color space. 
CGContextDrawImage(cgctx, rect, inImage); 

// Now we can get a pointer to the image data associated with the bitmap 
// context. 
unsigned char* data ; 
BOOL tSet = NO; 

    data= CGBitmapContextGetData (cgctx); 
if (data != NULL) { 
    for (x=0;x<w;x++) { 
     for (y=0;y<h;y++) { 

      //offset locates the pixel in the data from x,y. 
      //4 for 4 bytes of data per pixel, w is width of one row of data. 
      int offset = 4*((w*round(y))+round(x)); 
      int alpha = data[offset]; 
      if (alpha > 0) { 
       tSet = YES; 
       if (x > vMaxX) { 
        vMaxX = x; 
       } 
       if (x < vMinX) { 
        vMinX = x; 
       } 
       if (y > vMaxY) { 
        vMaxY = y; 
       } 
       if (y < vMinY) { 
        vMinY = y; 
       } 
      } 
     } 
    } 
} 

if (!tSet) { 
    vMaxX = w; 
    vMinX = 0; 
    vMaxY = h; 
    vMinY = 0; 
} 
// When finished, release the context 
CGContextRelease(cgctx); 
// Free image data memory for the context 
if (data) { free(data); } 

CGRect roiRect2 = {{vMinX,vMinY},{vMaxX - vMinX,vMaxY - vMinY}}; 

return roiRect2; 
} 

- (CGContextRef) createARGBBitmapContextFromImage:(CGImageRef) inImage { 

CGContextRef context = NULL; 
CGColorSpaceRef colorSpace; 
void *   bitmapData; 
int    bitmapByteCount; 
int    bitmapBytesPerRow; 

// Get image width, height. We'll use the entire image. 
size_t pixelsWide = CGImageGetWidth(inImage); 
size_t pixelsHigh = CGImageGetHeight(inImage); 

// Declare the number of bytes per row. Each pixel in the bitmap in this 
// example is represented by 4 bytes; 8 bits each of red, green, blue, and 
// alpha. 
bitmapBytesPerRow = (pixelsWide * 4); 
bitmapByteCount  = (bitmapBytesPerRow * pixelsHigh); 

// Use the generic RGB color space. 
//colorSpace = CGColorSpaceCreateWithName(kCGColorSpaceGenericRGB); 

colorSpace = CGColorSpaceCreateDeviceRGB(); 

if (colorSpace == NULL) 
{ 
    fprintf(stderr, "Error allocating color space\n"); 
    return NULL; 
} 

// Allocate memory for image data. This is the destination in memory 
// where any drawing to the bitmap context will be rendered. 
bitmapData = malloc(bitmapByteCount); 
if (bitmapData == NULL) 
{ 
    fprintf (stderr, "Memory not allocated!"); 
    CGColorSpaceRelease(colorSpace); 
    return NULL; 
} 

// Create the bitmap context. We want pre-multiplied ARGB, 8-bits 
// per component. Regardless of what the source image format is 
// (CMYK, Grayscale, and so on) it will be converted over to the format 
// specified here by CGBitmapContextCreate. 
context = CGBitmapContextCreate (bitmapData, pixelsWide, pixelsHigh, 8, bitmapBytesPerRow, colorSpace, kCGImageAlphaPremultipliedFirst); 
if (context == NULL) 
{ 
    free (bitmapData); 
    fprintf (stderr, "Context not created!"); 
} 

// Make sure and release colorspace before returning 
CGColorSpaceRelease(colorSpace); 

return context; 
} 
0

Lese Ich glaube nicht, dass es eine Möglichkeit, dies zu tun, ohne für Pixel der Bildpixel zu untersuchen. Woher kommen die Bilder? Wenn Sie sie steuern, können Sie den Pixel-für-Pixel-Teil zumindest einmal ausführen und dann entweder die Informationen zwischenspeichern oder sie zusammen mit den Bildern verteilen, wenn die Benutzer sie herunterladen.