From ad948bdbe2450f4ec1088b5e13e0ae4f9548222e Mon Sep 17 00:00:00 2001 From: paweldomas Date: Wed, 15 Jul 2020 13:22:56 -0500 Subject: [PATCH] feat(StateListenerRegistry): add 'deepEquals' option Adds an extra 'options' argument to the register method which allows to use deep equality instead of a shallow one when comparing the current and the previous selections. --- .../base/redux/StateListenerRegistry.js | 28 +++++++++++++++++-- 1 file changed, 25 insertions(+), 3 deletions(-) diff --git a/react/features/base/redux/StateListenerRegistry.js b/react/features/base/redux/StateListenerRegistry.js index cc68decbf..6ae1abf3c 100644 --- a/react/features/base/redux/StateListenerRegistry.js +++ b/react/features/base/redux/StateListenerRegistry.js @@ -2,6 +2,7 @@ import type { Store } from 'redux'; +import { equals } from './functions'; import logger from './logger'; /** @@ -37,6 +38,18 @@ type Listener */ type Selector = (state: Object, prevSelection: any) => any; +/** + * Options that can be passed to the register method. + */ +type RegistrationOptions = { + + /** + * @property {boolean} [deepEquals=false] - whether or not a deep equals check should be performed on the selection + * returned by {@link Selector}. + */ + deepEquals: ?boolean +} + /** * A type of a {@link Selector}-{@link Listener} association in which the * {@code Listener} listens to changes in the values derived from a redux @@ -50,6 +63,11 @@ type SelectorListener = { */ listener: Listener, + /** + * The {@link RegistrationOptions} passed during the registration to be applied on the listener. + */ + options: ?RegistrationOptions, + /** * The {@code Selector} which selects values whose changes are listened to * by {@link listener}. @@ -94,8 +112,10 @@ class StateListenerRegistry { = selectorListener.selector( store.getState(), prevSelection); + const useDeepEquals = selectorListener?.options?.deepEquals; - if (prevSelection !== selection) { + if ((useDeepEquals && !equals(prevSelection, selection)) + || (!useDeepEquals && prevSelection !== selection)) { prevSelections.set(selectorListener, selection); selectorListener.listener(selection, store, prevSelection); } @@ -117,12 +137,14 @@ class StateListenerRegistry { * @param {Function} listener - The listener to register with this * {@code StateListenerRegistry} so that it gets invoked when the value * returned by the specified {@code selector} changes. + * @param {RegistrationOptions} [options] - Any options to be applied to the registration. * @returns {void} */ - register(selector: Selector, listener: Listener) { + register(selector: Selector, listener: Listener, options: ?RegistrationOptions) { this._selectorListeners.add({ listener, - selector + selector, + options }); }