在自定义视图/ uiview子类上实现iphone的复制/粘贴控件

时间:2010-01-21 16:10:08

标签: iphone copy-paste uimenucontroller

我承认在S.O.上已经存在这些问题,但它缺乏实施细节,工作答案,我想更具体,所以我认为一个新问题是有道理的。显然,如果我错了,请告诉我,我们可以尝试restart the thread over there

基本上,当用户按住标签时,我想将UILabel中的文本复制到粘贴板。老实说,不难做到。但是,我认为提供视觉反馈的最佳方式是使用UIMenuController中的“复制”菜单选项提示用户。

根据“iPhone应用程序编程指南”的“事件处理”部分,特别是Copy, Cut, and Paste Operations部分,应该可以从自定义视图中提供复制,剪切和/或粘贴操作。

所以,我已经按照指南所描述的以下实现对UILabel进行了分类,但是UIMenuController将不会出现。指南中没有迹象表明还有其他任何需要这样做,并且NSLog语句会打印到控制台,表示当我按住标签时正在执行选择器:

//
//  CopyLabel.m
//  HoldEm
//
//  Created by Billy Gray on 1/20/10.
//  Copyright 2010 Zetetic LLC. All rights reserved.
//

#import "CopyLabel.h"

@implementation CopyLabel

- (void)showCopyMenu {
    NSLog(@"I'm tryin' Ringo, I'm tryin' reeeeal hard.");
    // bring up editing menu.
    UIMenuController *theMenu = [UIMenuController sharedMenuController];
    // do i even need to show a selection? There's really no point for my implementation...
    // doing it any way to see if it helps the "not showing up" problem...
    CGRect selectionRect = [self frame];
    [theMenu setTargetRect:selectionRect inView:self];
    [theMenu setMenuVisible:YES animated:YES]; // <-- doesn't show up...
}

// obviously, important to provide this, but whether it's here or not doesn't seem
// to change the fact that the UIMenuController view is not showing up
- (BOOL)canPerformAction:(SEL)action withSender:(id)sender {
    BOOL answer = NO;

    if (action == @selector(copy:))
        answer = YES;

    return answer;
}

- (BOOL)canBecomeFirstResponder {
    return YES;
}

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
    [self performSelector:@selector(showCopyMenu) withObject:nil afterDelay:0.8f];
}

- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {
    [NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(showCopyMenu) object:nil];
}

- (void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event {
    [NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(showCopyMenu) object:nil];
}

- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event {
    [NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(showCopyMenu) object:nil];
}

@end

那么,为了实现这一目标还需要做些什么呢?

对于那些关注并尝试执行此操作的人,您还需要为标签设置“用户互动已启用”

编辑:

为清楚起见,我要补充一点,这应该类似于按住它时某些iphone视图中图像上显示的小[复制]菜单项。 -B

1 个答案:

答案 0 :(得分:7)

我会先说我没有aswer,但我做了一些探索并找到了更多。我相信你已经看过了这个:CopyPasteTile

该代码在我的模拟器上运行,并且如下所示:

CGRect drawRect = [self rectFromOrigin:currentSelection inset:TILE_INSET];
[self setNeedsDisplayInRect:drawRect];

UIMenuController *theMenu = [UIMenuController sharedMenuController];
[theMenu setTargetRect:drawRect inView:self];
[theMenu setMenuVisible:YES animated:YES];

这里有一些不同之处:

  • drawRect是根据巨型视图图块和分接点计算
  • 计算的
  • setNeedsDisplayInRect被称为
  • self是一个大屏幕大小的视图,您可能需要屏幕坐标而不是本地坐标(您可以从self.superview获取)

我会先尝试进行这些调整以匹配示例,看看它会给我带来什么样的进展。