Tilemaps are a new placeable asset type that is painted with autotiles in the scene view, with layers, brush, eraser and rectangle, and is drawn at runtime and in the export (#128)
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
1 parent
0607221423
commit
33a7b1b63e
30 files changed
+2060
-20
No files matched your search
@@ -19,7 +19,15 @@ import {
|
||||
import { isParticleNodeDef } from '../particles/nodes';
|
||||
import { isShaderNodeDef } from '../shader/nodes';
|
||||
import { isKeyInterpolation, normalizeKeys } from '../model/animation';
|
||||
import type { AnimationKey, AnimationTrack, Asset, StateMachineAsset, TextureFrame } from '../model/Asset';
|
||||
import type {
|
||||
AnimationKey,
|
||||
AnimationTrack,
|
||||
Asset,
|
||||
StateMachineAsset,
|
||||
TextureFrame,
|
||||
TilemapLayer,
|
||||
} from '../model/Asset';
|
||||
import { parseCellKey } from '../model/tilemap';
|
||||
import { isAssetType } from '../model/AssetTypes';
|
||||
import { isFontFile } from '../model/font';
|
||||
import { isSoundFile } from '../model/sound';
|
||||
@@ -175,6 +183,8 @@ export function deserializeProject(raw: unknown, fallbackId = ''): Project {
|
||||
(id): id is string => typeof id === 'string' && id !== '',
|
||||
);
|
||||
assets.push({ id, type, name, props, pictures });
|
||||
} else if (type === 'tilemap') {
|
||||
assets.push({ id, type, name, props, layers: normalizeLayers(a.layers) });
|
||||
} else if (type === 'animation') {
|
||||
// A root or row aiming at something gone is kept: it reads as missing and keeps its keys.
|
||||
const root = typeof a.root === 'string' ? a.root : '';
|
||||
@@ -493,6 +503,26 @@ function normalizeTracks(raw: unknown): AnimationTrack[] {
|
||||
return tracks;
|
||||
}
|
||||
|
||||
/**
|
||||
* The layers of a tilemap. A cell whose key is not a pair of whole numbers, or which names nothing,
|
||||
* is dropped; one naming a deleted autotile is kept, like an animation's dangling row, so an undo
|
||||
* brings the drawing back. A doubled layer id is dropped as a doubled node is.
|
||||
*/
|
||||
function normalizeLayers(raw: unknown): TilemapLayer[] {
|
||||
const layers: TilemapLayer[] = [];
|
||||
for (const item of Array.isArray(raw) ? raw : []) {
|
||||
const l = asRecord(item);
|
||||
if (typeof l.id !== 'string' || !l.id || layers.some((o) => o.id === l.id)) continue;
|
||||
const cells: Record<string, string> = {};
|
||||
for (const [key, value] of Object.entries(asRecord(l.cells)))
|
||||
if (parseCellKey(key) && typeof value === 'string' && value !== '') cells[key] = value;
|
||||
const layer: TilemapLayer = { id: l.id, name: typeof l.name === 'string' ? l.name : 'Layer', cells };
|
||||
if (l.hidden === true) layer.hidden = true;
|
||||
layers.push(layer);
|
||||
}
|
||||
return layers;
|
||||
}
|
||||
|
||||
function normalizeBag(raw: unknown, schema: PropertySchema, sparse: boolean): PropertyBag {
|
||||
const r = asRecord(raw);
|
||||
const bag: PropertyBag = {};
|
||||
|
||||
Reference in new issue
Block a user