var __defProp = Object.defineProperty;
var __export = (target, all) => {
  for (var name in all)
    __defProp(target, name, { get: all[name], enumerable: true });
};

// node_modules/@fe-daily/libimagequant-wasm/dist/index.mjs
var LibImageQuant = class {
  constructor(options = {}) {
    this.wasmModule = null;
    this.isInitialized = false;
    this.wasmUrl = options.wasmUrl;
    this.preloadedWasmModule = options.wasmModule;
    this.initPromise = this.initializeWasm();
  }
  /**
   * Initialize the WASM module
   */
  async initializeWasm() {
    if (this.isInitialized) return;
    if (this.preloadedWasmModule) {
      this.wasmModule = this.preloadedWasmModule;
      await this.wasmModule.default(this.wasmUrl);
      this.isInitialized = true;
      return;
    }
    try {
      const wasmLoaderPath = this.wasmUrl || new URL("./wasm/libimagequant_wasm.js", import.meta.url).href;
      this.wasmModule = await import(wasmLoaderPath);
      await this.wasmModule.default(this.wasmUrl);
      this.isInitialized = true;
    } catch (error) {
      throw new Error(
        `Failed to load WASM module. For Next.js applications, please provide the WASM module directly: 
import wasmModule from '@fe-daily/libimagequant-wasm/wasm/libimagequant_wasm.js';
const quantizer = new LibImageQuant({ wasmModule });
Original error: ${error instanceof Error ? error.message : String(error)}`
      );
    }
  }
  /**
   * Quantize a PNG from bytes or Blob
   */
  async quantizePng(pngData, options = {}) {
    await this.initPromise;
    let pngBytes;
    if (pngData instanceof Blob) {
      const arrayBuffer = await pngData.arrayBuffer();
      pngBytes = new Uint8Array(arrayBuffer);
    } else if (pngData instanceof ArrayBuffer) {
      pngBytes = new Uint8Array(pngData);
    } else {
      pngBytes = pngData;
    }
    const decodedResult = this.wasmModule.decode_png_to_rgba(pngBytes);
    const rgbaData = decodedResult[0];
    const width = decodedResult[1];
    const height = decodedResult[2];
    return await this.quantizeRgbaData(rgbaData, width, height, options);
  }
  /**
   * Quantize from ImageData and return as PNG bytes or ImageData
   */
  async quantizeImageData(imageData, options = {}) {
    await this.initPromise;
    const rgbaData = new Uint8ClampedArray(imageData.data);
    return await this.quantizeRgbaData(rgbaData, imageData.width, imageData.height, options);
  }
  /**
   * Internal method to quantize RGBA data
   */
  async quantizeRgbaData(rgbaData, width, height, options) {
    const quantizer2 = new this.wasmModule.ImageQuantizer();
    if (options.speed !== void 0) {
      quantizer2.setSpeed(options.speed);
    }
    if (options.quality !== void 0) {
      const { min = 0, target = 100 } = options.quality;
      quantizer2.setQuality(min, target);
    }
    if (options.maxColors !== void 0) {
      quantizer2.setMaxColors(options.maxColors);
    }
    if (options.posterization !== void 0) {
      quantizer2.setPosterization(options.posterization);
    }
    const quantResult = quantizer2.quantizeImage(rgbaData, width, height);
    const palette = quantResult.getPalette();
    const quality = quantResult.getQuantizationQuality();
    const paletteLength = quantResult.getPaletteLength();
    if (options.dithering !== void 0) {
      quantResult.setDithering(options.dithering);
    }
    const remappedRgbaData = quantResult.remapImage(rgbaData, width, height);
    const paletteIndices = quantResult.getPaletteIndices(rgbaData, width, height);
    const pngBytes = this.wasmModule.encode_palette_to_png(
      paletteIndices,
      palette,
      width,
      height
    );
    let outputImageData;
    try {
      outputImageData = new ImageData(remappedRgbaData, width, height);
    } catch (error) {
      outputImageData = {
        data: remappedRgbaData,
        width,
        height,
        colorSpace: "srgb"
      };
    }
    return {
      palette,
      pngBytes,
      imageData: outputImageData,
      quality,
      paletteLength,
      width,
      height
    };
  }
  /**
   * Clean up resources (no longer needed since we're not using workers)
   */
  dispose() {
  }
};

// node_modules/@fe-daily/libimagequant-wasm/dist/wasm/libimagequant_wasm.js
var libimagequant_wasm_exports = {};
__export(libimagequant_wasm_exports, {
  ImageQuantizer: () => ImageQuantizer,
  QuantizationResult: () => QuantizationResult,
  decode_png_to_rgba: () => decode_png_to_rgba,
  default: () => libimagequant_wasm_default,
  encode_palette_to_png: () => encode_palette_to_png,
  initSync: () => initSync,
  main: () => main
});
var wasm;
var cachedTextDecoder = typeof TextDecoder !== "undefined" ? new TextDecoder("utf-8", { ignoreBOM: true, fatal: true }) : { decode: () => {
  throw Error("TextDecoder not available");
} };
if (typeof TextDecoder !== "undefined") {
  cachedTextDecoder.decode();
}
var cachedUint8ArrayMemory0 = null;
function getUint8ArrayMemory0() {
  if (cachedUint8ArrayMemory0 === null || cachedUint8ArrayMemory0.byteLength === 0) {
    cachedUint8ArrayMemory0 = new Uint8Array(wasm.memory.buffer);
  }
  return cachedUint8ArrayMemory0;
}
function getStringFromWasm0(ptr, len) {
  ptr = ptr >>> 0;
  return cachedTextDecoder.decode(getUint8ArrayMemory0().subarray(ptr, ptr + len));
}
var WASM_VECTOR_LEN = 0;
var cachedTextEncoder = typeof TextEncoder !== "undefined" ? new TextEncoder("utf-8") : { encode: () => {
  throw Error("TextEncoder not available");
} };
var encodeString = typeof cachedTextEncoder.encodeInto === "function" ? function(arg, view) {
  return cachedTextEncoder.encodeInto(arg, view);
} : function(arg, view) {
  const buf = cachedTextEncoder.encode(arg);
  view.set(buf);
  return {
    read: arg.length,
    written: buf.length
  };
};
function passStringToWasm0(arg, malloc, realloc) {
  if (realloc === void 0) {
    const buf = cachedTextEncoder.encode(arg);
    const ptr2 = malloc(buf.length, 1) >>> 0;
    getUint8ArrayMemory0().subarray(ptr2, ptr2 + buf.length).set(buf);
    WASM_VECTOR_LEN = buf.length;
    return ptr2;
  }
  let len = arg.length;
  let ptr = malloc(len, 1) >>> 0;
  const mem = getUint8ArrayMemory0();
  let offset = 0;
  for (; offset < len; offset++) {
    const code = arg.charCodeAt(offset);
    if (code > 127) break;
    mem[ptr + offset] = code;
  }
  if (offset !== len) {
    if (offset !== 0) {
      arg = arg.slice(offset);
    }
    ptr = realloc(ptr, len, len = offset + arg.length * 3, 1) >>> 0;
    const view = getUint8ArrayMemory0().subarray(ptr + offset, ptr + len);
    const ret = encodeString(arg, view);
    offset += ret.written;
    ptr = realloc(ptr, len, offset, 1) >>> 0;
  }
  WASM_VECTOR_LEN = offset;
  return ptr;
}
var cachedDataViewMemory0 = null;
function getDataViewMemory0() {
  if (cachedDataViewMemory0 === null || cachedDataViewMemory0.buffer.detached === true || cachedDataViewMemory0.buffer.detached === void 0 && cachedDataViewMemory0.buffer !== wasm.memory.buffer) {
    cachedDataViewMemory0 = new DataView(wasm.memory.buffer);
  }
  return cachedDataViewMemory0;
}
function isLikeNone(x) {
  return x === void 0 || x === null;
}
function main() {
  wasm.main();
}
function takeFromExternrefTable0(idx) {
  const value = wasm.__wbindgen_export_3.get(idx);
  wasm.__externref_table_dealloc(idx);
  return value;
}
function decode_png_to_rgba(png_bytes) {
  const ret = wasm.decode_png_to_rgba(png_bytes);
  if (ret[2]) {
    throw takeFromExternrefTable0(ret[1]);
  }
  return takeFromExternrefTable0(ret[0]);
}
function encode_palette_to_png(palette_indices, palette, width, height) {
  const ret = wasm.encode_palette_to_png(palette_indices, palette, width, height);
  if (ret[2]) {
    throw takeFromExternrefTable0(ret[1]);
  }
  return takeFromExternrefTable0(ret[0]);
}
var ImageQuantizerFinalization = typeof FinalizationRegistry === "undefined" ? { register: () => {
}, unregister: () => {
} } : new FinalizationRegistry((ptr) => wasm.__wbg_imagequantizer_free(ptr >>> 0, 1));
var ImageQuantizer = class {
  __destroy_into_raw() {
    const ptr = this.__wbg_ptr;
    this.__wbg_ptr = 0;
    ImageQuantizerFinalization.unregister(this);
    return ptr;
  }
  free() {
    const ptr = this.__destroy_into_raw();
    wasm.__wbg_imagequantizer_free(ptr, 0);
  }
  constructor() {
    const ret = wasm.imagequantizer_new();
    this.__wbg_ptr = ret >>> 0;
    ImageQuantizerFinalization.register(this, this.__wbg_ptr, this);
    return this;
  }
  /**
   * @param {number} speed
   */
  setSpeed(speed) {
    const ret = wasm.imagequantizer_setSpeed(this.__wbg_ptr, speed);
    if (ret[1]) {
      throw takeFromExternrefTable0(ret[0]);
    }
  }
  /**
   * @param {number} min
   * @param {number} target
   */
  setQuality(min, target) {
    const ret = wasm.imagequantizer_setQuality(this.__wbg_ptr, min, target);
    if (ret[1]) {
      throw takeFromExternrefTable0(ret[0]);
    }
  }
  /**
   * @param {number} colors
   */
  setMaxColors(colors) {
    const ret = wasm.imagequantizer_setMaxColors(this.__wbg_ptr, colors);
    if (ret[1]) {
      throw takeFromExternrefTable0(ret[0]);
    }
  }
  /**
   * @param {number} posterization
   */
  setPosterization(posterization) {
    const ret = wasm.imagequantizer_setPosterization(this.__wbg_ptr, posterization);
    if (ret[1]) {
      throw takeFromExternrefTable0(ret[0]);
    }
  }
  /**
   * @param {Uint8ClampedArray} rgba_data
   * @param {number} width
   * @param {number} height
   * @returns {QuantizationResult}
   */
  quantizeImage(rgba_data, width, height) {
    const ret = wasm.imagequantizer_quantizeImage(this.__wbg_ptr, rgba_data, width, height);
    if (ret[2]) {
      throw takeFromExternrefTable0(ret[1]);
    }
    return QuantizationResult.__wrap(ret[0]);
  }
};
var QuantizationResultFinalization = typeof FinalizationRegistry === "undefined" ? { register: () => {
}, unregister: () => {
} } : new FinalizationRegistry((ptr) => wasm.__wbg_quantizationresult_free(ptr >>> 0, 1));
var QuantizationResult = class _QuantizationResult {
  static __wrap(ptr) {
    ptr = ptr >>> 0;
    const obj = Object.create(_QuantizationResult.prototype);
    obj.__wbg_ptr = ptr;
    QuantizationResultFinalization.register(obj, obj.__wbg_ptr, obj);
    return obj;
  }
  __destroy_into_raw() {
    const ptr = this.__wbg_ptr;
    this.__wbg_ptr = 0;
    QuantizationResultFinalization.unregister(this);
    return ptr;
  }
  free() {
    const ptr = this.__destroy_into_raw();
    wasm.__wbg_quantizationresult_free(ptr, 0);
  }
  /**
   * @returns {Array<any>}
   */
  getPalette() {
    const ret = wasm.quantizationresult_getPalette(this.__wbg_ptr);
    return ret;
  }
  /**
   * @returns {number}
   */
  getPaletteLength() {
    const ret = wasm.quantizationresult_getPaletteLength(this.__wbg_ptr);
    return ret >>> 0;
  }
  /**
   * @returns {number}
   */
  getQuantizationQuality() {
    const ret = wasm.quantizationresult_getQuantizationQuality(this.__wbg_ptr);
    return ret;
  }
  /**
   * @param {number} dithering_level
   */
  setDithering(dithering_level) {
    const ret = wasm.quantizationresult_setDithering(this.__wbg_ptr, dithering_level);
    if (ret[1]) {
      throw takeFromExternrefTable0(ret[0]);
    }
  }
  /**
   * @param {Uint8ClampedArray} rgba_data
   * @param {number} width
   * @param {number} height
   * @returns {Uint8ClampedArray}
   */
  remapImage(rgba_data, width, height) {
    const ret = wasm.quantizationresult_remapImage(this.__wbg_ptr, rgba_data, width, height);
    if (ret[2]) {
      throw takeFromExternrefTable0(ret[1]);
    }
    return takeFromExternrefTable0(ret[0]);
  }
  /**
   * @param {Uint8ClampedArray} rgba_data
   * @param {number} width
   * @param {number} height
   * @returns {Uint8Array}
   */
  getPaletteIndices(rgba_data, width, height) {
    const ret = wasm.quantizationresult_getPaletteIndices(this.__wbg_ptr, rgba_data, width, height);
    if (ret[2]) {
      throw takeFromExternrefTable0(ret[1]);
    }
    return takeFromExternrefTable0(ret[0]);
  }
};
async function __wbg_load(module, imports) {
  if (typeof Response === "function" && module instanceof Response) {
    if (typeof WebAssembly.instantiateStreaming === "function") {
      try {
        return await WebAssembly.instantiateStreaming(module, imports);
      } catch (e) {
        if (module.headers.get("Content-Type") != "application/wasm") {
          console.warn("`WebAssembly.instantiateStreaming` failed because your server does not serve Wasm with `application/wasm` MIME type. Falling back to `WebAssembly.instantiate` which is slower. Original error:\n", e);
        } else {
          throw e;
        }
      }
    }
    const bytes = await module.arrayBuffer();
    return await WebAssembly.instantiate(bytes, imports);
  } else {
    const instance = await WebAssembly.instantiate(module, imports);
    if (instance instanceof WebAssembly.Instance) {
      return { instance, module };
    } else {
      return instance;
    }
  }
}
function __wbg_get_imports() {
  const imports = {};
  imports.wbg = {};
  imports.wbg.__wbg_buffer_609cc3eee51ed158 = function(arg0) {
    const ret = arg0.buffer;
    return ret;
  };
  imports.wbg.__wbg_error_7534b8e9a36f1ab4 = function(arg0, arg1) {
    let deferred0_0;
    let deferred0_1;
    try {
      deferred0_0 = arg0;
      deferred0_1 = arg1;
      console.error(getStringFromWasm0(arg0, arg1));
    } finally {
      wasm.__wbindgen_free(deferred0_0, deferred0_1, 1);
    }
  };
  imports.wbg.__wbg_get_b9b93047fe3cf45b = function(arg0, arg1) {
    const ret = arg0[arg1 >>> 0];
    return ret;
  };
  imports.wbg.__wbg_isArray_a1eab7e0d067391b = function(arg0) {
    const ret = Array.isArray(arg0);
    return ret;
  };
  imports.wbg.__wbg_length_238152a0aedbb6e7 = function(arg0) {
    const ret = arg0.length;
    return ret;
  };
  imports.wbg.__wbg_length_a446193dc22c12f8 = function(arg0) {
    const ret = arg0.length;
    return ret;
  };
  imports.wbg.__wbg_length_e2d2a49132c1b256 = function(arg0) {
    const ret = arg0.length;
    return ret;
  };
  imports.wbg.__wbg_new_78feb108b6472713 = function() {
    const ret = new Array();
    return ret;
  };
  imports.wbg.__wbg_new_7a91e41fe43b3c92 = function(arg0) {
    const ret = new Uint8ClampedArray(arg0);
    return ret;
  };
  imports.wbg.__wbg_new_8a6f238a6ece86ea = function() {
    const ret = new Error();
    return ret;
  };
  imports.wbg.__wbg_new_a12002a7f91c75be = function(arg0) {
    const ret = new Uint8Array(arg0);
    return ret;
  };
  imports.wbg.__wbg_newwithbyteoffsetandlength_6d34787141015158 = function(arg0, arg1, arg2) {
    const ret = new Uint8ClampedArray(arg0, arg1 >>> 0, arg2 >>> 0);
    return ret;
  };
  imports.wbg.__wbg_newwithbyteoffsetandlength_d97e637ebe145a9a = function(arg0, arg1, arg2) {
    const ret = new Uint8Array(arg0, arg1 >>> 0, arg2 >>> 0);
    return ret;
  };
  imports.wbg.__wbg_push_737cfc8c1432c2c6 = function(arg0, arg1) {
    const ret = arg0.push(arg1);
    return ret;
  };
  imports.wbg.__wbg_set_65595bdd868b3009 = function(arg0, arg1, arg2) {
    arg0.set(arg1, arg2 >>> 0);
  };
  imports.wbg.__wbg_set_6775f73144c2ef27 = function(arg0, arg1, arg2) {
    arg0.set(arg1, arg2 >>> 0);
  };
  imports.wbg.__wbg_stack_0ed75d68575b0f3c = function(arg0, arg1) {
    const ret = arg1.stack;
    const ptr1 = passStringToWasm0(ret, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
    const len1 = WASM_VECTOR_LEN;
    getDataViewMemory0().setInt32(arg0 + 4 * 1, len1, true);
    getDataViewMemory0().setInt32(arg0 + 4 * 0, ptr1, true);
  };
  imports.wbg.__wbindgen_init_externref_table = function() {
    const table = wasm.__wbindgen_export_3;
    const offset = table.grow(4);
    table.set(0, void 0);
    table.set(offset + 0, void 0);
    table.set(offset + 1, null);
    table.set(offset + 2, true);
    table.set(offset + 3, false);
    ;
  };
  imports.wbg.__wbindgen_memory = function() {
    const ret = wasm.memory;
    return ret;
  };
  imports.wbg.__wbindgen_number_get = function(arg0, arg1) {
    const obj = arg1;
    const ret = typeof obj === "number" ? obj : void 0;
    getDataViewMemory0().setFloat64(arg0 + 8 * 1, isLikeNone(ret) ? 0 : ret, true);
    getDataViewMemory0().setInt32(arg0 + 4 * 0, !isLikeNone(ret), true);
  };
  imports.wbg.__wbindgen_number_new = function(arg0) {
    const ret = arg0;
    return ret;
  };
  imports.wbg.__wbindgen_string_new = function(arg0, arg1) {
    const ret = getStringFromWasm0(arg0, arg1);
    return ret;
  };
  imports.wbg.__wbindgen_throw = function(arg0, arg1) {
    throw new Error(getStringFromWasm0(arg0, arg1));
  };
  return imports;
}
function __wbg_init_memory(imports, memory) {
}
function __wbg_finalize_init(instance, module) {
  wasm = instance.exports;
  __wbg_init.__wbindgen_wasm_module = module;
  cachedDataViewMemory0 = null;
  cachedUint8ArrayMemory0 = null;
  wasm.__wbindgen_start();
  return wasm;
}
function initSync(module) {
  if (wasm !== void 0) return wasm;
  if (typeof module !== "undefined") {
    if (Object.getPrototypeOf(module) === Object.prototype) {
      ({ module } = module);
    } else {
      console.warn("using deprecated parameters for `initSync()`; pass a single object instead");
    }
  }
  const imports = __wbg_get_imports();
  __wbg_init_memory(imports);
  if (!(module instanceof WebAssembly.Module)) {
    module = new WebAssembly.Module(module);
  }
  const instance = new WebAssembly.Instance(module, imports);
  return __wbg_finalize_init(instance, module);
}
async function __wbg_init(module_or_path) {
  if (wasm !== void 0) return wasm;
  if (typeof module_or_path !== "undefined") {
    if (Object.getPrototypeOf(module_or_path) === Object.prototype) {
      ({ module_or_path } = module_or_path);
    } else {
      console.warn("using deprecated parameters for the initialization function; pass a single object instead");
    }
  }
  if (typeof module_or_path === "undefined") {
    module_or_path = new URL("wasm/libimagequant_wasm_bg.wasm", import.meta.url);
  }
  const imports = __wbg_get_imports();
  if (typeof module_or_path === "string" || typeof Request === "function" && module_or_path instanceof Request || typeof URL === "function" && module_or_path instanceof URL) {
    module_or_path = fetch(module_or_path);
  }
  __wbg_init_memory(imports);
  const { instance, module } = await __wbg_load(await module_or_path, imports);
  return __wbg_finalize_init(instance, module);
}
var libimagequant_wasm_default = __wbg_init;

// oxipng-wasm/pkg/oxipng_wasm.js
var OxipngOptions = class {
  __destroy_into_raw() {
    const ptr = this.__wbg_ptr;
    this.__wbg_ptr = 0;
    OxipngOptionsFinalization.unregister(this);
    return ptr;
  }
  free() {
    const ptr = this.__destroy_into_raw();
    wasm2.__wbg_oxipngoptions_free(ptr, 0);
  }
  constructor() {
    const ret = wasm2.oxipngoptions_new();
    this.__wbg_ptr = ret;
    OxipngOptionsFinalization.register(this, this.__wbg_ptr, this);
    return this;
  }
  /**
   * @param {boolean} v
   */
  set alpha(v) {
    wasm2.oxipngoptions_set_alpha(this.__wbg_ptr, v);
  }
  /**
   * @param {number} level
   */
  set level(level) {
    wasm2.oxipngoptions_set_level(this.__wbg_ptr, level);
  }
  /**
   * @param {boolean} v
   */
  set strip_all(v) {
    wasm2.oxipngoptions_set_strip_all(this.__wbg_ptr, v);
  }
};
if (Symbol.dispose) OxipngOptions.prototype[Symbol.dispose] = OxipngOptions.prototype.free;
function optimize(data, opts) {
  try {
    const retptr = wasm2.__wbindgen_add_to_stack_pointer(-16);
    const ptr0 = passArray8ToWasm0(data, wasm2.__wbindgen_export);
    const len0 = WASM_VECTOR_LEN2;
    _assertClass(opts, OxipngOptions);
    wasm2.optimize(retptr, ptr0, len0, opts.__wbg_ptr);
    var r0 = getDataViewMemory02().getInt32(retptr + 4 * 0, true);
    var r1 = getDataViewMemory02().getInt32(retptr + 4 * 1, true);
    var r2 = getDataViewMemory02().getInt32(retptr + 4 * 2, true);
    var r3 = getDataViewMemory02().getInt32(retptr + 4 * 3, true);
    if (r3) {
      throw takeObject(r2);
    }
    var v2 = getArrayU8FromWasm0(r0, r1).slice();
    wasm2.__wbindgen_export2(r0, r1 * 1, 1);
    return v2;
  } finally {
    wasm2.__wbindgen_add_to_stack_pointer(16);
  }
}
function __wbg_get_imports2() {
  const import0 = {
    __proto__: null,
    __wbg___wbindgen_throw_bb96b2010945f0bc: function(arg0, arg1) {
      throw new Error(getStringFromWasm02(arg0, arg1));
    },
    __wbindgen_cast_0000000000000001: function(arg0, arg1) {
      const ret = getStringFromWasm02(arg0, arg1);
      return addHeapObject(ret);
    }
  };
  return {
    __proto__: null,
    "./oxipng_wasm_bg.js": import0
  };
}
var OxipngOptionsFinalization = typeof FinalizationRegistry === "undefined" ? { register: () => {
}, unregister: () => {
} } : new FinalizationRegistry((ptr) => wasm2.__wbg_oxipngoptions_free(ptr, 1));
function addHeapObject(obj) {
  if (heap_next === heap.length) heap.push(heap.length + 1);
  const idx = heap_next;
  heap_next = heap[idx];
  heap[idx] = obj;
  return idx;
}
function _assertClass(instance, klass) {
  if (!(instance instanceof klass)) {
    throw new Error(`expected instance of ${klass.name}`);
  }
}
function dropObject(idx) {
  if (idx < 1028) return;
  heap[idx] = heap_next;
  heap_next = idx;
}
function getArrayU8FromWasm0(ptr, len) {
  ptr = ptr >>> 0;
  return getUint8ArrayMemory02().subarray(ptr / 1, ptr / 1 + len);
}
var cachedDataViewMemory02 = null;
function getDataViewMemory02() {
  if (cachedDataViewMemory02 === null || cachedDataViewMemory02.buffer.detached === true || cachedDataViewMemory02.buffer.detached === void 0 && cachedDataViewMemory02.buffer !== wasm2.memory.buffer) {
    cachedDataViewMemory02 = new DataView(wasm2.memory.buffer);
  }
  return cachedDataViewMemory02;
}
function getStringFromWasm02(ptr, len) {
  return decodeText(ptr >>> 0, len);
}
var cachedUint8ArrayMemory02 = null;
function getUint8ArrayMemory02() {
  if (cachedUint8ArrayMemory02 === null || cachedUint8ArrayMemory02.byteLength === 0) {
    cachedUint8ArrayMemory02 = new Uint8Array(wasm2.memory.buffer);
  }
  return cachedUint8ArrayMemory02;
}
function getObject(idx) {
  return heap[idx];
}
var heap = new Array(1024).fill(void 0);
heap.push(void 0, null, true, false);
var heap_next = heap.length;
function passArray8ToWasm0(arg, malloc) {
  const ptr = malloc(arg.length * 1, 1) >>> 0;
  getUint8ArrayMemory02().set(arg, ptr / 1);
  WASM_VECTOR_LEN2 = arg.length;
  return ptr;
}
function takeObject(idx) {
  const ret = getObject(idx);
  dropObject(idx);
  return ret;
}
var cachedTextDecoder2 = new TextDecoder("utf-8", { ignoreBOM: true, fatal: true });
cachedTextDecoder2.decode();
var MAX_SAFARI_DECODE_BYTES = 2146435072;
var numBytesDecoded = 0;
function decodeText(ptr, len) {
  numBytesDecoded += len;
  if (numBytesDecoded >= MAX_SAFARI_DECODE_BYTES) {
    cachedTextDecoder2 = new TextDecoder("utf-8", { ignoreBOM: true, fatal: true });
    cachedTextDecoder2.decode();
    numBytesDecoded = len;
  }
  return cachedTextDecoder2.decode(getUint8ArrayMemory02().subarray(ptr, ptr + len));
}
var WASM_VECTOR_LEN2 = 0;
var wasmModule;
var wasmInstance;
var wasm2;
function __wbg_finalize_init2(instance, module) {
  wasmInstance = instance;
  wasm2 = instance.exports;
  wasmModule = module;
  cachedDataViewMemory02 = null;
  cachedUint8ArrayMemory02 = null;
  return wasm2;
}
async function __wbg_load2(module, imports) {
  if (typeof Response === "function" && module instanceof Response) {
    if (!module.ok) {
      throw new Error(`failed to fetch Wasm: ${module.status} ${module.statusText} fetching '${module.url}'`);
    }
    if (typeof WebAssembly.instantiateStreaming === "function") {
      try {
        return await WebAssembly.instantiateStreaming(module, imports);
      } catch (e) {
        const validResponse = expectedResponseType(module.type);
        if (validResponse && module.headers.get("Content-Type") !== "application/wasm") {
          console.warn("`WebAssembly.instantiateStreaming` failed because your server does not serve Wasm with `application/wasm` MIME type. Falling back to `WebAssembly.instantiate` which is slower. Original error:\n", e);
        } else {
          throw e;
        }
      }
    }
    const bytes = await module.arrayBuffer();
    return await WebAssembly.instantiate(bytes, imports);
  } else {
    const instance = await WebAssembly.instantiate(module, imports);
    if (instance instanceof WebAssembly.Instance) {
      return { instance, module };
    } else {
      return instance;
    }
  }
  function expectedResponseType(type) {
    switch (type) {
      case "basic":
      case "cors":
      case "default":
        return true;
    }
    return false;
  }
}
async function __wbg_init2(module_or_path) {
  if (wasm2 !== void 0) return wasm2;
  if (module_or_path !== void 0) {
    if (Object.getPrototypeOf(module_or_path) === Object.prototype) {
      ({ module_or_path } = module_or_path);
    } else {
      console.warn("using deprecated parameters for the initialization function; pass a single object instead");
    }
  }
  if (module_or_path === void 0) {
    module_or_path = new URL("oxipng_wasm_bg.wasm", import.meta.url);
  }
  const imports = __wbg_get_imports2();
  if (typeof module_or_path === "string" || typeof Request === "function" && module_or_path instanceof Request || typeof URL === "function" && module_or_path instanceof URL) {
    module_or_path = fetch(module_or_path);
  }
  const { instance, module } = await __wbg_load2(await module_or_path, imports);
  return __wbg_finalize_init2(instance, module);
}

// src/worker.js
var quantizer;
async function getQuantizer() {
  if (!quantizer) {
    quantizer = new LibImageQuant({ wasmModule: libimagequant_wasm_exports });
  }
  return quantizer;
}
var cjpegliWasm = null;
var cjpegliFailed = false;
var HEAPU32 = null;
var extBase = self.location.href.replace(/[^/]*$/, "");
function updateMemoryViews() {
  if (!cjpegliWasm) return;
  HEAPU32 = new Uint32Array(cjpegliWasm.memory.buffer);
}
async function getCjpegli() {
  if (cjpegliWasm && !cjpegliFailed) return cjpegliWasm;
  cjpegliFailed = false;
  try {
    const wasmUrl = extBase + "wasm/cjpegli.wasm";
    const response = await fetch(wasmUrl);
    if (!response.ok) {
      throw new Error(`WASM fetch fehlgeschlagen: ${response.status} ${response.url}`);
    }
    const bytes = await response.arrayBuffer();
    const importObject = {
      env: {
        emscripten_notify_memory_growth: () => updateMemoryViews(),
        fd_close: () => 52,
        fd_seek: () => 70,
        fd_write: (fd, iov, iovcnt, pnum) => {
          let num = 0;
          for (let i = 0; i < iovcnt; i++) {
            const ptr = HEAPU32[iov >> 2];
            const len = HEAPU32[iov + 4 >> 2];
            iov += 8;
            num += len;
          }
          HEAPU32[pnum >> 2] = num;
          return 0;
        },
        proc_exit: (code) => {
          console.log("[cjpegli] proc_exit:", code);
        }
      },
      wasi_snapshot_preview1: {
        fd_close: () => 52,
        fd_seek: () => 70,
        fd_write: (fd, iov, iovcnt, pnum) => {
          let num = 0;
          for (let i = 0; i < iovcnt; i++) {
            const ptr = HEAPU32[iov >> 2];
            const len = HEAPU32[iov + 4 >> 2];
            iov += 8;
            num += len;
          }
          HEAPU32[pnum >> 2] = num;
          return 0;
        },
        proc_exit: (code) => {
          console.log("[cjpegli] proc_exit:", code);
        }
      }
    };
    const result = await WebAssembly.instantiate(bytes, importObject);
    const instance = result.instance || result;
    const exports = instance.exports;
    cjpegliWasm = {
      encode: exports.encode,
      get_size: exports.get_size,
      malloc: exports.malloc,
      free: exports.free,
      initialize: exports._initialize,
      memory: exports.memory
    };
    updateMemoryViews();
    if (cjpegliWasm.initialize) {
      cjpegliWasm.initialize();
    }
    console.log("[cjpegli] WASM geladen, Memory:", cjpegliWasm.memory.buffer.byteLength, "bytes");
    return cjpegliWasm;
  } catch (err) {
    cjpegliFailed = true;
    throw err;
  }
}
var oxipngReady = false;
var oxipngFailed = false;
async function ensureOxipng() {
  if (oxipngReady || oxipngFailed) return;
  try {
    await __wbg_init2(extBase + "wasm/oxipng_wasm_bg.wasm");
    oxipngReady = true;
    console.log("oxipng WASM geladen (eigenes Build, oxipng 10.x)");
  } catch (err) {
    oxipngFailed = true;
    console.warn("oxipng Initialisierung fehlgeschlagen", err.message);
  }
}
async function optimisePngImpl(pngBytes, options) {
  if (!oxipngReady && !oxipngFailed) await ensureOxipng();
  if (oxipngFailed) return pngBytes;
  let opts = null;
  try {
    opts = new OxipngOptions();
    const level = Math.min(6, Math.max(1, options?.oxipngLevel ?? 2));
    const optimiseAlpha = options?.oxipngAlpha !== false;
    opts.level = level;
    opts.alpha = optimiseAlpha;
    opts.strip_all = false;
    const result = optimize(pngBytes, opts);
    if (result.length < pngBytes.length) {
      console.log(`oxipng L${level}${optimiseAlpha ? "+alpha" : ""}: ${pngBytes.length} B \u2192 ${result.length} B (\u2212${(100 - result.length / pngBytes.length * 100).toFixed(1)}%)`);
      return result;
    }
    console.log(`oxipng L${level}: keine Verbesserung (${pngBytes.length} B)`);
    return pngBytes;
  } catch (e) {
    console.warn("oxipng Optimierung fehlgeschlagen", e.message);
    return pngBytes;
  } finally {
    opts?.free();
  }
}
var PNG_PRESERVE = /* @__PURE__ */ new Set([
  "tEXt",
  "iTXt",
  "zTXt",
  "eXIf",
  "iCCP",
  "sRGB",
  "gAMA",
  "cHRM",
  "pHYs",
  "tIME",
  "sTER"
]);
function readUint32BE(bytes, offset) {
  return bytes[offset] * 16777216 + (bytes[offset + 1] << 16 | bytes[offset + 2] << 8 | bytes[offset + 3]);
}
function extractPngMetadata(bytes) {
  if (!(bytes instanceof Uint8Array) || bytes.length < 8) return [];
  if (bytes[0] !== 137 || bytes[1] !== 80 || bytes[2] !== 71) return [];
  const chunks = [];
  let offset = 8;
  while (offset + 8 <= bytes.length) {
    const length = readUint32BE(bytes, offset);
    const type = String.fromCharCode(bytes[offset + 4], bytes[offset + 5], bytes[offset + 6], bytes[offset + 7]);
    if (type === "IDAT") break;
    if (PNG_PRESERVE.has(type)) {
      const chunkEnd = offset + 12 + length;
      if (chunkEnd <= bytes.length) chunks.push(bytes.slice(offset, chunkEnd));
    }
    offset += 12 + length;
  }
  return chunks;
}
function injectPngMetadata(pngBytes, metadataChunks) {
  if (!metadataChunks || metadataChunks.length === 0) return pngBytes;
  if (pngBytes.length < 33) return pngBytes;
  const ihdrEnd = 8 + 25;
  if (ihdrEnd > pngBytes.length) return pngBytes;
  const existingTypes = /* @__PURE__ */ new Set();
  let pos = ihdrEnd;
  while (pos + 8 <= pngBytes.length) {
    const type = String.fromCharCode(pngBytes[pos + 4], pngBytes[pos + 5], pngBytes[pos + 6], pngBytes[pos + 7]);
    if (type === "IDAT" || type === "IEND") break;
    existingTypes.add(type);
    const len = readUint32BE(pngBytes, pos);
    pos += 12 + len;
  }
  const parts = [pngBytes.slice(0, ihdrEnd)];
  for (const chunk of metadataChunks) {
    const type = String.fromCharCode(chunk[4], chunk[5], chunk[6], chunk[7]);
    if (!existingTypes.has(type)) parts.push(chunk);
  }
  parts.push(pngBytes.slice(ihdrEnd));
  const totalLength = parts.reduce((s, p) => s + p.length, 0);
  const result = new Uint8Array(totalLength);
  let writePos = 0;
  for (const part of parts) {
    result.set(part, writePos);
    writePos += part.length;
  }
  if (metadataChunks.length > 0) {
    const preserved = metadataChunks.filter((c) => !existingTypes.has(String.fromCharCode(c[4], c[5], c[6], c[7])));
    if (preserved.length > 0) console.log(`[meta] PNG: ${preserved.length} Chunk(s) injiziert (${preserved.map((c) => String.fromCharCode(c[4], c[5], c[6], c[7])).join(", ")})`);
  }
  return result;
}
function extractJpegMetadata(bytes) {
  if (!(bytes instanceof Uint8Array) || bytes.length < 4) return [];
  if (bytes[0] !== 255 || bytes[1] !== 216) return [];
  const markers = [];
  let offset = 2;
  while (offset + 3 < bytes.length) {
    if (bytes[offset] !== 255) {
      offset++;
      continue;
    }
    let marker = bytes[offset + 1];
    while (marker === 255 && offset + 2 < bytes.length) {
      offset++;
      marker = bytes[offset + 1];
    }
    if (marker === 218) break;
    if (marker === 216 || marker === 217 || marker >= 208 && marker <= 215) {
      offset += 2;
      continue;
    }
    const length = bytes[offset + 2] << 8 | bytes[offset + 3];
    const markerEnd = offset + 2 + length;
    if (markerEnd > bytes.length) break;
    if (marker >= 224 && marker <= 239 || marker === 254) markers.push(bytes.slice(offset, markerEnd));
    offset = markerEnd;
  }
  return markers;
}
function injectJpegMetadata(jpegBytes, metadataMarkers) {
  if (!metadataMarkers || metadataMarkers.length === 0) return jpegBytes;
  if (jpegBytes.length < 2) return jpegBytes;
  if (jpegBytes[0] !== 255 || jpegBytes[1] !== 216) return jpegBytes;
  const parts = [jpegBytes.slice(0, 2)];
  for (const marker of metadataMarkers) parts.push(marker);
  parts.push(jpegBytes.slice(2));
  const totalLength = parts.reduce((s, p) => s + p.length, 0);
  const result = new Uint8Array(totalLength);
  let writePos = 0;
  for (const part of parts) {
    result.set(part, writePos);
    writePos += part.length;
  }
  const types = metadataMarkers.map((m) => "APP" + (m[1] - 224));
  console.log(`[meta] JPEG: ${metadataMarkers.length} Marker injiziert (${types.join(", ")})`);
  return result;
}
var CHROMA_RANK = { "420": 0, "422": 1, "440": 2, "444": 3 };
function detectJpegChromaSubsampling(bytes) {
  if (!(bytes instanceof Uint8Array) || bytes.length < 4) return null;
  if (bytes[0] !== 255 || bytes[1] !== 216) return null;
  let i = 2;
  while (i + 1 < bytes.length) {
    if (bytes[i] !== 255) {
      i++;
      continue;
    }
    let marker = bytes[i + 1];
    while (marker === 255 && i + 2 < bytes.length) {
      i++;
      marker = bytes[i + 1];
    }
    if (marker >= 192 && marker <= 207 && marker !== 196 && marker !== 200 && marker !== 204) {
      if (i + 9 >= bytes.length) return null;
      const numComponents = bytes[i + 9];
      if (numComponents !== 3) return null;
      const compStart = i + 10;
      const sf = [];
      for (let c = 0; c < 3; c++) {
        const offset = compStart + c * 3;
        if (offset + 1 >= bytes.length) return null;
        const s = bytes[offset + 1];
        sf.push({ h: s >> 4 & 15, v: s & 15 });
      }
      const yH = sf[0].h, yV = sf[0].v;
      const cbH = sf[1].h, cbV = sf[1].v;
      if (yH === 2 && yV === 2 && cbH === 1 && cbV === 1) return "420";
      if (yH === 2 && yV === 1 && cbH === 1 && cbV === 1) return "422";
      if (yH === 1 && yV === 2 && cbH === 1 && cbV === 1) return "440";
      if (yH === 1 && yV === 1 && cbH === 1 && cbV === 1) return "444";
      return "444";
    }
    if (marker === 216 || marker === 217 || marker >= 208 && marker <= 215) {
      i += 2;
    } else if (marker === 218) break;
    else {
      if (i + 3 >= bytes.length) return null;
      const length = bytes[i + 2] << 8 | bytes[i + 3];
      i += 2 + length;
    }
  }
  return null;
}
function limitChromaSubsampling(originalChroma, userChroma) {
  const valid = ["444", "440", "422", "420"];
  const user = valid.includes(userChroma) ? userChroma : "420";
  if (!originalChroma || !valid.includes(originalChroma)) return user;
  return CHROMA_RANK[originalChroma] < CHROMA_RANK[user] ? originalChroma : user;
}
var SMOOTHING_MAP = {
  "bilinear": "low",
  "bicubic": "medium",
  "lanczos": "high",
  "mitchell": "high",
  "auto": "high"
};
function applySmoothingQuality(ctx, algorithm) {
  if (algorithm === "nearest") {
    ctx.imageSmoothingEnabled = false;
  } else {
    ctx.imageSmoothingEnabled = true;
    ctx.imageSmoothingQuality = SMOOTHING_MAP[algorithm] || "high";
  }
}
function resizeViaCanvas(imageData, dstW, dstH, algorithm) {
  const srcCanvas = new OffscreenCanvas(imageData.width, imageData.height);
  const srcCtx = srcCanvas.getContext("2d", { willReadFrequently: true });
  srcCtx.putImageData(imageData, 0, 0);
  const dstCanvas = new OffscreenCanvas(dstW, dstH);
  const dstCtx = dstCanvas.getContext("2d", { willReadFrequently: true });
  applySmoothingQuality(dstCtx, algorithm);
  dstCtx.drawImage(srcCanvas, 0, 0, dstW, dstH);
  return dstCtx.getImageData(0, 0, dstW, dstH);
}
var LANCZOS_A = 3;
function lanczosWeight(distance, scale) {
  const x = scale > 1 ? distance / scale : distance;
  if (x === 0) return 1;
  if (Math.abs(x) >= LANCZOS_A) return 0;
  const px = Math.PI * x;
  return Math.sin(px) / px * (Math.sin(px / LANCZOS_A) / (px / LANCZOS_A));
}
var MITCHELL_B = 1 / 3;
var MITCHELL_C = 1 / 3;
var MITCHELL_SUPPORT = 2;
function mitchellWeight(distance, scale) {
  const x = scale > 1 ? distance / scale : distance;
  const ax = Math.abs(x);
  if (ax >= MITCHELL_SUPPORT) return 0;
  const B = MITCHELL_B;
  const C = MITCHELL_C;
  const x2 = ax * ax;
  const x3 = x2 * ax;
  if (ax < 1) {
    return 1 / 6 * ((12 - 9 * B - 6 * C) * x3 + (-18 + 12 * B + 6 * C) * x2 + (6 - 2 * B));
  } else {
    return 1 / 6 * ((-B - 6 * C) * x3 + (6 * B + 30 * C) * x2 + (-12 * B - 48 * C) * ax + (8 * B + 24 * C));
  }
}
function precomputeWeights(srcSize, dstSize, weightFn, supportRadius) {
  const scale = srcSize / dstSize;
  const support = scale > 1 ? supportRadius * scale : supportRadius;
  const weights = new Array(dstSize);
  for (let dst = 0; dst < dstSize; dst++) {
    const center = (dst + 0.5) * scale - 0.5;
    const left = Math.max(0, Math.floor(center - support));
    const right = Math.min(srcSize - 1, Math.ceil(center + support));
    const w = [];
    let sum = 0;
    for (let src = left; src <= right; src++) {
      const weight = weightFn(center - src, scale);
      if (weight !== 0) {
        w.push(src, weight);
        sum += weight;
      }
    }
    if (sum !== 0) {
      for (let i = 1; i < w.length; i += 2) w[i] /= sum;
    }
    weights[dst] = w;
  }
  return weights;
}
function resizeWithFilter(imageData, dstW, dstH, weightFn, supportRadius) {
  const { width: srcW, height: srcH, data: src } = imageData;
  if (srcW === dstW && srcH === dstH) return imageData;
  const xWeights = precomputeWeights(srcW, dstW, weightFn, supportRadius);
  const yWeights = precomputeWeights(srcH, dstH, weightFn, supportRadius);
  const temp = new Float32Array(dstW * srcH * 4);
  for (let y = 0; y < srcH; y++) {
    const sRow = y * srcW * 4;
    const tRow = y * dstW * 4;
    for (let x = 0; x < dstW; x++) {
      const w = xWeights[x];
      let r = 0, g = 0, b = 0, a = 0;
      for (let i = 0; i < w.length; i += 2) {
        const idx = sRow + (w[i] | 0) * 4;
        const wt = w[i + 1];
        r += src[idx] * wt;
        g += src[idx + 1] * wt;
        b += src[idx + 2] * wt;
        a += src[idx + 3] * wt;
      }
      const o = tRow + x * 4;
      temp[o] = r;
      temp[o + 1] = g;
      temp[o + 2] = b;
      temp[o + 3] = a;
    }
  }
  const dst = new Uint8ClampedArray(dstW * dstH * 4);
  for (let y = 0; y < dstH; y++) {
    const w = yWeights[y];
    for (let x = 0; x < dstW; x++) {
      let r = 0, g = 0, b = 0, a = 0;
      for (let i = 0; i < w.length; i += 2) {
        const idx = (w[i] | 0) * dstW * 4 + x * 4;
        const wt = w[i + 1];
        r += temp[idx] * wt;
        g += temp[idx + 1] * wt;
        b += temp[idx + 2] * wt;
        a += temp[idx + 3] * wt;
      }
      const o = y * dstW * 4 + x * 4;
      dst[o] = r;
      dst[o + 1] = g;
      dst[o + 2] = b;
      dst[o + 3] = a;
    }
  }
  return new ImageData(dst, dstW, dstH);
}
function resizeLanczos(imageData, dstW, dstH) {
  return resizeWithFilter(imageData, dstW, dstH, lanczosWeight, LANCZOS_A);
}
function resizeMitchell(imageData, dstW, dstH) {
  return resizeWithFilter(imageData, dstW, dstH, mitchellWeight, MITCHELL_SUPPORT);
}
async function decodeImage(bytes) {
  const blob = new Blob([bytes]);
  const bitmap = await createImageBitmap(blob);
  const canvas = new OffscreenCanvas(bitmap.width, bitmap.height);
  const context = canvas.getContext("2d", { willReadFrequently: true });
  context.drawImage(bitmap, 0, 0);
  const imageData = context.getImageData(0, 0, bitmap.width, bitmap.height);
  bitmap.close();
  return imageData;
}
async function decodeAndScale(bytes, targetWidth, targetHeight, algorithm) {
  if (!targetWidth || !targetHeight) return decodeImage(bytes);
  if (algorithm === "auto") return decodeImage(bytes);
  if (algorithm === "lanczos" || algorithm === "mitchell") {
    const fullData = await decodeImage(bytes);
    if (algorithm === "lanczos") {
      console.log(`[Worker] decodeAndScale (lanczos): ${fullData.width}x${fullData.height} \u2192 ${targetWidth}x${targetHeight}`);
      return resizeLanczos(fullData, targetWidth, targetHeight);
    }
    console.log(`[Worker] decodeAndScale (mitchell): ${fullData.width}x${fullData.height} \u2192 ${targetWidth}x${targetHeight}`);
    return resizeMitchell(fullData, targetWidth, targetHeight);
  }
  const blob = new Blob([bytes]);
  const bitmap = await createImageBitmap(blob);
  const canvas = new OffscreenCanvas(targetWidth, targetHeight);
  const context = canvas.getContext("2d", { willReadFrequently: true });
  applySmoothingQuality(context, algorithm || "lanczos");
  context.drawImage(bitmap, 0, 0, targetWidth, targetHeight);
  const imageData = context.getImageData(0, 0, targetWidth, targetHeight);
  bitmap.close();
  return imageData;
}
function hasTransparency(imageData) {
  const data = imageData.data;
  for (let i = 3; i < data.length; i += 4) {
    if (data[i] < 255) return true;
  }
  return false;
}
var CROSS_CHECK_MIN_SIZE = 2 * 1024 * 1024;
var CROSS_CHECK_MIN_REPETITION = 0.1;
function estimateColorRepetition(imageData) {
  const data = imageData.data;
  const totalPixels = data.length / 4 | 0;
  if (totalPixels === 0) return 0;
  const sampleSize = Math.min(totalPixels, 1e4);
  const step = Math.max(1, Math.floor(totalPixels / sampleSize));
  const counts = /* @__PURE__ */ new Map();
  let sampled = 0;
  let maxCount = 0;
  for (let p = 0; p < totalPixels; p += step) {
    const i = p * 4;
    const r = data[i] >> 3;
    const g = data[i + 1] >> 3;
    const b = data[i + 2] >> 3;
    const key = r << 10 | g << 5 | b;
    const c = (counts.get(key) || 0) + 1;
    counts.set(key, c);
    if (c > maxCount) maxCount = c;
    sampled++;
  }
  return sampled > 0 ? maxCount / sampled : 0;
}
async function encodePngImpl(imageData, options) {
  const q = await getQuantizer();
  const result = await q.quantizeImageData(imageData, {
    maxColors: options?.maxColors ?? 256,
    dithering: options?.dithering ?? 0.5,
    quality: { min: options?.minQuality ?? 0, target: options?.maxQuality ?? 100 },
    speed: options?.speed ?? 1
  });
  if (result?.pngBytes instanceof Uint8Array) return result.pngBytes;
  if (result instanceof Uint8Array) return result;
  if (result?.png instanceof Uint8Array) return result.png;
  if (result?.bytes instanceof Uint8Array) return result.bytes;
  if (result?.data instanceof Uint8Array) return result.data;
  throw new Error("libimagequant: kein PNG-Ergebnis: " + Object.keys(result || {}).join(", "));
}
function imageDataToRgba(imageData) {
  const { width, height, data } = imageData;
  let hasAlpha = false;
  for (let i = 3; i < data.length; i += 4) {
    if (data[i] < 255) {
      hasAlpha = true;
      break;
    }
  }
  if (!hasAlpha) return new Uint8Array(data.buffer, data.byteOffset, data.byteLength);
  const rgba = new Uint8Array(width * height * 4);
  for (let i = 0; i < data.length; i += 4) {
    const a = data[i + 3] / 255;
    rgba[i] = Math.round(data[i] * a);
    rgba[i + 1] = Math.round(data[i + 1] * a);
    rgba[i + 2] = Math.round(data[i + 2] * a);
    rgba[i + 3] = 255;
  }
  return rgba;
}
function ensureMemory(wasm3, neededBytes) {
  const currentBytes = wasm3.memory.buffer.byteLength;
  if (currentBytes < neededBytes) {
    const neededPages = Math.ceil((neededBytes - currentBytes) / 65536);
    try {
      wasm3.memory.grow(neededPages);
      updateMemoryViews();
    } catch (e) {
      console.warn("[cjpegli] Memory grow fehlgeschlagen:", e.message);
    }
  }
}
function chromaToInt(chroma) {
  const valid = { "444": 444, "440": 440, "422": 422, "420": 420 };
  return valid[chroma] || 420;
}
async function encodeJpegImpl(imageData, options, originalBytes) {
  const quality = options?.jpegQuality ?? 85;
  const userChroma = options?.chromaSubsampling ?? "420";
  const originalChroma = originalBytes ? detectJpegChromaSubsampling(originalBytes) : null;
  const effectiveChroma = limitChromaSubsampling(originalChroma, userChroma);
  if (originalChroma) console.log(`[cjpegli] Chroma: Original=${originalChroma}, User=${userChroma} \u2192 ${effectiveChroma}`);
  const rgba = imageDataToRgba(imageData);
  const { width, height } = imageData;
  const rgbaSize = rgba.length;
  const wasm3 = await getCjpegli();
  ensureMemory(wasm3, rgbaSize * 2);
  const rgbaPtr = wasm3.malloc(rgbaSize);
  if (!rgbaPtr) throw new Error("cjpegli: malloc fehlgeschlagen \u2014 Speicher voll?");
  try {
    updateMemoryViews();
    new Uint8Array(wasm3.memory.buffer, rgbaPtr, rgbaSize).set(rgba);
    const chromaSubsampling = chromaToInt(effectiveChroma);
    const jpegPtr = wasm3.encode(rgbaPtr, width, height, chromaSubsampling, quality, 2, 0, 1, 0);
    const jpegSize = wasm3.get_size();
    if (!jpegPtr || jpegPtr <= 0) throw new Error(`cjpegli: encode fehlgeschlagen \u2014 jpegPtr=${jpegPtr}`);
    if (!jpegSize || jpegSize <= 0) throw new Error(`cjpegli: encode fehlgeschlagen \u2014 jpegSize=${jpegSize}`);
    updateMemoryViews();
    const jpegView = new Uint8Array(wasm3.memory.buffer, jpegPtr, jpegSize);
    const jpeg = new Uint8Array(jpegView);
    if (jpeg[0] !== 255 || jpeg[1] !== 216) throw new Error("cjpegli: ung\xFCltiger JPEG-Header");
    console.log(`[cjpegli] JPEG: ${jpegSize} bytes, ${width}x${height}, q=${quality}, chroma=${effectiveChroma}`);
    return jpeg;
  } finally {
    wasm3.free(rgbaPtr);
  }
}
var NORESIZE_CHECK_MAX_PIXELS = 1e5;
function readPngDimensions(bytes) {
  if (!(bytes instanceof Uint8Array) || bytes.length < 24) return null;
  if (bytes[0] !== 137 || bytes[1] !== 80 || bytes[2] !== 78 || bytes[3] !== 71) return null;
  return { w: readUint32BE(bytes, 16), h: readUint32BE(bytes, 20) };
}
async function compressImage(bytes, options, format, tryPng, tryJpeg, targetWidth, targetHeight, resizePercent, forcePng) {
  const preserveMeta = options?.preserveMeta !== false;
  const resizeAlgorithm = options?.resizeAlgorithm ?? "lanczos";
  const pngMetadata = preserveMeta && format === "png" ? extractPngMetadata(bytes) : [];
  const jpegMetadata = preserveMeta && format === "jpeg" ? extractJpegMetadata(bytes) : [];
  if (format === "jpeg" && tryPng && !forcePng) {
    if (bytes.length > CROSS_CHECK_MIN_SIZE) {
      tryPng = false;
      console.log(`[Worker] JPEG ${(bytes.length / 1048576).toFixed(1)} MB > 2 MB \u2192 PNG cross-check \xFCbersprungen`);
    }
  }
  let imageData = await decodeAndScale(bytes, targetWidth, targetHeight, resizeAlgorithm);
  let pixelCount = imageData.width * imageData.height;
  let noResizeCheck = false;
  if (format === "png" && tryPng && targetWidth && targetHeight) {
    const dims = readPngDimensions(bytes);
    if (dims && dims.w * dims.h < NORESIZE_CHECK_MAX_PIXELS && (targetWidth < dims.w || targetHeight < dims.h)) {
      noResizeCheck = true;
      console.log(`[Worker] No-Resize-Check aktiv: ${dims.w}x${dims.h} (${dims.w * dims.h} px), Ziel ${targetWidth}x${targetHeight}`);
    }
  }
  if (format === "jpeg" && tryPng && !forcePng) {
    const repetition = estimateColorRepetition(imageData);
    if (repetition < CROSS_CHECK_MIN_REPETITION) {
      tryPng = false;
      console.log(`[Worker] Farb-Repetition ${(repetition * 100).toFixed(1)}% < 10% \u2192 PNG cross-check \xFCbersprungen`);
    } else {
      console.log(`[Worker] Farb-Repetition ${(repetition * 100).toFixed(1)}% \u2265 10% \u2192 PNG cross-check wird durchgef\xFChrt`);
    }
  }
  let originalImageData = null;
  let resizeDims = null;
  if (resizeAlgorithm === "auto" && targetWidth && targetHeight) {
    originalImageData = imageData;
    resizeDims = { newW: targetWidth, newH: targetHeight };
    console.log(`[Worker] Resize (auto): ${imageData.width}x${imageData.height} \u2192 ${targetWidth}x${targetHeight} \u2014 pro Format`);
  } else if (resizePercent && resizePercent < 100) {
    const origW = imageData.width;
    const origH = imageData.height;
    const newW = Math.max(1, Math.round(origW * resizePercent / 100));
    const newH = Math.max(1, Math.round(origH * resizePercent / 100));
    resizeDims = { newW, newH };
    if (resizeAlgorithm === "auto") {
      originalImageData = imageData;
      console.log(`[Worker] Resize (auto): ${origW}x${origH} \u2192 ${newW}x${newH} (${resizePercent}%) \u2014 pro Format`);
    } else if (resizeAlgorithm === "lanczos") {
      imageData = resizeLanczos(imageData, newW, newH);
      console.log(`[Worker] Resize (lanczos): ${origW}x${origH} \u2192 ${newW}x${newH} (${resizePercent}%)`);
    } else if (resizeAlgorithm === "mitchell") {
      imageData = resizeMitchell(imageData, newW, newH);
      console.log(`[Worker] Resize (mitchell): ${origW}x${origH} \u2192 ${newW}x${newH} (${resizePercent}%)`);
    } else {
      imageData = resizeViaCanvas(imageData, newW, newH, resizeAlgorithm);
      console.log(`[Worker] Resize (${resizeAlgorithm}): ${origW}x${origH} \u2192 ${newW}x${newH} (${resizePercent}%)`);
    }
  }
  function getResizeData(targetFormat) {
    if (!originalImageData) return imageData;
    const algo = targetFormat === "png" ? "mitchell" : "lanczos";
    const { newW, newH } = resizeDims;
    if (algo === "mitchell") {
      console.log(`[Worker] Resize (auto/mitchell \u2192 ${targetFormat}): ${originalImageData.width}x${originalImageData.height} \u2192 ${newW}x${newH}`);
      return resizeMitchell(originalImageData, newW, newH);
    }
    console.log(`[Worker] Resize (auto/lanczos \u2192 ${targetFormat}): ${originalImageData.width}x${originalImageData.height} \u2192 ${newW}x${newH}`);
    return resizeLanczos(originalImageData, newW, newH);
  }
  if (originalImageData && resizeDims) {
    pixelCount = resizeDims.newW * resizeDims.newH;
  } else if (resizePercent && resizePercent < 100) {
    pixelCount = imageData.width * imageData.height;
  }
  if (forcePng) {
    console.log(`[Worker] Force PNG aktiv: ${format.toUpperCase()} \u2192 PNG`);
  }
  const results = [];
  if (format === "png") {
    if (tryPng) {
      try {
        const data = getResizeData("png");
        let pngBytes = await encodePng(data, options);
        pngBytes = await optimisePng(pngBytes, options);
        if (pngMetadata.length > 0) pngBytes = injectPngMetadata(pngBytes, pngMetadata);
        if (noResizeCheck) {
          try {
            const fullData = originalImageData || await decodeImage(bytes);
            let nrBytes = await encodePng(fullData, options);
            nrBytes = await optimisePng(nrBytes, options);
            if (pngMetadata.length > 0) nrBytes = injectPngMetadata(nrBytes, pngMetadata);
            console.log(`[Worker] No-Resize-Check: resized ${pngBytes.length} B vs. unresized ${nrBytes.length} B`);
            if (nrBytes.length < pngBytes.length) {
              console.log(`[Worker] No-Resize-Check: Original-Aufl\xF6sung ${fullData.width}x${fullData.height} behalten \u2014 Resize \xFCbersprungen`);
              pngBytes = nrBytes;
            }
          } catch (e) {
            console.warn("[Worker] No-Resize-Check fehlgeschlagen:", e.message);
          }
        }
        results.push({ format: "png", bytes: pngBytes });
      } catch (e) {
        console.error("[Worker] PNG fehlgeschlagen:", e.message);
      }
    }
    if (tryJpeg && !hasTransparency(imageData)) {
      try {
        const data = getResizeData("jpeg");
        let jpegBytes = await encodeJpeg(data, options, null);
        if (jpegMetadata.length > 0) jpegBytes = injectJpegMetadata(jpegBytes, jpegMetadata);
        results.push({ format: "jpeg", bytes: jpegBytes });
      } catch (e) {
        console.error("[Worker] JPEG fehlgeschlagen:", e.message);
      }
    }
  } else {
    let jpegResult = null;
    if (tryJpeg) {
      try {
        const data = getResizeData("jpeg");
        let jpegBytes = await encodeJpeg(data, options, bytes);
        if (jpegMetadata.length > 0) jpegBytes = injectJpegMetadata(jpegBytes, jpegMetadata);
        jpegResult = { format: "jpeg", bytes: jpegBytes };
        results.push(jpegResult);
      } catch (e) {
        console.error("[Worker] JPEG fehlgeschlagen:", e.message);
      }
    }
    if (tryPng) {
      try {
        const data = getResizeData("png");
        let pngBytes = await encodePng(data, options);
        pngBytes = await optimisePng(pngBytes, options);
        if (jpegResult) {
          console.log(`[Worker] Formatvergleich: PNG (pngquant+oxipng) ${pngBytes.length} B vs. JPEG ${jpegResult.bytes.length} B \u2192 ${pngBytes.length < jpegResult.bytes.length ? "PNG" : "JPEG"} gewinnt`);
        }
        if (pngMetadata.length > 0) pngBytes = injectPngMetadata(pngBytes, pngMetadata);
        results.push({ format: "png", bytes: pngBytes });
      } catch (e) {
        console.error("[Worker] PNG fehlgeschlagen:", e.message);
      }
    }
  }
  if (results.length === 0) throw new Error("Keine Encodierung erfolgreich");
  results.sort((a, b) => a.bytes.length - b.bytes.length);
  return results[0];
}
var queue = Promise.resolve();
self.onmessage = (event) => {
  if (event.data && event.data.oxipngOnly) {
    const { id: id2, originalBytes, pngBytes, options: options2, metaOnly } = event.data;
    queue = queue.then(async () => {
      try {
        const r = await optimisePngStage(new Uint8Array(originalBytes), new Uint8Array(pngBytes), options2, !!metaOnly);
        const buf = r.final.buffer.slice(r.final.byteOffset, r.final.byteOffset + r.final.byteLength);
        const pre = r.preMeta.buffer.slice(r.preMeta.byteOffset, r.preMeta.byteOffset + r.preMeta.byteLength);
        self.postMessage({ id: id2, bytes: buf, format: "png", error: null, stages: { pngFinal: pre } }, [buf, pre]);
      } catch (error) {
        self.postMessage({ id: id2, bytes: null, format: null, error: error?.stack || error?.message || String(error) });
      }
    });
    return;
  }
  const { id, bytes, options, format, tryPng, tryJpeg, targetWidth, targetHeight, resizePercent, forcePng } = event.data;
  queue = queue.then(async () => {
    try {
      const inputBytes = new Uint8Array(bytes);
      stageCollector = (resizePercent || 100) === 100 && !targetWidth && !targetHeight ? {} : null;
      const result = await compressImage(inputBytes, options, format, tryPng || false, tryJpeg || false, targetWidth || null, targetHeight || null, resizePercent || 100, forcePng || false);
      const stages = stageCollector;
      stageCollector = null;
      const buffer = result.bytes.buffer.slice(result.bytes.byteOffset, result.bytes.byteOffset + result.bytes.byteLength);
      const msg = { id, bytes: buffer, format: result.format, error: null };
      const transfers = [buffer];
      if (stages && (stages.pqBytes || stages.pngFinal || stages.jpeg)) {
        msg.stages = {};
        for (const [k, v] of Object.entries(stages)) {
          if (!v) continue;
          const b = v.buffer.slice(v.byteOffset, v.byteOffset + v.byteLength);
          msg.stages[k] = b;
          transfers.push(b);
        }
      }
      self.postMessage(msg, transfers);
    } catch (error) {
      stageCollector = null;
      self.postMessage({ id, bytes: null, format: null, error: error?.stack || error?.message || String(error) });
    }
  });
};
var stageCollector = null;
async function encodePng(imageData, options) {
  const out = await encodePngImpl(imageData, options);
  if (stageCollector) stageCollector.pqBytes = out;
  return out;
}
async function optimisePng(pngBytes, options) {
  const out = await optimisePngImpl(pngBytes, options);
  if (stageCollector) {
    stageCollector.pqBytes = stageCollector.pqBytes || pngBytes;
    stageCollector.pngFinal = out;
  }
  return out;
}
async function encodeJpeg(imageData, options, originalBytes) {
  const out = await encodeJpegImpl(imageData, options, originalBytes);
  if (stageCollector) stageCollector.jpeg = out;
  return out;
}
async function optimisePngStage(originalBytes, pqBytes, options, metaOnly) {
  const preserveMeta = options?.preserveMeta !== false;
  const preMeta = metaOnly ? pqBytes : await optimisePngImpl(pqBytes, options);
  const metadata = preserveMeta ? extractPngMetadata(originalBytes) : [];
  const final = metadata.length > 0 ? injectPngMetadata(preMeta, metadata) : preMeta;
  return { preMeta, final };
}
