Skip to content

Commit ff8fefb

Browse files
committed
refactor(core) simplify event manager routing
1 parent 09832dc commit ff8fefb

2 files changed

Lines changed: 47 additions & 51 deletions

File tree

modules/core/src/lib/view-manager.ts

Lines changed: 36 additions & 51 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,11 @@ export type ViewStateObject<ViewsT extends ViewOrViews> =
4040
/** Canvas id used by views that do not declare a presentation canvas. */
4141
export const DEFAULT_CANVAS_ID = 'default-canvas';
4242

43+
type ViewEventManager = {
44+
canvasId: string;
45+
eventManager: EventManager;
46+
};
47+
4348
/** ViewManager props directly supplied by the user */
4449
type ViewManagerProps<ViewsT extends ViewOrViews> = {
4550
views: ViewsT;
@@ -68,8 +73,7 @@ export default class ViewManager<ViewsT extends View[]> {
6873
private _needsUpdate: string | false;
6974
private _eventManager: EventManager;
7075
private _eventManagers: Record<string, EventManager>;
71-
private _previousEventManagers: Record<string, EventManager> | null;
72-
private _viewCanvasIds: {[viewId: string]: string};
76+
private _viewEventManagers: {[viewId: string]: ViewEventManager};
7377
private _eventCallbacks: {
7478
onViewStateChange?: (params: ViewStateChangeParameters) => void;
7579
onInteractionStateChange?: (state: InteractionState) => void;
@@ -99,8 +103,7 @@ export default class ViewManager<ViewsT extends View[]> {
99103

100104
this._eventManager = props.eventManager;
101105
this._eventManagers = props.eventManagers || {};
102-
this._previousEventManagers = null;
103-
this._viewCanvasIds = {};
106+
this._viewEventManagers = {};
104107
this._eventCallbacks = {
105108
onViewStateChange: props.onViewStateChange,
106109
onInteractionStateChange: props.onInteractionStateChange
@@ -202,7 +205,9 @@ export default class ViewManager<ViewsT extends View[]> {
202205
/** Return the presentation canvas id assigned to a view. */
203206
getCanvasId(viewOrViewId: string | View): string | undefined {
204207
const view = typeof viewOrViewId === 'string' ? this.getView(viewOrViewId) : viewOrViewId;
205-
return view ? view.props.canvasId || DEFAULT_CANVAS_ID : undefined;
208+
return view
209+
? this._viewEventManagers[view.id]?.canvasId || view.props.canvasId || DEFAULT_CANVAS_ID
210+
: undefined;
206211
}
207212

208213
/**
@@ -320,64 +325,45 @@ export default class ViewManager<ViewsT extends View[]> {
320325
}
321326

322327
private _setEventManagers(eventManagers: Record<string, EventManager>): void {
323-
if (this._eventManagers === eventManagers) {
324-
return;
325-
}
326-
327-
const eventManagerIds = Object.keys(eventManagers);
328-
const previousEventManagerIds = Object.keys(this._eventManagers);
329-
if (
330-
deepEqual(eventManagerIds, previousEventManagerIds, 1) &&
331-
eventManagerIds.every(id => eventManagers[id] === this._eventManagers[id])
332-
) {
333-
return;
328+
if (this._eventManagers !== eventManagers) {
329+
this._eventManagers = eventManagers;
330+
this.setNeedsUpdate('eventManagers changed');
334331
}
335-
336-
this._previousEventManagers ||= this._eventManagers;
337-
this._eventManagers = eventManagers;
338-
this.setNeedsUpdate('eventManagers changed');
339332
}
340333

341-
private _getEventManager(canvasId: string): EventManager {
342-
return this._eventManagers[canvasId] || this._eventManager;
334+
private _getViewEventManager(view: View): ViewEventManager {
335+
const canvasId = this.getCanvasId(view) || DEFAULT_CANVAS_ID;
336+
return {
337+
canvasId,
338+
eventManager: this._eventManagers[canvasId] || this._eventManager
339+
};
343340
}
344341

345342
private _startViewportRebuild(): {
346343
oldControllers: {[viewId: string]: Controller<any> | null};
347-
oldEventManagers: Record<string, EventManager>;
348-
oldViewCanvasIds: {[viewId: string]: string};
344+
oldViewEventManagers: {[viewId: string]: ViewEventManager};
349345
} {
350346
const oldControllers = this.controllers;
351-
const oldEventManagers = this._previousEventManagers || this._eventManagers;
352-
const oldViewCanvasIds = this._viewCanvasIds;
347+
const oldViewEventManagers = this._viewEventManagers;
353348
this._viewports = [];
354349
this.controllers = {};
355-
this._viewCanvasIds = {};
356-
this._previousEventManagers = null;
357-
return {oldControllers, oldEventManagers, oldViewCanvasIds};
358-
}
359-
360-
private _registerCanvasId(view: View): void {
361-
this._viewCanvasIds[view.id] = this.getCanvasId(view) || DEFAULT_CANVAS_ID;
350+
this._viewEventManagers = {};
351+
return {oldControllers, oldViewEventManagers};
362352
}
363353

364354
private _getReusableController(
365-
view: View,
366355
controller: Controller<any> | null | undefined,
367-
oldCanvasId: string | undefined,
368-
oldEventManagers: Record<string, EventManager>
356+
oldViewEventManager: ViewEventManager | undefined,
357+
viewEventManager: ViewEventManager
369358
): Controller<any> | null | undefined {
370-
if (!controller) {
371-
return controller;
372-
}
373-
374-
const canvasId = this.getCanvasId(view) || DEFAULT_CANVAS_ID;
375-
const oldEventManager = (oldCanvasId && oldEventManagers[oldCanvasId]) || this._eventManager;
376-
if (oldCanvasId !== canvasId || oldEventManager !== this._getEventManager(canvasId)) {
359+
if (
360+
controller &&
361+
(oldViewEventManager?.canvasId !== viewEventManager.canvasId ||
362+
oldViewEventManager?.eventManager !== viewEventManager.eventManager)
363+
) {
377364
controller.finalize();
378365
return null;
379366
}
380-
381367
return controller;
382368
}
383369

@@ -386,11 +372,10 @@ export default class ViewManager<ViewsT extends View[]> {
386372
props: {id: string; type: ConstructorOf<Controller<any>>}
387373
): Controller<any> {
388374
const Controller = props.type;
389-
const canvasId = this.getCanvasId(view) || DEFAULT_CANVAS_ID;
390375

391376
const controller = new Controller({
392377
timeline: this.timeline,
393-
eventManager: this._getEventManager(canvasId),
378+
eventManager: this._getViewEventManager(view).eventManager,
394379
// Set an internal callback that calls the prop callback if provided
395380
onViewStateChange: this._eventCallbacks.onViewStateChange,
396381
onStateChange: this._eventCallbacks.onInteractionStateChange,
@@ -441,21 +426,21 @@ export default class ViewManager<ViewsT extends View[]> {
441426
private _rebuildViewports(): void {
442427
const {views} = this;
443428

444-
const {oldControllers, oldEventManagers, oldViewCanvasIds} = this._startViewportRebuild();
429+
const {oldControllers, oldViewEventManagers} = this._startViewportRebuild();
445430

446431
let invalidateControllers = false;
447432
// Create controllers in reverse order, so that views on top receive events first
448433
for (let i = views.length; i--; ) {
449434
const view = views[i];
450-
this._registerCanvasId(view);
435+
const viewEventManager = this._getViewEventManager(view);
436+
this._viewEventManagers[view.id] = viewEventManager;
451437
const viewState = this.getViewState(view);
452438
const viewport = view.makeViewport({viewState, width: this.width, height: this.height});
453439

454440
let oldController = this._getReusableController(
455-
view,
456441
oldControllers[view.id],
457-
oldViewCanvasIds[view.id],
458-
oldEventManagers
442+
oldViewEventManagers[view.id],
443+
viewEventManager
459444
);
460445
const hasController = Boolean(view.controller);
461446
if (hasController && !oldController) {

test/modules/core/lib/view-manager.spec.ts

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -245,7 +245,18 @@ test('ViewManager#routes controllers by canvas event manager', () => {
245245
expect((viewManager.controllers.left as any).eventManager).toBe(leftEventManager);
246246
expect((viewManager.controllers.right as any).eventManager).toBe(rightEventManager);
247247

248+
const originalLeftController = viewManager.controllers.left;
248249
const originalRightController = viewManager.controllers.right;
250+
viewManager.setProps({
251+
eventManagers: {
252+
'left-canvas': leftEventManager,
253+
'right-canvas': rightEventManager
254+
}
255+
});
256+
257+
expect(viewManager.controllers.left).toBe(originalLeftController);
258+
expect(viewManager.controllers.right).toBe(originalRightController);
259+
249260
viewManager.setProps({
250261
eventManagers: {
251262
'left-canvas': leftEventManager,

0 commit comments

Comments
 (0)