Swift 5-Mac OS-NSTrackingArea重叠视图

Swift 5-Mac OS-NSTrackingArea重叠视图,swift,macos,nsview,nsbutton,nstrackingarea,Swift,Macos,Nsview,Nsbutton,Nstrackingarea,目前,当涉及到按钮(NSButton)时,我有一个小问题,这些按钮上方有跟踪区域和视图(NSView覆盖),这是我的设置: 自定义按钮: class AppButton: NSButton { override func updateTrackingAreas() { super.updateTrackingAreas() let area = NSTrackingArea( rect: self.bounds,

目前,当涉及到按钮(
NSButton
)时,我有一个小问题,这些按钮上方有跟踪区域和视图(
NSView
覆盖),这是我的设置:

自定义按钮:

class AppButton: NSButton {
    override func updateTrackingAreas() {
        super.updateTrackingAreas()
        let area = NSTrackingArea(
            rect: self.bounds,
            options: [.mouseEnteredAndExited, .activeAlways],
            owner: self,
            userInfo: nil
        )
        self.addTrackingArea(area)
    }
    override func mouseEntered(with event: NSEvent) {
        NSCursor.pointingHand.set()
    }
    override func mouseExited(with event: NSEvent) {
        NSCursor.arrow.set()
    }
    required init?(coder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }
}
此按钮类的一个实例用于非常基本的
NSView

当我将鼠标悬停在按钮上时,光标将正确更改

当我单击按钮时,按钮上方会打开一个新的覆盖(
NSView

这就是问题的根源:

当我将鼠标悬停在按钮所在的覆盖层上时,光标仍会发生变化

我不知道一个
NSTrackingArea
正在浏览所有视图

我如何解决这个问题

我可以在覆盖(
NSView
)上设置任何属性,以某种方式禁用按钮上的
NSTrackingArea


谢谢

您可以子类化
NSView
并添加事件的本地监视。检查事件是否在视图上发生,如果为true,则返回nil。这将避免传播正在监视的事件。如果事件在图幅之外,则可以正常传播它,并返回监视的事件

class CustomView: NSView {
    override func viewWillMove(toSuperview newSuperview: NSView?) {
        super.viewWillMove(toSuperview: newSuperview)
        wantsLayer = true
        layer?.backgroundColor = NSColor.windowBackgroundColor.cgColor
        layer?.borderWidth = 1
        NSEvent.addLocalMonitorForEvents(matching: [.mouseEntered, .mouseExited, .leftMouseDown]) { event in
            if self.frame.contains(event.locationInWindow) {
                // if cursor is over the view just return nil to do not propagate the events
                return nil
            }
            return event
        }
    }
}

当我使用这种方法并在覆盖中的某个位置放置按钮时,我无法单击该按钮。。有什么建议吗?如果事件的位置在按钮上方,您可以传播
leftMouseDown
事件。如果您想知道该事件是否为
leftMouseDown
事件,则只需检查其
type
属性。请注意,这是为了避免单击视图后面的按钮