UNPKG

arx-convert

Version:

Converts various Arx Fatalis formats to JSON or YAML and back

92 lines 4.17 kB
import { BinaryIO } from '../common/BinaryIO.js'; import { concatArrayBuffers, times } from '../common/helpers.js'; import { DlfHeader } from './DlfHeader.js'; import { Fog } from './Fog.js'; import { InteractiveObject } from './InteractiveObject.js'; import { Scene } from './Scene.js'; import { ArxZoneAndPathFlags, ZoneAndPathHeader } from './ZoneAndPathHeader.js'; import { ZoneAndPathPoint } from './ZoneAndPathPoint.js'; export class DLF { static load(decompressedFile) { const file = new BinaryIO(decompressedFile); const { numberOfInteractiveObjects, numberOfFogs, numberOfZonesAndPaths, ...header } = DlfHeader.readFrom(file); const scene = Scene.readFrom(file); const data = { $schema: 'https://arx-tools.github.io/schemas/dlf.schema.json', header: { ...header, ...scene, }, interactiveObjects: times(() => { return InteractiveObject.readFrom(file); }, numberOfInteractiveObjects), fogs: times(() => { return Fog.readFrom(file); }, numberOfFogs), paths: [], zones: [], }; const numberOfNodes = 0; const numberOfNodeLinks = 12; file.readInt8Array(numberOfNodes * (204 + numberOfNodeLinks * 64)); times(() => { const { numberOfPoints, position, height, name, backgroundColor, ambience, ambienceMaxVolume, drawDistance, flags, } = ZoneAndPathHeader.readFrom(file); const points = times(() => { return ZoneAndPathPoint.readFrom(file, position); }, numberOfPoints); /** * zones and paths are the same, the only difference is if height = 0 then it's a path, otherwise a zone * * @see https://github.com/arx/ArxLibertatis/blob/1.2.1/src/scene/LoadLevel.cpp#L407 */ if (height === 0) { const path = { name, points }; data.paths.push(path); } else { const zone = { name, points, height }; if (flags & ArxZoneAndPathFlags.SetAmbience) { zone.ambience = ambience; zone.ambienceMaxVolume = ambienceMaxVolume; } if (flags & ArxZoneAndPathFlags.SetBackgroundColor) { zone.backgroundColor = backgroundColor; } if (flags & ArxZoneAndPathFlags.SetDrawDistance) { zone.drawDistance = drawDistance; } data.zones.push(zone); } }, numberOfZonesAndPaths); return data; } static save(json) { const header = DlfHeader.accumulateFrom(json); const scene = Scene.accumulateFrom({ levelIdx: json.header.levelIdx, }); const interactiveObjects = concatArrayBuffers(json.interactiveObjects.map(InteractiveObject.accumulateFrom)); const fogs = concatArrayBuffers(json.fogs.map(Fog.accumulateFrom)); const numberOfNodes = 0; const numberOfNodeLinks = 12; const nodes = new ArrayBuffer(numberOfNodes * (204 + numberOfNodeLinks * 64)); const paths = concatArrayBuffers(json.paths.flatMap((path) => { const header = ZoneAndPathHeader.allocateFrom(path); const { position } = path.points[0]; const points = path.points.map((point) => { return ZoneAndPathPoint.allocateFrom(point, position); }); return [header, ...points]; })); const zones = concatArrayBuffers(json.zones.flatMap((zone) => { const header = ZoneAndPathHeader.allocateFrom(zone); const { position } = zone.points[0]; const points = zone.points.map((point) => { return ZoneAndPathPoint.allocateFrom(point, position); }); return [header, ...points]; })); return concatArrayBuffers([header, scene, interactiveObjects, fogs, nodes, paths, zones]); } } //# sourceMappingURL=DLF.js.map