MouseDown to Click

JavaScript

在日常的开发过程中,对于一个按钮或者链接,一般会附上一个 onClick 事件,以响应用户的点击操作。当用户实际按下按钮或链接之后,再通过 onClick 事件去触发之后要进行的流程(比如网络请求或是链接跳转等)。

如果对于用户操作后的反馈速度有一定的要求,这里的行为就需要进行优化。以链接为例,一个常见的操作方法是(比如 quicklink),用程序对可视范围内的链接地址进行预加载(使用 prefetch)。这样,当用户真正点击的时候,资源很可能已经得到了加载,打开速度就会显著提升。

当然,这样的行为是没有预判的,纯粹暴力的进行可能的预备操作。如果预备操作损耗较多,这样的操作就显得不方便了。

一个更加“智能”的操作是,仅当用户“点击”了之后才进行预加载。实际上,即使是一个点击的的操作,也会分成好几个不同的事件,包括 MouseDownMouseUpClick。在 MouseDownClick 之间,差着大约 100ms 的时间。

换句话说,如果在 MouseDown 的时候就开始预处理,等到 Click 时才真正进行加载,那么整体的加载时间会减少 100ms 左右。在某些情况下,这也是个不小的提升了。

可以用下面的这段代码实际测试一下,MouseDown 事件和 Click 事件之间的时间差(具体时间差因人而异):

const button = document.createElement('button');
button.textContent = 'Click Me';
button.onmousedown = function () { console.log(`Mousedown: ${Date.now()}`); };
button.onclick = function () { console.log(`Click: ${Date.now()}`); };
document.body.appendChild(button);

也可以直接点击下面这个按钮尝试:

当然,比这个略激进的操作,可以将 MouseDown 事件换成 MouseEnter 事件,这样在 Hover 的时候就会开始预加载。大概能提前 300ms 左右开始操作,当然存在一定的误判风险(比如用户只是划过了鼠标,并没有想要点击的意愿)。

可以参考 InstantClick 了解更多实现的细节。