I have a UIScrollView
with no subviews. When I drag the scroll view, its hitTest:withEvent:
gets called three times, and there are never any touches in the event. Why is that (I saw another post but it doesn't seem to have a consclusion)? Here is the log of the scroll view's hitTest...
and pointInside:withEvent:
2011-05-11 20:12:37.472 MyApp[10909:707] hit test for UIScrollView 119.500000,102.000000, timestamp: 357978 touches: {()} 2011-05-11 20:12:37.475 MyApp[10909:707] pointInside for UIScrollView 119.500000,102.000000, timestamp: 357978 touches: {()} 2011-05-11 20:12:37.477 MyApp[10909:707] hit test for UIScrollView 119.500000,102.000000, timestamp: 357978 touches: {()} 2011-05-11 20:12:37.479 MyApp[10909:707] pointInside for UIScrollView 119.500000,102.000000, timestamp: 357978 touches: {()} 2011-05-11 20:12:37.481 MyApp[10909:707] hit test for UIScrollView 119.500000,102.000000, timestamp: 358021 touches: {()} 2011-05-11 20:12:37.482 MyApp[10909:707] pointInside for UIScrollView 119.500000,102.000000, timestamp: 358021 touches: {()} 2011-05-11 20:12:37.484 MyApp[10909:707] pointInside for UIScrollView 119.500000,396.000000, timestamp: 358021 touches: {()}
hitTest:
is a utility method designed to find a view at a specific point. It DOES NOT represent a user tapping on the touch screen. It is totally sensible for hitTest to be called several times in response to the same event; all the method is supposed to do is return the view under the point and it SHOULD NOT trigger any side effects.
If you want to track touch events, you should override touchesBegan:
and friends.
I had the same problem and didn't actually find an answer to this, but you could use one of these 2 solutions:
1. Store the hit tests in an array and compare them so you can return when it's the same to prevent it getting called 3 times in a row.
2. Instead of hittest, use touchesBegan, touchesCancelled, touchesEnded and touchesMoved like this:
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
{
UITouch * touch = [[event allTouches] anyObject];
CGPoint touchLocation = [touch locationInView:touch.view];
NSLog(@"%f - %f", touchLocation.x, touchLocation.y);
}
I used the touchesBegan, etc solution and it works like a charm :)
I don't know for sure why, but here are some further insights into this question:
UIResponder
methods aren't called until after all three hitTest calls complete. For example, touchesBegan:withEvent: won't be called until the end.My best guess is that, in some cases, the return value from hitTest
might change between calls. I cannot think of why this might happen, though. If this isn't true, then it doesn't make sense to call it multiple times.
Another idea is that the code is simply inefficiently-written. This seems less likely, but based on this information, it is a possibility.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With