Ein ausgeschaltetes Objekt zeichnet nichts, verschwand bisher aber auch aus der Auswahl - im Panel angeklickt blieb der Viewport leer, es gab kein Anzeichen, wo es liegt. Der Rahmen kommt jetzt, gedimmt auf 45 %, damit er sich nicht wie eine fehlgeschlagene Zeichnung liest. Ziehen bleibt aus: der Node ist weiterhin nicht interaktiv. Dazu __gm.gizmos() als Testhaken - Gizmos waren vorher gar nicht prüfbar. Es meldet das alpha, das wirklich in den Strich geht, kein daneben abgeleitetes Flag.
121 lines
5.5 KiB
JavaScript
121 lines
5.5 KiB
JavaScript
/** Text assets rendered in the scene, and the enabled switch in the editor and in the running game. */
|
||
export async function textAndEnabled(t) {
|
||
const {
|
||
check,
|
||
sleep,
|
||
evaluate,
|
||
json,
|
||
shot,
|
||
click,
|
||
clickText,
|
||
locate,
|
||
mutate,
|
||
object,
|
||
play,
|
||
press,
|
||
stop,
|
||
typeText,
|
||
} = t;
|
||
const has = (text) => evaluate(`Boolean(__gm.locate(${JSON.stringify(text)}))`);
|
||
|
||
// 17. Text assets: created through the + menu, placed, and rendered as real text in the scene.
|
||
await clickText('+');
|
||
await clickText('Text');
|
||
await sleep(100);
|
||
const textAssetId = await evaluate(`(__gm.state.project.assets.find(a => a.type === 'text') || {}).id`);
|
||
check('+ menu creates a text asset', Boolean(textAssetId));
|
||
await mutate(`
|
||
const id = ${JSON.stringify(textAssetId)};
|
||
__gm.state.project.assets.find(a => a.id === id).props.text = 'Hello world';
|
||
// On the camera so the game view really renders it (outside the frame it would be culled).
|
||
const cam = __gm.state.activeScene.objects.find(o => o.id === 'o3').position;
|
||
__gm.state.activeScene.objects.push({ id: 'otext', assetId: id, name: '', position: { x: cam.x, y: cam.y, z: 5 }, editorOffset: { x: 0, y: 0 }, overrides: {}, parentId: '', instanceEdits: {} });
|
||
__gm.state.select({ kind: 'object', holderId: 'scene1', objectIds: ['otext'], objectId: 'otext' })`);
|
||
await sleep(100);
|
||
check('a placed text object draws its content in the scene', await has('Hello world'));
|
||
await shot('29-text-object');
|
||
|
||
// 17a. The enabled switch: every object has it, switching it off is a normal override, and a
|
||
// switched-off object disappears from the scene view too (it stays in the hierarchy).
|
||
const enabledRow = await evaluate(`__gm.locate('Enabled')`);
|
||
check('the inspector shows the Enabled switch for a scene object', Boolean(enabledRow));
|
||
const visibleBefore = (await json('__gm.viewportInfo()')).visibleItems;
|
||
const gizmoOf = async (id) => (await json('__gm.gizmos()')).find((g) => g.id === id) ?? null;
|
||
const gizmoOn = await gizmoOf('otext');
|
||
check('a selected object is framed at full strength', gizmoOn?.alpha === 1, JSON.stringify(gizmoOn));
|
||
// The checkbox sits right of the 64 px label column; locate() gives the label's text centre.
|
||
await click(enabledRow.x + 55, enabledRow.y);
|
||
await sleep(100);
|
||
const textObject = await object('otext');
|
||
check(
|
||
'clicking it writes an override instead of changing the asset',
|
||
textObject.overrides.enabled === false,
|
||
JSON.stringify(textObject.overrides),
|
||
);
|
||
check(
|
||
'a switched-off object is not drawn in the scene view',
|
||
!(await json('__gm.drawOrder()')).includes('otext'),
|
||
);
|
||
const visibleAfter = (await json('__gm.viewportInfo()')).visibleItems;
|
||
check(
|
||
'the scene view renders one item less',
|
||
visibleAfter === visibleBefore - 1,
|
||
`${visibleBefore} → ${visibleAfter}`,
|
||
);
|
||
check('it stays selectable in the hierarchy, so its switch stays reachable', await has('Enabled'));
|
||
await shot('30-disabled');
|
||
|
||
// 17a-2. It draws nothing, so its outline is the only thing left that says where it sits – which
|
||
// is the whole point of being able to pick it in the hierarchy. Selecting another object
|
||
// and coming back proves the outline follows the panel, not a leftover from before.
|
||
const gizmoOff = await gizmoOf('otext');
|
||
check(
|
||
'a switched-off object is still framed, dimmed',
|
||
gizmoOff?.primary === true && gizmoOff.alpha > 0 && gizmoOff.alpha < 1,
|
||
JSON.stringify(gizmoOff),
|
||
);
|
||
const otherRow = await evaluate(`__gm.hierarchyRow('o3')`);
|
||
await click(otherRow.x, otherRow.y);
|
||
await sleep(100);
|
||
check('selecting something else drops the frame', (await gizmoOf('otext')) === null);
|
||
const offRow = await evaluate(`__gm.hierarchyRow('otext')`);
|
||
await click(offRow.x, offRow.y);
|
||
await sleep(100);
|
||
const gizmoBack = await gizmoOf('otext');
|
||
check(
|
||
'picking the switched-off object in the hierarchy frames it again',
|
||
gizmoBack?.alpha > 0 && gizmoBack.alpha < 1,
|
||
JSON.stringify(gizmoBack),
|
||
);
|
||
check('and it is still not drawn', !(await json('__gm.drawOrder()')).includes('otext'));
|
||
await shot('30b-disabled-gizmo');
|
||
|
||
// 17b. In the running game a switched-off object does not exist: it is not rendered, and
|
||
// switching it back on brings it back.
|
||
await play();
|
||
await sleep(200);
|
||
const offItems = (await json('__gm.gameInfo()')).visibleItems;
|
||
await mutate(`__gm.state.activeScene.objects.find(o => o.id === 'otext').overrides.enabled = true`);
|
||
await sleep(200);
|
||
const onItems = (await json('__gm.gameInfo()')).visibleItems;
|
||
check(
|
||
'the game renders one item more once the object is switched on',
|
||
onItems === offItems + 1,
|
||
`${offItems} → ${onItems}`,
|
||
);
|
||
await stop();
|
||
check('stop leaves the play-mode switch behind', (await object('otext')).overrides.enabled === false);
|
||
|
||
// 17c. A field that shows no decimals must not store any either. Font size is such a field, so
|
||
// typing a fraction has to round: showing "33" while the project holds 32.6 would be a lie.
|
||
const fontLabel = await locate('Font size');
|
||
check('Font size reads as a whole number', Boolean(await has('32')) && !(await has('32.000')));
|
||
await click(fontLabel.x + 160, fontLabel.y);
|
||
await typeText('32.6');
|
||
await press('Enter');
|
||
await sleep(200);
|
||
const fontSize = (await object('otext')).overrides.fontSize;
|
||
check('typing a fraction into it rounds the stored value', fontSize === 33, String(fontSize));
|
||
check('and the field shows exactly what was stored', Boolean(await has('33')));
|
||
}
|