实现的目标是长按label,弹出复制菜单,然后复制。
我的做法是实现一个通用的可复制UILabel控件。下面是具体的步骤。
创建UILabel子类
1 2 3 4
| @interface CopyLabel : UILabel
- (id)initWithFrame:(CGRect)frame; @end
|
使UILabel可响应
使CopyLabel可以成为第一响应者
1 2 3 4
| - (BOOL)canBecomeFirstResponder { return YES; }
|
使CopyLabel可响应copyText命令
1 2 3 4
| - (BOOL)canPerformAction:(SEL)action withSender:(id)sender { return (action == @selector(copyText:)); }
|
1、 UIResponder类声明了canPerformAction:withSender:方法。响应者类可以实现这个方法,以根据当前的上下文显示或移除编辑菜单上的命令。
2、 在自定义的UIView子类中,需要实现canBecomeFirstResponder方法,并返回YES(默认返回FALSE),才可使becomeFirstResponder可返回YES,才可使其成为第一响应者,即接受第一响应者状态。一个响应者只有当当前响应者可以取消第一响应者状态 (canResignFirstResponder) 并且新的响应者可以成为第一响应者时,才可以成为第一响应者。
添加监听
在初始化方法中添加长按手势
1 2 3 4 5
| UILongPressGestureRecognizer* longPressGr = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(pressToCopy:)];
longPressGr.minimumPressDuration = 0.5f; [self addGestureRecognizer:longPressGr];
|
使UILabel可交互
1
| self.userInteractionEnabled = YES;
|
添加菜单消失的监听
1
| [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(menuItemHidden:)name:UIMenuControllerWillHideMenuNotification object:nil];
|
实现响应方法
长按后在文字上方弹出复制菜单
1 2 3 4 5 6 7 8 9 10 11 12 13
| -(void)pressToCopy:(UILongPressGestureRecognizer *)sender{ if (sender.state == UIGestureRecognizerStateBegan) { [self becomeFirstResponder];
UIMenuController *menu = [UIMenuController sharedMenuController]; UIMenuItem *copy = [[UIMenuItem alloc] initWithTitle:@"复制" action:@selector(copyText:)]; menu.menuItems = @[copy]; [menu setTargetRect:self.bounds inView:self]; [menu setMenuVisible:YES animated:YES];
self.backgroundColor = [self.textColor colorWithAlphaComponent:0.5f]; } }
|
当复制菜单消失后,使uilabel背景色变为透明
1 2 3
| -(void)menuItemHidden:(id)sender{ self.backgroundColor = [UIColor clearColor]; }
|
实现复制方法
1 2 3 4 5
| -(void)copyText:(id)sender { UIPasteboard *pasteboard = [UIPasteboard generalPasteboard]; pasteboard.string = self.label.text; }
|
1、 UIMenuController类可以在选定的拷贝、剪切、和粘贴对象的上下方显示一个编辑菜单。编辑菜单上的命令可以有拷贝、剪切、粘贴、选定、和全部选定。
2、UIPasteboard类提供了粘贴板的接口。粘贴板是用于在一个应用程序内或不同应用程序间进行数据共享的受保护区域。该类提供了读写剪贴板上数据项目的方法。
移除监听
当组件释放的时候需要移除其上面的添加的所有监听
1 2 3
| -(void)dealloc{ [[NSNotificationCenter defaultCenter] removeObserver:self]; }
|