mirror of
https://github.com/bilawalsidhu/gods-eye-view.git
synced 2026-11-15 07:42:23 +00:00
fix(cockpit): a stalled water read is given up, and coarse reads only raise
Before the first full-detail read lands, a loaded-tile read could still lower a river height partway (27 m to a 15 m bank). Loaded-tile reads now only raise it; lowering is the full-detail read's to say. That makes a full read that never lands (stalled tile requests) hold a wrong height for the whole bridge, so one still running after 30 s is given up for a fresh one; its late answer is dropped. Also tests the other half of the double-click memory fix: another ship selected within the memory is not entered through the first ship's spot.
This commit is contained in:
1 parent
80a33ba52c
commit
1bc4f980e0
4 files changed
+110
-17
No files matched your search
@@ -53,6 +53,10 @@ function vesselLayer(record) {
|
||||
deselect() {
|
||||
selected = null;
|
||||
},
|
||||
/** Another ship selected in its place. */
|
||||
select(next) {
|
||||
selected = next;
|
||||
},
|
||||
/** Live AIS Vessels turned off: like the layer, it then has no subject. */
|
||||
disable() {
|
||||
enabled = false;
|
||||
@@ -1372,6 +1376,59 @@ test('before any full read lands, a coarse loaded read keeps the river it found'
|
||||
ship.viewer.scene.sampleHeight = () => 0.5;
|
||||
frames(ship.cockpit, clock, ship.shots, 240);
|
||||
near(eyeHeightM(ship.shots.at(-1)) - seaEyeM, 27, 'still on the river', 0.5);
|
||||
// Nor partway down: a probe on a 15 m bank is not the river either.
|
||||
ship.viewer.scene.sampleHeight = () => 15;
|
||||
frames(ship.cockpit, clock, ship.shots, 240);
|
||||
near(eyeHeightM(ship.shots.at(-1)) - seaEyeM, 27, 'not lowered partway', 0.5);
|
||||
});
|
||||
|
||||
test('a full water read that never lands is given up for a fresh one', async (t) => {
|
||||
const clock = manualClock(t, START_MS);
|
||||
const sea = await bridgeAt(t, clock);
|
||||
frames(sea.cockpit, clock, sea.shots, 60);
|
||||
const seaEyeM = eyeHeightM(sea.shots.at(-1));
|
||||
sea.cockpit.exit();
|
||||
|
||||
clock.set(START_MS);
|
||||
const record = { ...RECORD, lastPositionEpoch: START_MS / 1000 };
|
||||
const ship = fixture(t, { record });
|
||||
const reads = [];
|
||||
ship.viewer.scene.sampleHeightMostDetailed = (positions) =>
|
||||
new Promise((resolve) => reads.push({ positions, resolve }));
|
||||
// Coarse tiles first put the ship 27 m up; it is really at sea.
|
||||
ship.viewer.scene.sampleHeight = () => 27;
|
||||
ship.cockpit.enter();
|
||||
await settle();
|
||||
ship.cockpit.update();
|
||||
await settle();
|
||||
assert.equal(reads.length, 1);
|
||||
// The first read stalls. Twenty seconds on, still no second read.
|
||||
frames(ship.cockpit, clock, ship.shots, 400);
|
||||
await settle();
|
||||
assert.equal(reads.length, 1, 'not stacked while it may still land');
|
||||
// Past the timeout, a fresh read starts, and its answer applies.
|
||||
frames(ship.cockpit, clock, ship.shots, 300);
|
||||
await settle();
|
||||
assert.equal(reads.length, 2, 'a fresh read after the stalled one');
|
||||
const answer = (read, height) =>
|
||||
read.resolve(
|
||||
read.positions.map((position) => Object.assign(position, { height })),
|
||||
);
|
||||
answer(reads[1], 0.5);
|
||||
await settle();
|
||||
// The eye eases down; give it time to settle.
|
||||
frames(ship.cockpit, clock, ship.shots, 400);
|
||||
near(eyeHeightM(ship.shots.at(-1)), seaEyeM, 'back on the sea', 0.5);
|
||||
// The stalled read landing now changes nothing.
|
||||
answer(reads[0], 27);
|
||||
await settle();
|
||||
frames(ship.cockpit, clock, ship.shots, 60);
|
||||
near(
|
||||
eyeHeightM(ship.shots.at(-1)),
|
||||
seaEyeM,
|
||||
'the given-up read is dropped',
|
||||
0.5,
|
||||
);
|
||||
});
|
||||
|
||||
test('a client clock minutes fast does not age the bridge into a stale feed', async (t) => {
|
||||
@@ -1481,6 +1538,17 @@ test("a ship's double-click memory does not carry over to an aircraft followed s
|
||||
assert.equal(cockpit.active, false);
|
||||
});
|
||||
|
||||
test("a ship's double-click memory does not carry over to another ship", async (t) => {
|
||||
const { cockpit, viewer, vessels } = fixture(t);
|
||||
heightSensitiveProjection(viewer);
|
||||
cockpit.onScenePointerDown(1000);
|
||||
// Within the memory another ship is selected, drawn elsewhere.
|
||||
vessels.select({ ...RECORD, mmsi: '211000009', name: 'OTHER' });
|
||||
heightSensitiveProjection(viewer, { x: 900 });
|
||||
assert.equal(cockpit.onSceneDoubleClick({ x: 400, y: 300 }, 1250), false);
|
||||
assert.equal(cockpit.active, false);
|
||||
});
|
||||
|
||||
test("a double-click's second press keeps the first press's picture of the ship", async (t) => {
|
||||
const { cockpit, viewer, store } = fixture(t);
|
||||
heightSensitiveProjection(viewer);
|
||||
|
||||
Reference in new issue
Block a user