Domanda

Sto cercando di disegnare uno standard NSImage in bianco invece che nero. I seguenti funziona bene per disegnare l'immagine in nero nel NSGraphicsContext corrente:

NSImage* image = [NSImage imageNamed:NSImageNameEnterFullScreenTemplate];
[image drawInRect:r fromRect:NSZeroRect operation:NSCompositeSourceOver fraction:1.0];

Mi aspettavo NSCompositeXOR per fare il trucco, ma no. Ho bisogno di andare giù per la complicata [CIFilter filterWithName: @ "CIColorInvert"] percorso? Mi sento come Devo mancare qualcosa di semplice.

Anders

È stato utile?

Soluzione

Il percorso Core Image sarebbe il più affidabile. In realtà non è molto complicato, ho postato un esempio riportato di seguito. Se si conosce nessuna delle tue immagini verrà capovolto allora si può rimuovere il codice trasformare. La cosa principale da fare attenzione è che la conversione da NSImage a CIImage può essere costoso prestazioni-saggio, così si dovrebbe essere sicuri di memorizzare nella cache il CIImage se possibile, e non ricrearlo durante ogni operazione di disegno.

CIImage* ciImage = [[CIImage alloc] initWithData:[yourImage TIFFRepresentation]];
if ([yourImage isFlipped])
{
    CGRect cgRect    = [ciImage extent];
    CGAffineTransform transform;
    transform = CGAffineTransformMakeTranslation(0.0,cgRect.size.height);
    transform = CGAffineTransformScale(transform, 1.0, -1.0);
    ciImage   = [ciImage imageByApplyingTransform:transform];
}
CIFilter* filter = [CIFilter filterWithName:@"CIColorInvert"];
[filter setDefaults];
[filter setValue:ciImage forKey:@"inputImage"];
CIImage* output = [filter valueForKey:@"outputImage"];
[output drawAtPoint:NSZeroPoint fromRect:NSRectFromCGRect([output extent]) operation:NSCompositeSourceOver fraction:1.0];

Nota: rilascio / conservare gestione della memoria viene lasciata come esercizio, il codice precedente presuppone garbage collection

.

Se si vuole rendere l'immagine ad una dimensione arbitraria, si potrebbe procedere come segue:

NSSize imageSize = NSMakeSize(1024,768); //or whatever size you want
[yourImage setSize:imageSize];
[yourImage lockFocus];
NSBitmapImageRep* bitmap = [[NSBitmapImageRep alloc] initWithFocusedViewRect:NSMakeRect(0, 0, imageSize.width, imageSize.height)];
[yourImage unlockFocus];
CIImage* image = [CIImage imageWithData:[bitmap TIFFRepresentation]];

Altri suggerimenti

Solo una nota: ho trovato che il filtro CIColorInvert non è sempre affidabile. Ad esempio, se si vuole invertire di nuovo un'immagine invertita in Photoshop, il CIFilter produrrà un'immagine molto più leggero. Per quanto ho capito, succede a causa delle differenze di valore gamma di CIFilter (gamma è 1) e le immagini fornite da altre fonti.

Mentre ero alla ricerca di modi per cambiare il valore gamma per CIFilter, ho trovato una nota che c'è un bug in CIContext:. Cambiando il suo valore gamma dal default 1 produrrà risultati imprevedibili

Indipendentemente, c'è un'altra soluzione invertire NSImage, che produce sempre i risultati corretti -. Invertendo pixel di NSBitmapImageRep

Sono reinserire il codice etutorials.org ( http://bit.ly/Y6GpLn ):

// srcImageRep is the NSBitmapImageRep of the source image
int n = [srcImageRep bitsPerPixel] / 8;           // Bytes per pixel
int w = [srcImageRep pixelsWide];
int h = [srcImageRep pixelsHigh];
int rowBytes = [srcImageRep bytesPerRow];
int i;

NSImage *destImage = [[NSImage alloc] initWithSize:NSMakeSize(w, h)];
NSBitmapImageRep *destImageRep = [[[NSBitmapImageRep alloc] 
      initWithBitmapDataPlanes:NULL
          pixelsWide:w
          pixelsHigh:h
          bitsPerSample:8
          samplesPerPixel:n
          hasAlpha:[srcImageRep hasAlpha] 
          isPlanar:NO
          colorSpaceName:[srcImageRep colorSpaceName]
          bytesPerRow:rowBytes 
          bitsPerPixel:NULL] autorelease];

unsigned char *srcData = [srcImageRep bitmapData];
unsigned char *destData = [destImageRep bitmapData];

for ( i = 0; i < rowBytes * h; i++ )
    *(destData + i) = 255 - *(srcData + i);

[destImage addRepresentation:destImageRep];
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top