Question

Je suis en train de dessiner un NSImage standard blanc au lieu de noir. Les travaux suivants fins pour dessiner l'image en noir dans le NSGraphicsContext courant:

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

Je pensais NSCompositeXOR faire l'affaire, mais non. Ai-je besoin d'aller sur le complexe [CIFilter filterWithName: @ « CIColorInvert »] chemin? Je sens que je dois manquer quelque chose de simple.

Anders

Était-ce utile?

La solution

La route Core Image serait le plus fiable. Il est en fait pas très compliqué, je l'ai posté un exemple ci-dessous. Si vous connaissez aucun de vos images sera retournée alors vous pouvez supprimer le code de transformation. La principale chose à faire attention est que la conversion de NSImage à CIImage peut être la performance sage cher, donc vous devriez vous assurer de mettre en cache le CIImage si possible et ne recréez pas lors de chaque opération de dessin.

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];

Note: libération / conserver la gestion de la mémoire est laissée en exercice, le code ci-dessus suppose la collecte des ordures

.

Si vous voulez rendre l'image à une taille arbitraire, vous pouvez faire ce qui suit:

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]];

Autres conseils

Juste une remarque: je trouve que le filtre CIColorInvert est pas toujours fiable. Par exemple, si vous voulez inverser de nouveau une image inversée dans Photoshop, le CIFilter produira une image beaucoup plus léger. Pour autant que je compris, cela arrive à cause des différences de valeur gamma de CIFilter (gamma est 1) et des images qui sont venus d'autres sources.

Alors que je cherchais des moyens de changer la valeur gamma pour CIFilter, j'ai trouvé une note qu'il ya un bogue dans CIContext:. Changer la valeur gamma de la valeur par défaut 1 produira des résultats imprévisibles

Peu importe, il y a une autre solution pour inverser NSImage, qui produit toujours des résultats corrects -. En inversant pixels de NSBitmapImageRep

Je reposter le code de 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];
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top