UIButton touch down action, not called when touched, but called when touched

Hi, you need to perform an action when the user touched DOWN UIButton

[button addTarget:self action:@selector(touchDown:event:) forControlEvents:UIControlEventTouchDown]; [button addTarget:self action:@selector(drag:event:) forControlEvents:UIControlEventTouchDragInside]; [button addTarget:self action:@selector(drag:event:) forControlEvents:UIControlEventTouchDragOutside]; [button addTarget:self action:@selector(touchUp:event:) forControlEvents:UIControlEventTouchUpInside]; [button addTarget:self action:@selector(touchUp:event:) forControlEvents:UIControlEventTouchUpOutside]; - (void)touchDown:(UIButton *)sender event:(UIEvent *)event { //begin only called when I move my finger } - (void)drag:(UIButton *)sender event:(UIEvent *)event { //called when I move my finger, after touchDown was called } - (void)touchUp:(UIButton *)sender event:(UIEvent *)event { } 

The root view controller of my application is a tabbarviewcontroller, and each tab is a navigation view controller. in the viewWillAppear method of the conversation scene, I hide the tab bar.

the result, on the device, when I touch down, it is not called, and when I move my finger a little, it is called.

Note:

  • Using Long Press Gesture Recognizer also does not work.

  • If I remove the button from the tab bar area, it will work on the device.

  • everything is fine on the simulator.

I created a sample project: https://drive.google.com/folderview?id=0B_9_90avvmZtRmRDeHFkbFJLaFk&usp=sharing

+8
ios objective-c cocoa-touch uikit
source share
7 answers

Is this button inside a scroll (including collecting or viewing a table)? If so, then this is exactly the expected behavior. The system waits if you press a button or drag a scroll. From Apple:

Since there are no scroll bars in the scroll view, he should know if the touch signal indicates the intention of the scroll versus the intention to track the subview in the content. To make this determination, he temporarily intercepts the touch-down event, starting the timer, and before the timer fires, he sees that the touching finger makes any movement. If the timer fires without a significant change in position, the scroll view sends tracking events to an indirect view in the content view. If the user then drags his finger far enough before the timer expires, the scroll view cancels any tracking in the preview and scrolls. Subclasses can override the touchesShouldBegin:withEvent:inContentView: pagingEnabled, and touchesShouldCancelInContentView: (which are invoked in the scroll view) to affect the scroll view using gesture scrolling.

If you do not want this behavior, you can set parentview.delaysContentTouches to NO You may also need to set canCancelContentTouches to NO

+11
source share

Hi @OMGPOP I have the same problem with you, now I decided to add the code below:

 self.navigationController.interactivePopGestureRecognizer.delaysTouchesBegan = NO; 

I'm sure this is your savior, because I downloaded your sample code and added the code above, it works great. eg:

 self.navigationController.interactivePopGestureRecognizer.delaysTouchesBegan = NO; [self.holdToRecordButton addTarget:self action:@selector(touchDown:event:) forControlEvents:UIControlEventTouchDown]; [self.holdToRecordButton addTarget:self action:@selector(drag:event:) forControlEvents:UIControlEventTouchDragInside]; [self.holdToRecordButton addTarget:self action:@selector(drag:event:) forControlEvents:UIControlEventTouchDragOutside]; [self.holdToRecordButton addTarget:self action:@selector(touchUp:event:) forControlEvents:UIControlEventTouchUpInside]; [self.holdToRecordButton addTarget:self action:@selector(touchUp:event:) forControlEvents:UIControlEventTouchUpOutside]; 
+9
source share

Do you have any subtitles on your button? They can intercept strokes and lead to the behavior that you see.

0
source share

Do you have any UIGestureRecognizers on your button control? They can cause such a delay.

0
source share

I met the same problem and finally figured it out.

The problem is that the button cannot take action, as its observer can be obscured by scroll gesture recognizers.

What you need to do is add a gesture to the sound button container, set the gesture recognizer delegate to the view controller and disable the popGestureRecognizer navigation controller, as shown below.

 - (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch:(UITouch *)touch{ if ([UIDevice currentDevice].isIOS7 && touch.view == btnAudioRecorder)//issue is iOS7 only{ self.navigationController.interactivePopGestureRecognizer.enabled = NO; } return YES; } 

And check it out, the button can now respond to your touch event like a charm.

0
source share

I had the same problem and it was resolved.

In my case, there are two adjacent buttons. (The left button is button A. The right button is button B.) ButtonA is not called a touch down event. But ButtonB is called a touch down event.

I tried to override pointInside in ButtonB class.

 override func pointInside(point: CGPoint, withEvent event: UIEvent?) -> Bool { println(point) } 

Then I pressed button A and named pointInside ButtonB !! point.x is a negative value.

So, I checked the point and sendAction in the ButtonB class.

 override func pointInside(point: CGPoint, withEvent event: UIEvent?) -> Bool { if CGRectContainsPoint(self.bounds, point) { return true } // hoge.left means hoge.frame.origin.x if point.x < 0, let buttonA = optionalButtonA { buttonA.bounds.origin.x -= (self.left - buttonA.left) //self.left is buttonB.left if CGRectContainsPoint(buttonA.bounds, point) { buttonA.sendActionsForControlEvents(UIControlEvents.TouchDown) return false } } return false } 
0
source share

I had the same problem. And I tried all the answers with a post here, but none of them worked. Fortunately, my colleague had the same problem, and he solved it!

Decision:

put the following code in your relative ViewController:

 override var preferredScreenEdgesDeferringSystemGestures: UIRectEdge { return .bottom } override func viewDidLoad() { super.viewDidLoad() self.navigationController? .interactivePopGestureRecognizer? .delaysTouchesBegan = false } 

The reason the touch action wasn’t triggered immediately, probably when your button is under the bottom of the screen, the touch event will conflict with the iOS move up from the bottom gesture. So it dragged on.

0
source share

All Articles