为什么touchesBegan,target-action和touchesEnded的执行顺序会随着UIButton的快速触摸而改变?

时间:2011-01-31 16:48:51

标签: objective-c cocoa-touch uibutton

更新:随着羞耻的脸红我发现订单与点击的速度无关。我在super touchesEnded:withEvent调用之前调用了可视代码,这就是为什么如果你快速点击,显示器再也没有机会绘制突出显示的状态再被解雇。因为实际上导致主线程仅阻塞几毫秒的代码,突出显示的状态将保持可见,直到主线程再次解除阻塞,就好像你快速点击,看起来根本没有发生任何事情。将超级调用移动到重写方法的顶部会将其全部修复。对不起,如果主持人看到这篇文章,可以将其删除。 羞耻

此问题必须在SO处被问过1000次,但我找不到与我的具体问题相符的解释。

我有一个带有自定义设计的UIButton子类。当然,设计足够自定义,我不能只使用常规的setSomething:forControlState:方法。我需要一个不同的触摸背景颜色,一个,以及一些需要闪光的图标。

为了实现这些视图更改,我(反直觉地)将显示代码放在(A)touchesBegan:withEvent和(Z)touchesEnded:withEvent:中,然后再调用它们各自的超级方法。感觉很奇怪,但它按预期工作,或者最初似乎是这样。

实施addTarget:action:forControlEvents用于将UIControlEventTouchUpInside绑定到方法(X)itemTapped:之后,我希望这些方法始终按顺序(A)(X)触发( Z)。但是,如果您快速点击屏幕(或模拟器中的鼠标),它们按顺序(A)(Z)(X)触发。其中(A)和(Z)以如此快速的连续性相互跟随,使得攻丝的整个视觉反馈是不可见的。这是不受欢迎的行为。这也是不可能的,因为很多应用需要类似的行为,对吗?

所以我的问题是:我做错了什么?我猜测的一件事是,不应该在touchesBegan:withEventtouchesEnded:withEvent中操纵按钮的视觉外观,而是在哪里?或者我错过了其他一些众所周知的事实?

感谢轻推, 埃里克保

1 个答案:

答案 0 :(得分:4)

我不知道为什么订单不同,但这里有2条建议可以帮助处理它。

您对按钮进行了哪些视觉更改?如果更改标题/图像/背景图像,您可以通过修改按钮的突出显示状态来完成所有这些操作。您可以设置一些属性,如标题和背景图像每状态。当用户的手指按下按钮时,highlighted状态将打开,因此此时对此状态所做的任何更改都将显示。请注意,如果您正在使用按钮上的selected状态,那么您还需要为UIControlStateHighlighted|UIControlStateSelected设置视觉外观,否则它将默认返回到从Normal继承突出显示&选中了。

另一个建议是放弃touchesBegan:withEvent:touchesEnded:withEvent:并切换到使用从UIControl继承的方法,即beginTrackingWithTouch:withEvent:endTrackingWithTouch:withEvent:。如果触摸离开控件,您可能还需要实现continueTrackingWithTouch:withEvent:并使用touchInside属性关闭视觉调整。