Skip to content

Commit 33ba0e3

Browse files
authored
fix(runtime-dom): fix event listeners call in firefox <= 53 (#3501)
fix #3485
1 parent 42b68c7 commit 33ba0e3

File tree

1 file changed

+19
-13
lines changed

1 file changed

+19
-13
lines changed

packages/runtime-dom/src/modules/events.ts

+19-13
Original file line numberDiff line numberDiff line change
@@ -15,18 +15,23 @@ type EventValue = Function | Function[]
1515
// Async edge case fix requires storing an event listener's attach timestamp.
1616
let _getNow: () => number = Date.now
1717

18-
// Determine what event timestamp the browser is using. Annoyingly, the
19-
// timestamp can either be hi-res (relative to page load) or low-res
20-
// (relative to UNIX epoch), so in order to compare time we have to use the
21-
// same timestamp type when saving the flush timestamp.
22-
if (
23-
typeof document !== 'undefined' &&
24-
_getNow() > document.createEvent('Event').timeStamp
25-
) {
26-
// if the low-res timestamp which is bigger than the event timestamp
27-
// (which is evaluated AFTER) it means the event is using a hi-res timestamp,
28-
// and we need to use the hi-res version for event listeners as well.
29-
_getNow = () => performance.now()
18+
let skipTimestampCheck = false
19+
20+
if (typeof window !== 'undefined') {
21+
// Determine what event timestamp the browser is using. Annoyingly, the
22+
// timestamp can either be hi-res (relative to page load) or low-res
23+
// (relative to UNIX epoch), so in order to compare time we have to use the
24+
// same timestamp type when saving the flush timestamp.
25+
if (_getNow() > document.createEvent('Event').timeStamp) {
26+
// if the low-res timestamp which is bigger than the event timestamp
27+
// (which is evaluated AFTER) it means the event is using a hi-res timestamp,
28+
// and we need to use the hi-res version for event listeners as well.
29+
_getNow = () => performance.now()
30+
}
31+
// #3485: Firefox <= 53 has incorrect Event.timeStamp implementation
32+
// and does not fire microtasks in between event propagation, so safe to exclude.
33+
const ffMatch = navigator.userAgent.match(/firefox\/(\d+)/i)
34+
skipTimestampCheck = !!(ffMatch && Number(ffMatch[1]) <= 53)
3035
}
3136

3237
// To avoid the overhead of repeatedly calling performance.now(), we cache
@@ -111,7 +116,8 @@ function createInvoker(
111116
// and the handler would only fire if the event passed to it was fired
112117
// AFTER it was attached.
113118
const timeStamp = e.timeStamp || _getNow()
114-
if (timeStamp >= invoker.attached - 1) {
119+
120+
if (skipTimestampCheck || timeStamp >= invoker.attached - 1) {
115121
callWithAsyncErrorHandling(
116122
patchStopImmediatePropagation(e, invoker.value),
117123
instance,

0 commit comments

Comments
 (0)