13

如果 NSButton 未启用,则 mouseDown: 和 mouseUp: 行为正常(因此当鼠标按下时,mouseDown: 被调用,当它被释放时,mouseUp: 被调用)

但是,如果启用了 NSButton,则根本不会调用 mouseUp:,而在释放鼠标后会调用 mouseDown:

- (void)mouseDown:(NSEvent *)theEvent {
    [super mouseDown:theEvent];
}

- (void)mouseUp:(NSEvent *)theEvent {
    [super mouseUp:theEvent];
}

为什么这种行为不同,我如何强制正确的行为(与未启用按钮时相同)

4

4 回答 4

16

如果有人还在寻找这个......我不知道为什么,但这对我有用......

- (void)mouseDown:(NSEvent *)theEvent {
    NSLog(@"mouse down!");
    [super mouseDown:theEvent];
    NSLog(@"mouse up!");
}
于 2014-11-30T17:58:37.447 回答
9

行为是正确的。您期望所有鼠标向上事件都通过响应者方法是错误的。

当按钮被启用时,超类实现-mouseDown:将运行一个内部事件跟踪循环来跟踪鼠标的移动,只要鼠标在它里面就显示按钮被按下,当鼠标移出时显示它没有被按下。这个内部事件循环是接收NSLeftMouseUp事件的地方。它永远不会分派给响应者方法。

请参阅Cocoa 事件处理指南:处理鼠标事件 - 处理鼠标拖动操作 - 鼠标跟踪循环方法

于 2014-03-13T21:11:41.893 回答
6

如果希望创建一个自定义按钮,该按钮的操作方法可以区分按下和释放,请尝试将属性添加isPressed到其中,并添加以下代码:

 (void)mouseDown:(NSEvent *)event
 {
    self.isPressed = true;  
    [super mouseDown:event];

    self.isPressed = false;

    [self.target performSelector:self.action withObject:self];
}

自定义按钮必须设置为发送操作:

[self.button sendActionOn: NSLeftMouseDownMask | NSLeftMouseUpMask];

没有这个,在按钮被释放之前不会调用 action 方法。

在action方法中,isPressed可以查询。例如:

int state = (int)[sender isPressed];

一个烦人但无害的“功能”是当按钮被释放时动作方法被调用两次:一次从内部调用NSButtonisPressed仍然为真。(这应该被忽略。)第二次来自自定义按钮的performSelector方法,为isPressedfalse。

关于这是否可能适用于未来版本的任何评论?

于 2016-02-13T15:19:08.897 回答
1

在其他的基础上,这是一个与 Apple 文档中的 NSButton 子类中的 Objective-C 鼠标跟踪循环并行工作的 Swift。我们的代码保留事件而不是将它们传递给超类及其事件循环。

override func mouseDown(theEvent: NSEvent) {
    var isInside: Bool = true
    Swift.print( "MyButton Mouse Down" )

    self.highlighted = isInside
    while true {
        let event = self.window?.nextEventMatchingMask(
            Int(NSEventMask.LeftMouseUpMask.union(.LeftMouseDraggedMask).rawValue))
        let mouseLoc = self.convertPoint((event?.locationInWindow)!, toView: nil)
        isInside = CGRectContainsPoint(self.bounds, mouseLoc)
        if event?.type == .LeftMouseDragged {
            self.highlighted = isInside
        }
        else if event?.type == .LeftMouseUp {
            self.highlighted = false
            if isInside {
                Swift.print( "MyButton Mouse Up" )
            }
            break
        }
    }
于 2016-05-06T00:09:21.170 回答