Home | History | Annotate | Download | only in mac
      1 /*
      2  * Copyright (C) 2005, 2006, 2007 Apple, Inc.  All rights reserved.
      3  *           (C) 2007 Graham Dennis (graham.dennis (at) gmail.com)
      4  *           (C) 2007 Eric Seidel <eric (at) 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 (at) 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 
     54 static 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