2

新的一天,新的问题!

我一直在开发一个应用程序,该应用程序需要在用户触摸屏幕时显示用户手指所在的圆圈。

我遵循了一个关于子类化 UIWindow的教程,我的评论解释了如果您使用 Storyboards 和 ARC,如何传递这些内容。

我正在使用以下代码(基于本教程)来显示触摸指示器:

#pragma mark - Touch Events
- (void) touchesBegan:(NSSet*)touches withEvent:(UIEvent*)event {
    NSArray *subviews = [self.webView subviews];
    for (UIView *view in subviews) 
    {
        // Check if view is scrollview
        if ([view isKindOfClass:[UserTouchImageView class]])
        {
            [view removeFromSuperview];
        }
    }

    // Enumerate over all the touches and draw a red dot on the screen where the touches were
    [touches enumerateObjectsUsingBlock:^(id obj, BOOL *stop) {
        // Get a single touch and it's location
        UITouch *touch = obj;
        CGPoint touchPoint = [touch locationInView:self.webView]; 

        // Add touch indicator
        UserTouchImageView *touchView = [[UserTouchImageView alloc] initWithFrame:CGRectMake(touchPoint.x -15, touchPoint.y -15, 30, 30)];
        [self.webView addSubview:touchView];
    }];
    NSLog(@"Touches began");
}
- (void) touchesMoved:(NSSet*)touches withEvent:(UIEvent*)event {
    NSArray *subviews = [self.webView subviews];
    for (UIView *view in subviews) 
    {
        // Check if view is scrollview
        if ([view isKindOfClass:[UserTouchImageView class]])
        {
            [view removeFromSuperview];
        }
    }

    // Enumerate over all the touches and draw a red dot on the screen where the touches were
    [touches enumerateObjectsUsingBlock:^(id obj, BOOL *stop) {
        // Get a single touch and it's location
        UITouch *touch = obj;
        CGPoint touchPoint = [touch locationInView:self.webView]; 

        // Draw a red circle where the touch occurred
        UserTouchImageView *touchView = [[UserTouchImageView alloc] initWithFrame:CGRectMake(touchPoint.x -15, touchPoint.y -15, 30, 30)];
        [self.webView addSubview:touchView];
    }];
    NSLog(@"Touches moved");
}
- (void) touchesEnded:(NSSet*)touches withEvent:(UIEvent*)event {
    NSArray *subviews = [self.webView subviews];
    for (UIView *view in subviews) 
    {
        // Check if view is scrollview
        if ([view isKindOfClass:[UserTouchImageView class]])
        {
            [UIView animateWithDuration:0.5f 
                             animations:^{
                                 view.alpha = 0.0;
                             }
                             completion:^(BOOL finished) {
                                 [view removeFromSuperview];
                             }];
        }
    }
    NSLog(@"Touches ended");
}
- (void) touchesCancelled:(NSSet*)touches withEvent:(UIEvent*)event {
    NSArray *subviews = [self.webView subviews];
    for (UIView *view in subviews) 
    {
        // Check if view is scrollview
        if ([view isKindOfClass:[UserTouchImageView class]])
        {
            [view removeFromSuperview];
        }
    }
    NSLog(@"Touches cancelled");
}

UserTouchImageView 是 UIImageView 的子类,默认更改为:

- (id)initWithFrame:(CGRect)frame
{
    self = [super initWithFrame:frame];
    if (self) {
        // Initialization code
        self.image = [UIImage imageNamed:@"greyCircle.png"];
        self.alpha = 0.5f;
    }
    return self;
}

我已经在没有 UIWebview 的情况下测试了这段代码(用 替换self.webViewself.view,它工作正常,在我单击并拖动的地方绘制圆圈,然后在我释放按钮时淡出。

我还成功地实例化了 UserTouchImageView 并将其从 viewController 的viewDidLoad方法添加到 webView。

一旦我将 UIWebview 与上面的代码一起放入,同一行 ( [self.webView addSubview:touchView];) 就不起作用了。我仍然将 NSLog 消息发送到控制台,但子视图没有明显添加。

谁能帮我弄清楚为什么这没有出现?是否有任何其他代码我需要注意,或者我不能这样做的任何原因?

非常感谢!

编辑

到目前为止,我已经上传了我的源代码(MediaFire)

编辑 2

我添加了以下两种方法:

-(void)listWebViewSubViews
{
    NSLog(@"BEGIN LISTING SUBVIEWS");
    for (UIView *view in [self.webView subviews]) {
        NSLog(@"Subview: %@", view.description);
    }
    NSLog(@"END LISTING SUBVIEWS");
}
-(void)view:(UIView *)view addTouchIndicatorWithCentreAtPoint:(CGPoint)point
{
    NSLog(@"View: %@, x: %f, y: %f", view.description, point.x, point.y);

    // Add touch indicator
    UserTouchImageView *touchView = [[UserTouchImageView alloc] initWithFrame:CGRectMake(point.x -15, point.y -15, 30, 30)];

    [view addSubview:touchView];


}

这些是从 UIWebView 外部的两个按钮和 touchesbegan 方法中调用的:

- (void) touchesBegan:(NSSet*)touches withEvent:(UIEvent*)event {
    NSArray *subviews = [self.webView subviews];
    for (UIView *view in subviews) 
    {
        if ([view isKindOfClass:[UserTouchImageView class]])
        {
            [view removeFromSuperview];
        }
    }

    [touches enumerateObjectsUsingBlock:^(id obj, BOOL *stop) {
        UITouch *touch = obj;
        CGPoint touchPoint = [touch locationInView:self.webView]; 

        [self view:self.webView addTouchIndicatorWithCentreAtPoint:touchPoint];

        [self listWebViewSubViews];
    }];
    NSLog(@"Touches began");
}

日志记录似乎表明,在 touches started 方法中引用的 webviewself.webView 一个完全独立的实例,而不是从两个按钮引用的实例。我可以通过按钮添加多个子视图,然后列出它们,它们都显示在日志中,但是当我点击模拟器时,这些额外的子视图都没有列出。

有谁知道 UIWebView 中有任何特殊功能在触摸事件上有重复的实例?

4

3 回答 3

0

AUIWebView不是一个视图,而是视图的集合。当您将子视图添加到 UIWebView 时,新的子视图将添加到子视图的层次结构中。您的新子视图可能被添加到其他不透明视图后面。它在那里,但隐藏起来。我建议将此指示器视图添加到层​​次结构中的不同视图。

于 2012-07-20T13:09:20.397 回答
0

userInteractionEnabledforUIImageView的默认值为NO. 您可能需要将其设置为YES.

于 2012-07-20T13:16:14.147 回答
0

问题解决了:

不幸的是,这是由完全不同的东西引起的,所以感谢大家提供的帮助。

问题出在我尝试修复代码以与情节提要一起运行。我曾尝试从情节提要访问视图控制器,并将其添加为优先接收触摸事件的视图(请参阅我链接到的教程和我的评论,我也已回复)。我应该在哪里使用 self.window.rootViewController。

我的更新评论在这里

于 2012-07-20T16:19:00.403 回答