使用 UITapGestureRecognizer

Posted

技术标签:

【中文标题】使用 UITapGestureRecognizer【英文标题】:Using UITapGestureRecognizer 【发布时间】:2010-10-22 22:00:29 【问题描述】:

iPhone 开发新手。我有一个包含 UIScrollView 的视图,其中包含 UIImageView。我在图像视图上添加了一个(双击)手势识别器,它打开了一个警告框。出于某种原因,我确定我只是智障,它打开了 3 次。

这是我的代码:

- (void)viewDidLoad 

    scrollView.delegate = self;

    UIImage* image = imageView.image;
    imageView.bounds = CGRectMake(0, 0, image.size.width, image.size.height);
    scrollView.contentSize = image.size;

    UITapGestureRecognizer *tapGesture = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(handleTapGesture:)];
    tapGesture.numberOfTapsRequired = 2;
    [imageView addGestureRecognizer:tapGesture];
    [tapGesture release];

    NSLog(@"LOADED");

    [super viewDidLoad];


-(IBAction) handleTapGesture:(UIGestureRecognizer *) sender 
    CGPoint tapPoint = [sender locationInView:imageView];
    int tapX = (int) tapPoint.x;
    int tapY = (int) tapPoint.y;
    NSLog(@"TAPPED X:%d Y:%d", tapX, tapY);
    UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"Hello" message:@"How are you?" delegate:nil cancelButtonTitle:@"I'm awesome." otherButtonTitles:nil];
    [alert show];
    [alert release];

我几天前刚开始开发 iPhone。这个问题让我想起了我在 javascript 中处理过的事件冒泡问题。有什么想法吗?

【问题讨论】:

哦,似乎值得注意的是 NSLog 并非全部出现 3 次。 【参考方案1】:

不确定确切的原因是什么,但 UIAlertView 以某种方式导致手势再次触发。一种解决方法是使用 performSelector 在手势处理程序之外执行显示:

-(void) handleTapGesture:(UIGestureRecognizer *) sender 
    CGPoint tapPoint = [sender locationInView:imageView];
    int tapX = (int) tapPoint.x;
    int tapY = (int) tapPoint.y;
    NSLog(@"TAPPED X:%d Y:%d", tapX, tapY);
    [self performSelector:@selector(showMessage) withObject:nil afterDelay:0.0];


- (void)showMessage

    UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"Hello" message:@"How are you?" delegate:nil cancelButtonTitle:@"I'm awesome." otherButtonTitles:nil];
    [alert show];
    [alert release];

编辑: 手势识别器在手势中经历不同的状态(Began、Changed 等),并在每次状态改变时调用处理程序方法。因此,更好且可能正确的解决方案是在处理程序顶部检查手势识别器的 state 属性:

-(void) handleTapGesture:(UIGestureRecognizer *) sender 
    if (sender.state != UIGestureRecognizerStateEnded)  // <---
        return;                                         // <---

    CGPoint tapPoint = [sender locationInView:imageView];
    int tapX = (int) tapPoint.x;
    int tapY = (int) tapPoint.y;
    NSLog(@"TAPPED X:%d Y:%d", tapX, tapY);

    UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"Hello" message:@"How are you?" delegate:nil cancelButtonTitle:@"I'm awesome." otherButtonTitles:nil];
    [alert show];
    [alert release];

【讨论】:

检查状态是解决方案。谢谢!

以上是关于使用 UITapGestureRecognizer的主要内容,如果未能解决你的问题,请参考以下文章

使用UITapGestureRecognizer传递参数

在 Swift 中使用 UITapGestureRecognizer 中的参数

使用 UITapGestureRecognizer

使用 UITapGestureRecognizer 时不会调用 textFieldShouldEndEditing

UIlabel 中的 UITapGestureRecognizer 错误

使用 UITapGestureRecognizer 根据 iPhone 中的手指触摸位置添加新视图