【问题标题】:UIGestureRecognizer with selector being called from another class从另一个类调用选择器的 UIGestureRecognizer
【发布时间】:2017-12-31 03:00:16
【问题描述】:

我有两个类都添加UIPinchGestureRecognizer 并使用选择器来处理响应手势的代码。注意:手势识别器委托可能与此问题无关,但我将其包含在代码中以防万一。

class GameScene: SKScene, UIGestureRecognizerDelegate {

    override func didMove(to view: SKView) {
        let pinchGestureRecognizer = UIPinchGestureRecognizer(target: self, action: #selector(handlePinchFrom))
        pinchGestureRecognizer.delegate = self
        self.view!.addGestureRecognizer(pinchGestureRecognizer)
    }

    func gestureRecognizer(_ gestureRecognizer: UIGestureRecognizer, shouldRecognizeSimultaneouslyWith otherGestureRecognizer: UIGestureRecognizer) -> Bool {
        return true
    }

    @objc func handlePinchFrom(_ rec: UIPinchGestureRecognizer) {
        // This method should only be called when pinching in GameScene scene.
    }
}


class Level1: SKScene, UIGestureRecognizerDelegate {

    // Same code here as in GameScene class.

    @objc func handlePinchFrom(_ rec: UIPinchGestureRecognizer) {
        // This method should only be called when pinching in Level scene.
    }
}

GameScene 中,handlePinchFrom 方法被正常调用。在用户从GameScene 转换到Level1 场景后,Level1 中的handlePinchFrom 方法被正常调用。然而,GameScene 中的 handlePinchFrom 方法在 Level1 中执行捏合手势时仍然会被调用,即使 GameScene 不再出现在调试视图层次结构中。

同样,如果用户随后离开Level1 并转换回GameScene,当您在GameScene 中执行捏合手势时,来自Level1handlePinchFrom 方法也会被调用。

我猜这可能是由于两个选择器使用了相同的名称 (handlePinchFrom)。但是我尝试给其中一个选择器起一个不同的名称,但当我希望只调用其中一个时,它们仍然会被调用。

有谁知道为什么在加载Level1 后仍然会调用来自GameScenehandlePinchFrom 方法,即使程序不再运行GameScene 类?

【问题讨论】:

  • "有谁知道为什么 GameScene 中的 handlePinchFrom 方法仍然会被调用" 这显然是因为你在视图控制器中添加了一个观察者并且没有移除它。
  • @ElTomato 我理解我使用#selector 是一种让Objective-C 功能在Swift 中工作的方法。我承认我对 Obj-C 不太熟悉。我假设一旦我离开场景,选择器就会被移除。离开场景前是否需要明确移除选择器?
  • 手势识别器被添加到view 并且您在Level1 场景中使用相同的视图。您需要在willMove(from view:) 中删除带有view.removeGestureRecognizer(...) 的旧识别器

标签: ios swift sprite-kit uigesturerecognizer selector


【解决方案1】:

感谢 0x141E 的建议,我修复了我的代码。请参阅下面的更新代码。

我设置了手势识别器并在didMove(to view:) 中获取了对它的引用。然后我使用引用将其从willMove(from view:) 的场景视图中删除。

现在,在我的应用离开游戏场景后,不再调用手势识别器。

class GameScene: SKScene {
    var pinchGrRef: UIPinchGestureRecognizer?

    override func didMove(to view: SKView) {
        let pinchGestureRecognizer = UIPinchGestureRecognizer(target: self, action: #selector(handlePinchFrom))
        self.view!.addGestureRecognizer(pinchGestureRecognizer)
        self.pinchGrRef = pinchGestureRecognizer
    }

    @objc func handlePinchFrom(_ rec: UIPinchGestureRecognizer) {
        // Respond to pinch gesture
    }

    override func willMove(from view: SKView) {
        if pinchGrRef != nil { self.view!.removeGestureRecognizer(pinchGrRef!) }
    }
}

【讨论】:

    猜你喜欢
    • 2018-11-30
    • 1970-01-01
    • 2015-02-15
    • 1970-01-01
    • 2017-10-06
    • 2018-07-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多