UIPasteboard的使用

最近看了苹果的UIPasteboard文档,看完之后写个blog记录下。

有些术语还是会用英文,翻译太烂失去原有的感觉。


UIPasteboard主要用途:

让app可以和其他app共享数据

1. 使用全系统范围粘贴板(system-wide pasteboards),可以和任意app共享数据

2. 使用app特定粘贴板(app-specific pasteboards),可以和相同team ID的app共享数据

一个粘贴板就是一个可用于分享数据的有名字标识内存区域。

系统粘贴板

有两种:全局粘贴板(the General pasteboard),查找粘贴板(the Find pasteboard)。其中查找粘贴板经验证无效,可以当它不存在了,文档写的挺好,可惜获取不到数据,服!

一个粘贴板必须有一个唯一的名字标识。粘贴板有个属性persistent,设置为YES,粘贴板会app终结和系统重启之后持续存在。系统粘贴板persistent默认是YES,app特定粘贴板默认是NO。

粘贴板的存储是以item的方式,一个item是一个或多个键值对。举个栗子:

UIPasteboard *pb = [UIPasteboard generalPasteboard];
pb.string = @"hello";

NSLog(@"%@", pb.items);
NSLog(@"%@", pb.string);
输出:

(
        {
        "public.utf8-plain-text" = hello;
    }
)
hello

为什么这里这接使用pb.string,因为发现这个属性太方便了,常用的类型不用再繁琐,目前这种属性提供以下几种:string,URL,image,color,以及对应的数组strings,URLs,images,colors。我觉得简单的数据共享用这种足够了。

存储和读取

1. pasteboard type

一般用来存储/读取的数据类型pasteboard type是“Uniform Type Identifier (UTI) ”,这个东西是苹果为了统一文件/数据等类型而定义的。一个UTI用来唯一标识一种类型。比较难理解,可以举个栗子:

一个文本文件,后缀可能是:txt、text等。另外一个应用可以打开.txt文件可能也能打开.html文件。一个应用检测所有可以读取的文件类型是不可能的,用户体验就变得很糟糕,用户不理解为什么app可以打开一个文本却不能打开另外一个。所以苹果为了解决这个问题就定义了UTI。翻译的少了好多意味,有兴趣直接去看原文Uniform Type Identifiers Overview

不喜欢这个东西,感觉苹果这块做的不好。要在程序中使用UTI,可以直接查找对应的列表找到合适的字符串直接使用,但是,这种方式我是不能接受的,理由不谈了。后来发现是有对应的常量,定义在UTCoreTypes.h中。要使用常量要走三步,

1、引入MobileCoreServices.framework

2、#import <MobileCoreServices/UTCoreTypes.h>

3、转换为NSString,(NSString *)kUTTypePlainText

至于为什么要有第三步,因为UIPasteboard的函数中需要type都是NSString类型的。

2. 函数

2.1 粘贴板获取和删除

+ (UIPasteboard *)generalPasteboard
获取系统全局粘贴板,也就是说名叫UIPasteboardNameGeneral的系统粘贴板

+ (UIPasteboard *)pasteboardWithName:(NSString *)pasteboardName create:(BOOL)create
获取对应pasteboardName的粘贴板,create=YES表示如果没有则创建。

+ (UIPasteboard *)pasteboardWithUniqueName
获取一个有唯一名字的app粘贴板。

+ (void)removePasteboardWithName:(NSString *)pasteboardName
删除一个粘贴板


2.2 Object类型数据读写(单个item)

比如: NSString, NSArray, NSDictionary, NSDate, NSNumber, UIImage, NSURL

- (void)setValue:(id)value forPasteboardType:(NSString *)pasteboardType

- (id)valueForPasteboardType:(NSString *)pasteboardType
pasteboardType就是对应数据的UTI。如果pasteboardType和value不匹配,粘贴板不会进行赋值,它什么也不干。

2.3 二进制数据或者自定义pasteboardType(单个item)

- (void)setData:(NSData *)data forPasteboardType:(NSString *)pasteboardType
- (NSData *)dataForPasteboardType:(NSString *)pasteboardType
pasteType可以是UTI,也可以自己定义的pasteboardType。自定义pasteboardType一般的命名方式是com.companyName.packageName.typeName。

举个栗子:

#define PASTE_BOARD_NAME @"com.dali.pasteboard"
#define PASTE_BOARD_TYPE @"com.dali.pasteboard.dictionary"

-(void) writeDictToPasteBoard:(NSDictionary*) dict
{
    // 获取一个pasteboard,如果没有创建
    UIPasteboard * pb = [UIPasteboard pasteboardWithName:PASTE_BOARD_NAME create:YES];
    // 使pasteboard可持久
    [pb setPersistent:TRUE];
    // 将dict变为NSData并,存储进粘贴板
    [pb setData:[NSKeyedArchiver archivedDataWithRootObject:dict] forPasteboardType:PASTE_BOARD_TYPE];
}

-(NSDictionary*) readDictFromPasteboard
{
    UIPasteboard * pb=[UIPasteboard pasteboardWithName:PASTE_BOARD_NAME create:NO];
    NSData * data=[pb valueForPasteboardType:PASTE_BOARD_TYPE];
    NSDictionary * dict;
    
    if (!data) {
        return nil;
    }
    @try {
        dict = [NSKeyedUnarchiver unarchiveObjectWithData:data];
    }
    @catch (NSException* exception)
    {
        NSLog(@"Exception: %@",exception);
        return nil;
    }
    return dict;
}

2.4. 其他的一些函数,比如多个item操作,判断类型之类的,我用的不多,如果详细看,请看 Apple文档


文章内容参考了:

https://developer.apple.com/library/ios/documentation/UIKit/Reference/UIPasteboard_Class

http://hayageek.com/uipasteboard-example-read-write-share/


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值