arx-convert
Version:
Converts various Arx Fatalis formats to JSON or YAML and back
97 lines • 4.46 kB
JavaScript
import { BinaryIO } from '../common/BinaryIO.js';
import { MAP_DEPTH_IN_CELLS, MAP_WIDTH_IN_CELLS } from '../common/constants.js';
import { concatArrayBuffers, times } from '../common/helpers.js';
import { Vertex } from './Vertex.js';
import { isBetween, isQuad } from './helpers.js';
/**
* @see https://github.com/arx/ArxLibertatis/blob/1.2.1/src/graphics/GraphicsTypes.h#L88
*/
export var ArxPolygonFlags;
(function (ArxPolygonFlags) {
ArxPolygonFlags[ArxPolygonFlags["None"] = 0] = "None";
ArxPolygonFlags[ArxPolygonFlags["NoShadow"] = 1] = "NoShadow";
ArxPolygonFlags[ArxPolygonFlags["DoubleSided"] = 2] = "DoubleSided";
ArxPolygonFlags[ArxPolygonFlags["Transparent"] = 4] = "Transparent";
ArxPolygonFlags[ArxPolygonFlags["Water"] = 8] = "Water";
ArxPolygonFlags[ArxPolygonFlags["Glow"] = 16] = "Glow";
ArxPolygonFlags[ArxPolygonFlags["Ignore"] = 32] = "Ignore";
ArxPolygonFlags[ArxPolygonFlags["Quad"] = 64] = "Quad";
/** unused by arx */
ArxPolygonFlags[ArxPolygonFlags["Tiled"] = 128] = "Tiled";
ArxPolygonFlags[ArxPolygonFlags["Metal"] = 256] = "Metal";
ArxPolygonFlags[ArxPolygonFlags["Hide"] = 512] = "Hide";
ArxPolygonFlags[ArxPolygonFlags["Stone"] = 1024] = "Stone";
ArxPolygonFlags[ArxPolygonFlags["Wood"] = 2048] = "Wood";
ArxPolygonFlags[ArxPolygonFlags["Gravel"] = 4096] = "Gravel";
ArxPolygonFlags[ArxPolygonFlags["Earth"] = 8192] = "Earth";
ArxPolygonFlags[ArxPolygonFlags["NoCollision"] = 16384] = "NoCollision";
ArxPolygonFlags[ArxPolygonFlags["Lava"] = 32768] = "Lava";
ArxPolygonFlags[ArxPolygonFlags["Climbable"] = 65536] = "Climbable";
ArxPolygonFlags[ArxPolygonFlags["Falling"] = 131072] = "Falling";
ArxPolygonFlags[ArxPolygonFlags["NoPath"] = 262144] = "NoPath";
ArxPolygonFlags[ArxPolygonFlags["NoDraw"] = 524288] = "NoDraw";
ArxPolygonFlags[ArxPolygonFlags["PrecisePath"] = 1048576] = "PrecisePath";
// NoClimb = 1 << 21, // unused
// Angular = 1 << 22, // unused
// AngularIdx0 = 1 << 23, // unused
// AngularIdx1 = 1 << 24, // unused
// AngularIdx2 = 1 << 25, // unused
// AngularIdx3 = 1 << 26, // unused
ArxPolygonFlags[ArxPolygonFlags["LateMip"] = 134217728] = "LateMip";
})(ArxPolygonFlags || (ArxPolygonFlags = {}));
export class Polygon {
static readFrom(binary) {
const data = {
vertices: times(() => {
return Vertex.readFrom(binary);
}, 4),
textureContainerId: binary.readInt32(),
norm: binary.readVector3(),
norm2: binary.readVector3(),
normals: binary.readVector3Array(4),
transval: binary.readFloat32(),
area: binary.readFloat32(),
flags: binary.readInt32(),
room: binary.readInt16(),
};
binary.readInt16(); // paddy - unused by Arx, always 0
return data;
}
static accumulateFrom(polygon) {
const buffer = new ArrayBuffer(Polygon.sizeOf());
const binary = new BinaryIO(buffer);
binary.writeBuffer(concatArrayBuffers(polygon.vertices.map(Vertex.accumulateFrom)));
binary.writeInt32(polygon.textureContainerId);
binary.writeVector3(polygon.norm);
binary.writeVector3(polygon.norm2);
binary.writeVector3Array(polygon.normals ?? [polygon.norm, polygon.norm, polygon.norm, polygon.norm2]);
binary.writeFloat32(polygon.transval);
binary.writeFloat32(polygon.area);
binary.writeInt32(polygon.flags);
binary.writeInt16(polygon.room);
binary.writeInt16(0); // paddy
return buffer;
}
static sizeOf() {
return (Vertex.sizeOf() * 4 +
BinaryIO.sizeOfInt32() * 2 +
BinaryIO.sizeOfVector3Array(1 + 1 + 4) +
BinaryIO.sizeOfFloat32() * 2 +
BinaryIO.sizeOfInt16() * 2);
}
/**
* A polygon is considered out of bounds when any of its vertices are not 0 <= x < 16000 or 0 <= z < 16000
*/
static isOutOfBounds(polygon) {
let numberOfPolygons = 3;
if (isQuad(polygon)) {
numberOfPolygons = 4;
}
return polygon.vertices.slice(0, numberOfPolygons).some(({ x, z }) => {
const fitsX = isBetween(0, MAP_WIDTH_IN_CELLS * 100 - 1, x);
const fitsZ = isBetween(0, MAP_DEPTH_IN_CELLS * 100 - 1, z);
return !fitsX || !fitsZ;
});
}
}
//# sourceMappingURL=Polygon.js.map