mousedown/mouseup/click执行顺序

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了mousedown/mouseup/click执行顺序相关的知识,希望对你有一定的参考价值。

参考技术A 一般情况下执行顺序是从左到右。有时需要解决mousedown和click冲突的事件。下面是一个网友的解决办法:

之前做项目遇到同一个dom上要同时绑定单击和mousedown事件, 然后就发现冲突了,总是先执行mousedown事件,click时间不会被执行。因为想要click的时候必然先mousedown,所以……
后来通过setTimeout解决了此冲突,简单总结demo如下:

<!DOCTYPE html>
<html>
<head>
<title></title>
</head>
<style type="text/css">
div
width:100px;
height:100px;
background:green;

</style>
<body>
<div class="demo"></div>
</body>
</html>
<script src="http://cdn.static.runoob.com/libs/jquery/1.10.2/jquery.min.js"></script>
<script type="text/javascript">
$(document).ready(function()
var down=null;
var mouse=false;
$('.demo').mousedown(function()
clearTimeout(down);
down=setTimeout(function()
mouse=true;
console.log('鼠标按下了');
,200);
);
$('.demo').click(function()
clearTimeout(down);//要清除down事件,否则在执行了click事件之后,会接着执行mousedown事件
if(!mouse)
console.log('被点击了');
else
mouse=false;

);
);
</script>

以下是我在Chrome里查看执行顺序时的情况。点击一下后的执行顺序。

NSButton mouseDown mouseUp 在启用时表现不同

【中文标题】NSButton mouseDown mouseUp 在启用时表现不同【英文标题】:NSButton mouseDown mouseUp behaving differently on enabled 【发布时间】:2014-03-13 20:04:05 【问题描述】:

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

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

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


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

为什么会有不同的行为,以及如何强制正确的行为(与未启用按钮时相同)

【问题讨论】:

【参考方案1】:

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

- (void)mouseDown:(NSEvent *)theEvent 
    NSLog(@"mouse down!");
    [super mouseDown:theEvent];
    NSLog(@"mouse up!");

【讨论】:

如何在 Swift 中编写 [super mouseDown:theEvent]?我需要做同样的事情,但在 Swift 中,我没有在我的覆盖有趣的 mouseDown 中获得 mouseDown 事件? @NealDavis 在 Swift 你这样写:super.mouseDown(theEvent) 如果您想让 mouseUp 功能在释放鼠标时实际运行,这是不正确的。这只是在 mouseDown 上调用 NSLog(@"mouse up!")【参考方案2】:

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

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

见Cocoa Event Handling Guide: Handling Mouse Events – Handling Mouse Dragging Operations – The Mouse-Tracking Loop Approach。

【讨论】:

让我烦恼的是 isEnabled 为 YES 和 NO 时的不同行为 当按钮被禁用时,它不需要做内部鼠标跟踪循环。【参考方案3】:

如果希望创建一个自定义按钮,其动作方法可以区分按下和释放,则要从前一个中删除,请尝试向其添加属性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方法中,可以查询isPressed。例如:

int state = (int)[sender isPressed];

其中一个烦人但无害的“功能”是在释放按钮时会调用两次操作方法:一次来自NSButton 内部,isPressed 仍然正确。 (这应该被忽略。)第二次来自自定义按钮的performSelector 方法,isPressed false。

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

【讨论】:

【参考方案4】:

在其他的基础上,这是一个与 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
        
    

【讨论】:

以上是关于mousedown/mouseup/click执行顺序的主要内容,如果未能解决你的问题,请参考以下文章

如何检索 mousedown 到 mouseup 事件之间的所有鼠标坐标

NSButton mouseDown mouseUp 在启用时表现不同

使用 MouseUp 和 MouseDown 事件或其他方式模拟单击的最佳方法是啥?

在jQuery中同时拥有mousedown / mouseup和dblclick

在 Tampermonkey 中模拟 mousedown、click、mouseup 序列?

如何在 mousedown 元素之外捕获 mouseup 事件? (即正确的拖放?)