63

JavaScript 中处理事件的优先顺序是什么?

以下是按字母顺序排列的事件...

  1. onabort - 图像加载中断
  2. onblur - 元素失去焦点
  3. onchange - 用户更改字段的内容
  4. onclick - 鼠标点击一个对象
  5. ondblclick - 鼠标双击一个对象
  6. onerror - 加载文档或图像时发生错误
  7. onfocus - 元素获得焦点
  8. onkeydown - 按下键盘键
  9. onkeypress - 按下或按住键盘键
  10. onkeyup - 释放键盘键
  11. onload - 页面或图像已完成加载
  12. onmousedown - 按下鼠标按钮
  13. onmousemove - 鼠标移动
  14. onmouseout - 鼠标从元素上移开
  15. onmouseover - 鼠标移到一个元素上
  16. onmouseup - 释放鼠标按钮
  17. onreset - 单击重置按钮
  18. onresize - 调整窗口或框架的大小
  19. onselect - 文本被选中
  20. onsubmit - 单击提交按钮
  21. onunload - 用户退出页面

他们在事件队列中的处理顺序是什么?

我相信优先级不是先进先出(FIFO)。

4

4 回答 4

39

据我所知,这在过去没有明确定义。不同的浏览器可以自由地实现它们认为合适的事件排序。虽然大多数情况对于所有实际目的来说都足够接近,但已经存在并且继续存在一些奇怪的边缘情况,其中浏览器有所不同(当然,更多的情况是某些浏览器根本无法发送某些事件)。

也就是说,HTML 5 草案建议确实尝试指定事件将如何排队和分派 -事件循环

为了协调事件、用户交互、脚本、渲染、网络等,用户代理必须使用本节中描述的事件循环。

每个用户代理必须至少有一个事件循环,并且每个相关的同源浏览上下文单元最多有一个事件循环。

一个事件循环有一个或多个任务队列。任务队列是任务的有序列表 [...] 当用户代理要对任务进行排队时,它必须将给定任务添加到相关事件循环的任务队列之一。来自一个特定任务源的所有任务必须始终添加到同一个任务队列中,但来自不同任务源的任务可能被放置在不同的任务队列中。[...]

[...]用户代理可以有一个用于鼠标和按键事件的任务队列(用户交互任务源),另一个用于其他所有事件。然后,用户代理可以在四分之三的时间内将键盘和鼠标事件优先于其他任务,保持界面响应但不会饿死其他任务队列,并且永远不会无序地处理来自任何一个任务源的事件。[...]

请注意最后一点:由浏览器实现决定哪些事件将被组合在一起并按顺序处理,以及赋予任何特定类型事件的优先级。因此,几乎没有理由期望所有浏览器都以固定顺序调度所有事件,无论是现在还是将来。

于 2008-11-11T21:55:25.247 回答
24

对于任何想知道调用顺序相关事件的人,请参见下文。到目前为止,我只在 Chrome 中进行了测试。

  1. 鼠标移到
  2. 鼠标移动
  3. 鼠标移出

  1. 鼠标按下
  2. 改变(聚焦输入)
  3. 模糊(在焦点元素上)
  4. 重点
  5. mouseup
  6. 点击
  7. dblclick

  1. 按键
  2. 按键
  3. 键位
于 2016-06-08T06:06:13.537 回答
5

如果您正在查看鼠标/触摸事件,Patrick H. Lauke 发表了关于该主题的演讲。绝对是一本有趣的读物——涉及不同浏览器、不同设备和不同标准的所有怪癖。

他还捆绑了一套全面的测试

于 2014-10-09T13:56:19.370 回答
2

这是一些事件的演示:

<input  onclick="console.log('onclick - Mouse clicks an object')" 
     ondblclick="console.log('ondblclick - Mouse double-clicks an object')"
    onmousedown="console.log('onmousedown - A mouse button is pressed')"
      onmouseup="console.log('onmouseup - A mouse button is released')"
    onmousemove="console.log('onmousemove - The mouse is moved')"
   onmouseenter="console.log('onmousenter - The mouse is moved over an element (not bubbling)')"
    onmouseover="console.log('onmouseover - The mouse is moved over an element')"
     onmouseout="console.log('onmouseout - The mouse is moved off an element')"
   onmouseleave="console.log('onmouseout - The mouse is moved off an element (not bubbling)')"
       onchange="console.log('onchange - The user changes the content of a field')"
      onfocusin="console.log('onfocusin - An element gets focus')"
        onfocus="console.log('onfocus - An element gets focus (not bubbling)')"
      onkeydown="console.log('onkeydown - A keyboard key is pressed')"
     onkeypress="console.log('onkeypress - A keyboard key is pressed or held down')"
onselectionchange="console.log('onselectionchange - The caret position changed')"
        onkeyup="console.log('onkeyup - A keyboard key is released')"
       onselect="console.log('onselect - Text is selected')"
     onfocusout="console.log('onfocusout - Loosing focus')"
         onblur="console.log('onblur - Loosing focus (not bubbling)')"
   ontouchstart="console.log('ontouchstart')"
    ontouchmove="console.log('ontouchmove')"
     ontouchend="console.log('ontouchend')"
  ontouchcancel="console.log('ontouchcancel')"
    placeholder="edit me"
/>

我注意到之前在 chrome/firefox 桌面上onselectionchange触发过onkey,而在 android chrome 上则相反。

https://jsfiddle.net/yv8zg5d1

于 2021-10-03T23:18:49.493 回答