Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit 0513789

Browse filesBrowse files
committed
fix: lazily bind context to removeEventListener callbacks
1 parent ab56e11 commit 0513789
Copy full SHA for 0513789

File tree

Expand file treeCollapse file tree

1 file changed

+13
-7
lines changed
Filter options
Expand file treeCollapse file tree

1 file changed

+13
-7
lines changed

‎packages/core/data/dom-events/dom-event.ts

Copy file name to clipboardExpand all lines: packages/core/data/dom-events/dom-event.ts
+13-7Lines changed: 13 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -306,7 +306,13 @@ export class DOMEvent implements Event {
306306
// the static method named `removeEventListener` on the target's class
307307
// allows us to be robust to the possiblity of the case of the target
308308
// overriding it (however unlikely).
309-
const removeGlobalEventListener = (target.constructor as unknown as typeof target).removeEventListener.bind(target.constructor) as Observable['removeEventListener'];
309+
//
310+
// Rather than eagerly binding the context to the function right here,
311+
// we pass the function along with its context to handleEvent() to allow
312+
// binding only once needed - doing this for each of the
313+
// removeEventListener callbacks saves 100 nanoseconds per dispatchTo()
314+
// call.
315+
const removeGlobalEventListener = (target.constructor as unknown as typeof target).removeEventListener as Observable['removeEventListener'];
310316

311317
// Global event handlers are a NativeScript-only concept, so we'll not
312318
// try to add new formal event phases for them (as that could break DOM
@@ -326,7 +332,7 @@ export class DOMEvent implements Event {
326332
// possible.
327333

328334
this.listenersLazyCopy = this.listenersLive = getGlobalEventHandlersPreHandling?.() || emptyArray;
329-
this.handleEvent(data, true, this.CAPTURING_PHASE, removeGlobalEventListener);
335+
this.handleEvent(data, true, this.CAPTURING_PHASE, removeGlobalEventListener, target.constructor);
330336

331337
const eventPath = this.getEventPath(target, 'capture');
332338

@@ -339,7 +345,7 @@ export class DOMEvent implements Event {
339345
this.eventPhase = this.target === this.currentTarget ? this.AT_TARGET : this.CAPTURING_PHASE;
340346

341347
this.listenersLazyCopy = this.listenersLive = currentTarget.getEventList(this.type) || emptyArray;
342-
this.handleEvent(data, false, this.CAPTURING_PHASE, currentTarget.removeEventListener.bind(currentTarget) as Observable['removeEventListener']);
348+
this.handleEvent(data, false, this.CAPTURING_PHASE, currentTarget.removeEventListener, currentTarget);
343349

344350
if (this.propagationState !== EventPropagationState.resume) {
345351
this.resetForRedispatch();
@@ -354,7 +360,7 @@ export class DOMEvent implements Event {
354360
this.eventPhase = this.target === this.currentTarget ? this.AT_TARGET : this.BUBBLING_PHASE;
355361

356362
this.listenersLazyCopy = this.listenersLive = currentTarget.getEventList(this.type) || emptyArray;
357-
this.handleEvent(data, false, this.BUBBLING_PHASE, currentTarget.removeEventListener.bind(currentTarget) as Observable['removeEventListener']);
363+
this.handleEvent(data, false, this.BUBBLING_PHASE, currentTarget.removeEventListener, currentTarget);
358364

359365
if (this.propagationState !== EventPropagationState.resume) {
360366
this.resetForRedispatch();
@@ -375,15 +381,15 @@ export class DOMEvent implements Event {
375381
}
376382

377383
this.listenersLazyCopy = this.listenersLive = getGlobalEventHandlersPostHandling?.() || emptyArray;
378-
this.handleEvent(data, true, this.BUBBLING_PHASE, removeGlobalEventListener);
384+
this.handleEvent(data, true, this.BUBBLING_PHASE, removeGlobalEventListener, target.constructor);
379385

380386
this.resetForRedispatch();
381387
return !this.defaultPrevented;
382388
}
383389

384390
// Taking multiple params instead of a single property bag saves 250
385391
// nanoseconds per dispatchTo() call.
386-
private handleEvent(data: EventData, isGlobal: boolean, phase: 0 | 1 | 2 | 3, removeEventListener: (eventName: string, callback?: any, thisArg?: any, capture?: boolean) => void) {
392+
private handleEvent(data: EventData, isGlobal: boolean, phase: 0 | 1 | 2 | 3, removeEventListener: (eventName: string, callback?: any, thisArg?: any, capture?: boolean) => void, removeEventListenerContext: unknown) {
387393
// Set a listener to clone the array just before any mutations.
388394
this.listenersLive.onMutation = this.onCurrentListenersMutation.bind(this);
389395

@@ -416,7 +422,7 @@ export class DOMEvent implements Event {
416422
}
417423

418424
if (once) {
419-
removeEventListener(this.type, callback, thisArg, capture);
425+
removeEventListener.call(removeEventListenerContext, this.type, callback, thisArg, capture);
420426
}
421427

422428
// Consistent with the original implementation, we only apply

0 commit comments

Comments
0 (0)
Morty Proxy This is a proxified and sanitized view of the page, visit original site.