mirror of
https://github.com/bilawalsidhu/gods-eye-view.git
synced 2026-11-15 07:42:23 +00:00
test(migration): establish W2 native oracle and release removed overlay identities
Add the sequential W2/completion plan and deterministic earthquake ground-raster, geometry, lifecycle and strict runtime QA. Prove the comparator rejects incomplete evidence and release deleted overlay entries from the collision arbiter. Record native dev/preview acceptance and full checkpoint gates.
This commit is contained in:
1 parent
0600964249
commit
e8870a4766
4 files changed
+154
-7
No files matched your search
@@ -951,6 +951,14 @@ export function registerWorldOverlayPaintLane(laneId, painter, options = {}) {
|
||||
};
|
||||
}
|
||||
|
||||
// Removed entries cannot paint an exit fade: their source no longer owns
|
||||
// them. Release the arbiter identity too, so later layout changes cannot
|
||||
// wake the idle renderer for an invisible minimum-lifetime/fade state.
|
||||
function forgetOverlayEntry(entry) {
|
||||
_records.delete(entry._overlayKey);
|
||||
_domains.get(entry.collisionGroup)?.arbiter.remove(entry._overlayKey);
|
||||
}
|
||||
|
||||
/**
|
||||
* Replace all entries owned by a source atomically.
|
||||
* @param {string} sourceId
|
||||
@@ -968,7 +976,7 @@ export function setOverlayEntries(sourceId, entries, options = {}) {
|
||||
const next = new Map();
|
||||
for (const entry of normalized) next.set(entry.id, entry);
|
||||
for (const entry of source.entries.values()) {
|
||||
if (!next.has(entry.id)) _records.delete(entry._overlayKey);
|
||||
if (!next.has(entry.id)) forgetOverlayEntry(entry);
|
||||
const replacement = next.get(entry.id);
|
||||
if (replacement && isProtected(entry) !== isProtected(replacement))
|
||||
getOrCreateDomain(entry.collisionGroup).arbiter.remove(entry._overlayKey);
|
||||
@@ -1005,9 +1013,10 @@ export function removeOverlayEntry(sourceId, entryId) {
|
||||
const source = _sources.get(assertSourceId(sourceId));
|
||||
if (!source) return false;
|
||||
const id = String(entryId);
|
||||
const removed = source.entries.delete(id);
|
||||
if (!removed) return false;
|
||||
_records.delete(entryKey(source.id, id));
|
||||
const entry = source.entries.get(id);
|
||||
if (!entry) return false;
|
||||
source.entries.delete(id);
|
||||
forgetOverlayEntry(entry);
|
||||
rebuildSourceCohorts(source);
|
||||
updateEntryDiagnostics();
|
||||
invalidateHost();
|
||||
@@ -1023,8 +1032,7 @@ export function clearOverlaySource(sourceId) {
|
||||
if (_destroyed) return false;
|
||||
const source = _sources.get(assertSourceId(sourceId));
|
||||
if (!source) return false;
|
||||
for (const entry of source.entries.values())
|
||||
_records.delete(entry._overlayKey);
|
||||
for (const entry of source.entries.values()) forgetOverlayEntry(entry);
|
||||
source.entries.clear();
|
||||
source.cohortDomainIds.length = 0;
|
||||
source.cohortLists.length = 0;
|
||||
|
||||
@@ -2378,3 +2378,92 @@ test('the host takes a globe engine and refuses a bare viewer', async () => {
|
||||
assert.equal(engine.frames.postRender.numberOfListeners, 1);
|
||||
env.cleanup();
|
||||
});
|
||||
|
||||
// Source deletion is final: invisible candidates must not retain minimum-life
|
||||
// or fade state which wakes a dormant scene on a later UI/layout invalidation.
|
||||
for (const [name, remove] of [
|
||||
["clear", () => clearOverlaySource("deleted-static")],
|
||||
["remove", () => removeOverlayEntry("deleted-static", "event")],
|
||||
["replace-empty", () => setOverlayEntries("deleted-static", [])],
|
||||
]) {
|
||||
test(`removed static labels stay dormant after ${name}`, () => {
|
||||
const env = installMockEnvironment();
|
||||
try {
|
||||
initWorldOverlay(env.engine);
|
||||
setOverlayEntries(
|
||||
"deleted-static",
|
||||
[
|
||||
selectedEntry("event", {
|
||||
selected: false,
|
||||
protected: false,
|
||||
variant: "card",
|
||||
collisionGroup: "deleted-static",
|
||||
priority: 100,
|
||||
verticalOnly: true,
|
||||
}),
|
||||
],
|
||||
{ collisionCapacity: 1, maxVisible: 1 },
|
||||
);
|
||||
env.advanceTime(600);
|
||||
env.postRender.raise();
|
||||
env.advanceTime(600);
|
||||
env.postRender.raise();
|
||||
assert.ok(getWorldOverlayDiagnostics().selectedCount > 0);
|
||||
remove();
|
||||
env.postRender.raise();
|
||||
env.viewer.scene.requestRenderCount = 0;
|
||||
for (let i = 0; i < 16; i++) {
|
||||
env.advanceTime(250);
|
||||
for (const observer of env.resizeObservers) observer.callback();
|
||||
env.postRender.raise();
|
||||
}
|
||||
assert.equal(getWorldOverlayDiagnostics().paintedCount, 0);
|
||||
assert.equal(
|
||||
env.viewer.scene.requestRenderCount,
|
||||
0,
|
||||
"removed source must not retain fades/minimum lifetimes and wake idle",
|
||||
);
|
||||
} finally {
|
||||
env.cleanup();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
test("clearing one static source preserves another source in the same label domain", () => {
|
||||
const env = installMockEnvironment();
|
||||
try {
|
||||
initWorldOverlay(env.engine);
|
||||
for (const [source, x] of [
|
||||
["left", -0.5],
|
||||
["right", 0.5],
|
||||
])
|
||||
setOverlayEntries(
|
||||
source,
|
||||
[
|
||||
selectedEntry("event", {
|
||||
position: new Cesium.Cartesian3(x, 0, 0),
|
||||
selected: false,
|
||||
protected: false,
|
||||
collisionGroup: "ambient-card",
|
||||
verticalOnly: true,
|
||||
}),
|
||||
],
|
||||
{ collisionCapacity: 1, maxVisible: 1 },
|
||||
);
|
||||
env.advanceTime(100);
|
||||
env.postRender.raise();
|
||||
env.advanceTime(600);
|
||||
env.postRender.raise();
|
||||
assert.deepEqual(getWorldOverlayDiagnostics().paintedBySource, {
|
||||
left: 1,
|
||||
right: 1,
|
||||
});
|
||||
clearOverlaySource("left");
|
||||
env.postRender.raise();
|
||||
assert.deepEqual(getWorldOverlayDiagnostics().paintedBySource, {
|
||||
right: 1,
|
||||
});
|
||||
} finally {
|
||||
env.cleanup();
|
||||
}
|
||||
});
|
||||
Reference in new issue
Block a user