1/* 2 * Copyright (C) 2005, 2006, 2007 Apple, Inc. All rights reserved. 3 * (C) 2007 Graham Dennis (graham.dennis@gmail.com) 4 * (C) 2007 Eric Seidel <eric@webkit.org> 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of 16 * its contributors may be used to endorse or promote products derived 17 * from this software without specific prior written permission. 18 * 19 * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY 20 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 21 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 22 * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY 23 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 24 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 25 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 26 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 28 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 29 */ 30 31// 32// This file comes from WebKit: 33// WebKit/Tools/DumpRenderTree/mac/DumpRenderTreePasteboard.m 34// It is copied here since that location is the best for pulling into Chromium 35// and has a few includes commented out. darin@chromium.org suggests in the 36// future we see if there is a better place for it to live so it could be 37// shared. 38// 39 40// #import "DumpRenderTreeMac.h" 41#import "DumpRenderTreePasteboard.h" 42 43// #import <WebKit/WebTypesInternal.h> 44 45@interface LocalPasteboard : NSPasteboard 46{ 47 NSMutableArray *typesArray; 48 NSMutableSet *typesSet; 49 NSMutableDictionary *dataByType; 50 NSInteger changeCount; 51} 52@end 53 54static NSMutableDictionary *localPasteboards; 55 56@implementation DumpRenderTreePasteboard 57 58// Return a local pasteboard so we don't disturb the real pasteboards when running tests. 59+ (NSPasteboard *)_pasteboardWithName:(NSString *)name 60{ 61 static int number = 0; 62 if (!name) 63 name = [NSString stringWithFormat:@"LocalPasteboard%d", ++number]; 64 if (!localPasteboards) 65 localPasteboards = [[NSMutableDictionary alloc] init]; 66 LocalPasteboard *pasteboard = [localPasteboards objectForKey:name]; 67 if (pasteboard) 68 return pasteboard; 69 pasteboard = [[LocalPasteboard alloc] init]; 70 [localPasteboards setObject:pasteboard forKey:name]; 71 [pasteboard release]; 72 return pasteboard; 73} 74 75+ (void)releaseLocalPasteboards 76{ 77 [localPasteboards release]; 78 localPasteboards = nil; 79} 80 81// Convenience method for JS so that it doesn't have to try and create a NSArray on the objc side instead 82// of the usual WebScriptObject that is passed around 83- (NSInteger)declareType:(NSString *)type owner:(id)newOwner 84{ 85 return [self declareTypes:[NSArray arrayWithObject:type] owner:newOwner]; 86} 87 88@end 89 90@implementation LocalPasteboard 91 92+ (id)alloc 93{ 94 return NSAllocateObject(self, 0, 0); 95} 96 97- (id)init 98{ 99 typesArray = [[NSMutableArray alloc] init]; 100 typesSet = [[NSMutableSet alloc] init]; 101 dataByType = [[NSMutableDictionary alloc] init]; 102 return self; 103} 104 105- (void)dealloc 106{ 107 [typesArray release]; 108 [typesSet release]; 109 [dataByType release]; 110 [super dealloc]; 111} 112 113- (NSString *)name 114{ 115 return nil; 116} 117 118- (void)releaseGlobally 119{ 120} 121 122- (NSInteger)declareTypes:(NSArray *)newTypes owner:(id)newOwner 123{ 124 [typesArray removeAllObjects]; 125 [typesSet removeAllObjects]; 126 [dataByType removeAllObjects]; 127 return [self addTypes:newTypes owner:newOwner]; 128} 129 130- (NSInteger)addTypes:(NSArray *)newTypes owner:(id)newOwner 131{ 132 unsigned count = [newTypes count]; 133 unsigned i; 134 for (i = 0; i < count; ++i) { 135 NSString *type = [newTypes objectAtIndex:i]; 136 NSString *setType = [typesSet member:type]; 137 if (!setType) { 138 setType = [type copy]; 139 [typesArray addObject:setType]; 140 [typesSet addObject:setType]; 141 [setType release]; 142 } 143 if (newOwner && [newOwner respondsToSelector:@selector(pasteboard:provideDataForType:)]) 144 [newOwner pasteboard:self provideDataForType:setType]; 145 } 146 return ++changeCount; 147} 148 149- (NSInteger)changeCount 150{ 151 return changeCount; 152} 153 154- (NSArray *)types 155{ 156 return typesArray; 157} 158 159- (NSString *)availableTypeFromArray:(NSArray *)types 160{ 161 unsigned count = [types count]; 162 unsigned i; 163 for (i = 0; i < count; ++i) { 164 NSString *type = [types objectAtIndex:i]; 165 NSString *setType = [typesSet member:type]; 166 if (setType) 167 return setType; 168 } 169 return nil; 170} 171 172- (BOOL)setData:(NSData *)data forType:(NSString *)dataType 173{ 174 if (data == nil) 175 data = [NSData data]; 176 if (![typesSet containsObject:dataType]) 177 return NO; 178 [dataByType setObject:data forKey:dataType]; 179 ++changeCount; 180 return YES; 181} 182 183- (NSData *)dataForType:(NSString *)dataType 184{ 185 return [dataByType objectForKey:dataType]; 186} 187 188- (BOOL)setPropertyList:(id)propertyList forType:(NSString *)dataType 189{ 190 CFDataRef data = NULL; 191 if (propertyList) 192 data = CFPropertyListCreateXMLData(NULL, propertyList); 193 BOOL result = [self setData:(NSData *)data forType:dataType]; 194 if (data) 195 CFRelease(data); 196 return result; 197} 198 199- (BOOL)setString:(NSString *)string forType:(NSString *)dataType 200{ 201 CFDataRef data = NULL; 202 if (string) { 203 if ([string length] == 0) 204 data = CFDataCreate(NULL, NULL, 0); 205 else 206 data = CFStringCreateExternalRepresentation(NULL, (CFStringRef)string, kCFStringEncodingUTF8, 0); 207 } 208 BOOL result = [self setData:(NSData *)data forType:dataType]; 209 if (data) 210 CFRelease(data); 211 return result; 212} 213 214@end 215