2013-04-26 18 views
14

. IL MIO codice: Come gestire il valore RGB per le diverse tonalità di viso e come applicare? questo codice cambierà il colore del viso insieme ai capelli, ma voglio 1. solo faccia da colorare escludendo i capelli.Come cambiare il colore della pelle del viso dall'immagine sorgente in ios?

-(void)changeSkinColorValue:(float)value WithImage:(UIImage*)needToModified 
    { 

     CGContextRef ctx; 

     CGImageRef imageRef = needToModified.CGImage; 
     NSUInteger width = CGImageGetWidth(imageRef); 
     NSUInteger height = CGImageGetHeight(imageRef); 
     CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); 
     //unsigned char *rawData = malloc(firstImageV.image.size.height * firstImageV.image.size.width * 10); 

     CFMutableDataRef m_DataRef = CFDataCreateMutableCopy(0, 0,CGDataProviderCopyData(CGImageGetDataProvider(firstImageV.image.CGImage))); 
     UInt8 *rawData = (UInt8 *) CFDataGetMutableBytePtr(m_DataRef); 
     int length = CFDataGetLength(m_DataRef); 
     NSUInteger bytesPerPixel = 4; 
     NSUInteger bytesPerRow = bytesPerPixel * firstImageV.image.size.width; 
     NSUInteger bitsPerComponent = 8; 

       CGContextRef context1 = CGBitmapContextCreate(rawData, firstImageV.image.size.width, firstImageV.image.size.height, bitsPerComponent, bytesPerRow, colorSpace,      kCGImageAlphaPremultipliedLast | kCGBitmapByteOrder32Big); 
     CGColorSpaceRelease(colorSpace); 

     CGContextDrawImage(context1, CGRectMake(0, 0, firstImageV.image.size.width, firstImageV.image.size.height), imageRef); 

     NSLog(@"%d::%d",width,height); 


     // for(int ii = 0 ; ii < 250 ; ii+=4) 
     //{ 

      for(int ii = 0 ; ii < length ; ii+=4) 
      { 
      //NSLog(@"Raw data %s",rawData); 

      int R = rawData[ii]; 
      int G = rawData[ii+1]; 
      int B = rawData[ii+2]; 

      //  NSLog(@"%d %d %d", R, G, B); 
      //if(((R>60)&&(R<237)) || ((G>10)&&(G<120))||((B>4) && (B<120))) 
       //  if(((R>100)&&(R<186)) || ((G>56)&&(G<130))||((B>30) && (B<120))) 
       //  if(((R>188)&&(R<228)) || ((G>123)&&(G<163))||((B>85) && (B<125))) 
         // if(((R>95)&&(R<260)) || ((G>40)&&(G<210))||((B>20) && (B<170))) 

         //new code...... 

       if(((R>0)&&(R<260)) || ((G>0)&&(G<210))||((B>0) && (B<170))) 

        { 
         rawData[ii+1]=R;//13; 
         rawData[ii+2]=G;//43; 
         rawData[ii+3]=value;//63 
        } 
       } 


     ctx = CGBitmapContextCreate(rawData, 
          CGImageGetWidth(imageRef), 
          CGImageGetHeight(imageRef), 
          8, 
          CGImageGetBytesPerRow(imageRef), 
          CGImageGetColorSpace(imageRef), 
          kCGImageAlphaPremultipliedLast); 

     imageRef = CGBitmapContextCreateImage(ctx); 
     UIImage* rawImage = [UIImage imageWithCGImage:imageRef]; 
     //UIImageView *ty=[[UIImageView alloc]initWithFrame:CGRectMake(100, 200, 400, 400)]; 
     //ty.image=rawImage; 
     //[self.view addSubview:ty]; 
     [secondImageV setImage:rawImage]; 
     CGContextRelease(context1); 
     CGContextRelease(ctx); 
     free(rawData); 
    } 
+0

Questo codice non cambia solo volto e capelli ma tutta l'immagine, non è vero? –

+0

@SAMIR RATHOD puoi aiutarmi nella stessa domanda di cambio del colore dell'immagine? http://stackoverflow.com/questions/37113740/change-face-color-from-main-color-in-xcode?noredirect=1#comment61769372_37113740 –

risposta

0

La risposta più immediata è quella di cambiare le sale operatorie:

  if(((R>0)&&(R<260)) || ((G>0)&&(G<210)) || ((B>0) && (B<170))) 

a AND:

  if(((R>0)&&(R<260)) && ((G>0)&&(G<210)) && ((B>0) && (B<170))) 

quindi regolare la vostra RGB gamme per approssimare la gamma di tonalità della pelle nell'immagine (provate con alcuni cursori nella tua interfaccia utente).

A proposito, presumo si sa che questo:

 rawData[ii+1]=R;//13; 
     rawData[ii+2]=G;//43; 
     rawData[ii+3]=value;//63 

sta assegnando il canale rosso per il canale verde, il canale verde per il canale blu, e value al canale alfa. Non mi aspetto che sia quello che vuoi.

Anche l'immagine needToModified è probabilmente intesa come la stessa immagine di firstImageV.image, che non si riflette nel codice come è ora.

Questo approccio funzionerà solo se le gamme cromatiche identificate sono interamente e solo presenti nelle regioni della carne dell'immagine.

Una lunga risposta poteva guardare più sofisticata selezione di gamme di colori, modi alternativi di selezione delle regioni di immagine, l'uso di CIFilter o quadro OpenCV ...

+0

Dopo aver applicato l'operatore AND, lascerà alcuni pixel dell'immagine e del colore tutti i image.Voglio cambiare solo il colore della pelle. – madhyamika

+1

"Questo approccio funzionerà solo se le gamme cromatiche identificate sono interamente e solo presenti nelle regioni della carne dell'immagine." ... questo è un approccio molto approssimativo per selezionare la regione di interesse. Hai davvero bisogno di qualcosa come lo strumento bacchetta magica di Photoshop per selezionare aree simili adiacenti di un'immagine e alcuni input/UI utente interattivi. Ti suggerisco di investigare [openCV] (http://openCV.org) ... – foundry

0

Prova Mascherare l'immagine ... lo farà aiutare a cambiare la gamma specifica di colori definiti in maschera

Codice:

- (UIImage *)doctorTheImage:(UIImage *)originalImage 
{ 

    const float brownsMask[6] = {85, 255, 85, 255, 85, 255}; 


    UIImageView *imageView = [[UIImageView alloc] initWithImage:originalImage]; 

    UIGraphicsBeginImageContext(originalImage.size); 
    CGContextRef context = UIGraphicsGetCurrentContext(); 

    CGContextSetRGBFillColor (context, 1.0,1.0, 1.0, 1); 


    CGContextFillRect(context, CGRectMake(0, 0, imageView.image.size.width, imageView.image.size.height)); 

    CGImageRef brownRef = CGImageCreateWithMaskingColors(imageView.image.CGImage, brownsMask); 

    CGRect imageRect = CGRectMake(0, 0, imageView.image.size.width, imageView.image.size.height); 

    CGContextTranslateCTM(context, 0, imageView.image.size.height); 
    CGContextScaleCTM(context, 1.0, -1.0); 
    //CGImageRef whiteRef = CGImageCreateWithMaskingColors(brownRef, whiteMask); 
    CGContextDrawImage (context, imageRect, brownRef); 

    //[originalImage drawInRect:CGRectMake(0, 0, imageView.image.size.width, imageView.image.size.height)]; 

    CGImageRelease(brownRef); 
    // CGImageRelease(whiteRef); 

    UIImage *doctoredImage = UIGraphicsGetImageFromCurrentImageContext(); 
    UIGraphicsEndImageContext(); 

    return doctoredImage; 
} 
0

CFDataGetBytePtr Secondo la documentazione, restituisce un puntatore di sola lettura per i byte di un oggetto CFData., Sei sicuro che non stai cercando CFDataGetBytes che copia il contenuto di byte di un oggetto CFData ad un buffer esterno. Nel qual caso dovrai allocare il tuo buffer per contenere width * height * bpp. Una volta che hai questa copia, puoi manipolarla comunque vuoi creare la nuova immagine.

Selezione pixel In base alla tua domanda, mi sembra di capire che vuoi cambiare il colore della pelle dal bianco al nero. Il tuo codice corrente itera su ogni pixel per cambiarne il colore.Dovresti valutare la "distanza" tra il colore del pixel e quello che stai cercando, e se è al di sotto di una certa soglia lo processa. Potrebbe essere più semplice eseguire l'operazione in HSV piuttosto che trattare con i colori RGB

0

1) Ottenere un CGPath di faccia in cui si desidera applicare l'algoritmo. 2) Ottieni larghezza di CGimage.

int width = CGImageGetWidth(image); 

3) Ottieni pixel CGPoint del pixel attualmente in elaborazione. Verifica la condizione prima di applicare l'algoritmo. E poi applica la tua condizione. Questo è tutto. Ecco la porzione di codice del campione.

CGFloat pointY = (int)(i/4)/(int)width; 
CGFloat pointX = (int)(i/4)%(int)width; 
CGPoint point = CGPointMake(pointX, pointY); 

if (CGPathContainsPoint(yourFacePath, NULL, point, NO)) 
{ 
    if(((R>0)&&(R<260)) || ((G>0)&&(G<210))||((B>0) && (B<170))) 
    { 
     rawData[ii+1]=R;//13; 
     rawData[ii+2]=G;//43; 
     rawData[ii+3]=value;//63 
    } 
} 
0

rendere il viso e i capelli come oggetti. l'oggetto ha un colore e ha un metodo globale per cambiare i loro colori. quindi nel tuo principale, crea entrambi gli oggetti (capelli, faccia) e specifica ciò che vuoi colorare esattamente. Questo è l'approccio giusto. spero che sia d'aiuto!