2 // WebNSPasteboardExtras.m
5 // Created by John Sullivan on Thu Sep 19 2002.
6 // Copyright (c) 2002 Apple Computer, Inc. All rights reserved.
9 #import <WebKit/WebNSPasteboardExtras.h>
11 #import <WebKit/WebArchive.h>
12 #import <WebKit/WebAssertions.h>
13 #import <WebKit/WebImageRenderer.h>
14 #import <WebKit/WebImageRendererFactory.h>
15 #import <WebKit/WebNSURLExtras.h>
16 #import <WebKit/WebResourcePrivate.h>
17 #import <WebKit/WebURLsWithTitles.h>
18 #import <WebKit/WebViewPrivate.h>
20 #import <Foundation/NSString_NSURLExtras.h>
21 #import <Foundation/NSURL_NSURLExtras.h>
22 #import <Foundation/NSURLFileTypeMappings.h>
24 #import <HIServices/CoreTranslationFlavorTypeNames.h>
26 NSString *WebURLPboardType = nil;
27 NSString *WebURLNamePboardType = nil;
29 @interface NSFilePromiseDragSource : NSObject
30 - initWithSource:(id)draggingSource;
31 - (void)setTypes:(NSArray *)types onPasteboard:(NSPasteboard *)pboard;
34 @implementation NSPasteboard (WebExtras)
38 // FIXME The code below addresses 3446192. However we can't enable until 3446669 has been fixed.
40 CFStringRef osTypeString = UTCreateStringForOSType('url ');
41 CFStringRef utiTypeString = UTTypeCreatePreferredIdentifierForTag( kUTTagClassOSType, osTypeString, NULL );
42 WebURLPboardType = (NSString *)UTTypeCopyPreferredTagWithClass( kUTTagClassNSPboardType, utiTypeString );
44 osTypeString = UTCreateStringForOSType('urln');
45 utiTypeString = UTTypeCreatePreferredIdentifierForTag( kUTTagClassOSType, osTypeString, NULL );
46 WebURLNamePboardType = (NSString *)UTTypeCopyPreferredTagWithClass( kUTTagClassNSPboardType, utiTypeString );
48 CreatePasteboardFlavorTypeName('url ', (CFStringRef*)&WebURLPboardType);
49 CreatePasteboardFlavorTypeName('urln', (CFStringRef*)&WebURLNamePboardType);
53 + (NSArray *)_web_writableTypesForURL
55 static NSArray *types = nil;
57 types = [[NSArray alloc] initWithObjects:
58 WebURLsWithTitlesPboardType,
68 static NSArray *_writableTypesForImageWithoutArchive (void)
70 static NSMutableArray *types = nil;
72 types = [[NSMutableArray alloc] initWithObjects:NSTIFFPboardType, nil];
73 [types addObjectsFromArray:[NSPasteboard _web_writableTypesForURL]];
78 static NSArray *_writableTypesForImageWithArchive (void)
80 static NSMutableArray *types = nil;
82 types = [_writableTypesForImageWithoutArchive() mutableCopy];
83 [types addObject:NSRTFDPboardType];
84 [types addObject:WebArchivePboardType];
89 + (NSArray *)_web_writableTypesForImageIncludingArchive:(BOOL)hasArchive
92 ? _writableTypesForImageWithArchive()
93 : _writableTypesForImageWithoutArchive();
96 + (NSArray *)_web_dragTypesForURL
98 return [NSArray arrayWithObjects:
99 WebURLsWithTitlesPboardType,
102 WebURLNamePboardType,
104 NSFilenamesPboardType,
108 - (NSURL *)_web_bestURL
110 NSArray *types = [self types];
112 if ([types containsObject:NSURLPboardType]) {
113 NSURL *URLFromPasteboard = [NSURL URLFromPasteboard:self];
114 NSString *scheme = [URLFromPasteboard scheme];
115 if ([scheme isEqualToString:@"http"] || [scheme isEqualToString:@"https"]) {
116 return [URLFromPasteboard _webkit_canonicalize];
120 if ([types containsObject:NSStringPboardType]) {
121 NSString *URLString = [self stringForType:NSStringPboardType];
122 if ([URLString _web_looksLikeAbsoluteURL]) {
123 NSURL *URL = [[NSURL _web_URLWithUserTypedString:URLString] _webkit_canonicalize];
130 if ([types containsObject:NSFilenamesPboardType]) {
131 NSArray *files = [self propertyListForType:NSFilenamesPboardType];
132 if ([files count] == 1) {
133 NSString *file = [files objectAtIndex:0];
135 if([[NSFileManager defaultManager] fileExistsAtPath:file isDirectory:&isDirectory] && !isDirectory){
136 if ([WebView canShowFile:file]) {
137 return [[NSURL fileURLWithPath:file] _webkit_canonicalize];
146 - (void)_web_writeURL:(NSURL *)URL andTitle:(NSString *)title types:(NSArray *)types
150 if ([title length] == 0) {
151 title = [[URL path] lastPathComponent];
152 if ([title length] == 0) {
153 title = [URL _web_userVisibleString];
157 if ([types containsObject:NSURLPboardType]) {
158 [URL writeToPasteboard:self];
160 if ([types containsObject:WebURLPboardType]) {
161 [self setString:[URL _web_userVisibleString] forType:WebURLPboardType];
163 if ([types containsObject:WebURLNamePboardType]) {
164 [self setString:title forType:WebURLNamePboardType];
166 if ([types containsObject:NSStringPboardType]) {
167 [self setString:[URL _web_userVisibleString] forType:NSStringPboardType];
169 if ([types containsObject:WebURLsWithTitlesPboardType]) {
170 [WebURLsWithTitles writeURLs:[NSArray arrayWithObject:URL] andTitles:[NSArray arrayWithObject:title] toPasteboard:self];
174 + (int)_web_setFindPasteboardString:(NSString *)string withOwner:(id)owner
176 NSPasteboard *findPasteboard = [NSPasteboard pasteboardWithName:NSFindPboard];
177 [findPasteboard declareTypes:[NSArray arrayWithObject:NSStringPboardType] owner:owner];
178 [findPasteboard setString:string forType:NSStringPboardType];
179 return [findPasteboard changeCount];
182 - (void)_web_writeFileWrapperAsRTFDAttachment:(NSFileWrapper *)wrapper
184 NSTextAttachment *attachment = [[NSTextAttachment alloc] initWithFileWrapper:wrapper];
186 NSAttributedString *string = [NSAttributedString attributedStringWithAttachment:attachment];
187 [attachment release];
189 NSData *RTFDData = [string RTFDFromRange:NSMakeRange(0, [string length]) documentAttributes:nil];
190 [self setData:RTFDData forType:NSRTFDPboardType];
193 - (void)_web_writeImage:(WebImageRenderer *)image
195 title:(NSString *)title
196 archive:(WebArchive *)archive
197 types:(NSArray *)types
202 [self _web_writeURL:URL andTitle:title types:types];
204 if ([types containsObject:NSTIFFPboardType]) {
205 [self setData:[image TIFFRepresentation] forType:NSTIFFPboardType];
209 if ([types containsObject:NSRTFDPboardType]) {
210 // This image data is either the only subresource of an archive (HTML image case)
211 // or the main resource (standalone image case).
212 NSArray *subresources = [archive subresources];
213 WebResource *resource = [subresources count] > 0 ? [subresources objectAtIndex:0] : [archive mainResource];
214 ASSERT(resource != nil);
216 ASSERT([[[WebImageRendererFactory sharedFactory] supportedMIMETypes] containsObject:[resource MIMEType]]);
217 [self _web_writeFileWrapperAsRTFDAttachment:[resource _fileWrapperRepresentation]];
219 if ([types containsObject:WebArchivePboardType]) {
220 [self setData:[archive data] forType:WebArchivePboardType];
223 // We should not have declared types that we aren't going to write (4031826).
224 ASSERT(![types containsObject:NSRTFDPboardType]);
225 ASSERT(![types containsObject:WebArchivePboardType]);
229 - (id)_web_declareAndWriteDragImage:(WebImageRenderer *)image
231 title:(NSString *)title
232 archive:(WebArchive *)archive
235 ASSERT(self == [NSPasteboard pasteboardWithName:NSDragPboard]);
236 NSMutableArray *types = [[NSMutableArray alloc] initWithObjects:NSFilesPromisePboardType, nil];
237 [types addObjectsFromArray:[NSPasteboard _web_writableTypesForImageIncludingArchive:(archive != nil)]];
238 [self declareTypes:types owner:source];
239 [self _web_writeImage:image URL:URL title:title archive:archive types:types];
242 NSString *extension = [[NSURLFileTypeMappings sharedMappings] preferredExtensionForMIMEType:[image MIMEType]];
243 if (extension == nil) {
246 NSArray *extensions = [NSArray arrayWithObject:extension];
248 #ifdef OMIT_TIGER_FEATURES
249 id dragSource = [[NSFilePromiseDragSource alloc] initWithSource:source];
250 [dragSource setTypes:extensions onPasteboard:self];
253 [self setPropertyList:extensions forType:NSFilesPromisePboardType];