UNPKG

@modern-js-reduck/react

Version:

The meta-framework suite designed from scratch for frontend-focused modern web development.

93 lines (92 loc) 2.47 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); Object.defineProperty(exports, "createBatchManager", { enumerable: true, get: () => createBatchManager }); const _store = require("@modern-js-reduck/store"); const _reactdom = require("react-dom"); const combineSubscribe = (store, subscribes) => { let changed = false; const handlers = /* @__PURE__ */ new Set(); return (handler) => { handlers.add(handler); const disposer = []; subscribes.forEach((subscribe) => { disposer.push(subscribe(() => { changed = true; })); }); const unsubscribeStore = store.subscribe(() => { if (changed) { handlers.forEach((h) => h()); } changed = false; }); return () => { unsubscribeStore(); disposer.forEach((dispose) => dispose()); }; }; }; const createBatchManager = (store) => { const usingModelsMap = /* @__PURE__ */ new Map(); let unsubscribe; const updateList = []; const setupSubscribe = () => { if (typeof unsubscribe === "function") { unsubscribe(); } const modelSet = /* @__PURE__ */ new Set(); for (const [model, count] of usingModelsMap) { if (count !== 0) { modelSet.add(model); } } const subscribe = combineSubscribe(store, [ ...modelSet ].map((m) => store.use(m)[2])); unsubscribe = subscribe(() => { (0, _reactdom.unstable_batchedUpdates)(() => { let update = updateList.shift(); while (update) { update(); update = updateList.shift(); } }); }); }; const changeModels = (action, ...models) => { models.forEach((model) => { if (!_store.utils.isModel(model)) { return; } let usingCount = usingModelsMap.get(model); if (action === "add") { usingModelsMap.set(model, (usingCount || 0) + 1); } else if (action === "remove") { if (usingCount) { usingCount -= 1; if (usingCount === 0) { usingModelsMap.delete(model); } else { usingModelsMap.set(model, usingCount); } } } }); setupSubscribe(); }; const addModels = (...args) => changeModels("add", ...args); const removeModels = (...args) => changeModels("remove", ...args); const pushUpdate = (update) => { updateList.push(update); }; return { addModels, removeModels, pushUpdate }; };