"use strict"; (() => { // src/lib/utils/version.ts var VERSION = true ? "4.3.1" : "latest"; // src/lib/parsers/parse-npy.ts var a = new Uint32Array([305419896]); var b = new Uint8Array(a.buffer, a.byteOffset, a.byteLength); var isLittleEndian = !(b[0] === 18); var LITTLE_ENDIAN_OS = isLittleEndian; var DTYPES = { u1: Uint8Array, i1: Int8Array, u2: Uint16Array, i2: Int16Array, u4: Uint32Array, i4: Int32Array, f4: Float32Array, f8: Float64Array }; function parseNPY(arrayBuffer, options) { const view = new DataView(arrayBuffer); const { header, headerEndOffset } = parseHeader(view); const numpyType = header.descr; const ArrayType = DTYPES[numpyType.slice(1, 3)]; if (!ArrayType) { throw new Error(`Unimplemented type ${numpyType}`); } const nArrayElements = header.shape?.reduce((a2, b2) => a2 * b2); const arrayByteLength = nArrayElements * ArrayType.BYTES_PER_ELEMENT; if (arrayBuffer.byteLength < headerEndOffset + arrayByteLength) { throw new Error("Buffer overflow"); } const data = new ArrayType(arrayBuffer.slice(headerEndOffset, headerEndOffset + arrayByteLength)); if (numpyType[0] === ">" && LITTLE_ENDIAN_OS || numpyType[0] === "<" && !LITTLE_ENDIAN_OS) { throw new Error("Incorrect endianness"); } return { data, header }; } function parseHeader(view) { const majorVersion = view.getUint8(6); let offset = 8; let headerLength; if (majorVersion >= 2) { headerLength = view.getUint32(offset, true); offset += 4; } else { headerLength = view.getUint16(offset, true); offset += 2; } const encoding = majorVersion <= 2 ? "latin1" : "utf-8"; const decoder = new TextDecoder(encoding); const headerArray = new Uint8Array(view.buffer, offset, headerLength); const headerText = decoder.decode(headerArray); offset += headerLength; const header = JSON.parse( headerText.replace(/'/g, '"').replace("False", "false").replace("(", "[").replace(/,*\),*/g, "]") ); return { header, headerEndOffset: offset }; } // src/npy-loader.ts var NPY_MAGIC_NUMBER = new Uint8Array([147, 78, 85, 77, 80, 89]); var NPYWorkerLoader = { dataType: null, batchType: null, name: "NPY", id: "npy", module: "textures", version: VERSION, worker: true, extensions: ["npy"], mimeTypes: [], tests: [NPY_MAGIC_NUMBER.buffer], options: { npy: {} } }; var NPYLoader = { ...NPYWorkerLoader, parseSync: parseNPY, parse: async (arrayBuffer, options) => parseNPY(arrayBuffer, options) }; // ../worker-utils/src/lib/node/worker_threads-browser.ts var parentPort = null; // ../worker-utils/src/lib/worker-utils/get-transfer-list.ts function getTransferList(object, recursive = true, transfers) { const transfersSet = transfers || /* @__PURE__ */ new Set(); if (!object) { } else if (isTransferable(object)) { transfersSet.add(object); } else if (isTransferable(object.buffer)) { transfersSet.add(object.buffer); } else if (ArrayBuffer.isView(object)) { } else if (recursive && typeof object === "object") { for (const key in object) { getTransferList(object[key], recursive, transfersSet); } } return transfers === void 0 ? Array.from(transfersSet) : []; } function isTransferable(object) { if (!object) { return false; } if (object instanceof ArrayBuffer) { return true; } if (typeof MessagePort !== "undefined" && object instanceof MessagePort) { return true; } if (typeof ImageBitmap !== "undefined" && object instanceof ImageBitmap) { return true; } if (typeof OffscreenCanvas !== "undefined" && object instanceof OffscreenCanvas) { return true; } return false; } // ../worker-utils/src/lib/worker-farm/worker-body.ts async function getParentPort() { return parentPort; } var onMessageWrapperMap = /* @__PURE__ */ new Map(); var WorkerBody = class { /** Check that we are actually in a worker thread */ static async inWorkerThread() { return typeof self !== "undefined" || Boolean(await getParentPort()); } /* * (type: WorkerMessageType, payload: WorkerMessagePayload) => any */ static set onmessage(onMessage) { async function handleMessage(message) { const parentPort2 = await getParentPort(); const { type, payload } = parentPort2 ? message : message.data; onMessage(type, payload); } getParentPort().then((parentPort2) => { if (parentPort2) { parentPort2.on("message", (message) => { handleMessage(message); }); parentPort2.on("exit", () => console.debug("Node worker closing")); } else { globalThis.onmessage = handleMessage; } }); } static async addEventListener(onMessage) { let onMessageWrapper = onMessageWrapperMap.get(onMessage); if (!onMessageWrapper) { onMessageWrapper = async (message) => { if (!isKnownMessage(message)) { return; } const parentPort3 = await getParentPort(); const { type, payload } = parentPort3 ? message : message.data; onMessage(type, payload); }; } const parentPort2 = await getParentPort(); if (parentPort2) { console.error("not implemented"); } else { globalThis.addEventListener("message", onMessageWrapper); } } static async removeEventListener(onMessage) { const onMessageWrapper = onMessageWrapperMap.get(onMessage); onMessageWrapperMap.delete(onMessage); const parentPort2 = await getParentPort(); if (parentPort2) { console.error("not implemented"); } else { globalThis.removeEventListener("message", onMessageWrapper); } } /** * Send a message from a worker to creating thread (main thread) * @param type * @param payload */ static async postMessage(type, payload) { const data = { source: "loaders.gl", type, payload }; const transferList = getTransferList(payload); const parentPort2 = await getParentPort(); if (parentPort2) { parentPort2.postMessage(data, transferList); } else { globalThis.postMessage(data, transferList); } } }; function isKnownMessage(message) { const { type, data } = message; return type === "message" && data && typeof data.source === "string" && data.source.startsWith("loaders.gl"); } // ../loader-utils/src/lib/worker-loader-utils/create-loader-worker.ts var requestId = 0; async function createLoaderWorker(loader) { if (!await WorkerBody.inWorkerThread()) { return; } WorkerBody.onmessage = async (type, payload) => { switch (type) { case "process": try { const { input, options = {}, context = {} } = payload; const result = await parseData({ loader, arrayBuffer: input, options, // @ts-expect-error fetch missing context: { ...context, _parse: parseOnMainThread } }); WorkerBody.postMessage("done", { result }); } catch (error) { const message = error instanceof Error ? error.message : ""; WorkerBody.postMessage("error", { error: message }); } break; default: } }; } function parseOnMainThread(arrayBuffer, loader, options, context) { return new Promise((resolve, reject) => { const id = requestId++; const onMessage = (type, payload2) => { if (payload2.id !== id) { return; } switch (type) { case "done": WorkerBody.removeEventListener(onMessage); resolve(payload2.result); break; case "error": WorkerBody.removeEventListener(onMessage); reject(payload2.error); break; default: } }; WorkerBody.addEventListener(onMessage); const payload = { id, input: arrayBuffer, options }; WorkerBody.postMessage("process", payload); }); } async function parseData({ loader, arrayBuffer, options, context }) { let data; let parser; if (loader.parseSync || loader.parse) { data = arrayBuffer; parser = loader.parseSync || loader.parse; } else if (loader.parseTextSync) { const textDecoder = new TextDecoder(); data = textDecoder.decode(arrayBuffer); parser = loader.parseTextSync; } else { throw new Error(`Could not load data with ${loader.name} loader`); } options = { ...options, modules: loader && loader.options && loader.options.modules || {}, worker: false }; return await parser(data, { ...options }, context, loader); } // src/workers/npy-worker.ts createLoaderWorker(NPYLoader); })();