Hi Dom,
First of all kudos on the lib! Looks really nice!
I looked at the code and there was one thing I noticed. You use the auditTime
operator to wait 16ms before updating for example the selectedItems
or the selectBox
. This way, Angular will only update the UI every 16ms which makes sense, 60FPS ftw.
I was just wondering if it would make even more sense to hook the updates you want to do into the requestAnimationFrame
hook. Using the subscribeOn
operator this should be fairly easy. You could update your code from:
selectBox$.pipe(
auditTime(AUDIT_TIME),
withLatestFrom(mousemove$, ...),
filter(() => this.selectOnDrag),
filter(({ selectBox }) => selectBox.width > MIN_WIDTH || selectBox.height > MIN_HEIGHT),
tap(({ selectBox, event }) => this.selectItems(selectBox, event)),
takeUntil(this.destroy$)
).subscribe();
to
selectBox$.pipe(
auditTime(AUDIT_TIME),
withLatestFrom(mousemove$, ...)
filter(() => this.selectOnDrag),
filter(({ selectBox }) => selectBox.width > MIN_WIDTH || selectBox.height > MIN_HEIGHT),
tap(({ selectBox, event }) => this.selectItems(selectBox, event)),
takeUntil(this.destroy$),
subscribeOn(animationFrame),
).subscribe();
By adding the subscribeOn(animationFrame)
, RxJS will schedule this execution to be run as a callback in the requestAnimationFrame
and thus just before repainting. I'm not 100% sure if this makes absolute sense in the context of Angular, since you would only update properties on the scope of your component and it still Angular that needs to update the DOM.
But since zone.js monkey-patches requestAnimationFrame
, Angular will run CD on this hook so I guess it makes sense.
As I am not 100% sure, any feedback, input is more than welcome.
If we can agree this could enhance the library, I'd be happy to create a PR.
Let me know what you think :)