/* IKCompositor.m IconKit compositor core class which implements compositing facilities with NSImage class Copyright (C) 2004 Nicolas Roard Quentin Mathe Author: Nicolas Roard Quentin Mathe Date: August 2004 This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ #import "IKCompositor.h" @implementation IKCompositor - (void) dealloc { RELEASE(operations); [super dealloc]; } - (id) initWithSize: (NSSize)size { if ((self = [super init]) != nil) { operations = [[NSMutableArray alloc] init]; originalSize = size; compositingSize = originalSize; return self; } return nil; } - (id) initWithImage: (NSImage *)image { if (image == nil) { RELEASE(self); // May be we should raise an exception } else { if ((self = [self initWithSize: [image size]]) != nil) { IKCompositorOperation* initialOperation = [[IKCompositorOperation alloc] initWithImage: image position: IKCompositedImagePositionCenter operation: NSCompositeSourceOver alpha: 1.0]; [operations addObject: initialOperation]; RELEASE(initialOperation); return self; } } return nil; } - (id) initWithPropertyList: (NSDictionary *)propertyList { NSNumber* number = nil; NSDictionary* dict = nil; NSArray *array = nil; NSSize size; if (propertyList == nil) { RELEASE(self); return nil; // May be we should raise an exception } dict = [propertyList objectForKey: @"originalSize"]; if (dict != nil) { float width, height; number = [dict objectForKey: @"width"]; if (number != nil) width = [number floatValue]; number = [dict objectForKey: @"height"]; if (number != nil) height = [number floatValue]; size = NSMakeSize (width, height); } if ((self = [self initWithSize: size]) != nil) { dict = [propertyList objectForKey: @"compositingSize"]; if (dict != nil) { float width, height; number = [dict objectForKey: @"width"]; if (number != nil) width = [number floatValue]; number = [dict objectForKey: @"height"]; if (number != nil) height = [number floatValue]; compositingSize = NSMakeSize (width, height); } array = [propertyList objectForKey: @"operations"]; if (array != nil) { int i; for (i = 0; i< [array count]; i++) { NSDictionary* item = [array objectAtIndex: i]; IKCompositorOperation* op = [[IKCompositorOperation alloc] initWithPropertyList: item]; [operations addObject: op]; RELEASE(op); } } return self; } return nil; } - (NSSize) size { return originalSize; } - (NSSize) compositingSize { return compositingSize; } - (void) setCompositingSize: (NSSize)size { compositingSize = size; } - (void) compositeImage: (NSImage *)source withPosition: (IKCompositedImagePosition) position { [self compositeImage: source withPosition: position operation: NSCompositeSourceOver alpha: 1.0]; } - (void) compositeImage: (NSImage *)source inRect:(NSRect)rect { [self compositeImage: source inRect: rect operation: NSCompositeSourceOver alpha: 1.0]; } - (void) compositeImage: (NSImage *)source withPosition: (IKCompositedImagePosition)position operation: (NSCompositingOperation)operation alpha: (float)a { IKCompositorOperation* op = [[IKCompositorOperation alloc] initWithImage: source position: position operation: operation alpha: a]; [operations addObject: op]; RELEASE(op); } - (void) compositeImage: (NSImage *)source inRect: (NSRect)rect operation: (NSCompositingOperation)operation alpha: (float)a { IKCompositorOperation* op = [[IKCompositorOperation alloc] initWithImage: source rect: rect operation: operation alpha: a]; [operations addObject: op]; RELEASE(op); } - (NSImage *) render { int i; NSImage* image = [[NSImage alloc] initWithSize: originalSize]; NSBitmapImageRep* rep; [image lockFocus]; for (i = 0; i < [operations count]; i++) { IKCompositorOperation* op = [operations objectAtIndex: i]; NSImage* compositedImage = [op image]; [compositedImage setScalesWhenResized: YES]; [compositedImage setSize: [op rect].size]; [compositedImage compositeToPoint: [op rect].origin operation: [op operation]]; } rep = [[NSBitmapImageRep alloc] initWithFocusedViewRect: NSMakeRect (0,0,compositingSize.width, compositingSize.height)]; [image unlockFocus]; [image addRepresentation: rep]; RELEASE(rep); return AUTORELEASE(image); } - (NSDictionary *) propertyList { NSMutableDictionary* dictionary = [[NSMutableDictionary alloc] init]; NSMutableDictionary* dictOriginalSize = [[NSMutableDictionary alloc] init]; NSMutableDictionary* dictCompositingSize = [[NSMutableDictionary alloc] init]; NSMutableArray* arrayOperations = [[NSMutableArray alloc] init]; int i; [dictOriginalSize setObject: [NSNumber numberWithFloat: originalSize.width] forKey: @"width"]; [dictOriginalSize setObject: [NSNumber numberWithFloat: originalSize.height] forKey: @"height"]; [dictionary setObject: dictOriginalSize forKey: @"originalSize"]; RELEASE(dictOriginalSize); [dictCompositingSize setObject: [NSNumber numberWithFloat: compositingSize.width] forKey: @"width"]; [dictCompositingSize setObject: [NSNumber numberWithFloat: compositingSize.height] forKey: @"height"]; [dictionary setObject: dictCompositingSize forKey: @"compositingSize"]; RELEASE(dictCompositingSize); for (i = 0; i < [operations count]; i++) { IKCompositorOperation* item = [operations objectAtIndex: i]; [arrayOperations addObject: [item propertyList]]; } [dictionary setObject: arrayOperations forKey: @"operations"]; RELEASE(arrayOperations); return AUTORELEASE(dictionary); } @end