UNPKG

fluidstate

Version:

Library for fine-grained reactivity state management

236 lines (235 loc) 8.87 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.createReactiveSet = void 0; var _reactiveNames = require("../extras/reactive-names"); var _reactivePlugin = require("../extras/reactive-plugin"); var _reactiveAtom = require("../primitives/reactive-atom"); var _reactiveChildren = require("./reactive-children"); var _reactiveProxy = require("./reactive-proxy"); var _reactivePluginSet = require("../extras/reactive-plugin-set"); const createReactiveSet = (inertSet, reactiveOptions, nameOptions) => { const atomName = (0, _reactiveNames.createAtomNameFromOptions)(nameOptions); const proxy = new Proxy(inertSet, new ReactiveSetProxyHandler(new ReactiveSetOverrides(atomName, inertSet, { items: (0, _reactiveAtom.createAtom)((0, _reactiveNames.createSetAtomName)(atomName)) }, () => proxy, reactiveOptions))); return proxy; }; exports.createReactiveSet = createReactiveSet; class ReactiveSetProxyHandler { constructor(setOverrides) { this.setOverrides = setOverrides; } get(inertSet, property, receiver) { const ownPropertyDescriptor = Reflect.getOwnPropertyDescriptor(inertSet, property); const isInherited = Reflect.has(inertSet, property) && !ownPropertyDescriptor; if (isInherited && property in this.setOverrides) { return this.setOverrides[property]; } return Reflect.get(inertSet, property, receiver); } } class ReactiveSetOverrides { #atomName; #inertSet; #reactive; #getProxy; #options; constructor(atomName, inertSet, reactive, getProxy, reactiveOptions) { this.#atomName = atomName; this.#inertSet = inertSet; this.#reactive = reactive; this.#getProxy = getProxy; this.#options = { reactiveOptions }; } [Symbol.iterator] = () => { return this.#getSetValues(); }; entries = () => { return this.#entries(); }; keys = () => { return this.#getSetValues(); }; values = () => { return this.#getSetValues(); }; get [Symbol.toStringTag]() { return Set.prototype[Symbol.toStringTag]; } get size() { this.#reactive.items.reportObserved(); return this.#inertSet.size; } has = value => { const result = this.#hasStoredValue(this.#getStored(value)); this.#reactive.items.reportObserved(); return result; }; add = value => { const valueToStore = this.#getStored(value); const itemAlreadyExists = this.#hasStoredValue(valueToStore); const changes = !this.#hasPlugins() || itemAlreadyExists ? null : (0, _reactivePluginSet.getSetAddChanges)(this.#getProxy(), valueToStore); if (changes) { (0, _reactivePlugin.beforeChange)(changes, this.#options.reactiveOptions?.plugins); } Set.prototype.add.call(this.#inertSet, valueToStore); if (!itemAlreadyExists) { this.#reactive.items.reportChanged(); } if (changes) { (0, _reactivePlugin.afterChange)(changes, this.#options.reactiveOptions?.plugins); } return this; }; delete = value => { const valueToDelete = this.#getStored(value); const itemAlreadyExists = this.#hasStoredValue(valueToDelete); const changes = !this.#hasPlugins() || !itemAlreadyExists ? null : (0, _reactivePluginSet.getSetDeleteChanges)(this.#getProxy(), valueToDelete); if (changes) { (0, _reactivePlugin.beforeChange)(changes, this.#options.reactiveOptions?.plugins); } const resultStored = Set.prototype.delete.call(this.#inertSet, valueToDelete); const reactive = (0, _reactiveProxy.getReactive)(valueToDelete); const resultReactive = !!(reactive && Set.prototype.delete.call(this.#inertSet, reactive)); const result = resultStored || resultReactive; if (result) { this.#reactive.items.reportChanged(); } if (changes) { (0, _reactivePlugin.afterChange)(changes, this.#options.reactiveOptions?.plugins); } return result; }; clear = () => { const isAlreadyEmpty = this.#inertSet.size === 0; const changes = !this.#hasPlugins() || isAlreadyEmpty ? null : (0, _reactivePluginSet.getSetClearChanges)(this.#getProxy(), Array.from(this.#inertSet.values())); if (changes) { (0, _reactivePlugin.beforeChange)(changes, this.#options.reactiveOptions?.plugins); } Set.prototype.clear.call(this.#inertSet); if (!isAlreadyEmpty) { this.#reactive.items.reportChanged(); } if (changes) { (0, _reactivePlugin.afterChange)(changes, this.#options.reactiveOptions?.plugins); } }; forEach = (callbackfn, thisArg) => { try { const result = Set.prototype.forEach.call(this.#inertSet, (_value, key, set) => { const keyValue = (0, _reactiveChildren.getChild)(this.#options, key, () => (0, _reactiveProxy.createProxy)(key, (0, _reactiveChildren.getChildOptions)(this.#options), { parentAtomName: this.#atomName, createAtomName: _reactiveNames.createSetValueAtomName })); return callbackfn.call(this, keyValue, keyValue, set); }, thisArg); return result; } finally { this.#reactive.items.reportObserved(); } }; union = other => { try { return (0, _reactiveProxy.createProxy)(this.#inertSet.union(other), (0, _reactiveChildren.getChildOptions)(this.#options), { parentAtomName: this.#atomName, createAtomName: _reactiveNames.createSetTransformedAtomName }); } finally { this.#reactive.items.reportObserved(); } }; intersection = other => { try { return (0, _reactiveProxy.createProxy)(this.#inertSet.intersection(other), (0, _reactiveChildren.getChildOptions)(this.#options), { parentAtomName: this.#atomName, createAtomName: _reactiveNames.createSetTransformedAtomName }); } finally { this.#reactive.items.reportObserved(); } }; difference = other => { try { return (0, _reactiveProxy.createProxy)(this.#inertSet.difference(other), (0, _reactiveChildren.getChildOptions)(this.#options), { parentAtomName: this.#atomName, createAtomName: _reactiveNames.createSetTransformedAtomName }); } finally { this.#reactive.items.reportObserved(); } }; symmetricDifference = other => { try { return (0, _reactiveProxy.createProxy)(this.#inertSet.symmetricDifference(other), (0, _reactiveChildren.getChildOptions)(this.#options), { parentAtomName: this.#atomName, createAtomName: _reactiveNames.createSetTransformedAtomName }); } finally { this.#reactive.items.reportObserved(); } }; isSubsetOf = other => { (0, _reactiveProxy.getReactive)(other)?.size; try { return this.#inertSet.isSubsetOf((0, _reactiveProxy.ensureInert)(other)); } finally { this.#reactive.items.reportObserved(); } }; isSupersetOf = other => { (0, _reactiveProxy.getReactive)(other)?.size; try { return this.#inertSet.isSupersetOf((0, _reactiveProxy.ensureInert)(other)); } finally { this.#reactive.items.reportObserved(); } }; isDisjointFrom = other => { (0, _reactiveProxy.getReactive)(other)?.size; try { return this.#inertSet.isDisjointFrom((0, _reactiveProxy.ensureInert)(other)); } finally { this.#reactive.items.reportObserved(); } }; *#entries() { const result = Set.prototype.entries.call(this.#inertSet); this.#reactive.items.reportObserved(); for (const [key] of result) { const keyValue = (0, _reactiveChildren.getChild)(this.#options, key, () => (0, _reactiveProxy.createProxy)(key, (0, _reactiveChildren.getChildOptions)(this.#options), { parentAtomName: this.#atomName, createAtomName: _reactiveNames.createSetValueAtomName })); yield [keyValue, keyValue]; } } *#getSetValues() { const result = Set.prototype.values.call(this.#inertSet); this.#reactive.items.reportObserved(); for (const item of result) { yield (0, _reactiveChildren.getChild)(this.#options, item, () => (0, _reactiveProxy.createProxy)(item, (0, _reactiveChildren.getChildOptions)(this.#options), { parentAtomName: this.#atomName, createAtomName: _reactiveNames.createSetValueAtomName })); } } #getStored(value) { return this.#options.reactiveOptions?.deep === false ? value : (0, _reactiveProxy.ensureInert)(value); } #hasStoredValue(storedValue) { const hasStoredValueDirectly = Set.prototype.has.call(this.#inertSet, storedValue); if (hasStoredValueDirectly || this.#options.reactiveOptions?.deep === false) { return hasStoredValueDirectly; } const reactive = (0, _reactiveProxy.getReactive)(storedValue); return reactive && Set.prototype.has.call(this.#inertSet, reactive) || false; } #hasPlugins() { return (this.#options.reactiveOptions?.plugins?.length ?? 0) > 0; } } //# sourceMappingURL=reactive-set.js.map