diff --git a/src/index.html b/src/index.html index 0631323..3bd6937 100644 --- a/src/index.html +++ b/src/index.html @@ -23932,25 +23932,31 @@ function _bookCollectThreadChain(layer) { // Walk backwards to the head, then forward to the tail. // Returns layers in flow order (head → ... → tail). - const seen = new Set(); - // Backwards: find the layer whose nextFrame.frameId equals - // current.frameId; loop until none exists. + // + // Bug fix: each walk needs its OWN seen-set. Sharing seen + // between backward and forward walks meant the forward walk + // tripped its cycle guard on the middle frames the backward + // walk had already visited. A → B → C starting from C would + // walk back through B + A (seen={B,A}), then the forward walk + // from A would find B in `seen` and break — returning chain + // [A] instead of [A, B, C]. let head = layer; + const seenBack = new Set([layer.id]); let guard = 0; while (guard++ < 1000) { const prev = _findBookFrameLayer(o => o !== head && o.nextFrame?.frameId === head.frameId); - if (!prev || seen.has(prev.id)) break; - seen.add(prev.id); + if (!prev || seenBack.has(prev.id)) break; + seenBack.add(prev.id); head = prev; } const chain = [head]; - seen.add(head.id); + const seenFwd = new Set([head.id]); let cursor = head; guard = 0; while (cursor.nextFrame?.frameId && guard++ < 1000) { const nxt = _findBookFrameLayer(o => o.frameId === cursor.nextFrame.frameId); - if (!nxt || seen.has(nxt.id)) break; - seen.add(nxt.id); + if (!nxt || seenFwd.has(nxt.id)) break; + seenFwd.add(nxt.id); chain.push(nxt); cursor = nxt; }