jens@0: // jens@0: // GraphicsUtils.m jens@0: // MYUtilities jens@0: // jens@0: // Copyright 2008 Jens Alfke. All rights reserved. jens@0: // jens@0: jens@0: #import "GraphicsUtils.h" jens@0: jens@0: jens@0: @implementation NSImage (MYUtilities) jens@0: jens@0: jens@0: - (NSSize) my_sizeOfLargestRep jens@0: { jens@0: NSArray *reps = [self representations]; jens@0: NSSize max = {0,0}; jens@0: int i; jens@0: for( i=[reps count]-1; i>=0; i-- ) { jens@0: NSImageRep *rep = [reps objectAtIndex: i]; jens@0: NSSize size = [rep size]; jens@0: if( size.width > max.width || size.height > max.height ) { jens@0: max = size; jens@0: } jens@0: } jens@0: return max; jens@0: } jens@0: jens@0: jens@0: - (NSImage*) my_shrunkToFitIn: (NSSize) maxSize jens@0: { jens@0: NSSize size = self.size; jens@0: float scale = MIN( size.width/maxSize.width, size.height/maxSize.height ); jens@0: if( scale >= 1.0 ) jens@0: return self; jens@0: jens@0: NSSize newSize = {roundf(size.width*scale), roundf(size.height*scale)}; jens@0: NSImage *newImage = [[NSImage alloc] initWithSize: newSize]; jens@0: [newImage lockFocus]; jens@0: NSGraphicsContext *context = [NSGraphicsContext currentContext]; jens@0: [context saveGraphicsState]; jens@0: [context setImageInterpolation: NSImageInterpolationHigh]; jens@0: [self drawInRect: NSMakeRect(0,0,newSize.width,newSize.height) jens@0: fromRect: NSMakeRect(0,0,size.width,size.height) jens@0: operation: NSCompositeCopy fraction: 1.0f]; jens@0: [context restoreGraphicsState]; jens@0: [newImage unlockFocus]; jens@0: return [newImage autorelease]; jens@0: } jens@0: jens@0: jens@0: - (NSData*) my_JPEGData jens@0: { jens@0: NSImage *tiffImage = [[NSImage alloc] initWithData:[self TIFFRepresentation]]; jens@0: NSBitmapImageRep *rep = [[tiffImage representations] objectAtIndex:0]; jens@0: NSDictionary *props = [NSDictionary dictionaryWithObjectsAndKeys: jens@0: [NSNumber numberWithFloat: 0.75f], NSImageCompressionFactor, nil]; jens@0: NSData *jpeg = [rep representationUsingType: NSJPEGFileType properties: props]; jens@0: [tiffImage release]; jens@0: return jpeg; jens@0: } jens@0: jens@0: jens@0: #if 0 jens@0: jens@0: // Adapted from Apple's CocoaCreateMovie sample jens@0: // jens@0: static void CopyNSImageRepToGWorld(NSBitmapImageRep *imageRepresentation, GWorldPtr gWorldPtr) jens@0: { jens@0: PixMapHandle pixMapHandle; jens@0: unsigned char* pixBaseAddr; jens@0: jens@0: // Lock the pixels jens@0: pixMapHandle = GetGWorldPixMap(gWorldPtr); jens@0: LockPixels (pixMapHandle); jens@0: pixBaseAddr = (unsigned char*) GetPixBaseAddr(pixMapHandle); jens@0: jens@0: const unsigned char* bitMapDataPtr = [imageRepresentation bitmapData]; jens@0: jens@0: if ((bitMapDataPtr != nil) && (pixBaseAddr != nil)) jens@0: { jens@0: int i,j; jens@0: int pixmapRowBytes = GetPixRowBytes(pixMapHandle); jens@0: NSSize imageSize = [imageRepresentation size]; jens@0: for (i=0; i< imageSize.height; i++) jens@0: { jens@0: const unsigned char *src = bitMapDataPtr + i * [imageRepresentation bytesPerRow]; jens@0: unsigned char *dst = pixBaseAddr + i * pixmapRowBytes; jens@0: for (j = 0; j < imageSize.width; j++) jens@0: { jens@0: *dst++ = 0; // X - our src is 24-bit only jens@0: *dst++ = *src++; // Red component jens@0: *dst++ = *src++; // Green component jens@0: *dst++ = *src++; // Blue component jens@0: } jens@0: } jens@0: } jens@0: UnlockPixels(pixMapHandle); jens@0: } jens@0: jens@0: jens@0: - (NSData*) my_PICTData jens@0: { jens@0: // Locate the bitmap image rep: jens@0: NSBitmapImageRep *rep; jens@0: NSEnumerator *e = [[self representations] objectEnumerator]; jens@0: while( (rep=[e nextObject]) != nil ) { jens@0: if( [rep isKindOfClass: [NSBitmapImageRep class]] ) jens@0: break; jens@0: } jens@0: if( ! rep ) { jens@0: Warn(@"No bitmap image rep in image"); jens@0: return nil; jens@0: } jens@0: jens@0: // Copy the image data into a GWorld: jens@0: Rect bounds; jens@0: SetRect(&bounds, 0,0,[rep pixelsWide],[rep pixelsHigh]); jens@0: GWorldPtr gworld; jens@0: OSStatus err = NewGWorld(&gworld, 32, &bounds, NULL, NULL, 0); jens@0: if( err ) { jens@0: Warn(@"NewGWorld failed with err %i",err); jens@0: return nil; jens@0: } jens@0: CopyNSImageRepToGWorld(rep,gworld); jens@0: jens@0: // Draw the GWorld into a PicHandle: jens@0: CGrafPtr oldPort; jens@0: GDHandle oldDevice; jens@0: GetGWorld(&oldPort,&oldDevice); jens@0: SetGWorld(gworld,NULL); jens@0: ClipRect(&bounds); jens@0: PicHandle pic = OpenPicture(&bounds); jens@0: CopyBits(GetPortBitMapForCopyBits(gworld), jens@0: GetPortBitMapForCopyBits(gworld), jens@0: &bounds,&bounds,srcCopy,NULL); jens@0: ClosePicture(); jens@0: err = QDError(); jens@0: SetGWorld(oldPort,oldDevice); jens@0: DisposeGWorld(gworld); jens@0: jens@0: if( err ) { jens@0: Warn(@"Couldn't convert to PICT: error %i",err); jens@0: return nil; jens@0: } jens@0: jens@0: // Copy the PicHandle into an NSData: jens@0: HLock((Handle)pic); jens@0: //Test to put PICT on clipboard: jens@0: /*ScrapRef scrap; jens@0: GetCurrentScrap(&scrap); jens@0: ClearScrap(&scrap); jens@0: PutScrapFlavor(scrap,'PICT',0,GetHandleSize((Handle)pic),*pic);*/ jens@0: NSData *data = [NSData dataWithBytes: *pic length: GetHandleSize((Handle)pic)]; jens@0: DisposeHandle((Handle)pic); jens@0: Log(@"Converted image to %i bytes of PICT data",[data length]); jens@0: return data; jens@0: } jens@0: #endif jens@0: jens@0: jens@0: @end jens@0: jens@0: jens@0: jens@0: jens@0: @implementation NSBezierPath (MYUtilities) jens@0: jens@0: + (NSBezierPath*) my_bezierPathWithRoundRect: (NSRect)rect radius: (float)radius jens@0: { jens@0: radius = MIN(radius, floorf(rect.size.width/2)); jens@0: float x0 = NSMinX(rect), y0 = NSMinY(rect), jens@0: x1 = NSMaxX(rect), y1 = NSMaxY(rect); jens@0: NSBezierPath *path = [NSBezierPath bezierPath]; jens@0: jens@0: [path moveToPoint: NSMakePoint(x0+radius,y0)]; jens@0: jens@0: [path appendBezierPathWithArcFromPoint: NSMakePoint(x1,y0) jens@0: toPoint: NSMakePoint(x1,y1) radius: radius]; jens@0: [path appendBezierPathWithArcFromPoint: NSMakePoint(x1,y1) jens@0: toPoint: NSMakePoint(x0,y1) radius: radius]; jens@0: [path appendBezierPathWithArcFromPoint: NSMakePoint(x0,y1) jens@0: toPoint: NSMakePoint(x0,y0) radius: radius]; jens@0: [path appendBezierPathWithArcFromPoint: NSMakePoint(x0,y0) jens@0: toPoint: NSMakePoint(x1,y0) radius: radius]; jens@0: [path closePath]; jens@0: return path; jens@0: } jens@0: jens@0: @end