Update Healer Man server
This commit is contained in:
1 parent
6114a2295f
commit
69809f7228
593 files changed
+903643
-40774
No files matched your search
@@ -0,0 +1,62 @@
|
||||
import { createHash } from "node:crypto";
|
||||
|
||||
const sha256 = (bytes) => createHash("sha256").update(bytes).digest("hex");
|
||||
|
||||
/** Validate a legacy DXT1 DDS and describe every source mip without decoding or resampling it. */
|
||||
export function inspectNativeWaterDxt1Dds(bytes) {
|
||||
if (!Buffer.isBuffer(bytes)) bytes = Buffer.from(bytes);
|
||||
if (bytes.length < 128 || bytes.toString("ascii", 0, 4) !== "DDS ") {
|
||||
throw new Error("Native water frame is not a complete DDS file.");
|
||||
}
|
||||
const headerSize = bytes.readUInt32LE(4);
|
||||
const height = bytes.readUInt32LE(12);
|
||||
const width = bytes.readUInt32LE(16);
|
||||
const pixelFormatSize = bytes.readUInt32LE(76);
|
||||
const formatFourCC = bytes.toString("ascii", 84, 88);
|
||||
const mipCount = Math.max(1, bytes.readUInt32LE(28));
|
||||
if (headerSize !== 124 || pixelFormatSize !== 32) {
|
||||
throw new Error(`Unsupported DDS header sizes ${headerSize}/${pixelFormatSize}.`);
|
||||
}
|
||||
if (formatFourCC !== "DXT1") throw new Error(`Unsupported native water frame format ${formatFourCC}.`);
|
||||
if (width < 1 || height < 1 || width % 4 !== 0 || height % 4 !== 0) {
|
||||
throw new Error(`Native water DXT1 dimensions must be positive multiples of four; got ${width}x${height}.`);
|
||||
}
|
||||
const maxMipCount = 1 + Math.floor(Math.log2(Math.max(width, height)));
|
||||
if (mipCount > maxMipCount) throw new Error(`DDS declares ${mipCount} mips for ${width}x${height}.`);
|
||||
|
||||
let offset = 128;
|
||||
let mipWidth = width;
|
||||
let mipHeight = height;
|
||||
const mips = [];
|
||||
for (let level = 0; level < mipCount; level += 1) {
|
||||
const byteLength = Math.ceil(mipWidth / 4) * Math.ceil(mipHeight / 4) * 8;
|
||||
const end = offset + byteLength;
|
||||
if (end > bytes.length) throw new Error(`DDS mip ${level} is truncated.`);
|
||||
const data = bytes.subarray(offset, end);
|
||||
mips.push({
|
||||
level,
|
||||
width: mipWidth,
|
||||
height: mipHeight,
|
||||
offset,
|
||||
byteLength,
|
||||
sha256: sha256(data),
|
||||
});
|
||||
offset = end;
|
||||
mipWidth = Math.max(1, Math.floor(mipWidth / 2));
|
||||
mipHeight = Math.max(1, Math.floor(mipHeight / 2));
|
||||
}
|
||||
if (offset !== bytes.length) {
|
||||
throw new Error(`DDS has ${bytes.length - offset} trailing bytes after its declared mip chain.`);
|
||||
}
|
||||
return {
|
||||
width,
|
||||
height,
|
||||
mipCount,
|
||||
formatFourCC,
|
||||
headerBytes: 128,
|
||||
fileBytes: bytes.length,
|
||||
sha256: sha256(bytes),
|
||||
mips,
|
||||
exactMipChainConsumption: offset === bytes.length,
|
||||
};
|
||||
}
|
||||
Reference in new issue
Block a user