malevic
Version:
Malevič.js - minimalistic reactive UI library
49 lines (46 loc) • 1.47 kB
JavaScript
/* malevic@0.20.2 - Aug 10, 2024 */
import { getContext } from 'malevic/dom';
let currentUseStateFn = null;
function useState(initialState) {
if (!currentUseStateFn) {
throw new Error('`useState()` should be called inside a component');
}
return currentUseStateFn(initialState);
}
function withState(type) {
const Stateful = (props, ...children) => {
const context = getContext();
const useState = (initial) => {
if (!context) {
return { state: initial, setState: null };
}
const { store, refresh } = context;
store.state = store.state || initial;
const setState = (newState) => {
if (lock) {
throw new Error('Setting state during unboxing causes infinite loop');
}
store.state = Object.assign(Object.assign({}, store.state), newState);
refresh();
};
return {
state: store.state,
setState,
};
};
let lock = true;
const prevUseStateFn = currentUseStateFn;
currentUseStateFn = useState;
let result;
try {
result = type(props, ...children);
}
finally {
currentUseStateFn = prevUseStateFn;
lock = false;
}
return result;
};
return Stateful;
}
export { useState, withState };