Swift 如何防止在双击函数中调用一键函数?

Swift 如何防止在双击函数中调用一键函数?,swift,macos,gesture,Swift,Macos,Gesture,我正在尝试向按钮添加自定义行为。如果单击一次,则执行一个操作。如果单击两次,将执行另一次 我看到并尝试了所有可能的组合: clickOnce.shouldBeRequiredToFailByGestureRecognizer(clickTwice) clickTwice.shouldBeRequiredToFailByGestureRecognizer(clickOnce) clickOnce.shouldRequireFailureOfGestu

我正在尝试向按钮添加自定义行为。如果单击一次,则执行一个操作。如果单击两次,将执行另一次

我看到并尝试了所有可能的组合:

        clickOnce.shouldBeRequiredToFailByGestureRecognizer(clickTwice)
        clickTwice.shouldBeRequiredToFailByGestureRecognizer(clickOnce)
        clickOnce.shouldRequireFailureOfGestureRecognizer(clickTwice)
        clickTwice.shouldRequireFailureOfGestureRecognizer(clickOnce)
        clickOnce.canPreventGestureRecognizer(clickTwice)
        clickOnce.canBePreventedByGestureRecognizer(clickTwice)
        clickTwice.canPreventGestureRecognizer(clickOnce)
        clickTwice.canBePreventedByGestureRecognizer(clickOnce)
但对我来说什么都不管用

下面是完整的代码:

import Cocoa

class ViewController: NSViewController {
    override func viewDidLoad() {
        super.viewDidLoad()

        // Do any additional setup after loading the view.

        let buttonTestOne = NSButton(frame: CGRect(x: 500, y: 500, width: 100, height: 500))

        let clickOnceForTestOne = NSClickGestureRecognizer(target: buttonTestOne, action: #selector(ViewController.clickOneTime(_:)))
        clickOnceForTestOne.numberOfClicksRequired = 1
        buttonTestOne.addGestureRecognizer(clickOnceForTestOne)
        self.view.addSubview(buttonTestOne)

        let arrTestButtons = ["One", "Two", "Three"]

        var x = 0
        var y = 0

        for item in arrTestButtons{
            let buttonNew = NSButton(frame: CGRect(x: x, y: y, width: 100, height: 100))
            x = x + 120
            y = y + 120
            buttonNew.attributedTitle = NSAttributedString(string: item)
            let clickOnce = NSClickGestureRecognizer(target: self, action: #selector(ViewController.clickOneTime(_:)))
            clickOnce.numberOfClicksRequired = 1
            buttonNew.addGestureRecognizer(clickOnce)
            let clickTwice = NSClickGestureRecognizer(target: self, action: #selector(ViewController.clickTwoTimes(_:)))
            clickTwice.numberOfClicksRequired = 2
            buttonNew.addGestureRecognizer(clickTwice)
            clickOnce.shouldBeRequiredToFailByGestureRecognizer(clickTwice)
            clickTwice.shouldBeRequiredToFailByGestureRecognizer(clickOnce)
            clickOnce.shouldRequireFailureOfGestureRecognizer(clickTwice)
            clickTwice.shouldRequireFailureOfGestureRecognizer(clickOnce)
            clickOnce.canPreventGestureRecognizer(clickTwice)
            clickOnce.canBePreventedByGestureRecognizer(clickTwice)
            clickTwice.canPreventGestureRecognizer(clickOnce)
            clickTwice.canBePreventedByGestureRecognizer(clickOnce)

            self.view.addSubview(buttonNew)
        }


    }

    func clickOneTime(g:NSClickGestureRecognizer){
        if g.state == .Ended {
            Swift.print("single click")
        }
    }
    func clickTwoTimes(g: NSClickGestureRecognizer){
        if g.state == .Ended {
            Swift.print("DOUBLE CLICK!")
        }
    }
    override var representedObject: AnyObject? {
        didSet {
        // Update the view, if already loaded.
        }
    }


}
我做错了什么?我想这个错误一定很简单,我不是从错误的地方打来的,就是有点像那样,但我不明白

以下是日志文件,对于所有组合都是相同的:

        clickOnce.shouldBeRequiredToFailByGestureRecognizer(clickTwice)
        clickTwice.shouldBeRequiredToFailByGestureRecognizer(clickOnce)
        clickOnce.shouldRequireFailureOfGestureRecognizer(clickTwice)
        clickTwice.shouldRequireFailureOfGestureRecognizer(clickOnce)
        clickOnce.canPreventGestureRecognizer(clickTwice)
        clickOnce.canBePreventedByGestureRecognizer(clickTwice)
        clickTwice.canPreventGestureRecognizer(clickOnce)
        clickTwice.canBePreventedByGestureRecognizer(clickOnce)
单击一次:

single click
果然

单击两次:

single click
DOUBLE CLICK!
它可以从单击和双击开始

我已经阅读了文件。我尝试了所有的组合,因为找不到解决方案


我也尝试过使用日志。所以,
Swift.print(clickOnce.should不需要人工智能手势识别器(ClickTworth))
和其中的一个,但是它给了我
false

也许你可以这样尝试,其中“按钮”是你的按钮

let doubleTapRecognizer = UITapGestureRecognizer(target: self, action: #selector(ViewController.clickTwoTimes(_:)))
let singleTapRecognizer = UITapGestureRecognizer(target: self, action: #selector(ViewController.clickOneTime(_:)))
singleTapRecognizer.numberOfTapsRequired = 1
doubleTapRecognizer.numberOfTapsRequired = 2
button.addGestureRecognizer(doubleTapRecognizer)
button.addGestureRecognizer(singleTapRecognizer)
singleTapRecognizer.requireGestureRecognizerToFail(doubleTapRecognizer)
试试这个:

let click = NSClickGestureRecognizer(target: self, action: #selector(clicked(_:))
click.numberOfClicksRequired = 2

我试图自己解决这个问题;事实证明,解决方案相对简单

使用手势识别器进行双击(在这里,我已经将它们添加到视图中,但相同的原则也适用于按钮)

然后通过

override func mouseDown(with event: NSEvent) {
    print("mouse down; once")
}
(或适当的等效物)

NSgestureRecognitor已启用

var delaysPrimaryMouseButtonEvents: Bool
默认情况下设置为true,因此使用此组合,它会等到DoubleClickRecognitor处理完双击后再进入响应器链,以查看还有谁对鼠标单击感兴趣

两个手势识别器与在mouseDown中处理单次和双击的问题相同:单次单击首先触发。为了克服这个问题,您需要覆盖

func gestureRecognizer(_ gestureRecognizer: NSGestureRecognizer, shouldRequireFailureOf otherGestureRecognizer: NSGestureRecognizer) -> Bool  
这不是您调用的函数,而是您重写的委托函数。因此,您将viewController设置为符合NSgestureRecognitizerDelegate(这意味着它将接收委托方法);设置singleClickRecognizer.delegate=self(self是您的viewController),并实现

func gestureRecognizer(_ gestureRecognizer: NSGestureRecognizer, shouldRequireFailureOf otherGestureRecognizer: NSGestureRecognizer) -> Bool {
    if gestureRecognizer == singleClickRecognizer && otherGestureRecognizer == doubleClickRecognizer {
        return true
    }
    return false
    }
这表示您的singleClickRecognizer在执行其选择器之前等待doubleClickRecognizer失败


不幸的是,我发现在SpriteKit中,虽然这段代码按照它在tin上所说的做了(首先双击),但它会导致不可接受的延迟,因此我不确定是否可以推荐它

您不能简单地将各种cod行混合在一起,并期望代码按预期运行。阅读您调用的每个方法的文档,并尝试找出哪个手势识别器可以以何种方式影响其他方法。您提到的示例是针对iOS而不是OS X的,因此用鼠标单击两次可能不会产生与用手指双击设备相同的效果。同样,“没有任何东西对我有用”也没有说明它是如何不起作用的,你应该在你的问题中解释一下。@luk2302我没有把它们都混合在一起,我只是尝试了所有的组合,并为brevityI发布了这样的代码。我怀疑你尝试了所有的组合,有2^8,也就是256个组合。请接受我的建议并阅读文档。@luk2302我已经阅读了文档,好的,我没有尝试所有256个组合,但我已经尝试了文档中似乎最符合逻辑的组合。一个接一个,全部。至少如果有一个组合可以工作的话,它会出现。这是iOS,我正在尝试为OSX找到解决方案。
func gestureRecognizer(_ gestureRecognizer: NSGestureRecognizer, shouldRequireFailureOf otherGestureRecognizer: NSGestureRecognizer) -> Bool {
    if gestureRecognizer == singleClickRecognizer && otherGestureRecognizer == doubleClickRecognizer {
        return true
    }
    return false
    }