【发布时间】:2012-10-23 09:31:41
【问题描述】:
我有一个 UIView 子类,我在其中使用 touchesBegan、touchesMoved、touchesEnded 处理触摸。 我注意到当我在内部开始触摸然后在 UIView touchesEnded 外部拖动时不会触发,当我在 UIView 框架外拖动时有没有办法调用它? 谢谢
【问题讨论】:
我有一个 UIView 子类,我在其中使用 touchesBegan、touchesMoved、touchesEnded 处理触摸。 我注意到当我在内部开始触摸然后在 UIView touchesEnded 外部拖动时不会触发,当我在 UIView 框架外拖动时有没有办法调用它? 谢谢
【问题讨论】:
改用 touchesCancelled。
- (void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event
{
}
【讨论】:
可能它正在调用- (void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event
请查看UIResponder Class Reference
touchesCancelled:withEvent:
当系统事件(如内存不足 警告)取消触摸事件。
- (void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event参数
触摸
A set of UITouch instances that represent the touches for the ending phase of the event represented by event. event An object representing the event to which the touches belong.讨论
当 Cocoa Touch 框架收到一个 系统中断需要取消触摸事件;为了 这样,它会生成一个 UITouch 对象,其相位为 UITouchPhaseCancel。中断是可能导致 应用程序不再处于活动状态或视图从 窗口
当一个对象收到一个 touchesCancelled:withEvent: 消息时 应该清理在其建立的任何状态信息 touchesBegan:withEvent: 实现。
这个方法的默认实现什么都不做。然而 UIResponder 的直接 UIKit 子类,尤其是 UIView, 将消息向上转发到响应者链。将消息转发到 下一个响应者,将消息发送给 super(超类 执行);不要直接发消息给下一个 响应者。例如,
[super touchesCancelled:touches withEvent:event];
如果你在不调用 super 的情况下重写了这个方法(一个常见的用法 模式),您还必须覆盖其他处理触摸的方法 事件,如果只是作为存根(空)实现。可用性
Available in iOS 2.0 and later.
【讨论】:
即使您在视图框架之外,您仍然应该在您的 viewController 中获得 touchesMoved。我会将数组添加到您的自定义 UIView 中,这将保留分配此视图的触摸对象并实现以下逻辑:
touchesBegan 时 - 将触摸对象添加到给定 UIView 的数组中,其中触摸坐标匹配(您可能必须遍历所有子视图并将坐标与框架匹配以找到正确的子视图)touchesMoved 时 - 从 UIView's 数组中删除先前位置的触摸并将其添加到 UIView 以获取当前位置(如果有)touchesEnded 和 touchesCancelled - 从所有 UIViews 数组中删除触摸当您从自定义 UIView 数组中删除或添加触摸对象时,您可能会调用委托方法(实现观察者模式),因为此时您知道它是真正按下还是未按下事件。请记住,您可能在一个数组中有许多触摸对象,因此在调用您的委托之前,请检查您是添加了第一个对象还是删除了最后一个对象,因为这是您应该调用您的委托的唯一情况。
我在上一个游戏中实现了这样的解决方案,但我没有UIViews,而是使用了虚拟按钮。
【讨论】: