Dev console refuses buildable piece materials; loose piece grains cleared on load (t97)
This commit is contained in:
@@ -107,4 +107,72 @@ check('completion supports keywords and help commands', run("devComplete('free o
|
||||
check('completion leaves unmatched input intact', run("devComplete('give zzzzz').text === 'give zzzzz'"));
|
||||
check('history validates stored data', run("devHistory(null).items.length === 0 && devHistory(['ok', 5, '', ' ']).items.join() === 'ok'"));
|
||||
check('history caps at 50 and navigates to empty after newest', run("(() => { const h = devHistory([]); for (let i=0; i<55; i++) devRemember(h, 'money ' + i); devRemember(h, ' '); const newest = devRecall(h, -1); for (let i=0;i<60;i++) devRecall(h,-1); const oldest = devRecall(h,-1); for(let i=0;i<60;i++) devRecall(h,1); return h.items.length === 50 && newest === 'money 54' && oldest === 'money 5' && devRecall(h,1) === ''; })()"));
|
||||
// Construction materials are pieces, never loose inventory or nozzle grains.
|
||||
flatWorld(run, 240, 160, 110);
|
||||
run('enableDevConsole();');
|
||||
check('construction material markers cover every dedicated piece material', run(`
|
||||
[BELTL, BELTR, SHAFT, GATE, HULL, PIPE, DOCKW, GRINDER, SAWB, PRESSB, RACKB].every(m => PARTMAT[m])
|
||||
`));
|
||||
check('give refuses internal and display names of every construction material', run(`(() => {
|
||||
const before = JSON.stringify([bagTotal, Array.from(bag), devLog]);
|
||||
for (const [key, m] of Object.entries(DEV_MATERIALS)) if (PARTMAT[m]) {
|
||||
for (const name of [key, MD[m].name]) {
|
||||
const out = devCommand('give ' + name + ' 3');
|
||||
if (!out.error || !out[0].includes('built from the build menu')) return false;
|
||||
}
|
||||
}
|
||||
return before === JSON.stringify([bagTotal, Array.from(bag), devLog]);
|
||||
})()`));
|
||||
check('give wall refuses without changing inventory', command('give wall 3').error === true && run('bagTotal === 0'));
|
||||
check('construction pieces stay out of lists, suggestions and completion', run(`
|
||||
devMaterialList().every(([, m]) => !PARTMAT[m]) &&
|
||||
devComplete('give saw').matches.length === 0 &&
|
||||
!devSuggestions('sawb').includes(MD[SAWB].name)
|
||||
`));
|
||||
command('give sand 7'); command('give copper bar 2'); command('give stone 4');
|
||||
check('grains, bars and wall ingredients still work', run('bag[SAND] === 7 && bag[BARCU] === 2 && bag[RSTONE] === 4'));
|
||||
check('bag pickup and refund cannot introduce piece grains', run(`(() => {
|
||||
const before = bagTotal;
|
||||
const added = bagAdd(SAWB, 2, true);
|
||||
giveOrDrop(GATE, 3, 40, 40);
|
||||
return added === 0 && bagTotal === before && !bag[SAWB] && !bag[GATE] && mat[40 * W + 40] === EMPTY;
|
||||
})()`));
|
||||
run('bag[SAWB] = 4; bagTotal += 4;');
|
||||
check('nozzle refuses even a directly contaminated bag', run('toolBlow(50, 40, 1, SAWB).placed === 0 && flyers.length === 0'));
|
||||
check('mixed nozzle skips piece grains while blowing sand', run(`(() => {
|
||||
const out = toolBlow(50, 40, 1, SAWB, [SAWB, SAND]);
|
||||
return out.placed > 0 && flyers.every(f => f.m === SAND) && bag[SAWB] === 4;
|
||||
})()`));
|
||||
// Keep legitimate blocks, slopes and their outside seals, parts, machines and natural rock.
|
||||
flatWorld(run, 240, 160, 110);
|
||||
run(`
|
||||
const builtCodes = [BP_WALL, BP_SAW, BP_GRIND, BP_PRESS, BP_RACK, BP_BELT, BP_SHAFT, BP_GATE, BP_PIPE, BP_PUMP, BP_OUTLET, BP_SCREW, BP_GRATE, BP_FILTER, BP_BELT_UP];
|
||||
for (let k = 0; k < builtCodes.length; k++) placeBlock(builtCodes[k], k === 0 ? RSTONE : 0, 2 + k * 3, 10, true);
|
||||
placeMachineAt('fan', 0, 4, 17, true);
|
||||
addMold('ingot', 12, 17, LCLAY, true);
|
||||
placeDock(180);
|
||||
const ownedBefore = JSON.stringify([Array.from(mat.slice(40 * W, 80 * W)), Array.from(part.slice(40 * W, 80 * W)), Array.from(blockP)]);
|
||||
const pieceIds = Object.values(DEV_MATERIALS).filter(m => PARTMAT[m]);
|
||||
for (let k = 0; k < pieceIds.length; k++) setCell(20 * W + 20 + k, pieceIds[k], 20, 0);
|
||||
// A nozzle grain in the open side of a real sloped belt is still loose.
|
||||
const looseCorner = 40 * W + 176;
|
||||
setCell(looseCorner, SAWB, 20, 0);
|
||||
bag[SAWB] = 5; bag[HULL] = 2; bag[SAND] = 7; bagTotal = 14;
|
||||
const straySave = serializeWorld(); straySave.meta.flyers.push(GATE, SAND);
|
||||
deserializeWorld(straySave.meta, straySave.buffers);
|
||||
`);
|
||||
check('loading clears all loose construction grains', run('pieceIds.every((m, k) => mat[20 * W + 20 + k] === EMPTY) && mat[looseCorner] === EMPTY'));
|
||||
check('loading preserves built cells, slope seals, parts, machines and molds', run(`
|
||||
ownedBefore === JSON.stringify([Array.from(mat.slice(40 * W, 80 * W)), Array.from(part.slice(40 * W, 80 * W)), Array.from(blockP)]) && machines.some(m => m && m.type === 'fan') && molds.length === 1
|
||||
`));
|
||||
check('loading clears construction inventory and saved nozzle grains with correct totals', run('bag[SAWB] === 0 && bag[HULL] === 0 && bag[GATE] === 0 && bag[SAND] === 8 && bagTotal === 8'));
|
||||
check('taking down a saw and a wall refunds ingredients without piece grains', run(`(() => {
|
||||
removeBlock(5, 10); removeBlock(2, 10);
|
||||
return bag[RSTONE] === 16 && Object.values(DEV_MATERIALS).filter(m => PARTMAT[m]).every(m => !bag[m]);
|
||||
})()`));
|
||||
check('ordinary natural rock survives cleanup', run('mat[120 * W + 20] === STONE'));
|
||||
check('free building and unlock still work with construction materials excluded', run(`(() => {
|
||||
enableDevConsole(); devCommand('unlock'); devCommand('free on');
|
||||
return seen[SAWB] && placeBlock(BP_SAW, 0, 5, 5, false) === '' && mat[20 * W + 20] === SAWB;
|
||||
})()`));
|
||||
done();
|
||||
|
||||
Reference in New Issue
Block a user