• Open Menu Close Menu
  • Apple
  • Shopping Bag
  • Apple
  • Mac
  • iPad
  • iPhone
  • Watch
  • TV
  • Music
  • Support
  • Search apple.com
  • Shopping Bag

Lists

Open Menu Close Menu
  • Terms and Conditions
  • Lists hosted on this site
  • Email the Postmaster
  • Tips for posting to public mailing lists
Re: I just don't get NSAffineTransform and compositeToPoint:
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: I just don't get NSAffineTransform and compositeToPoint:


  • Subject: Re: I just don't get NSAffineTransform and compositeToPoint:
  • From: Serge Meynard <email@hidden>
  • Date: Sun, 13 Mar 2005 22:59:40 -0500

GOAL: To select a region of an image, crop to a new image (ie just copy that portion). I have started with some good samples from Apple.

With their code I have it selecting and copying the image, the problem is that it creates an image the same size of the original image.

I have tried changing sourceImageRect on line #10 to newImageBounds. And that created an image of the right size, but only contained my selection if I select from the lower left corner.

I tried playing with pathAdjustment on line #16 and that didn't help

I tried using compositeToPoint:fromRect:operation on line #23, but that didn't help.

1: // Returns an autoreleased NSImage, consisting of the selected portion of the reciever's image.
2: // If there's no selection, this method will return the original image.
3: - (NSImage *)croppedImage
4: {
5: NSRect sourceImageRect = [[self cell] rectCoveredByImageInBounds:[self bounds]];
6: NSRect newImageBounds = NSIntersectionRect([selectionMarker selectedRect], sourceImageRect);
7:
8: if (!NSIsEmptyRect(newImageBounds))
9: {
10: NSImage *newImage = [[NSImage alloc] initWithSize:sourceImageRect.size];
11:
12: NSAffineTransform *pathAdjustment = [NSAffineTransform transform];
13:
14: NSBezierPath *croppingPath = [selectionMarker selectedPath];
15:
16: [pathAdjustment translateXBy: -NSMinX(sourceImageRect) yBy: -NSMinY(sourceImageRect)];
17: croppingPath = [pathAdjustment transformBezierPath:[selectionMarker selectedPath]];
18:
19: [newImage lockFocus];
20: [[NSGraphicsContext currentContext] setShouldAntialias:NO];
21: [[NSColor blackColor] set];
22: [croppingPath fill];
23: [[self image] compositeToPoint:NSZeroPoint operation:NSCompositeSourceIn];
24: [newImage unlockFocus];
25:
26: return [newImage autorelease];
27: }
28: return [self image];
29: }


I have read the docs on NSAffineTransform and what I can find on the net. But what it comes down to is I just don't understand it.

1) Is there a good place that explains these? I have spent over two days and I just don't get it.

2) How do I fix the above code.

Thanks,
Jim

I didn't follow the start of this thread, so forgive me if I repeat anything that's been said or tried...
You definitely need to use newImageBounds as the size of the new image (as you point out yourself). As for the rest, I'm doing a bit of guesswork since you don't specify everything in context. But I'm assuming sourceImageRect is the complete rect for the source image, and that [selectionMarker selectedPath] is defined in the same coordinate system as the source image. I'm also assuming that [selectionMarker selectedRect] basically matches with [[selectionMarker selectedPath] bounds]. I think this code should work (barring any brain farts or typos):


NSImage* newImage = [[NSImage alloc] initWithSize: newImageBounds.size];
NSBezierPath* croppingPath = [selectionMarker selectedPath];
[newImage lockFocus];
[[NSGraphicsContext currentContext] saveGraphicsState];
NSAffineTransform* pathAdjustment = [NSAffineTransform transform];
[pathAdjustment translateXBy:-newImageBounds.origin.x yBy:-newImageBounds.origin.y];
[pathAdjustment concat];
[[NSGraphicsContext currentContext] setShouldAntialias:NO];
[[NSColor clearColor] set];
NSRectFill(newImageBounds);
[[NSColor blackColor] set];
[croppingPath fill];
[[self image] compositeToPoint:newImageBounds.origin fromRect:newImageBounds operation:NSCompositeSourceIn];
[[NSGraphicsContext currentContext] restoreGraphicsState];
[newImage unlockFocus];


The pathAdjustment transform lets you modify the coordinate system of the target image so it matches up with the source. You then clear the target to transparent (so that NSCompositeSourceIn will clip to the black fill) and composite the part of the source that you want into the target.
This bit of code is very similar to something I wrote last week for a similar purpose, so it should work OK; if it doesn't, let me know and we can figure out what I typed wrong :) I'm actually not sure if the save/restore is really needed, but it doesn't hurt (much).


Serge

_______________________________________________
Do not post admin requests to the list. They will be ignored.
Cocoa-dev mailing list      (email@hidden)
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden


  • Follow-Ups:
    • Re: I just don't get NSAffineTransform and compositeToPoint:
      • From: James Housley <email@hidden>
References: 
 >I just don't get NSAffineTransform and compositeToPoint: (From: James Housley <email@hidden>)

  • Prev by Date: Re: how to show other application in front of others?
  • Next by Date: Training in Australia?
  • Previous by thread: I just don't get NSAffineTransform and compositeToPoint:
  • Next by thread: Re: I just don't get NSAffineTransform and compositeToPoint:
  • Index(es):
    • Date
    • Thread