@dark-engine/core
Version:
The lightweight and powerful UI rendering engine without dependencies and written in TypeScript (Browser, Node.js, Android, iOS, Windows, Linux, macOS)
104 lines (103 loc) • 3.14 kB
JavaScript
;
Object.defineProperty(exports, '__esModule', { value: true });
exports.notifyParents =
exports.createLoc =
exports.createHookLoc =
exports.resolveBoundary =
exports.resolveSuspense =
exports.detectIsFiberAlive =
exports.getFiberWithElement =
exports.collectElements =
exports.walk =
void 0;
const constants_1 = require('../constants');
function walk(fiber, onWalk) {
let shouldDeep = true;
let shouldStop = false;
const skip = () => (shouldDeep = false);
const stop = () => (shouldStop = true);
const stack = [fiber];
while (stack.length !== 0) {
const unit = stack.pop();
onWalk(unit, skip, stop);
if (shouldStop) break;
unit !== fiber && unit.next && stack.push(unit.next);
shouldDeep && unit.child && stack.push(unit.child);
shouldDeep = true;
}
}
exports.walk = walk;
function collectElements(fiber, transform) {
const elements = [];
walk(fiber, onWalkInCollectElements(elements, transform));
return elements;
}
exports.collectElements = collectElements;
function onWalkInCollectElements(elements, transform) {
return (fiber, skip) => {
if (fiber.el) {
!fiber.hook?.getIsPortal() && elements.push(transform(fiber));
return skip();
}
};
}
function getFiberWithElement(fiber) {
let $fiber = fiber;
while ($fiber) {
if ($fiber.el) return $fiber;
$fiber = $fiber.parent;
}
return $fiber;
}
exports.getFiberWithElement = getFiberWithElement;
function detectIsFiberAlive(fiber) {
let $fiber = fiber;
while ($fiber) {
if ($fiber.tag === constants_1.DELETE_EFFECT_TAG) return false;
$fiber = $fiber.parent;
}
return Boolean(fiber);
}
exports.detectIsFiberAlive = detectIsFiberAlive;
function getSuspense(fiber, isPending) {
let suspense = fiber;
while (suspense) {
if (suspense.hook?.getIsSuspense() && (isPending ? suspense.hook.getIsPending() : true)) return suspense;
suspense = suspense.parent;
}
return null;
}
function resolveSuspense(fiber) {
return getSuspense(fiber, true) || getSuspense(fiber, false) || null;
}
exports.resolveSuspense = resolveSuspense;
function resolveBoundary(fiber) {
let boundary = fiber;
while (boundary) {
if (boundary.hook?.getIsBoundary()) return boundary;
boundary = boundary.parent;
}
return null;
}
exports.resolveBoundary = resolveBoundary;
function createHookLoc(rootId, idx, hook) {
const fiber = hook.owner;
let $fiber = fiber;
let loc = `${fiber.idx}${constants_1.HOOK_DELIMETER}${idx}`;
while ($fiber) {
$fiber = $fiber.parent;
$fiber && (loc = `${$fiber.idx}.${loc}`);
}
loc = `[${rootId}]${loc}`;
return loc;
}
exports.createHookLoc = createHookLoc;
const createLoc = (rootId, idx, hook) => () => createHookLoc(rootId, idx, hook);
exports.createLoc = createLoc;
function notifyParents(fiber, alt = fiber) {
fiber.increment(alt.el ? 1 : alt.cec);
alt.mask & constants_1.EFFECT_HOST_MASK && fiber.markHost(constants_1.EFFECT_HOST_MASK);
alt.mask & constants_1.CLEANUP_HOST_MASK && fiber.markHost(constants_1.CLEANUP_HOST_MASK);
}
exports.notifyParents = notifyParents;
//# sourceMappingURL=walk.js.map