2011-02-08 6 views
12

Desidero creare un oggetto UIImage da un UIView. La vista NON è opaca. per che sto utilizzando il seguente codice:Problema con la trasparenza durante la conversione di UIView in UIImage

+ (UIImage *) imageWithView:(UIView *)view 
{  
    UIGraphicsBeginImageContextWithOptions(view.bounds.size, view.opaque, [[UIScreen mainScreen] scale]);  
    [view.layer renderInContext:UIGraphicsGetCurrentContext()];  
    UIImage * img = UIGraphicsGetImageFromCurrentImageContext();  UIGraphicsEndImageContext();  
    return img; 
} 

Ma per qualche ragione, invece di sfondo trasparente sto ottenendo un'immagine con sfondo nero. Ho già provato a impostare il parametro "opaco" in UIGraphicsBeginImageContextWithOptions su NO ma senza risultati diversi.

Qualche suggerimento?

(domanda simile CGContext transparency problem con nessuna risposta)

risposta

2

Sono abbastanza sicuro che non è possibile definire una trasparenza durante la creazione di UIImages come questo - si potrebbe mascherare il vostro UIImageView che usa l'immagine però.

Qualcosa come le seguenti funzioni consentono di questo tipo di operazione:

// handles img masking operation 
CGImageRef CopyImageAndAddAlphaChannel(CGImageRef sourceImage) { 
    CGImageRef retVal = NULL; 

    size_t width = CGImageGetWidth(sourceImage); 
    size_t height = CGImageGetHeight(sourceImage); 

    CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); 

    CGContextRef offscreenContext = CGBitmapContextCreate(NULL, width, height, 
                  8, 0, colorSpace, kCGImageAlphaPremultipliedFirst); 

    if (offscreenContext != NULL) { 
     CGContextDrawImage(offscreenContext, CGRectMake(0, 0, width, height), sourceImage); 

     retVal = CGBitmapContextCreateImage(offscreenContext); 
     CGContextRelease(offscreenContext); 
    } 

    CGColorSpaceRelease(colorSpace); 

    return retVal; 
} 
    // png masks can mask png, gif or jpg... 
- (UIImage*)maskImage:(UIImage *)image withMask:(UIImage *)maskImage 
{ 
    CGImageRef maskRef = maskImage.CGImage; 
    CGImageRef mask = CGImageMaskCreate(CGImageGetWidth(maskRef), 
             CGImageGetHeight(maskRef), 
             CGImageGetBitsPerComponent(maskRef), 
             CGImageGetBitsPerPixel(maskRef), 
             CGImageGetBytesPerRow(maskRef), 
             CGImageGetDataProvider(maskRef), NULL, false); 

    CGImageRef sourceImage = [image CGImage]; 
    CGImageRef imageWithAlpha = sourceImage; 
    //add alpha channel for images that don't have one (ie GIF, JPEG, etc...) 
    //this however has a computational cost 
    if ((CGImageGetAlphaInfo(sourceImage) == kCGImageAlphaNone) || (CGImageGetAlphaInfo(sourceImage) == kCGImageAlphaNoneSkipFirst)) 
    { 
     imageWithAlpha = CopyImageAndAddAlphaChannel(sourceImage); 
    } 

    CGImageRef masked = CGImageCreateWithMask(imageWithAlpha, mask); 
    CGImageRelease(mask); 

    //release imageWithAlpha if it was created by CopyImageAndAddAlphaChannel 
    if (sourceImage != imageWithAlpha) 
    { 
     CGImageRelease(imageWithAlpha); 
    } 

    UIImage* retImage = [UIImage imageWithCGImage:masked]; 
    CGImageRelease(masked); 

    return retImage; 
} 

È possibile che chiamare in questo modo:

UIImage *imgMasked = [self maskImage:[UIImage imageNamed:@"full_image.png"] withMask:[UIImage imageNamed:@"masked_image.png"]]; 

masked_image.png deve essere un'immagine incanalata alpha che sarà ritaglia il tuo nero bg.

+0

Potete per favore darmi più in dettaglio che cosa si intende per "mascherare mio punto di vista dell'immagine"? E realizzerà ciò che sto cercando di ottenere? –

+0

l'immagine gif può essere utilizzata come immagine di mascheramento? – Dhruv

+0

@Lemonsanver: CopyImageAndAddAlphaChannel Ho ottenuto questo come simbolo non definito. Per favore dimmi cosa può fare ora – Seeker

0

mi sono imbattuto in questo stesso problema. quello che ha funzionato per me è stato assicurarmi che stavo lavorando con PNG e non con JPG, dal momento che i JPG non supportano il canale alfa. spero che questo funzioni per te

42

A meno che non mi manca qualcosa, credo che si ottiene il risultato desiderato impostando opaco a NO

UIGraphicsBeginImageContextWithOptions(CGSize size, BOOL opaque, CGFloat scale); 


+ (UIImage *) imageWithView:(UIView *)view 
{  
    UIGraphicsBeginImageContextWithOptions(view.bounds.size, NO, [[UIScreen mainScreen] scale]);  
    [view.layer renderInContext:UIGraphicsGetCurrentContext()];  
    UIImage * img = UIGraphicsGetImageFromCurrentImageContext();  UIGraphicsEndImageContext();  
    return img; 
} 
+1

Hai salvato la mia giornata! –

+0

hahaha ottima risposta. non so perché questo non è contrassegnato come la soluzione ma w.e! –

+0

Invece di impostare esplicitamente il parametro opaco su NO, utilizzare invece "view.opaque", a condizione che la vista sia stata definita come non opaca. Ciò consente allo stesso codice di funzionare per visualizzazioni opache e non opache. –

Problemi correlati