2

新しい日、新しい質問!

私は、ユーザーが画面に触れているときにユーザーの指がある場所に円を表示する必要があるアプリに取り組んでいます。

UIWindow のサブクラス化で見つけたチュートリアルに従いました。私のコメントでは、ストーリーボードと 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 のメソッドから webView に追加することにも成功していますviewDidLoad

上記のコードで UIWebview を配置するとすぐに、同じ行 ( [self.webView addSubview:touchView];) が機能しません。コンソールに NSLog メッセージが表示されますが、サブビューが目に見えて追加されません。

これが表示されない理由を理解するのを手伝ってくれる人はいますか? 他に注意する必要があるコードはありますか、またはこれを行うことができない理由はありますか?

どうもありがとう!

編集

これまでにソースをここにアップロードしました(MediaFire)

編集2

以下の 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 の外側の 2 つのボタンと 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");
}

self.webView ロギングは、 WITHIN the touches begin メソッドによって参照される Webviewが、2 つのボタンから参照される場合とは完全に別のインスタンスであることを示しているようです。ボタンを使用して複数のサブビューを追加し、それらを一覧表示すると、それらはすべてログに表示されますが、クリックしてシミュレーターに触れると、これらの追加のサブビューは一覧表示されません。

タッチイベントでインスタンスを複製する UIWebView の特別な機能を知っている人はいますか?

4

3 に答える 3

0

userInteractionEnabledforのデフォルト値はUIImageViewですNO。に設定する必要がある場合がありますYES

于 2012-07-20T13:16:14.147 に答える
0

問題が解決しました:

残念ながら、これはまったく別の原因によるものでした。ご協力いただきありがとうございました。

この問題は、ストーリーボードで実行するようにコードを修正しようとしたことから発生しました。ストーリーボードからView Controllerにアクセスしようとし、それをビューとして追加して、タッチイベントを優先的に受け取りました(リンクしたチュートリアルと、私も返信したコメントを参照してください)。私はself.window.rootViewControllerを使用していたはずです。

私の更新されたコメントはこちら

于 2012-07-20T16:19:00.403 に答える
0

AUIWebViewは 1 つのビューではなく、ビューのコレクションです。サブビューを UIWebView に追加すると、新しいサブビューがサブビューの階層に追加されます。新しいサブビューは、おそらく他の不透明なビューの背後に追加されています。ありますが、隠れています。このインジケーター ビューを階層内の別のビューに追加することをお勧めします。

于 2012-07-20T13:09:20.397 に答える