前段时间偶然看到了天猫客户端有一个很贴心的功能,就是领取红包的时候,只要复制了一段特定信息,然后打开天猫的客户端,就会提醒你去领红包,如下图。

虽然功能很简单,但是确实很贴心的为用户考虑。

        整个功能的原理其实很简单的,就是使用了iOS剪切板UIPasteboard。下面我们来细看一下这个类,来实现天猫客户端的这个功能。

可以看出创建UIPasteboard实例有三个类方法:

  • + (UIPasteboard *)generalPasteboard;这个方法是获取通用的剪切板实例,就是所有的应用程序都可以访问的;

  • + (UIPasteboard *)pasteboardWithName:(NSString *)pasteboardName create:(BOOL)create;这个方法是通过’pasteboardName’获取剪切板,如果没有我们可以指定是否创建;

  • + (UIPasteboard *)pasteboardWithUniqueName;创建一个唯一的剪切板,有系统命名的,名字我们可以通过pasteboard.name来获取。

如果要实现天猫这样的功能,我们使用只能使用+ (UIPasteboard *)generalPasteboard;来获取剪切板实例。我们可以在AppDelegate.m中的- (void)applicationDidBecomeActive:(UIApplication *)application方法中加入获取剪切板内容的代码,如下:

1
2
3
4
UIPasteboard *pasteboard = [UIPasteboard generalPasteboard];
if ([pasteboard.string isEqualToString:@"123"]) {
[[[UIAlertView alloc] initWithTitle:@"Tips" message:[NSString stringWithFormat:@"剪切板的信息是%@,可以去领红包了",pasteboard.string] delegate:nil cancelButtonTitle:@"确定" otherButtonTitles:nil, nil] show];
}

好了 这个功能就完成了,就是这么简单,看一下效果:

扩展

iOS系统中,UITextFieldUITextViewUIWebView默认是可以使用剪切板的,如果其他的UI控件使用剪切板的话,就需要自己处理了,下面我们给UILabelUIImageView添加剪切板。

首先我们创建一个继承UILabel的子类LBCopyPasteLabel,使用剪切板我们需要把userInteractionEnabled设置为YES,然后需要设置视图可以成为第一响应者,如下代码:

1
2
3
- (BOOL)canBecomeFirstResponder {
return YES;
}

然后在UIPasteboard中只使用CopyPaste功能,代码如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
-(BOOL)canPerformAction:(SEL)action withSender:(id)sender {
if (action == @selector(cut:)) {
return NO;
} else if (action == @selector(copy:)) {
return YES;
} else if (action == @selector(paste:)) {
return YES;
} else if (action == @selector(select:)) {
return NO;
} else if (action == @selector(selectAll:)) {
return NO;
} else {
return [super canPerformAction:action withSender:sender];
}
}

接着实现- (void)copy:(id)sender- (void)paste:(id)sender方法,
具体实现如下:

1
2
3
4
5
6
7
8
9
- (void)copy:(id)sender {
UIPasteboard *pasteboard = [UIPasteboard generalPasteboard];
pasteboard.string = self.text;
}

- (void)paste:(id)sender {
UIPasteboard *pasteboard = [UIPasteboard generalPasteboard];
self.text = pasteboard.string;
}

最后我们可以在label中添加一个UIPanGestureRecognizer长按的手势,本文中使用的是在- (void)touchesBegan:(NSSet*)touches withEvent:(UIEvent*)event这个方法中操作的,所以就没有添加长按的手势,我们看一下具体的实现代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
- (void)touchesBegan:(NSSet*)touches withEvent:(UIEvent*)event {
[self becomeFirstResponder];
[self performSelector:@selector(showMenu:)
withObject:self afterDelay:1.0f];
[super touchesBegan:touches withEvent:event];
}

- (void)showMenu:(id)view {
//get UIMenuController
UIMenuController * menu = [UIMenuController sharedMenuController];
[menu setTargetRect:CGRectZero inView: view];
[menu setMenuVisible: YES animated: YES];
}

OK,这样就实现了一个可以CopyPasteUILabel,实现可以复制和剪切的UIImageView,原理也是一样的,只是实现- (void)copy:(id)sender- (void)paste:(id)sender稍微不一样,如下:

1
2
3
4
5
6
7
8
9
10
11
- (void)copy:(id)sender {
UIPasteboard *pasteboard = [UIPasteboard generalPasteboard];
if (self.image) {
pasteboard.image = self.image;
}
}

- (void)paste:(id)sender {
UIPasteboard *pasteboard = [UIPasteboard generalPasteboard];
self.image = pasteboard.image;
}

好了,这样就完成了,具体的效果如下图,本文Demo