rapier-jxl 2.2.0 → 2.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AGENTS.md +23 -28
- package/README.md +63 -158
- package/{effort.min.mjs → dist/effort.min.mjs} +1 -1
- package/{jpeg-ans.min.mjs → dist/jpeg-ans.min.mjs} +1 -1
- package/{jpeg.min.mjs → dist/jpeg.min.mjs} +1 -1
- package/{photo-ans.min.mjs → dist/photo-ans.min.mjs} +1 -1
- package/{photo.min.mjs → dist/photo.min.mjs} +1 -1
- package/{rapier-jxl.min.mjs → dist/rapier-jxl.min.mjs} +1 -1
- package/{sizes.json → dist/sizes.json} +24 -24
- package/{wasm.min.mjs → dist/wasm.min.mjs} +1 -1
- package/{build-jxl-kernels.mjs → kernels/build.mjs} +6 -4
- package/package.json +32 -39
- package/ENCODER-COMPARISON.md +0 -185
- package/KERNELS.md +0 -58
- package/public/encoder-sizes.json +0 -355
- package/public/encoders.json +0 -139
- package/public/examples/browser.html +0 -39
- package/public/examples/worker.mjs +0 -42
- package/public/measure-encoders.mjs +0 -60
- /package/{kernels-probe.wat → kernels/kernels-probe.wat} +0 -0
- /package/{kernels-scalar.wat → kernels/kernels-scalar.wat} +0 -0
- /package/{kernels-simd.wat → kernels/kernels-simd.wat} +0 -0
- /package/{admit.mjs → src/admit.mjs} +0 -0
- /package/{ans.mjs → src/ans.mjs} +0 -0
- /package/{bits.mjs → src/bits.mjs} +0 -0
- /package/{coefficient-ans.mjs → src/coefficient-ans.mjs} +0 -0
- /package/{coefficient-effort.mjs → src/coefficient-effort.mjs} +0 -0
- /package/{effort-job.mjs → src/effort-job.mjs} +0 -0
- /package/{effort-level.mjs → src/effort-level.mjs} +0 -0
- /package/{effort.d.mts → src/effort.d.mts} +0 -0
- /package/{effort.mjs → src/effort.mjs} +0 -0
- /package/{entropy.mjs → src/entropy.mjs} +0 -0
- /package/{frame.mjs → src/frame.mjs} +0 -0
- /package/{index.d.mts → src/index.d.mts} +0 -0
- /package/{index.mjs → src/index.mjs} +0 -0
- /package/{jfif.mjs → src/jfif.mjs} +0 -0
- /package/{jpeg-ans.d.mts → src/jpeg-ans.d.mts} +0 -0
- /package/{jpeg-ans.mjs → src/jpeg-ans.mjs} +0 -0
- /package/{jpeg-job.mjs → src/jpeg-job.mjs} +0 -0
- /package/{jpeg.d.mts → src/jpeg.d.mts} +0 -0
- /package/{jpeg.mjs → src/jpeg.mjs} +0 -0
- /package/{kernel-control.d.mts → src/kernel-control.d.mts} +0 -0
- /package/{kernel-hooks.mjs → src/kernel-hooks.mjs} +0 -0
- /package/{kernels-bytes.mjs → src/kernels-bytes.mjs} +0 -0
- /package/{kernels.mjs → src/kernels.mjs} +0 -0
- /package/{local.mjs → src/local.mjs} +0 -0
- /package/{lossless-coding.mjs → src/lossless-coding.mjs} +0 -0
- /package/{lossless.mjs → src/lossless.mjs} +0 -0
- /package/{lossy.mjs → src/lossy.mjs} +0 -0
- /package/{modular.mjs → src/modular.mjs} +0 -0
- /package/{photo-ans.d.mts → src/photo-ans.d.mts} +0 -0
- /package/{photo-ans.mjs → src/photo-ans.mjs} +0 -0
- /package/{photo-dct.mjs → src/photo-dct.mjs} +0 -0
- /package/{photo-job.mjs → src/photo-job.mjs} +0 -0
- /package/{photo-quant.mjs → src/photo-quant.mjs} +0 -0
- /package/{photo.d.mts → src/photo.d.mts} +0 -0
- /package/{photo.mjs → src/photo.mjs} +0 -0
- /package/{pool.mjs → src/pool.mjs} +0 -0
- /package/{prefix.mjs → src/prefix.mjs} +0 -0
- /package/{rct-search.mjs → src/rct-search.mjs} +0 -0
- /package/{squeeze.mjs → src/squeeze.mjs} +0 -0
- /package/{vardct.mjs → src/vardct.mjs} +0 -0
- /package/{wasm.d.mts → src/wasm.d.mts} +0 -0
- /package/{wasm.mjs → src/wasm.mjs} +0 -0
- /package/{weighted.mjs → src/weighted.mjs} +0 -0
- /package/{writer.mjs → src/writer.mjs} +0 -0
package/AGENTS.md
CHANGED
|
@@ -1,33 +1,28 @@
|
|
|
1
|
-
#
|
|
1
|
+
# Adding Rapier JXL to an app
|
|
2
2
|
|
|
3
|
-
1. `npm install rapier-jxl`, or copy one file from
|
|
4
|
-
`
|
|
5
|
-
2. `import {encode} from 'rapier-jxl'`
|
|
6
|
-
|
|
7
|
-
`{effort: 3}`.
|
|
3
|
+
1. `npm install rapier-jxl`, or copy one file from `dist/`: `rapier-jxl.min.mjs` (the core), `effort.min.mjs`,
|
|
4
|
+
`jpeg.min.mjs` or `photo.min.mjs`. No build.
|
|
5
|
+
2. `import {encode} from 'rapier-jxl'`, `transcode` from `rapier-jxl/jpeg`, `encodePhoto` from `rapier-jxl/photo`.
|
|
6
|
+
Smaller lossless files at more time: `encode` from `rapier-jxl/effort` with `{effort: 3}`.
|
|
8
7
|
3. Pixels: `encode(rgba, width, height, {quality})`, straight RGBA row by row as `getImageData` gives it; from a
|
|
9
|
-
Display P3 canvas
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
6. The error codes are `JXL_INPUT`, `JXL_DIMENSIONS`, `JXL_SIZE`, `JXL_MEMORY` and `JXL_JPEG`, no others;
|
|
23
|
-
`JXL_DIMENSIONS` is past the door's own `LIMITS` (24 million pixels for the core and `effort`, 40 million for
|
|
24
|
-
`photo`, 64 million for a carried JPEG). Keep the original pixels until the encode and its storage succeed.
|
|
8
|
+
Display P3 canvas add `colorSpace: 'display-p3'`. Quality 100 (the default) is lossless, 1 to 99 lossy, alpha exact
|
|
9
|
+
at every quality. Photographs: `encodePhoto(rgba, width, height, {quality: 90})`. The result is a `Uint8Array`:
|
|
10
|
+
save it as `.jxl` or in a `Blob` of type `image/jxl`.
|
|
11
|
+
4. A JPEG: `transcode(jpegBytes)` gives `{bytes, width, height, orientation}` without decoding. On `JXL_JPEG`, decode
|
|
12
|
+
it and call `encodePhoto` on the pixels. `{effort: 4}` tries a smaller entropy representation with identical
|
|
13
|
+
pixels (default 1); `rapier-jxl/jpeg-ans` and `rapier-jxl/photo-ans` take `{effort: 2}` to also try ANS, for about
|
|
14
|
+
1.1 kB gzip more.
|
|
15
|
+
5. Run anything larger than an icon in a worker. Calls are synchronous: cancel by terminating the worker, or loop over
|
|
16
|
+
the door's twin (`encodeSteps`, `transcodeSteps`, `encodePhotoSteps`) and leave the loop. A transferred buffer is
|
|
17
|
+
gone from the sender: copy first if you may retry.
|
|
18
|
+
6. Errors have `code` `JXL_INPUT`, `JXL_DIMENSIONS`, `JXL_SIZE`, `JXL_MEMORY` or `JXL_JPEG`. `JXL_DIMENSIONS` is past
|
|
19
|
+
the door's `LIMITS` (24 million pixels for the core and `effort`, 40 million for `photo`, 64 million for a
|
|
20
|
+
carried JPEG). Keep the original pixels until the encode and its storage succeed.
|
|
25
21
|
7. Show the result only where the browser decodes JPEG XL (`<picture>` with a fallback, or a one-pixel feature test).
|
|
26
22
|
|
|
27
|
-
Nothing here reads files, fetches or touches the DOM: it runs in a worker, Node or Deno alike.
|
|
28
|
-
|
|
23
|
+
Nothing here reads files, fetches or touches the DOM: it runs in a worker, Node or Deno alike. Keep the licence with
|
|
24
|
+
the file you take; do not vendor a minified copy under another name.
|
|
29
25
|
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
to share kernel controls: use the one-file accelerated door.
|
|
26
|
+
Acceleration with unchanged bytes: use `rapier-jxl/wasm` (or `dist/wasm.min.mjs`) in place of `effort`. It falls back
|
|
27
|
+
to JavaScript when SIMD is missing or blocked. Use that one file; do not combine separate minified bundles to share
|
|
28
|
+
kernel controls. See `docs/KERNELS.md`.
|
package/README.md
CHANGED
|
@@ -1,44 +1,20 @@
|
|
|
1
1
|
# Rapier JXL
|
|
2
2
|
|
|
3
|
-
A JPEG XL encoder in pure JavaScript
|
|
4
|
-
|
|
3
|
+
A JPEG XL encoder in pure JavaScript. It writes `.jxl` from canvas pixels or a JPEG in a browser, a worker, Node or
|
|
4
|
+
Deno. No dependencies, no server, MIT.
|
|
5
5
|
|
|
6
6
|
- The core is one file of 21.3 kB, 9.3 kB gzipped: the smallest JavaScript or WebAssembly JPEG XL
|
|
7
|
-
encoder
|
|
7
|
+
encoder in the [payloads measured](docs/ENCODER-COMPARISON.md).
|
|
8
8
|
- Lossless and lossy in one `encode` call; alpha stays exact at every quality.
|
|
9
|
-
- Photographs, JPEGs carried without decoding,
|
|
10
|
-
only when
|
|
11
|
-
- The same input writes the same bytes in every JavaScript engine
|
|
12
|
-
- No dependencies, MIT. An agent adding it to an app reads `AGENTS.md`.
|
|
9
|
+
- Photographs, JPEGs carried without decoding, smaller exact files at more time and WebAssembly acceleration are
|
|
10
|
+
separate imports, loaded only when used.
|
|
11
|
+
- The same input writes the same bytes in every JavaScript engine.
|
|
13
12
|
|
|
14
13
|
```sh
|
|
15
14
|
npm install rapier-jxl
|
|
16
15
|
```
|
|
17
16
|
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
## What it does
|
|
21
|
-
|
|
22
|
-
- **Lossless.** Every pixel back as it went in: 8-bit grey, grey with alpha, RGB, RGBA.
|
|
23
|
-
- **Lossy**, quality 1 to 99, for flat-colour rasters (screenshots, pixel art, scanned line art). Alpha stays exact.
|
|
24
|
-
A picture of few colours is written exact when that is smaller.
|
|
25
|
-
- **Smaller exact pictures, slower**: `rapier-jxl/effort`, the same `encode` with `{effort: 2}`, `3`, `4` or `6`, each never
|
|
26
|
-
larger than the effort below. Effort 1, its default, is the core's bytes.
|
|
27
|
-
- **Photographs**: `rapier-jxl/photo`, DCT8 compression with exact alpha, a door of its own. Effort 5 searches
|
|
28
|
-
quantisation per block and keeps a candidate only when its complete stream is smaller.
|
|
29
|
-
- **A JPEG carried as its coefficients**: `rapier-jxl/jpeg`, one call, no decode, the way libjxl transcodes. Not
|
|
30
|
-
carried: the reconstruction data (the JPEG file cannot be rebuilt), the ICC bytes, Exif beyond the orientation, XMP.
|
|
31
|
-
- **Optional ANS entropy coding**: import `transcode` from `rapier-jxl/jpeg-ans` or `encodePhoto` from
|
|
32
|
-
`rapier-jxl/photo-ans` and pass `{effort: 2}`. Each tries ANS after writing the prefix-coded floor and keeps
|
|
33
|
-
the smaller complete stream, with identical reconstructed pixels. These imports leave the core unchanged.
|
|
34
|
-
- **sRGB or Display P3.** `{colorSpace: 'display-p3'}` declares a wide-gamut canvas's samples. A JPEG's profile is
|
|
35
|
-
read by what it does, not what it says: sRGB and Display P3 are carried and declared.
|
|
36
|
-
|
|
37
|
-
For the accelerated effort door, use `rapier-jxl/wasm` or the self-contained `wasm.min.mjs`.
|
|
38
|
-
It falls back to JavaScript when SIMD is unavailable and writes identical lossless bytes.
|
|
39
|
-
See [KERNELS.md](KERNELS.md) for controls, memory, source and rebuild instructions.
|
|
40
|
-
|
|
41
|
-
## Use it
|
|
17
|
+
## Use
|
|
42
18
|
|
|
43
19
|
```js
|
|
44
20
|
import {encode} from 'rapier-jxl';
|
|
@@ -55,145 +31,74 @@ const {bytes, width: w, height: h, orientation} = transcode(new Uint8Array(await
|
|
|
55
31
|
```
|
|
56
32
|
|
|
57
33
|
`encode(data, width, height, {quality = 100})` takes straight RGBA bytes, row by row, and returns a `Uint8Array`
|
|
58
|
-
holding a bare JPEG XL codestream
|
|
59
|
-
`{bytes, width, height, orientation}
|
|
34
|
+
holding a bare JPEG XL codestream. `{colorSpace: 'display-p3'}` declares a wide-gamut canvas. `transcode(jpeg)` returns
|
|
35
|
+
`{bytes, width, height, orientation}`. TypeScript declarations sit beside each module in `src/`.
|
|
60
36
|
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
gives a module's author the layers beneath the doors (readable only; they change only with the major version).
|
|
65
|
-
TypeScript declarations sit beside each door, and a worker and a page are under `public/examples/`. Quality numbers
|
|
66
|
-
are not the same fidelity across encoders or pictures, and lossy is not always smaller than lossless.
|
|
37
|
+
Calls are synchronous: run them in a worker (`examples/worker.mjs`, `examples/browser.html`). Each door has a
|
|
38
|
+
twin that works in steps (`encodeSteps`, `transcodeSteps`, `encodePhotoSteps`): loop over the job for progress, leave
|
|
39
|
+
the loop to cancel, set `job.hurry = true` to finish with the smallest stream written so far.
|
|
67
40
|
|
|
68
|
-
|
|
69
|
-
bounds effort 1's unclipped RGB sample reconstruction error on edge-extended DCT blocks, before clipping and integer output.
|
|
70
|
-
Decoded integer RGB error can differ from that model. Quality 100 remains exact at every effort.
|
|
71
|
-
The quantisation search keeps the preceding stream when its estimated memory would exceed the photo door's
|
|
72
|
-
working budget; the door's 40-million-pixel admission stays the same.
|
|
41
|
+
## Imports
|
|
73
42
|
|
|
74
|
-
|
|
43
|
+
| import | what it does |
|
|
44
|
+
| --- | --- |
|
|
45
|
+
| `rapier-jxl` | `encode`: 8-bit grey, grey with alpha, RGB and RGBA. Quality 100 is lossless; 1 to 99 is lossy, for flat-colour rasters. |
|
|
46
|
+
| `rapier-jxl/min` | The core as one minified file. |
|
|
47
|
+
| `rapier-jxl/effort` | The same `encode` with `{effort: 2, 3, 4 or 6}`: smaller exact files, more time, never larger than the effort below. Effort 1 is the core. |
|
|
48
|
+
| `rapier-jxl/wasm` | The effort door with integer WebAssembly SIMD kernels; the same bytes, JavaScript when SIMD is unavailable. See [docs/KERNELS.md](docs/KERNELS.md). |
|
|
49
|
+
| `rapier-jxl/photo` | `encodePhoto`: DCT compression for photographs, exact alpha. |
|
|
50
|
+
| `rapier-jxl/jpeg` | `transcode`: a JPEG carried as its coefficients, no decode. The JPEG file itself cannot be rebuilt; ICC bytes, Exif beyond orientation and XMP are not carried. |
|
|
51
|
+
| `rapier-jxl/jpeg-ans`, `rapier-jxl/photo-ans` | The same doors with `{effort: 2}` also trying ANS entropy coding, keeping the smaller stream. |
|
|
52
|
+
| `rapier-jxl/writer` | The layers beneath the doors, readable only. |
|
|
53
|
+
| `rapier-jxl/kernels` | Controls for the WebAssembly kernels. |
|
|
75
54
|
|
|
76
|
-
|
|
55
|
+
Each door is a readable module in `src/` (a bundler carries shared modules once) and, except `writer` and `kernels`,
|
|
56
|
+
a single minified file in `dist/` that can be copied on its own.
|
|
77
57
|
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
self.postMessage({id, ok: true, ...out}, [out.bytes.buffer]);
|
|
86
|
-
} catch (error) { self.postMessage({id, ok: false, code: error.code || 'JXL_ERROR', message: String(error.message || error)}); }
|
|
87
|
-
};
|
|
88
|
-
```
|
|
58
|
+
## Limits
|
|
59
|
+
|
|
60
|
+
One picture at a time, at most 16,384 pixels a side and a 16 MiB stream. Each door's `LIMITS` sets its pixels: 24 million
|
|
61
|
+
for the core and `effort`, 40 million for `photo`, 64 million for a JPEG that `jpeg` carries. Arguments are checked
|
|
62
|
+
before any work. A refusal is an `Error` whose `code` is `JXL_INPUT`, `JXL_DIMENSIONS`, `JXL_SIZE`, `JXL_MEMORY` or
|
|
63
|
+
`JXL_JPEG` (arithmetic coding, 12-bit, lossless, CMYK, a DNL height, a colour profile other than sRGB or Display P3,
|
|
64
|
+
or a JPEG cut short: decode it and encode the pixels instead).
|
|
89
65
|
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
Each door has a twin that does the same work in steps: `encodeSteps`, `transcodeSteps`, `encodePhotoSteps` return a
|
|
93
|
-
job, `for (const done of job)` runs one group of one pass per step (`done` is the fraction, the last exactly 1), and
|
|
94
|
-
`job.bytes` is the stream after the loop, the same bytes the door writes. Leaving the loop cancels, so a worker can
|
|
95
|
-
take messages and report progress between steps (`public/examples/worker.mjs`). `job.hurry = true` (the example's
|
|
96
|
-
`deadline` sets it) ends a door's search at its next step with the smallest stream written so far, never
|
|
97
|
-
larger than effort 1's.
|
|
98
|
-
|
|
99
|
-
The JPEG and photograph doors also read effort: 3 tries a 32-cluster budget, and 4 also tries an order learned
|
|
100
|
-
from coefficient counts. These entropy rungs keep the smaller complete stream and preserve every reconstructed pixel. Their
|
|
101
|
-
default remains 1; effort 2 keeps the default plan. A hurried JPEG job finishes its effort-1 floor in its first
|
|
102
|
-
half; through effort 4 the photo job first makes coefficients, then writes that floor, and searches in its final
|
|
103
|
-
quarter. At effort 5, its first half finishes the preceding stream and its second half searches quantisation,
|
|
104
|
-
keeping the completed floor on a hurry.
|
|
105
|
-
|
|
106
|
-
The optional ANS doors keep default effort 1's prefix bytes. Effort 2 adds one ANS candidate; efforts 3 and 4
|
|
107
|
-
also retain the ordinary prefix searches, and photo effort 5 retains its quantisation search. ANS uses a bounded
|
|
108
|
-
group buffer of 1,376,256 bytes plus histogram tables; encoding both candidates costs more CPU and may raise peak
|
|
109
|
-
RSS. Hurry keeps a completed candidate even when it arrives at the final group's yield.
|
|
110
|
-
|
|
111
|
-
Version 2.2.0 adds the `kernels` and `wasm` doors (integer WebAssembly under the lossless hot loops, JavaScript
|
|
112
|
-
fallback), a worker pool for large exact pictures, exact hybrid-integer codes, and a colour-transform search at effort 4.
|
|
113
|
-
Exact pictures stay lossless; 27 of the 154 test streams change bytes, none larger.
|
|
114
|
-
|
|
115
|
-
Version 2.1.0 fits the photo door's existing quantisation constants across thumbnail and source-sized photos.
|
|
116
|
-
Lossy photo bytes change deliberately; lossless and ordinary JPEG streams retain their hashes. Pin a package
|
|
117
|
-
version when exact lossy output bytes matter. Quality numbers remain a setting, not a guarantee of equal
|
|
118
|
-
perceptual quality on every image.
|
|
119
|
-
|
|
120
|
-
### Limits and errors
|
|
121
|
-
|
|
122
|
-
One picture at a time, at most 16,384 pixels a side and a 16 MiB stream. Each door's `LIMITS` sets its pixels by its
|
|
123
|
-
memory, so that none needs more at its limit than the core at its own: 24 million for the core and `effort` (a lossy
|
|
124
|
-
picture holds its planes whole, 15.7 bytes a pixel at its peak besides the input), 40 million for `photo` (6.5), and
|
|
125
|
-
64 million for a JPEG that `jpeg` carries (3.3 at 4:2:0, 6.4 at 4:4:4), so a phone's 24 and 48 megapixel
|
|
126
|
-
photographs are carried. Arguments are checked before any work. A refusal is an `Error` whose `code` is `JXL_INPUT`,
|
|
127
|
-
`JXL_DIMENSIONS`, `JXL_SIZE`, `JXL_MEMORY` or `JXL_JPEG` (arithmetic coding, 12-bit, lossless, CMYK, a DNL height, a
|
|
128
|
-
colour profile other than sRGB or Display P3, or a JPEG cut short: decode it and encode the pixels instead).
|
|
129
|
-
|
|
130
|
-
### From 1.x
|
|
131
|
-
|
|
132
|
-
2.0.0 is the package's own version (1.x took Rapier's), and the core is pixels only:
|
|
133
|
-
|
|
134
|
-
- `transcode` is in `rapier-jxl/jpeg`, and `encodePhotoRGBA` is `encodePhoto` in `rapier-jxl/photo`.
|
|
135
|
-
- `encodeLosslessRGBA(data, width, height)` and `rapier-jxl/lossless` are `encode(data, width, height)`;
|
|
136
|
-
`encodeLossyRGBA(data, width, height, quality)` is `encode(data, width, height, {quality})`.
|
|
137
|
-
- `encodeLossless`, `encodeLossy`, `inspectPixels`, `parseJPEG` and `transcodeJPEG` are in `rapier-jxl/writer`.
|
|
138
|
-
- A JPEG's colour profile is read by what it does: Display P3 (an iPhone's) is carried and declared, where 1.x
|
|
139
|
-
refused it; a profile of lookup tables is refused, even one named sRGB.
|
|
140
|
-
- Lossless streams and carried JPEGs are 1.x's bytes. Lossy streams of a picture wider or taller than 256 pixels,
|
|
141
|
-
or of a colour picture one pixel wide or high, and every photo stream changed where Chrome's decoder (jxl-rs
|
|
142
|
-
0.7.4) misread a valid stream; each decodes to the same pixels as before through jxl-oxide and libjxl.
|
|
143
|
-
|
|
144
|
-
New: `rapier-jxl/effort`, each door's twin in steps with `hurry`, `colorSpace: 'display-p3'`, each door's own
|
|
145
|
-
`LIMITS`.
|
|
66
|
+
Quality numbers are not the same fidelity across encoders or pictures, and lossy is not always smaller than lossless.
|
|
146
67
|
|
|
147
68
|
## Sizes
|
|
148
69
|
|
|
149
|
-
| file | bytes | gzip | Brotli | added to the core, gzip |
|
|
70
|
+
| file in `dist/` | bytes | gzip | Brotli | added to the core, gzip |
|
|
150
71
|
| --- | ---: | ---: | ---: | ---: |
|
|
151
72
|
| `rapier-jxl.min.mjs`, the core: `encode` | 21,326 | 9,271 | 8,233 | |
|
|
152
|
-
| `effort.min.mjs`: `encode` with effort | 33,584 | 13,793 | 12,
|
|
153
|
-
| `wasm.min.mjs`: accelerated effort, JS fallback | 43,535 | 18,533 | 16,
|
|
73
|
+
| `effort.min.mjs`: `encode` with effort | 33,584 | 13,793 | 12,205 | 4,522 |
|
|
74
|
+
| `wasm.min.mjs`: accelerated effort, JS fallback | 43,535 | 18,533 | 16,233 | 9,262 |
|
|
154
75
|
| `jpeg.min.mjs`: `transcode` | 32,354 | 13,505 | 11,946 | 8,524 |
|
|
155
|
-
| `photo.min.mjs`: `encodePhoto` | 33,011 | 13,616 | 12,
|
|
156
|
-
| `jpeg-ans.min.mjs`: optional ANS carrier | 35,491 | 14,608 | 12,
|
|
157
|
-
| `photo-ans.min.mjs`: optional ANS photo | 35,994 | 14,650 | 12,
|
|
158
|
-
| every door in one bundle | 74,625 | 30,285 | 26,
|
|
159
|
-
| all readable modules | 211,215 | 67,195 | | |
|
|
160
|
-
|
|
161
|
-
Exact bytes of release 2.2.
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
Tests and seeded structure-aware fuzzing in `public/test/`: `npm test`, decoded through
|
|
180
|
-
[jxl-oxide](https://github.com/tirr-c/jxl-oxide) 0.12.6 and FFmpeg's native libjxl (a missing native decoder is
|
|
181
|
-
reported, and fails in CI). Exact pixels and alpha where promised, fidelity where relevant, the accepted JPEG
|
|
182
|
-
forms, refusal of malformed input. The same input writes the same bytes in every JavaScript engine: nothing that
|
|
183
|
-
decides a byte uses a function engines round differently, and `public/test/bytes.test.mjs` holds the streams' hashes
|
|
184
|
-
under Node and Bun. The 30 September run put 2,000,000 JPEG mutations and 32,768 pixel cases
|
|
185
|
-
through both decoders. The two decoders differ by one RGB unit on some JPEG and photo streams (floating-point
|
|
186
|
-
reconstruction), kept in `public/test/seeds/`; alpha and modular output are exact. With a C compiler and libjxl
|
|
187
|
-
headers, `npm run fuzz:scale -- --out fuzz-run --workers 4` repeats the fixed budget.
|
|
188
|
-
|
|
189
|
-
## Why
|
|
190
|
-
|
|
191
|
-
Rapier keeps pictures inside Markdown, and its standard defaults to JPEG XL for raster pictures in Markdown: exact where
|
|
192
|
-
it must be, small where it may be. Drawings stay SVG. An editor carrying an encoder offline in a small page needed
|
|
193
|
-
one this size, and none existed. The standard is at [rapier.website](https://rapier.website); for an agent, see
|
|
194
|
-
`AGENTS.md`.
|
|
76
|
+
| `photo.min.mjs`: `encodePhoto` | 33,011 | 13,616 | 12,084 | 6,249 |
|
|
77
|
+
| `jpeg-ans.min.mjs`: optional ANS carrier | 35,491 | 14,608 | 12,896 | 9,580 |
|
|
78
|
+
| `photo-ans.min.mjs`: optional ANS photo | 35,994 | 14,650 | 12,983 | 7,315 |
|
|
79
|
+
| every door in one bundle | 74,625 | 30,285 | 26,416 | |
|
|
80
|
+
| all readable modules in `src/` | 211,215 | 67,195 | | |
|
|
81
|
+
|
|
82
|
+
Exact bytes of release 2.2.1, with hashes and tools in `dist/sizes.json` (terser 5.51.2, Node v22.22.2; gzip 9,
|
|
83
|
+
Brotli 11). Each minified file stands alone and writes the same bytes as its readable source. The last column is what
|
|
84
|
+
a door adds to a bundle that already holds the core; `effort`'s `encode` is the core's at effort 1, so it takes the
|
|
85
|
+
core's place.
|
|
86
|
+
|
|
87
|
+
## Output
|
|
88
|
+
|
|
89
|
+
Bare codestreams, 8-bit, one frame, prefix codes (ANS in the optional doors). No preview, animation, XYB, chroma-from-luma
|
|
90
|
+
or filters; sRGB or Display P3 is declared. Lossless uses modular mode with a palette of up to 2,048 colours, reversible
|
|
91
|
+
YCoCg and a predictor and integer code chosen per channel by exact cost. Lossy uses Squeeze with exact alpha. Carried
|
|
92
|
+
JPEGs use VarDCT with the JPEG's own tables.
|
|
93
|
+
|
|
94
|
+
## Tests
|
|
95
|
+
|
|
96
|
+
`npm test` in a clone decodes every stream through [jxl-oxide](https://github.com/tirr-c/jxl-oxide) and, where
|
|
97
|
+
installed, libjxl, and checks exact pixels and alpha, fidelity, the accepted JPEG forms, refusal of malformed input and
|
|
98
|
+
the hashes of the written streams under Node and Bun. `npm run fuzz:scale` repeats the seeded fuzzing budget.
|
|
99
|
+
Contributions: [.github/CONTRIBUTING.md](.github/CONTRIBUTING.md). Agents adding the encoder to an app: [AGENTS.md](AGENTS.md).
|
|
195
100
|
|
|
196
101
|
## Licence
|
|
197
102
|
|
|
198
|
-
MIT, copyright rapier.website. The design follows ISO/IEC 18181 and libjxl's encoders, whose sources were read;
|
|
199
|
-
|
|
103
|
+
MIT, copyright rapier.website. The design follows ISO/IEC 18181 and libjxl's encoders, whose sources were read; none of
|
|
104
|
+
their code is here. The encoder is part of [Rapier](https://rapier.website).
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
/*! Rapier JXL 2.2.
|
|
1
|
+
/*! Rapier JXL 2.2.1 | MIT License Copyright (c) 2026 rapier.website Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
|
|
2
2
|
const t=Object.freeze({bytes:16777216,pixels:24e6,edge:16384}),n=[1];for(let t=1;t<=32;t++)n.push(2*n[t-1]);class e{constructor(t=4096){this.bytes=new Uint8Array(t),this.at=0,this.t=0,this.pending=0}write(t,e){if(!(e>=0&&e<n[t]))throw new Error("bit write out of range: "+t+" bits, "+e);let r=this.t+e*(1<<this.pending),o=this.pending+t;this.at+5>=this.bytes.length&&this.grow();const s=this.bytes;for(;o>=8;)s[this.at++]=255&r,r=Math.floor(r/256),o-=8;this.t=r,this.pending=o}o(t,e){for(let r=0;r<4;r++){const[o,s]=t[r];if(e>=s&&e-s<n[o])return this.write(2,r),void(o&&this.write(o,e-s))}throw new Error("U32 value out of range: "+e)}i(){this.pending&&(this.at+1>=this.bytes.length&&this.grow(),this.bytes[this.at++]=this.t,this.t=0,this.pending=0)}get u(){return 8*this.at+this.pending}grow(n=0){const e=t.bytes+64;if(this.at+n+16>e)throw Object.assign(new Error("The encoded picture exceeds 16 MiB."),{code:"JXL_SIZE"});const r=new Uint8Array(Math.min(e,Math.max(2*this.bytes.length,this.at+n+16)));r.set(this.bytes.subarray(0,this.at)),this.bytes=r}append(t){if(this.at+t.at+8>=this.bytes.length&&this.grow(t.at+8),this.pending)for(let n=0;n<t.at;n++)this.write(8,t.bytes[n]);else this.bytes.set(t.bytes.subarray(0,t.at),this.at),this.at+=t.at;t.pending&&this.write(t.pending,t.t)}finish(){const t=this.at+(this.pending?1:0),n=this.bytes.slice(0,t);return this.pending&&(n[this.at]=this.t),n}}function*r(t,n,e){let r,s;for(;!(r=t.next(s)).done;)s=yield o(r.value,t=>(n+t)/e);return r.value}const o=(t,n)=>"number"==typeof t?n(t):{...t,at:e=>n(t.at(e))};function s(t){return t>=0?2*t:2*-t-1}function c(t){return 31-Math.clz32(t)}function l(t){return t<=1?0:32-Math.clz32(t-1)}const i=(t,n)=>Object.assign(new Error(n),{code:t});function f(n){if(n>t.bytes)throw i("JXL_SIZE","The encoded picture exceeds 16 MiB.")}function a(t){try{return t()}catch(t){if(t instanceof RangeError&&!t.code)throw i("JXL_MEMORY","Not enough memory for this picture.");throw t}}const u=256;function h(t,n){t.o([[9,1],[13,1],[18,1],[30,1]],n)}function y(t,n,e,r,o,{xyb:s=!1,orientation:c=1,colorSpace:l}={}){t.write(16,2815),t.write(1,0),h(t,e),t.write(3,0),h(t,n),t.write(1,0);const i=1!==c;t.write(1,i?1:0),i&&t.write(6,c-1),t.write(4,8),o?t.write(3,5):t.write(2,0),t.write(1,s?1:0),3===r&&"display-p3"===l?t.write(21,903568):3===r?t.write(1,1):t.write(15,14100),i&&t.write(1,1),t.write(2,0),t.write(1,1),t.i()}function p(t,{alpha:n,shift:e=1}){t.write(9,8),n&&t.write(2,0),t.write(2,e),function(t,n){t.write(n?7:5,0),t.write(11,1)}(t,n)}function w(t,n,e=256){const r=Math.ceil(t/e),o=Math.ceil(n/e);return{p:r,A:o,M:Math.ceil(t/(8*e)),m:Math.ceil(n/(8*e)),U:1===r&&1===o}}function d(t,n,e,r){const o=r%t.p*u,s=(r/t.p|0)*u;return[o,s,Math.min(u,n-o),Math.min(u,e-s)]}function*A(t,n,e,r){if(t.pooled){const n=yield t;return n?(n.results.forEach((t,n)=>r(n,t)),n.hurried):null}let o=!1;for(let r=0;r<n;r++)if(e(r),o=yield t.at(r),o&&t.stop(r))return null;return o}function M(t,n){t.forEach((t,e)=>{const r=n[e];for(let n=0;n<t.length;n++)t[n]+=r[n]})}function g(t,n){const e=n.map(t=>t.length);!function(t,n){t.write(1,0),t.i();for(const e of n)t.o([[10,0],[14,1024],[22,17408],[30,4211712]],e);t.i()}(t,e);const r=t.finish(),o=r.length+e.reduce((t,n)=>t+n,0);f(o);const s=new Uint8Array(o);s.set(r);let c=r.length;for(const t of n)s.set(t,c),c+=t.length;return s}const b=[1,2,3,4,0,5,17,6,16,7,8,9,10,11,12,13,14,15],m=[2,4,3,2,2,4],U=[0,7,3,2,1,15];function I(t,n){const e=new Uint8Array(t.length),r=[];for(let n=0;n<t.length;n++)t[n]>0&&r.push(n);if(!r.length)return e;if(1===r.length)return e[r[0]]=1,e;for(let o=1;;o*=2){const s=r.map(n=>({w:Math.max(t[n],o),I:n,l:null,r:null})).sort((t,n)=>t.w-n.w||t.I-n.I),c=[];let l=0,i=0;const f=()=>l<s.length&&(i>=c.length||s[l].w<=c[i].w)?s[l++]:c[i++];for(;s.length-l+(c.length-i)>1;){const t=f(),n=f();c.push({w:t.w+n.w,I:-1,l:t,r:n})}const a=[[f(),0]];let u=0;for(;a.length;){const[t,n]=a.pop();t.I>=0?(e[t.I]=n,n>u&&(u=n)):a.push([t.l,n+1],[t.r,n+1])}if(u<=n)return e}}function S(t,n,e,r,o,s){const c=[];for(;c.push(r&o),r>>=s;)r--;for(let r=c.length-1;r>=0;r--)t.push(e),n.push(c[r])}function v(t,n){let e=0;for(let r=0;r<n;r++)e=e<<1|1&t,t>>=1;return e}function x(t){const n=new Uint32Array(17),e=new Uint32Array(17),r=new Uint16Array(t.length);for(const e of t)n[e]++;n[0]=0;for(let t=1,r=0;t<=16;t++)r=r+n[t-1]<<1,e[t]=r;for(let n=0;n<t.length;n++)t[n]&&(r[n]=v(e[t[n]]++,t[n]));return r}function C(t){const n=[];for(let e=0;e<t.length;e++)t[e]>0&&n.push(e);const e=n.length,r=n[e-1]+1||1,o=e<=4?new Uint8Array(r):I(t,15).subarray(0,r);let s=0;if(e<=4){n.sort((n,e)=>t[e]-t[n]||n-e),s=4===e&&t[n[0]]>t[n[2]]+t[n[3]]?1:0;const r=e<2?[0]:2===e?[1,1]:3===e?[1,2,2]:s?[1,2,3,3]:[2,2,2,2];n.forEach((t,n)=>{o[t]=r[n]}),n.sort((t,n)=>o[t]-o[n]||t-n)}return{S:r,v:o,C:x(o),T:e&&e<=4?n:null,q:s}}function T(t,n){if(n.S<=1)return;if(n.T){const e=c(n.S-1)+1;t.write(2,1),t.write(2,n.T.length-1);for(const r of n.T)t.write(e,r);return void(4===n.T.length&&t.write(1,n.q))}const e=n.v,r=[],o=[];let s=e.length-1;for(;s>0&&!e[s];)s--;let l=8;for(let t=0;t<=s;){const n=e[t];let c=1;for(;t+c<=s&&e[t+c]===n;)c++;let i=c;if(n&&n!==l&&(r.push(n),o.push(0),i--,l=n),i<3)for(let t=0;t<i;t++)r.push(n),o.push(0);else S(r,o,n?16:17,i-3,n?3:7,n?2:3);t+=c}const i=new Uint32Array(18);for(const t of r)i[t]++;let f=0;for(const t of i)t&&f++;1===f&&(i[r[0]?0:1]=i[r[0]]);const a=I(i,5),u=x(a);let h=18;for(;h>0&&!a[b[h-1]];)h--;t.write(2,0);for(let n=0;n<h;n++){const e=a[b[n]];t.write(m[e],U[e])}for(let n=0;n<r.length;n++){const e=r[n];t.write(a[e],u[e]),16===e?t.write(2,o[n]):17===e&&t.write(3,o[n])}}function q(t,n=0,e=0){return{split:t,L:n,X:e,J:1<<t}}function E(t,n,e=15){t.write(l(e+1),n.split),n.split!==e&&(t.write(l(n.split+1),n.L),t.write(l(n.split-n.L+1),n.X))}function L(t,n,e){if(n<t.J)return e[0]=n,e[1]=0,void(e[2]=0);const r=c(n),o=n-(1<<r),s=r-t.L-t.X;e[0]=t.J+(r-t.split<<t.L+t.X|o>>r-t.L<<t.X|o&(1<<t.X)-1),e[1]=s,e[2]=n>>t.X&(1<<s)-1}function X(t,n,e,r=0){L(t,n,J),e[r+J[0]]++}const J=[0,0,0];function N(t,n,e,r,o=0){L(e,r,J);const s=o+J[0];t.write(n.v[s],n.C[s]),J[1]&&t.write(J[1],J[2])}function _(t,{N:n=null,_:e,P:r}){t.write(1,n?1:0),n&&(t.o([[0,224],[0,512],[0,4096],[15,8]],n.G),t.o([[0,3],[0,4],[2,5],[8,9]],n.minLength),E(t,n.O,8)),e.length>1&&function(t,n){let e=0;for(const t of n)e=Math.max(e,t);const r=e?l(e+1):0;if(r<=3){if(t.write(1,1),t.write(2,r),r)for(const e of n)t.write(r,e);return}t.write(1,0),t.write(1,0);const o=q(8),s=q(4),c=n.length>=64,i=new Uint32Array(c?257:e+1),f=[];for(let t=0;t<n.length;){let e=1;for(;c&&t+e<n.length&&n[t+e]===n[t];)e++;if(e>=8)f.push([n[t],e-1]),i[n[t]]++,X(s,e-1-7,i,224),t+=e;else{for(let r=0;r<e;r++)f.push([n[t],0]),i[n[t]]++;t+=e}}const a=C(i);if(!c){_(t,{_:new Uint8Array(1),P:[{config:o,code:a}]});for(const[n]of f)N(t,a,o,n);return}const u=new Uint32Array(1);u[0]=1,_(t,{N:{G:224,minLength:7,O:s},_:new Uint8Array([1,0]),P:[{config:q(0),code:C(u)},{config:o,code:a}]});for(const[n,e]of f)N(t,a,o,n),e&&N(t,a,s,e-7,224)}(t,e),t.write(1,1);for(const n of r)E(t,n.config,15);for(const n of r){const e=n.code.S-1;if(e){const n=c(e);t.write(1,1),t.write(4,n),t.write(n,e-(1<<n))}else t.write(1,0)}for(const n of r)T(t,n.code)}const P={channel:null,weighted:null,fill:null},z=3,G=5,O=q(4),k=Object.freeze({G:224,minLength:7,O:O}),j=q(0),R=257;function Z(t,n=0,e=1){return{k:t,offset:n,j:e,context:-1}}function B(t,n,e,r){return{R:t,Z:n,left:e,right:r}}function Y(t,n){const e=(r,o)=>{if(r===o)return n?t[r].B:t[r];const s=r+o>>1;return B(n,n?t[s].Y:s,e(s+1,o),e(r,s))};return e(0,t.length-1)}function D(t){return Y(t,0)}function F(t,n){const e=[n],r=[],o=[];for(const t of e){if(t.left){r.push(t.R+1,s(t.Z)),e.push(t.left,t.right);continue}t.context=o.length,o.push(t);const n=1===t.j?0:31-Math.clz32(t.j&-t.j);r.push(0,t.k,s(t.offset),n,(t.j>>n)-1)}const c=new Uint32Array(64);for(const t of r)X(j,t,c);const l=C(c);_(t,{_:new Uint8Array(6),P:[{config:j,code:l}]});for(const n of r)N(t,l,j,n);return o}function Q(t,n){const e=[[3,0],[6,8],[10,72],[13,1096]];if("rct"===n.type)t.write(2,0),t.o(e,n.D),t.o([[0,6],[2,0],[4,2],[6,10]],n.F??6);else if("palette"===n.type)t.write(2,1),t.o(e,n.D),t.o([[0,1],[0,3],[0,4],[13,1]],n.H),t.o([[8,0],[10,256],[12,1280],[16,5376]],n.K),t.o([[0,0],[8,1],[10,257],[16,1281]],n.V??0),t.write(4,n.k??0);else{if("squeeze"!==n.type)throw new Error("unknown transform "+n.type);{t.write(2,2);const r=n.W??[];t.o([[0,0],[4,1],[6,9],[8,41]],r.length);for(const n of r)t.write(1,n.$?1:0),t.write(1,n.tt?1:0),t.o(e,n.D),t.o([[0,1],[0,2],[0,3],[4,4]],n.H)}}}function H(t,{nt:n=!0,et:e=[]}={}){t.write(1,n?1:0),t.write(1,1),t.o([[0,0],[0,1],[4,2],[8,18]],e.length);for(const n of e)Q(t,n)}function K(t,n,e,r=t=>t.context,o=()=>j){const s=new Uint8Array(n.length+1);for(const t of n)s[t.context]=r(t)+1;const c=new Uint32Array(2);c[1]=1;const l=[{config:j,code:C(c)}],i=Math.max(...s);for(let t=0;t<i;t++)l.push({config:o(t),code:C(e[t])});return _(t,{N:k,_:s,P:l}),l}function V(t,n,e,r,o,c,l=!1){if(P.channel?.(t,n,e,r,o,c,l))return;const i=c.k,f=c.offset,a=c.j,u=c.config||j,h=O;let y=0;const p=(e,r=u,o=0)=>{t?N(t,n,r,e,o):l&&!o?n[e]++:X(r,e,n,l?n.length-33:o)},w=()=>{if(y){if(y>=8)p(0),p(y-7-1,h,224);else for(let t=0;t<y;t++)p(0);y=0}},d=(t,n)=>{const r=e[t];let o;1===a?o=r-n-f:(o=Math.round((r-n-f)/a),e[t]=n+f+o*a),0!==o?(w(),p(s(o))):y++};for(let t=0,n=0;t<o;t++)for(let o=0;o<r;o++,n++){let s;if(0===i)s=0;else{const c=o?e[n-1]:t?e[n-r]:0,l=t?e[n-r]:c;if(1===i)s=c;else if(2===i)s=l;else if(3===i)s=(c+l)/2|0;else{const f=c+l-(o&&t?e[n-r-1]:c);if(5===i){const t=c<l?c:l,n=c<l?l:c;s=f<t?t:f>n?n:f}else{if(4!==i)throw new Error("predictor "+i+" is not coded here");s=Math.abs(f-c)<Math.abs(f-l)?c:l}}}d(n,s)}w()}const W=[q(0),q(4),q(4,1,1),q(3,0,1)];function $(t){const n=t.length-33,r=[0,0,0];let o,s;for(const l of W){const i=new Uint32Array(R);let f=0;for(let e=0;e<n;e++)t[e]&&(L(l,e,r),i[r[0]]+=t[e],f+=t[e]*r[1]);for(let e=0;e<33;e++)i[224+e]=t[n+e],f+=t[n+e]*Math.max(0,e-12);const a=C(i),u=new e(128);E(u,l),T(u,a);let h=u.u+f+(1===a.S?1:5+c(a.S-1));for(let t=0;t<i.length;t++)i[t]&&(h+=i[t]*a.v[t]);const y={config:l,rt:i,ot:h,extra:f};o||(o=y),(!s||h<s.ot)&&(s=y)}return[o,s]}const tt=(t,n,e,r)=>e?r?t[n]+256*t[n+3]:t[n]:t[n]+256*t[n+1]+65536*t[n+2]+(r?16777216*t[n+3]:0);function nt(t,n,e,{palette:r=!0}={}){const o=n*e;let s=!0,c=!0;for(let n=0,e=0;e<o&&(255===t[n+3]||(s=!1,c))&&(t[n]===t[n+1]&&t[n]===t[n+2]||(c=!1,s));e++,n+=4);const l=c?1:3,i=!s,f=l+(i?1:0),a=n=>tt(t,n,c,i),u=new Map;let h=null;for(let t=0,n=0;r&&n<o;n++,t+=4){const n=a(t);if(0!==n&&!u.has(n)&&(u.set(n,1),u.size>=2048))break}if(r&&u.size<2048){const t=[...u.keys()],n=(t,n)=>t>>>8*n&255,e=t=>(.299*n(t,0)+.587*n(t,1)+.114*n(t,2)+.01)*(4===f?n(t,3):1);t.sort((t,n)=>e(t)-e(n)),h={colours:[0,...t],byte:n}}return{colour:l,alpha:i,channels:f,palette:h}}function et({channels:t,alpha:n,palette:e},r){const o=t-(n?1:0)==1,s=e&&new Map(e.map((t,n)=>[t,n]));return(c,l,i,f,a,u,h)=>{if(r&&!e&&t>=3)r.fill(c,l,i,f,a,u,h);else if(e||!P.fill?.(l,i,f,a,u,h,t,c))for(let r=0;r<h;r++){let h=4*((a+r)*i+f),y=r*u;for(let r=0;r<u;r++,h+=4,y++)if(e)c[0][y]=s.get(tt(l,h,o,n));else if(t>=3){const n=l[h],e=l[h+1],r=l[h+2],o=n-r,s=r+(o>>1),i=e-s;c[0][y]=s+(i>>1),c[1][y]=o,c[2][y]=i,4===t&&(c[3][y]=l[h+3])}else c[0][y]=l[h],2===t&&(c[1][y]=l[h+3])}}}function rt(t,n){const{leaves:r,picture:o,C:s}=t,c=et(t,n),l=o.map(()=>new Int16Array(65536));return(t,n,i,f,a,u,h)=>{if(c(l,t,n,i,f,a,u),!s)return void o.forEach((t,n)=>V(null,h[t],l[n],a,u,r[t],!0));const y=h||new e(a*u*o.length+64);return h||H(y,{nt:!0,et:[]}),o.forEach((t,n)=>V(y,s[t],l[n],a,u,r[t])),h?void 0:y.finish()}}function*ot(t,n,e,{shape:o=nt(t,n,e),colorSpace:s,rct:c,pooled:l}={}){let i,f;const a=o.palette?[o,{...o,palette:null}]:[o];for(let o=0;o<a.length;o++)try{const f=yield*r(st(t,n,e,a[o],s,c,l),o,a.length);(!i||f.length<i.length)&&(i=f)}catch(t){if("JXL_SIZE"!==t.code)throw t;f=t}if(!i)throw f;return i}function*st(t,n,r,o,s,c,l){const{channels:i,alpha:f,palette:a}=o,u=w(n,r),h=u.p*u.A,b=a?2:i,m=Array.from({length:b},()=>Z(G)),U=D(m),I={channels:i,alpha:f,palette:a&&a.colours,rct:c?.type,leaves:m,picture:a?[u.U?1:0]:m.map((t,n)=>n)},S=et(I,c),v=Array.from({length:i},()=>new Int16Array(1024)),x=t=>d(u,n,r,t);let q=null;if(a){const t=a.colours.length;q=new Int16Array(t*i),a.colours.forEach((n,e)=>{for(let r=0;r<i;r++)q[r*t+e]=a.byte(n,r)})}if(!a){const o=t=>{const n=C(t),r=new e(128);T(r,n);let o=r.u;for(let e=0;e<t.length;e++)t[e]&&(o+=t[e]*(n.v[e]+Math.max(0,e<224?e-1:e-236)));return o},s=Math.min(n,32),c=Math.min(r,32),l=[G,z].map(t=>({k:t,rt:m.map(()=>new Uint32Array(R))}));for(const e of[0,.5,1]){S(v,t,n,Math.floor((n-s)*e),Math.floor((r-c)*e),s,c);for(const t of l)for(let n=0;n<i;n++)V(null,t.rt[n],v[n],s,c,Z(t.k))}m.forEach((t,n)=>{const e=l.map(t=>o(t.rt[n])),r=e[1]<e[0]?1:0;t.k=l[r].k})}const E=a?[{type:"palette",D:0,H:i,K:a.colours.length}]:i>=3&&0!==c?.type?[{type:"rct",D:0,F:c?.type??6}]:[];let L=m.map(()=>new Uint32Array(33+(a?4096:1024)));q&&V(null,L[0],q,a.colours.length,i,m[0],!0);const X=rt(I,c);yield*A({pooled:l,kind:"plan",setup:{...I,sizes:L.map(t=>t.length)},at:t=>(t+1)/(2*h),stop:()=>!1},h,e=>X(t,n,...x(e),L),(t,n)=>M(L,n));const J=L.map($),N=J.reduce((t,n)=>t+n[0].ot-n[1].ot,0)>27*(u.U?1:h+1)+8?1:0;m.forEach((t,n)=>{t.config=J[n][N].config}),L=J.map(t=>t[N].rt);const _=new e(256);y(_,n,r,o.colour,o.alpha,{colorSpace:s}),p(_,{alpha:o.alpha});const P=new e(4096);P.write(1,1),P.write(1,1);const O=K(P,F(P,U),L,t=>m.indexOf(t),t=>m[t].config),k={...I,C:m.map((t,n)=>O[n+1]?.code)},j=rt(k,c);H(P,{nt:!0,et:E}),q&&V(P,k.C[0],q,a.colours.length,i,m[0]);const B=[];if(u.U)j(t,n,0,0,n,r,P),yield 1,B.push(P.finish());else{B.push(P.finish());for(let t=0;t<u.M*u.m+1;t++)B.push(new Uint8Array(0));const e=B.length,r=(t,n)=>{B[e+t]=n};yield*A({pooled:l,kind:"plan",setup:k,at:t=>(h+t+1)/(2*h),stop:()=>!1},h,e=>r(e,j(t,n,...x(e))),r)}return g(_,B)}const ct=(t,n)=>t+n+(t>n?1:0)>>1;function lt(t,n,e){const r=t>=n&&n>=e?1:t<=n&&n<=e?-1:0;if(!r)return 0;let o=(4*(t*=r)-3*(e*=r)-(n*=r)+6)/12|0;return o-(1&o)>2*(t-n)&&(o=2*(t-n)+1),o+(1&o)>2*(n-e)&&(o=2*(n-e)),r*o}function it(t,n){const{w:e,h:r,data:o}=t,s=n?e:r,c=s+1>>1,l=s-c,i=n?c:e,f=n?r:c,a=n?l:e,u=n?r:l,h=new Int16Array(i*f),y=new Int16Array(a*u),p=n?1:e;for(let t=0;t<f;t++)for(let r=0;r<i;r++){const c=n?r:t,f=n?t*e+2*r:2*t*e+r;if(c===l){h[t*i+r]=o[f];continue}const u=o[f],w=o[f+p],d=ct(u,w),A=c+1<l?ct(o[f+2*p],o[f+3*p]):1&s?o[f+2*p]:d;h[t*i+r]=d,y[t*a+r]=u-w-lt(c?o[f-p]:d,d,A)}const w=(e,r,o)=>({w:r,h:o,st:t.st+ +n,ct:t.ct+!n,data:e});return[w(h,i,f),w(y,a,u)]}function ft(t){const n=[],e=t.length;let r=t[0].w,o=t[0].h;for(e>2&&t[1].w===r&&t[1].h===o&&(n.push({$:!0,tt:!1,D:1,H:2}),n.push({$:!1,tt:!1,D:1,H:2})),!(r>o)&&o>8&&(n.push({$:!1,tt:!0,D:0,H:e}),o=o+1>>1);r>8||o>8;)r>8&&(n.push({$:!0,tt:!0,D:0,H:e}),r=r+1>>1),o>8&&(n.push({$:!1,tt:!0,D:0,H:e}),o=o+1>>1);return n}const at=1024,ut=8192;function*ht(t,n,r,{quality:o=90,shape:s=nt(t,n,r,{palette:!1}),colorSpace:c}={}){const l=function(t){return t>=100?0:t>=30?.1+.09*(100-t):53/3e3*t*t-1.15*t+25}(o);if(!(l>0))throw new Error("lossy encoding needs a quality below 100");const{colour:i,alpha:f,channels:a}=s,u=n*r,h=Array.from({length:a},()=>new Int16Array(u));for(let n=0,e=0;e<u;e++,n+=4){if(3===i){const r=t[n],o=t[n+1],s=t[n+2],c=r-s,l=s+(c>>1),i=o-l;h[0][e]=l+(i>>1),h[1][e]=c,h[2][e]=i}else h[0][e]=t[n];f&&(h[a-1][e]=t[n+3])}const d=h.map((t,e)=>({w:n,h:r,st:0,ct:0,data:t,component:3===i?e:0===e?0:3})),A=1===n&&r>at&&3===i,M=A?ft(d).filter(t=>!t.$):1!==n&&1!==r||3!==i?[]:ft(d),b=function(t,n=ft(t)){const e=t.map(t=>({...t,level:0,lt:!1}));for(const t of n){const n=t.D+t.H-1,r=t.tt?n+1:e.length;for(let o=t.D;o<=n;o++){const[n,s]=it(e[o],t.$),c=e[o].level+1;e[o]={...n,level:c,lt:e[o].lt,component:e[o].component},e.splice(r+(o-t.D),0,{...s,level:c,lt:!0,component:e[o].component})}}return e}(d,M.length?M:void 0),m=t=>t.lt?0:G,U=t=>function(t,n,e,r){let o=Math.min(16,n+e);if(o>0&&o--,3===t)return 1;const s=.25*function(t){let n=1;for(let e=0;e<24;e++)n=(4*n+t/(n*n*n*n))/5;return t*n}(r),c=1<<o,l=1===t||2===t?.35*s*Math.max(.5,1024/c):.35*s*1.1*(163.84/c);return Math.max(1,Math.floor(l))}(t.component,t.st+(A&&t.component>0&&t.component<3?1:0),t.ct,l),I=[...3===i?[{type:"rct",D:0,F:6}]:[],{type:"squeeze",W:M}],S=w(n,r,at),v=S.M*S.m,x=S.p*S.A;let C=0;for(;C<b.length&&b[C].w<=at&&b[C].h<=at;)C++;const T=(t,n,e,r)=>{const o=n>>t.st,s=e>>t.ct;return{x:o,y:s,w:Math.min(t.w,o+(r>>t.st))-o,h:Math.min(t.h,s+(r>>t.ct))-s}},q=[{index:0,Y:0,it:[]}];for(let t=0;t<C;t++)q[0].it.push({c:t,rect:{x:0,y:0,w:b[t].w,h:b[t].h}});if(!S.U){for(let t=0;t<v;t++){const n=t%S.M,e=t/S.M|0,r={index:1+t,Y:1+v+t,it:[]};for(let t=C;t<b.length;t++){const o=b[t];if(Math.min(o.st,o.ct)<3)continue;const s=T(o,n*ut,e*ut,ut);s.w>0&&s.h>0&&r.it.push({c:t,rect:s})}q.push(r)}for(let t=0;t<x;t++){const n=t%S.p,e=t/S.p|0,r={index:2+v+t,Y:1+3*v+17+t,it:[]};for(let t=C;t<b.length;t++){const o=b[t];if(Math.min(o.st,o.ct)>2)continue;const s=T(o,n*at,e*at,at);s.w>0&&s.h>0&&r.it.push({c:t,rect:s})}q.push(r)}}for(const t of q)for(const n of t.it){const t=b[n.c];n.ft=Z(m(t),0,U(t)),n.ft.channel=n.c}const E=q.filter(t=>t.it.length),L=1===E.length?D(E[0].it.map(t=>t.ft)):function(t){return Y(t,1)}(E.map(t=>({Y:t.Y,B:D(t.it.map(t=>t.ft))}))),X=new Int16Array(1048576),J=t=>{const n=b[t.c],e=t.rect;if(e.w===n.w&&e.h===n.h)return n.data;for(let t=0;t<e.h;t++)X.set(n.data.subarray((e.y+t)*n.w+e.x,(e.y+t)*n.w+e.x+e.w),t*e.w);return X},N=[...new Set(q.flatMap(t=>t.it.map(t=>t.c)))].sort((t,n)=>t-n),_=new Map(N.map((t,n)=>[t,n])),P=N.map(()=>new Uint32Array(R)),z=1+2*q.length;let O=1;yield O/z;for(const t of q){for(const n of t.it)V(null,P[_.get(n.c)],J(n),n.rect.w,n.rect.h,n.ft);yield++O/z}const k=new e(256);y(k,n,r,i,f,{colorSpace:c}),p(k,{alpha:f,shift:n>256||r>256?3:1});const j=Array.from({length:S.U?1:2+v+x},()=>null),B=j[0]=new e(65536);B.write(1,1),B.write(1,1);const Q=K(B,F(B,L),P,t=>_.get(t.channel));H(B,{nt:!0,et:I});for(const t of q){let n=j[t.index];n||(n=j[t.index]=new e(4096),t.it.length&&H(n,{nt:!0,et:[]}));for(const e of t.it)V(n,Q[_.get(e.c)+1].code,J(e),e.rect.w,e.rect.h,e.ft);yield++O/z}return g(k,function(t){return t.map(t=>t?t.finish():new Uint8Array(0))}(j))}const yt=[-500,-392,-255,-191,-127,-95,-63,-47,-31,-23,-15,-11,-7,-4,-3,-1,0,1,3,5,7,11,15,23,31,47,63,95,127,191,255,392,500],pt=Int8Array.from({length:1003},(t,n)=>yt.filter(t=>t<n-501).length),wt=Int32Array.from({length:64},(t,n)=>Math.floor(16777216/(n+1))),dt=(t,n)=>{const e=Math.max(0,26-Math.clz32(t+1));return 4+(n*wt[t>>e]>>e)},At=[12,13].map(t=>Int32Array.from({length:2048},(n,e)=>dt(e,t))),Mt=(t,n)=>t<2048?At[n-12][t]:dt(t,n),gt=new Int32Array(yt.length+1);let bt;function mt(t,n,e,r,o,c=0,l=gt,i,f){if(P.weighted?.(t,n,e,r,o,c,l,i,f))return;const a=r+2,u=bt&&bt[0].length>=2*a?bt:Array.from({length:6},(t,n)=>new Int32Array(n<5?2*a:8));bt=null;for(const t of u)t.fill(0);const[h,y,p,w,d,A]=u;let M=0;const g=(e,r,o=j,s=0)=>{t?N(t,n[e],o,r,s):X(o,r,n[e],s)},b=()=>{if(M){if(M>k.minLength)g(A[0],0),g(A[1],M-k.minLength-1,k.O,k.G);else for(let t=0;t<M;t++)g(A[t],0);M=0}};for(let t=0,n=0;t<o;t++){const o=1&t?0:a,u=1&t?a:0;for(let a=0;a<r;a++,n++){const m=a?e[n-1]:t?e[n-r]:0,U=t?e[n-r]:m,I=a+1<r&&t?e[n-r+1]:U,S=u+a,v=a<r-1?S+1:S,x=a?S-1:S;let C=Mt(h[S]+h[v]+h[x],13),T=Mt(y[S]+y[v]+y[x],12),q=Mt(p[S]+p[v]+p[x],12),E=Mt(w[S]+w[v]+w[x],12);const L=8*U,X=8*m,J=8*I,N=a?d[o+a-1]:0,_=d[S],P=d[x],z=d[v],G=_+N;let O=N;Math.abs(_)>Math.abs(O)&&(O=_),Math.abs(P)>Math.abs(O)&&(O=P),Math.abs(z)>Math.abs(O)&&(O=z);const k=l[pt[O<-501?0:O>501?1002:O+501]];f&&(f[n]=O);const j=X+J-L,R=L-(16*(G+z)>>5),Z=X-(10*(G+P)>>5),B=L-(7*(P+_+z)>>5),Y=27-Math.clz32(C+T+q+E);C>>=Y,T>>=Y,q>>=Y,E>>=Y;const D=C+T+q+E;let F=Math.floor(((D>>1)-1+j*C+R*T+Z*q+B*E)*wt[D-1]/16777216);if((_^N|_^P)<=0){const t=Math.min(X,J,L),n=Math.max(X,J,L);F=F<t?t:F>n?n:F}const Q=e[n],H=Q-(F+3>>3)-c;i?i[n]=s(H):0===H?(M<8&&(A[M]=k),M++):(b(),g(k,s(H)));const K=8*Q,V=Math.abs(j-K)+3>>3,W=Math.abs(R-K)+3>>3,$=Math.abs(Z-K)+3>>3,tt=Math.abs(B-K)+3>>3;d[o+a]=F-K,h[o+a]=V,y[o+a]=W,p[o+a]=$,w[o+a]=tt,h[u+a+1]+=V,y[u+a+1]+=W,p[u+a+1]+=$,w[u+a+1]+=tt}}b(),bt=u}const Ut=t=>Math.max(0,t<224?t-1:t-236),It=t=>{const n=C(t),r=new e(128);T(r,n);let o=r.u;for(let e=0;e<t.length;e++)t[e]&&(o+=t[e]*(n.v[e]+Ut(e)));return o};function St(t,n,e,r,o){const c=new Uint32Array(n*e);if(6===r)return mt(null,null,t,n,e,0,void 0,c,o),c;for(let o=0,l=0;o<e;o++)for(let e=0;e<n;e++,l++){const i=e?t[l-1]:o?t[l-n]:0,f=o?t[l-n]:i,a=e&&o?t[l-n-1]:i,u=3===r?(i+f)/2|0:Math.max(Math.min(i,f),Math.min(Math.max(i,f),i+f-a));c[l]=s(t[l]-u)}return c}function vt(t,n,e=1){const r=Array.from({length:e},()=>new Uint32Array(R)),o=[],s=(t,e,s=0)=>{const c=n?n[t]:0;o.push(e,s,c),X(s?k.O:j,e,r[c],s)};for(let n=0;n<t.length;){let e=1;if(!t[n])for(;n+e<t.length&&!t[n+e];)e++;if(s(n,t[n]),e>k.minLength)s(n+1,e-1-k.minLength,k.G);else for(let t=1;t<e;t++)s(n+t,0);n+=e}return{rt:r,it:o}}function xt(t,n,e,r,o){const s=vt(t,Uint8Array.from(n,t=>{let n=0,e=o.length;for(;n<e;){const r=n+e>>1;t>o[r]?n=r+1:e=r}return n}),o.length+1),c=s.rt.length,l=s.rt.map(t=>t.some(t=>t)),i=new Float64Array(c+1).fill(1/0),f=new Uint8Array(c+1);i[0]=0;for(let t=1;t<=c;t++){const n=new Uint32Array(R);let e=0;for(let r=t-1;r>=0;r--){if(l[r]){for(let t=0;t<R;t++)n[t]+=s.rt[r][t];e=It(n)}const o=i[r]+e+24;o<i[t]&&(i[t]=o,f[t]=r)}}const a=[];for(let t=c;t;t=f[t])a.unshift([f[t],t]);const u=a.map(()=>Z(e)),h=new Uint8Array(c),y=a.map(([t,n],e)=>{const r=new Uint32Array(R);for(let o=t;o<n;o++){h[o]=e;for(let t=0;t<R;t++)r[t]+=s.rt[o][t]}return r});for(let t=2;t<s.it.length;t+=3)s.it[t]=h[s.it[t]];const p=(t,n)=>{if(t===n)return u[t];const e=t+n>>1;return B(r,o[a[e][1]-1],p(e+1,n),p(t,e))};return{leaves:u,B:p(0,a.length-1),rt:y,it:s.it}}const Ct=[-127,-31,-7,-1,0,1,7,31,127],Tt=[-191,-127,-63,-31,-7,-1,0,7,31,63,127,191,255];function qt(t,n,e,r){const o=new Int32Array(n*e);for(let s=0,c=0;s<e;s++)for(let e=0;e<n;e++,c++){const l=e?t[c-1]:s?t[c-n]:0,i=s?t[c-n]:l,f=e&&s?t[c-n-1]:l;o[c]=9===r?l+i-f:l-f}return o}function Et(t){const n=new e(512),r=K(n,F(n,t.B),t.rt,n=>t.leaves.indexOf(n));let o=n.u;return t.rt.forEach((t,n)=>{const{v:e}=r[n+1].code;for(let n=0;n<t.length;n++)o+=t[n]*((e[n]||0)+Ut(n))}),o}function Lt(t,n,e,r){return t.map(t=>{let o;for(const s of[5,3,6]){const c=6===s?new Int32Array(n*e):null,l=St(t,n,e,s,c),i=Z(s),f=[{...vt(l),leaves:[i],B:i}];if(c&&f.push(xt(l,c,s,15,Ct)),r>=6&&5===s)for(const r of[9,10]){const o=qt(t,n,e,r),c=9===r?Tt:Ct;f.push(xt(l,o,s,r,c))}for(const t of f){const n=Et(t);(!o||n<o.ot)&&(o={...t,ot:n})}}return o})}function Xt(t,n){const e=n.flatMap(t=>t.leaves),r=K(t,F(t,D(n.map(t=>t.B))),n.flatMap(t=>t.rt),t=>e.indexOf(t));return()=>{for(let o=0;o<n.length;o++){const{it:s}=n[o],c=n[o].leaves.map(t=>r[e.indexOf(t)+1].code);for(let n=0;n<s.length;n+=3){const e=s[n+1];N(t,c[s[n+2]],e?k.O:j,s[n],e)}}}}function*Jt(t,n,r,o,s,c=4,l=!1,i){const{channels:a}=o,u=w(n,r),h=u.p*u.A,M=l?o.palette:null;if(l&&!M)return null;const b={channels:a,alpha:o.alpha,palette:M&&M.colours,rung:c},m=new e(256);y(m,n,r,o.colour,o.alpha,{colorSpace:s}),p(m,{alpha:o.alpha});const U=M?[{type:"palette",D:0,H:a,K:M.colours.length}]:a>=3?[{type:"rct",D:0,F:6}]:[];let I;if(M){const t=M.colours.length,n=new Int16Array(t*a);M.colours.forEach((e,r)=>{for(let o=0;o<a;o++)n[o*t+r]=M.byte(e,o)}),I=Lt([n],t,a,c)}const S=new e(4096),v=[];let x=0;const C=t=>{x+=t.length,f(x),v.push(t)};if(S.write(1,1),S.write(1,1),u.U){const e=Array.from({length:M?1:a},()=>new Int16Array(65536));et(b)(e,t,n,0,0,n,r);const o=Xt(S,[...I||[],...Lt(e,n,r,c)]);return H(S,{et:U}),o(),C(S.finish()),(yield 1)?null:g(m,v)}let T;if(I)T=Xt(S,I);else{const t=Array.from({length:a},()=>Z(5));K(S,F(S,D(t)),t.map(()=>new Uint32Array(R)),n=>t.indexOf(n))}H(S,{et:U}),T&&T(),C(S.finish());for(let t=0;t<u.M*u.m+1;t++)v.push(new Uint8Array(0));const q=function(t){const n=et(t),r=Array.from({length:t.palette?1:t.channels},()=>new Int16Array(65536));return(o,s,c,l,i,f)=>{n(r,o,s,c,l,i,f);const a=new e(i*f*r.length+256);return H(a,{nt:!1}),Xt(a,Lt(r,i,f,t.rung))(),a.finish()}}(b);return null===(yield*A({pooled:i,kind:"local",setup:b,at:t=>(t+1)/h,stop:()=>!0},h,e=>C(q(t,n,...d(u,n,r,e))),(t,n)=>C(n)))?null:g(m,v)}function Nt(t,n){const e=Math.floor(t/7),r=t%7,o=e%3,s=(e+1+Math.floor(e/3))%3,c=(e+2-Math.floor(e/3))%3;return{type:t,fill(t,e,l,i,f,a,u){for(let h=0;h<u;h++)for(let u=0,y=h*a,p=4*((f+h)*l+i);u<a;u++,y++,p+=4){const l=e[p+o],i=e[p+s],f=e[p+c];if(6===r){const n=l-f,e=f+(n>>1),r=i-e;t[0][y]=e+(r>>1),t[1][y]=n,t[2][y]=r}else t[0][y]=l,t[1][y]=i-(r>>1==1?l:r>>1==2?l+f>>1:0),t[2][y]=f-(1&r?l:0);4===n&&(t[3][y]=e[p+3])}}}}const _t=t=>null===t||("object"==typeof t?t.hurried:t);function Pt(n,s,c,l,f){const{quality:a,colorSpace:u}=function(t={},n=100){if(null===t||"object"!=typeof t)throw i("JXL_INPUT","Options are an object: {quality, colorSpace}.");if(void 0!==t.quality&&(n=t.quality),"number"!=typeof n||!Number.isFinite(n)||n<1||n>100)throw i("JXL_INPUT","Quality is a number from 1 to 100.");const e=void 0===t.colorSpace?"srgb":t.colorSpace;if("srgb"!==e&&"display-p3"!==e)throw i("JXL_INPUT","The colour space is srgb or display-p3.");return{quality:n,colorSpace:e}}(l),h=void 0===l?.effort?1:l.effort;if(!Number.isInteger(h)||h<1||h>9)throw i("JXL_INPUT","Effort is a whole number from 1 to 9.");return function(n,e,r,o){if(function(n,e,r=t){if(!Number.isInteger(n)||!Number.isInteger(e)||n<1||e<1)throw i("JXL_INPUT","A picture is at least one pixel wide and high, in whole pixels.");if(n>r.edge||e>r.edge)throw i("JXL_DIMENSIONS","A picture is at most "+r.edge+" pixels on a side.");if(n*e>r.pixels)throw i("JXL_DIMENSIONS","A picture is at most "+r.pixels.toLocaleString("en-US")+" pixels.")}(e,r,o),!(n instanceof Uint8Array||n instanceof Uint8ClampedArray))throw i("JXL_INPUT","Pixels are a Uint8Array or Uint8ClampedArray of RGBA bytes.");if(n.length!==e*r*4)throw i("JXL_INPUT","Pixels are width * height * 4 bytes: straight (not premultiplied) RGBA, row by row.")}(n,s,c),function*(t,n,s,c,l,i,f){const a=nt(t,n,s);if(c<100){if(!a.palette)return yield*ht(t,n,s,{quality:c,shape:a,colorSpace:l});const e=yield*r(ot(t,n,s,{shape:a,colorSpace:l}),0,2);let o;try{o=yield*r(ht(t,n,s,{quality:c,shape:a,colorSpace:l}),1,2)}catch(t){if("JXL_SIZE"!==t.code&&(!(t instanceof RangeError)||t.code))throw t;o=e}return e.length<=o.length?e:o}if(i<2)return yield*ot(t,n,s,{shape:a,colorSpace:l,pooled:f});let u=yield*r(ot(t,n,s,{shape:a,colorSpace:l,pooled:f}),0,2);const h=a.palette?{...a,palette:null}:a;if(i>=4){const r=[Zt(t,n,s,h,l,3,f)];a.palette&&r.push(Jt(t,n,s,a,l,4,!0,f)),i>=6&&(r.push(Jt(t,n,s,a,l,6,!1,f)),a.palette&&r.push(Jt(t,n,s,a,l,6,!0,f))),r.push(function*(t,n,r,o,s,c){if(3!==o.colour||n*r<4096)return null;const l=Math.min(n,32),i=Math.min(r,32),f=Array.from({length:o.channels},()=>new Int16Array(l*i)),a=[6,...Array.from({length:42},(t,n)=>n).filter(t=>6!==t)];let u;for(let s=0;s<a.length;s++){const c=Nt(a[s],o.channels),h=[5,3].map(t=>({k:t,rt:Array.from({length:3},()=>new Uint32Array(1057))}));for(let e=0;e<3;e++){c.fill(f,t,n,Math.floor((n-l)*e/2),Math.floor((r-i)*e/2),l,i);for(const t of h)for(let n=0;n<3;n++)V(null,t.rt[n],f[n],l,i,Z(t.k),!0)}const y=new e(32);c.type&&Q(y,{type:"rct",D:0,F:c.type});let p=y.u;for(let t=0;t<3;t++)p+=Math.min(...h.map(n=>$(n.rt[t])[1].ot));if((!u||p<u.ot)&&(u={rct:c,ot:p}),yield(s+1)/(4*a.length))return null}if(6===u.rct.type)return null;const h=ot(t,n,r,{shape:{...o,palette:null},colorSpace:s,rct:u.rct,pooled:c});let y,p;for(;!(y=h.next(p)).done;){const t=y.value,n="number"==typeof t;if(p=yield n?.25+.75*t:{...t,at:n=>.25+.75*t.at(n),stop:n=>t.at(n)<1},n?p&&t<1:!p)return null}return y.value}(t,n,s,a,l,f));for(let t=0;t<r.length;t++)try{let n,e,s=!1;for(;!(n=r[t].next(e)).done;)s=_t(e=yield o(n.value,n=>.5+(t+n)/(2*r.length)));if(n.value&&n.value.length<u.length&&(u=n.value),s)return u}catch(t){if("JXL_SIZE"!==t.code&&(!(t instanceof RangeError)||t.code))throw t}return u}try{const e=yield*r(Zt(t,n,s,h,l,i,f),1,2);e&&e.length<u.length&&(u=e)}catch(t){if("JXL_SIZE"!==t.code&&(!(t instanceof RangeError)||t.code))throw t}return u}(n,s,c,a,u,h,f&&a>=100&&!w(s,c).U)}const zt=t=>Math.max(0,t<224?t-1:t-236);function Gt(t){const n=C(t),r=new e(128);T(r,n);let o=r.u;for(let e=0;e<t.length;e++)t[e]&&(o+=t[e]*(n.v[e]+zt(e)));return o}const Ot=t=>{const n=new Uint32Array(R);for(const e of t)for(let t=0;t<R;t++)n[t]+=e[t];return n},kt=yt.length+1,jt=Int32Array.from({length:kt},(t,n)=>n);function Rt(t){const{channels:n,first:r,plans:o}=t,s=et(t),c=r?.map(t=>Z(t)),l=Array.from({length:n},()=>new Int16Array(65536));return(t,r,i,f,a,u,h)=>{if(s(l,t,r,i,f,a,u),!o){for(let t=0;t<n;t++)V(null,h[t],l[t],a,u,c[t]),mt(null,h.slice(n+t*kt,n+(t+1)*kt),l[t],a,u,0,jt);return}const y=h||new e(a*u*n+64);return h||H(y,{nt:!0,et:[]}),o.forEach(({ft:t,C:n,ut:e},r)=>{6===t.k?mt(y,n,l[r],a,u,0,e):V(y,n[0],l[r],a,u,t)}),h?void 0:y.finish()}}function*Zt(t,n,r,o,s,c,l){const{channels:i}=o,f=w(n,r),a=f.p*f.A,u={channels:i,alpha:o.alpha,palette:null},h=et(u),b=Array.from({length:i},()=>new Int16Array(1024)),m=t=>d(f,n,r,t),U=Math.min(n,32),I=Math.min(r,32),S=[G,z].map(t=>({k:t,rt:b.map(()=>new Uint32Array(R))}));for(const e of[0,.5,1]){h(b,t,n,Math.floor((n-U)*e),Math.floor((r-I)*e),U,I);for(const t of S)for(let n=0;n<i;n++)V(null,t.rt[n],b[n],U,I,Z(t.k))}const v=b.map((t,n)=>Z(S[Gt(S[1].rt[n])<Gt(S[0].rt[n])?1:0].k)),x=kt,C=b.map(()=>new Uint32Array(R)),T=b.map(()=>Array.from({length:x},()=>new Uint32Array(R))),q=[...C,...T.flat()],E={...u,first:v.map(t=>t.k)},L=Rt(E);if(null===(yield*A({pooled:l,kind:"search",setup:{...E,sizes:q.map(t=>t.length)},at:t=>(t+1)/(2*a),stop:()=>!0},a,e=>L(t,n,...m(e),q),(t,n)=>M(q,n))))return null;const X=b.map((t,n)=>{const e={ht:Gt(C[n]),leaves:[v[n]],rt:[C[n]],cuts:[]},r=Ot(T[n]),o=Gt(r);return o<e.ht?{ht:o,leaves:[Z(6)],rt:[r],cuts:[]}:e}),J=c<3?X:X.map((t,n)=>{const e=T[n].map(t=>t.some(t=>t)),r=new Float64Array(x+1).fill(1/0),o=new Int32Array(x+1);r[0]=0;for(let t=1;t<=x;t++){const s=new Uint32Array(R);let c=0;for(let l=t-1;l>=0;l--){if(e[l]){const t=T[n][l];for(let n=0;n<R;n++)s[n]+=t[n];c=Gt(s)}const i=r[l]+c+24;i<r[t]&&(r[t]=i,o[t]=l)}}if(!(r[x]<t.ht))return t;const s=[];for(let t=x;t>0;t=o[t])s.unshift([o[t],t]);return{ht:r[x],leaves:s.map(()=>Z(6)),rt:s.map(([t,e])=>Ot(T[n].slice(t,e))),cuts:s.slice(0,-1).map(([,t])=>yt[t-1]),ut:Int32Array.from({length:x},(t,n)=>s.findIndex(([t,e])=>n>=t&&n<e))}}),N=[X,J].filter((t,n)=>n?t.some((t,n)=>t!==X[n]):t.some((t,n)=>t.leaves[0]!==v[n]));if(!N.length)return null;const _=t=>({B:D(t.map(t=>((t,n)=>{const e=(r,o)=>{if(r===o)return t[r];const s=r+o>>1;return B(15,n[s],e(s+1,o),e(r,s))};return e(0,t.length-1)})(t.leaves,t.cuts))),leaves:t.flatMap(t=>t.leaves),rt:t.flatMap(t=>t.rt)}),P=t=>{const{B:n,leaves:r,rt:o}=_(t),s=new e(4096),c=K(s,F(s,n),o,t=>r.indexOf(t));let l=s.u;return o.forEach((t,n)=>{const{v:e}=c[n+1].code;for(let n=0;n<t.length;n++)t[n]&&(l+=t[n]*(e[n]+zt(n)))}),l};let O=N;if(N.length>1){const[t,n]=N.map(P),e=27*(f.U?1:a+1)+8;n+e<=t?O=[N[1]]:t+e<=n?O=[N[0]]:n<t&&(O=[N[1],N[0]])}let k=0,j=!1,Y=null;for(const t of O){const n=yield*Q(t);if(!n)return Y;if((!Y||n.length<Y.length||n.length===Y.length&&t===N[0])&&(Y=n),j)return Y}return Y;function*Q(c){const{B:h,leaves:w,rt:d}=_(c),M=i>=3?[{type:"rct",D:0,F:6}]:[],b=new e(256);y(b,n,r,o.colour,o.alpha,{colorSpace:s}),p(b,{alpha:o.alpha});const U=new e(4096);U.write(1,1),U.write(1,1);const I=K(U,F(U,h),d,t=>w.indexOf(t));H(U,{nt:!0,et:M});const S={...u,plans:c.map(t=>({ft:t.leaves[0],C:t.leaves.map(t=>I[w.indexOf(t)+1].code),ut:t.ut}))},v=Rt(S),x=[];if(f.U)v(t,n,0,0,n,r,U),j=yield.5+ ++k/(2*O.length*a),x.push(U.finish());else{x.push(U.finish());for(let t=0;t<f.M*f.m+1;t++)x.push(new Uint8Array(0));const e=k,r=x.length,o=(t,n)=>{x[r+t]=n};if(j=yield*A({pooled:l,kind:"search",setup:S,at:t=>.5+(e+t+1)/(2*O.length*a),stop:t=>t+1<a},a,e=>o(e,v(t,n,...m(e))),o),null===j)return null;k+=a}return g(b,x)}}function Bt(t,n,e,r){return function(t){let n;for(;!(n=t.next()).done;);return n.value}(Yt(t,n,e,r))}function Yt(t,n,e,r){return function(t){const n=function*(){let e,r;for(;!(e=a(()=>t.next(n.hurry))).done;)yield r=e.value;return r<1&&(yield 1),n.bytes=function(t){return f(t.length),t}(e.value)}();return n.bytes=null,n.hurry=!1,n}(Pt(t,n,e,r))}export{t as LIMITS,Bt as encode,Yt as encodeSteps};
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
/*! Rapier JXL 2.2.
|
|
1
|
+
/*! Rapier JXL 2.2.1 | MIT License Copyright (c) 2026 rapier.website Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
|
|
2
2
|
const t=Object.freeze({bytes:16777216,pixels:24e6,edge:16384}),o=Object.freeze({bytes:16777216,pixels:64e6,edge:16384}),n=[1];for(let t=1;t<=32;t++)n.push(2*n[t-1]);class r{constructor(t=4096){this.bytes=new Uint8Array(t),this.at=0,this.t=0,this.pending=0}write(t,o){if(!(o>=0&&o<n[t]))throw new Error("bit write out of range: "+t+" bits, "+o);let r=this.t+o*(1<<this.pending),e=this.pending+t;this.at+5>=this.bytes.length&&this.grow();const i=this.bytes;for(;e>=8;)i[this.at++]=255&r,r=Math.floor(r/256),e-=8;this.t=r,this.pending=e}o(t,o){for(let r=0;r<4;r++){const[e,i]=t[r];if(o>=i&&o-i<n[e])return this.write(2,r),void(e&&this.write(e,o-i))}throw new Error("U32 value out of range: "+o)}i(){this.pending&&(this.at+1>=this.bytes.length&&this.grow(),this.bytes[this.at++]=this.t,this.t=0,this.pending=0)}get u(){return 8*this.at+this.pending}grow(o=0){const n=t.bytes+64;if(this.at+o+16>n)throw Object.assign(new Error("The encoded picture exceeds 16 MiB."),{code:"JXL_SIZE"});const r=new Uint8Array(Math.min(n,Math.max(2*this.bytes.length,this.at+o+16)));r.set(this.bytes.subarray(0,this.at)),this.bytes=r}append(t){if(this.at+t.at+8>=this.bytes.length&&this.grow(t.at+8),this.pending)for(let o=0;o<t.at;o++)this.write(8,t.bytes[o]);else this.bytes.set(t.bytes.subarray(0,t.at),this.at),this.at+=t.at;t.pending&&this.write(t.pending,t.t)}finish(){const t=this.at+(this.pending?1:0),o=this.bytes.slice(0,t);return this.pending&&(o[this.at]=this.t),o}}const e=(t,o)=>"number"==typeof t?o(t):{...t,at:n=>o(t.at(n))};function i(t){return t>=0?2*t:2*-t-1}function s(t){return 31-Math.clz32(t)}function f(t){return t<=1?0:32-Math.clz32(t-1)}function c(t){if(0===t)return 0;const o=t<0?32768:0;if(!((t=Math.abs(t))<65520))throw new Error("half float out of range: "+t);let n=0,r=t;for(;r>=2;)r/=2,n++;for(;r<1;)r*=2,n--;n<-14?(r=16384*t,n=-15):r-=1;let e=Math.round(1024*r);return 1024===e&&(e=0,n++),o|n+15<<10|e}const a=[0,1,8,16,9,2,3,10,17,24,32,25,18,11,4,5,12,19,26,33,40,48,41,34,27,20,13,6,7,14,21,28,35,42,49,56,57,50,43,36,29,22,15,23,30,37,44,51,58,59,52,45,38,31,39,46,53,60,61,54,47,55,62,63];function l(t,o="JXL_JPEG"){return Object.assign(new Error("JPEG: "+t),{code:o})}function h(t,o){const n=new Uint16Array(65536);let r=0,e=0;for(let i=1;i<=16;i++){for(let s=0;s<t[i-1];s++){const t=o[e++],s=r<<16-i,f=1<<16-i;if(s+f>=65536)throw l("bad Huffman table");n.fill(i<<8|t,s,s+f),r++}r<<=1}return n}const u=[.436,.2225,.0139,.3851,.7169,.0971,.143,.0606,.7139],w=[.5151,.2412,-.001,.292,.6922,.0419,.1571,.0666,.7841],d=[0,.00516,.01435,.02934,.05088,.07958,.11602,.16068,.21404,.27652,.34851,.43039,.52252,.62523,.73884,.86367,1],y=[2.4,1/1.055,.055/1.055,1/12.92,.04045];function p(t){if(t<=.04045)return t/12.92;const o=(t+.055)/1.055;let n=1;for(let t=0;t<24;t++)n=(4*n+o/(n*n*n*n))/5;return o*o*n*n}function b(t,o,n){const r=77===t[o]&&77===t[o+1];if(!r&&(73!==t[o]||73!==t[o+1]))return 1;const e=o=>o+2>n?0:r?t[o]<<8|t[o+1]:t[o]|t[o+1]<<8;if(42!==e(o+2))return 1;const i=o+(o=>o+4>n?0:r?(t[o]<<24|t[o+1]<<16|t[o+2]<<8|t[o+3])>>>0:(t[o]|t[o+1]<<8|t[o+2]<<16|t[o+3]<<24)>>>0)(o+4),s=e(i);for(let t=0,o=i+2;t<s&&o+12<=n;t++,o+=12){if(274!==e(o))continue;const t=e(o+8);return t>=1&&t<=8?t:1}return 1}function m(t,o,n,r,e,i,s,f,c){!function(t,o,n,r,e,i){if(!t.progressive){if(0!==n||63!==r||0!==e||0!==i)throw l("a bad spectral selection");for(const t of o){if(t.component.coverage.some(t=>-1!==t))throw l("a component coded twice");t.component.coverage.fill(0)}return}if(i>13||e&&e!==i+1)throw l("a bad successive approximation");if(0===n){if(0!==r)throw l("a bad spectral selection");for(const{component:t}of o){if(t.coverage[0]!==(e||-1))throw l(e?"a refinement scan out of order":"a DC scan twice");t.coverage[0]=i}return}if(1!==o.length)throw l("an interleaved AC scan");if(r>63||n>r)throw l("a bad spectral selection");const{coverage:s}=o[0].component;if(-1===s[0])throw l("an AC scan before the DC scan");for(let t=n;t<=r;t++){if(s[t]!==(e||-1))throw l(e?"a refinement scan out of order":"a band coded twice");s[t]=i}}(n,r,e,i,s,f);let h=o,u=0,w=0,d=0,y=!1;const p=()=>{for(;w<=24;){let o=0;if(y||h>=t.length)y=!0,d+=8;else if(o=t[h],255===o){const n=t[h+1];if(0===n)h+=2;else{if(255===n){h++;continue}y=!0,o=0,d+=8}}else h++;u=(u<<8|o)>>>0,w+=8}},b=()=>l("a scan cut short"),m=t=>{if(!t)return 0;if(p(),t>w-d)throw b();const o=u>>>w-t&(1<<t)-1;return w-=t,o},M=(t,o)=>t<1<<o-1?t-(1<<o)+1:t,g=t=>{if(!t)throw l("a scan without its Huffman table");p();const o=t[u>>>w-16&65535];if(!o)throw l("bad Huffman code");if(o>>8>w-d)throw b();return w-=o>>8,255&o},A=()=>{const o=w-d;if(o>=8)throw l("bytes left over in a scan");if(v)throw l("an end-of-band run past its interval");if(o&&(u>>>d&(1<<o)-1)!=(1<<o)-1)throw l("bad scan padding");for(;h+1<t.length&&255===t[h]&&255===t[h+1];)h++},U=o=>{if(A(),255!==t[h]||t[h+1]!==208+(7&o))throw l("a restart marker missing or out of order");h+=2,u=0,w=0,d=0,y=!1;for(const t of r)t.component.pred=0;v=0},I=(t,o)=>{if(o>11)throw l("a DC value out of range");const n=o?M(m(o),o):0;if(t.component.pred+=n,t.component.pred>2047||t.component.pred<-2048)throw l("a DC value out of range");return t.component.pred},x=(t,o)=>{if(t>10)throw l("an AC value out of range");const n=M(m(t),t)*(1<<o);if(n>1023||n<-1023)throw l("an AC value out of range");return n};let v=0;const E=1===r.length,S=n.progressive,C=()=>l("coefficients past the "+(S?"band":"block")),J=(t,o,n)=>{if(v>0)v--;else for(let r=e||1;r<=i;){const e=g(t.ac),s=e>>4,c=15&e;if(c){if(r+=s,r>i)throw C();o[n+a[r]]=x(c,f),r++}else{if(s<15){if(s&&!S)throw l("an end-of-band run in a sequential scan");v=(1<<s)-1+(s?m(s):0);break}if(r+=16,r>i+1)throw C()}}},L=S?0===e?0===s?(t,o,n)=>{const r=I(t,g(t.dc))*(1<<f);if(r>2047||r<-2048)throw l("a DC value out of range");o[n]=r}:(t,o,n)=>{m(1)&&(o[n]|=1<<f)}:0===s?J:(t,o,n)=>{const r=1<<f,s=-1<<f;let c=e;if(v<=0)for(;c<=i;c++){const e=g(t.ac);let f=e>>4,h=0;const u=15&e;if(u){if(1!==u)throw l("a bad refinement code");h=m(1)?r:s}else if(15!==f){v=1<<f,f&&(v+=m(f));break}for(;c<=i;c++){const t=n+a[c];if(0!==o[t])m(1)&&0===(o[t]&r)&&(o[t]+=o[t]>=0?r:s);else if(--f<0)break}if(f>=0||h&&c>i)throw l("coefficients past the band");h&&(o[n+a[c]]=h)}if(v>0){for(;c<=i;c++){const t=n+a[c];0!==o[t]&&m(1)&&0===(o[t]&r)&&(o[t]+=o[t]>=0?r:s)}v--}}:(t,o,n)=>{o[n]=I(t,g(t.dc)),J(t,o,n)};for(const t of r)t.component.pred=0;const X=r[0].component,k=E?X.blocksW*X.blocksH:n.mcusX*n.mcusY;for(let t=0;t<k;t++)if(c&&t>0&&t%c===0&&U(t/c-1),E){const o=t/X.blocksW|0,n=t-o*X.blocksW;L(r[0],X.coeffs,64*(o*X.stride+n))}else{const o=t/n.mcusX|0,e=t-o*n.mcusX;for(const t of r){const n=t.component;for(let r=0;r<n.v;r++)for(let i=0;i<n.h;i++)L(t,n.coeffs,64*((o*n.v+r)*n.stride+e*n.h+i))}}if(A(),255===t[h]&&t[h+1]>=208&&t[h+1]<=215){if(!c||k%c||t[h+1]!==208+(k/c-1&7))throw l("a restart marker out of order");for(h+=2;h+1<t.length&&255===t[h]&&255===t[h+1];)h++}if(h<t.length&&!(255===t[h]&&h+1<t.length&&0!==t[h+1]&&255!==t[h+1]))throw l("bytes left over after a scan");return h}const M=(t,o)=>Object.assign(new Error(o),{code:t});function g(o){if(o>t.bytes)throw M("JXL_SIZE","The encoded picture exceeds 16 MiB.")}function A(t){try{return t()}catch(t){if(t instanceof RangeError&&!t.code)throw M("JXL_MEMORY","Not enough memory for this picture.");throw t}}function U(n,r,e){const i=function(t={}){if(null===t||"object"!=typeof t)throw M("JXL_INPUT","Options are an object.");const o=void 0===t.effort?1:t.effort;if(!Number.isInteger(o)||o<1||o>9)throw M("JXL_INPUT","Effort is a whole number from 1 to 9.");return o}(r);if(!(n instanceof Uint8Array&&n.length))throw M("JXL_INPUT","A JPEG is a non-empty Uint8Array.");if(n.length>o.bytes)throw M("JXL_SIZE","A JPEG is at most 16 MiB.");const s=function(t){const o=function*(){let n,r;for(;!(n=A(()=>t.next(o.hurry))).done;)yield r=n.value;return r<1&&(yield 1),o.bytes=function(t){return g(t.length),t}(n.value)}();return o.bytes=null,o.hurry=!1,o}(function*(n,r,e,i){const f=function(t){if(!(t.length>4)||255!==t[0]||216!==t[1])throw l("not a JPEG");const n=[],r=[[],[]],e=new Set,i={count:0,p:[]};let s=null,f=0,c=-1,M=!1,g=1,A=2;const U=o=>t[o]<<8|t[o+1],I=(o,n)=>{for(let r=0;r<n.length;r++)if(t[o+r]!==n.charCodeAt(r))return!1;return!0};for(;;){if(A>=t.length){if(s&&s.scans)break;throw l("truncated")}if(255!==t[A])throw l("marker expected");for(;255===t[A];)A++;const u=t[A++];if(217===u)break;if(216===u)throw l("a second start");if(u>=208&&u<=215)throw l("a restart marker outside a scan");if(1===u)continue;if(A+2>t.length)throw l("truncated");const w=U(A),d=A+2,y=A+w;if(w<2||y>t.length)throw l("bad segment");if(A=y,219===u)for(let o=d;o<y;){const r=t[o]>>4,e=15&t[o];if(r>1||e>3||o+1+(r?128:64)>y)throw l("bad quantisation table");o++;const i=new Int32Array(64);for(let n=0;n<64;n++)if(i[a[n]]=r?U(o):t[o],o+=r?2:1,!i[a[n]])throw l("a zero quantisation step");if(s?.progressive&&s.components.some(t=>t.tq===e&&t.quant&&t.coverage.some(t=>0!==t)&&t.quant.some((t,o)=>t!==i[o])))throw l("a quantisation table changed between progressive scans");n[e]=i}else if(196===u)for(let o=d;o<y;){const n=t[o]>>4,i=15&t[o];if(n>1||i>3||o+17>y)throw l("bad Huffman table");o++;const s=t.subarray(o,o+16);let f=0;for(const t of s)f+=t;if(f>256||o+16+f>y)throw l("bad Huffman table");const c=t.subarray(o+16,o+16+f);r[n][i]=h(s,c),0===n&&(c.some(t=>t>15)?e.add(i):e.delete(i)),o+=16+f}else if(192===u||193===u||194===u){if(s)throw l("two frames");if(y-d<6)throw l("bad frame header");if(8!==t[d])throw l("only 8-bit samples");const n=U(d+1),r=U(d+3),e=t[d+5];if(!r||!n)throw l("a height left to a DNL marker");if(1!==e&&3!==e)throw l("only grey or three components");if(y-d<6+3*e)throw l("bad frame header");if(r>o.edge||n>o.edge)throw l("a picture past "+o.edge+" pixels on a side","JXL_DIMENSIONS");if(r*n>o.pixels)throw l("a picture past "+o.pixels+" pixels","JXL_DIMENSIONS");const i=[];let f=0;for(let o=0,n=d+6;o<e;o++,n+=3){const o=t[n+1]>>4,r=15&t[n+1],e=t[n+2];if(o<1||o>4||r<1||r>4)throw l("bad sampling");if(e>3)throw l("bad quantisation table");if(i.some(o=>o.id===t[n]))throw l("two components with one id");f+=o*r,i.push({id:t[n],h:o,v:r,tq:e,pred:0,coverage:new Int8Array(64).fill(-1)})}if(f>10)throw l("bad sampling");const c=Math.max(...i.map(t=>t.h)),a=Math.max(...i.map(t=>t.v)),h=Math.ceil(r/(8*c)),w=Math.ceil(n/(8*a));for(const t of i)t.blocksW=Math.ceil(Math.ceil(r*t.h/c)/8),t.blocksH=Math.ceil(Math.ceil(n*t.v/a)/8),t.stride=h*t.h,t.rows=w*t.v,t.coeffs=new Int16Array(t.stride*t.rows*64);s={progressive:194===u,width:r,height:n,components:i,hmax:c,vmax:a,mcusX:h,mcusY:w,scans:0}}else{if(195===u||u>=197&&u<=199||u>=201&&u<=203||u>=205&&u<=207)throw l("lossless, hierarchical or arithmetic coding");if(221===u){if(w<4)throw l("bad segment");f=U(d)}else{if(220===u)throw l("a DNL marker");if(218===u){if(!s)throw l("a scan before the frame");const o=t[d],i=[];if(o<1||o>4||d+1+2*o+3>y)throw l("bad scan header");let c=d+1;for(let e=0;e<o;e++,c+=2){const o=s.components.find(o=>o.id===t[c]);if(!o)throw l("a scan of an unknown component");if(i.some(t=>t.component===o))throw l("a component twice in one scan");if(o.quant||(o.quant=n[o.tq]),!o.quant)throw l("a scan without its quantisation table");i.push({component:o,dc:r[0][t[c+1]>>4],ac:r[1][15&t[c+1]],dcSlot:t[c+1]>>4})}const a=t[c],h=t[c+1],u=t[c+2]>>4,w=15&t[c+2];if((!s.progressive||0===a&&0===u)&&i.some(t=>e.has(t.dcSlot)))throw l("bad Huffman table");A=m(t,y,s,i,a,h,u,w,f),s.scans++}else if(224===u)I(d,"JFIF")&&(M=!0);else if(225===u)1===g&&I(d,"Exif")&&(g=b(t,d+6,y));else if(226===u){if(w>=16&&I(d,"ICC_PROFILE\0")){const o=t[d+12],n=t[d+13];if(!o||!n||o>n||i.count&&i.count!==n||i.p[o])throw l("a colour profile cut short");i.count=n,i.p[o]=t.subarray(d+14,y)}}else 238===u&&w>=14&&I(d,"Adobe")&&(c=t[d+11])}}}if(!s||!s.scans)throw l("no picture");for(const t of s.components)for(let o=0;o<64;o++)if(0!==t.coverage[o])throw l(s.progressive?"a progressive JPEG whose scans do not finish every coefficient":"a component without its scan");let x="srgb";if(i.count){const t=[];for(let o=1;o<=i.count;o++){if(!i.p[o])throw l("a colour profile cut short");t.push(i.p[o])}const o=new Uint8Array(t.reduce((t,o)=>t+o.length,0));for(let n=0,r=0;n<t.length;r+=t[n].length,n++)o.set(t[n],r);if(x=function(t){const o=t.length,n=o=>t[o]<<8|t[o+1],r=n=>n+4<=o?(t[n]<<24|t[n+1]<<16|t[n+2]<<8|t[n+3])>>>0:0,e=n=>n+4<=o?String.fromCharCode(t[n],t[n+1],t[n+2],t[n+3]):"",i=t=>(0|r(t))/65536,s=r(128);if(o<132||132+12*s>o||"acsp"!==e(36)||"XYZ "!==e(20))return null;const f=t=>{for(let n=0;n<s;n++){const i=132+12*n,s=r(i+4);if(e(i)===t)return s+r(i+8)<=o?s:-1}return-1},c=t=>{const s=f(t);if(s<0)return!1;if("para"===e(s)){const t=n(s+8),o=[1,3,4,5,7][t];if(3!==t&&4!==t)return!1;for(let t=0;t<o;t++)if(Math.abs(i(s+12+4*t)-(t<5?y[t]:0))>(t?.002:.01))return!1;return!0}const c="curv"===e(s)?r(s+8):0;if(c<2||s+12+2*c>o)return!1;for(let t=0;t<c;t++)if(Math.abs(n(s+12+2*t)/65535-p(t/(c-1)))>.001)return!1;return d.every((t,o)=>{const r=o*(c-1)/16,e=Math.floor(r),i=Math.min(c-1,e+1),f=r-e;return Math.abs((n(s+12+2*e)*(1-f)+n(s+12+2*i)*f)/65535-t)<=.001})};if(["A2B0","A2B1","A2B2"].some(t=>f(t)>=0))return null;if("GRAY"===e(16))return c("kTRC")?"srgb":null;if("RGB "!==e(16)||!["rTRC","gTRC","bTRC"].every(c))return null;const a=["rXYZ","gXYZ","bXYZ"].flatMap(t=>{const o=f(t);return o>=0&&"XYZ "===e(o)?[i(o+8),i(o+12),i(o+16)]:[9,9,9]}),l=t=>t.every((t,o)=>Math.abs(a[o]-t)<=.004);return l(u)?"srgb":l(w)?"display-p3":null}(o),!x)throw l("a colour profile other than sRGB or Display P3 (decode the picture and encode its pixels)")}let v=!1;return 3!==s.components.length||M||(v=c>=0?0===c:82===s.components[0].id&&71===s.components[1].id&&66===s.components[2].id),{width:s.width,height:s.height,components:s.components,progressive:s.progressive,ycbcr:!v,orientation:g,colorSpace:x}}(n);!function(o,n,r=t){if(!Number.isInteger(o)||!Number.isInteger(n)||o<1||n<1)throw M("JXL_INPUT","A picture is at least one pixel wide and high, in whole pixels.");if(o>r.edge||n>r.edge)throw M("JXL_DIMENSIONS","A picture is at most "+r.edge+" pixels on a side.");if(o*n>r.pixels)throw M("JXL_DIMENSIONS","A picture is at most "+r.pixels.toLocaleString("en-US")+" pixels.")}(f.width,f.height,o);const c=f.orientation>=5;return(t=>{Object.assign(s,t)})({width:c?f.height:f.width,height:c?f.width:f.height,orientation:f.orientation}),yield*i(f,r)}(n,i,0,e));return s}const I=256;function x(t,o){t.o([[9,1],[13,1],[18,1],[30,1]],o)}const v={channel:null,weighted:null,fill:null},E=[1,2,3,4,0,5,17,6,16,7,8,9,10,11,12,13,14,15],S=[2,4,3,2,2,4],C=[0,7,3,2,1,15];function J(t,o){const n=new Uint8Array(t.length),r=[];for(let o=0;o<t.length;o++)t[o]>0&&r.push(o);if(!r.length)return n;if(1===r.length)return n[r[0]]=1,n;for(let e=1;;e*=2){const i=r.map(o=>({w:Math.max(t[o],e),m:o,l:null,r:null})).sort((t,o)=>t.w-o.w||t.m-o.m),s=[];let f=0,c=0;const a=()=>f<i.length&&(c>=s.length||i[f].w<=s[c].w)?i[f++]:s[c++];for(;i.length-f+(s.length-c)>1;){const t=a(),o=a();s.push({w:t.w+o.w,m:-1,l:t,r:o})}const l=[[a(),0]];let h=0;for(;l.length;){const[t,o]=l.pop();t.m>=0?(n[t.m]=o,o>h&&(h=o)):l.push([t.l,o+1],[t.r,o+1])}if(h<=o)return n}}function L(t,o,n,r,e,i){const s=[];for(;s.push(r&e),r>>=i;)r--;for(let r=s.length-1;r>=0;r--)t.push(n),o.push(s[r])}function X(t,o){let n=0;for(let r=0;r<o;r++)n=n<<1|1&t,t>>=1;return n}function k(t){const o=new Uint32Array(17),n=new Uint32Array(17),r=new Uint16Array(t.length);for(const n of t)o[n]++;o[0]=0;for(let t=1,r=0;t<=16;t++)r=r+o[t-1]<<1,n[t]=r;for(let o=0;o<t.length;o++)t[o]&&(r[o]=X(n[t[o]]++,t[o]));return r}function N(t){const o=[];for(let n=0;n<t.length;n++)t[n]>0&&o.push(n);const n=o.length,r=o[n-1]+1||1,e=n<=4?new Uint8Array(r):J(t,15).subarray(0,r);let i=0;if(n<=4){o.sort((o,n)=>t[n]-t[o]||o-n),i=4===n&&t[o[0]]>t[o[2]]+t[o[3]]?1:0;const r=n<2?[0]:2===n?[1,1]:3===n?[1,2,2]:i?[1,2,3,3]:[2,2,2,2];o.forEach((t,o)=>{e[t]=r[o]}),o.sort((t,o)=>e[t]-e[o]||t-o)}return{M:r,A:e,U:k(e),I:n&&n<=4?o:null,S:i}}function O(t,o){if(o.M<=1)return;if(o.I){const n=s(o.M-1)+1;t.write(2,1),t.write(2,o.I.length-1);for(const r of o.I)t.write(n,r);return void(4===o.I.length&&t.write(1,o.S))}const n=o.A,r=[],e=[];let i=n.length-1;for(;i>0&&!n[i];)i--;let f=8;for(let t=0;t<=i;){const o=n[t];let s=1;for(;t+s<=i&&n[t+s]===o;)s++;let c=s;if(o&&o!==f&&(r.push(o),e.push(0),c--,f=o),c<3)for(let t=0;t<c;t++)r.push(o),e.push(0);else L(r,e,o?16:17,c-3,o?3:7,o?2:3);t+=s}const c=new Uint32Array(18);for(const t of r)c[t]++;let a=0;for(const t of c)t&&a++;1===a&&(c[r[0]?0:1]=c[r[0]]);const l=J(c,5),h=k(l);let u=18;for(;u>0&&!l[E[u-1]];)u--;t.write(2,0);for(let o=0;o<u;o++){const n=l[E[o]];t.write(S[n],C[n])}for(let o=0;o<r.length;o++){const n=r[o];t.write(l[n],h[n]),16===n?t.write(2,e[o]):17===n&&t.write(3,e[o])}}function _(t,o=0,n=0){return{split:t,C:o,J:n,L:1<<t}}function T(t,o,n=15){t.write(f(n+1),o.split),o.split!==n&&(t.write(f(o.split+1),o.C),t.write(f(o.split-o.C+1),o.J))}function D(t,o,n){if(o<t.L)return n[0]=o,n[1]=0,void(n[2]=0);const r=s(o),e=o-(1<<r),i=r-t.C-t.J;n[0]=t.L+(r-t.split<<t.C+t.J|e>>r-t.C<<t.J|e&(1<<t.J)-1),n[1]=i,n[2]=o>>t.J&(1<<i)-1}function P(t,o,n,r=0){D(t,o,G),n[r+G[0]]++}const G=[0,0,0];function R(t,o,n,r,e=0){D(n,r,G);const i=e+G[0];t.write(o.A[i],o.U[i]),G[1]&&t.write(G[1],G[2])}function Z(t,o){let n=0;for(const t of o)n=Math.max(n,t);const r=n?f(n+1):0;if(r<=3){if(t.write(1,1),t.write(2,r),r)for(const n of o)t.write(r,n);return}t.write(1,0),t.write(1,0);const e=_(8),i=_(4),s=o.length>=64,c=new Uint32Array(s?257:n+1),a=[];for(let t=0;t<o.length;){let n=1;for(;s&&t+n<o.length&&o[t+n]===o[t];)n++;if(n>=8)a.push([o[t],n-1]),c[o[t]]++,P(i,n-1-7,c,224),t+=n;else{for(let r=0;r<n;r++)a.push([o[t],0]),c[o[t]]++;t+=n}}const l=N(c);if(!s){j(t,{X:new Uint8Array(1),k:[{config:e,code:l}]});for(const[o]of a)R(t,l,e,o);return}const h=new Uint32Array(1);h[0]=1,j(t,{N:{O:224,minLength:7,_:i},X:new Uint8Array([1,0]),k:[{config:_(0),code:N(h)},{config:e,code:l}]});for(const[o,n]of a)R(t,l,e,o),n&&R(t,l,i,n-7,224)}function j(t,{N:o=null,X:n,k:r}){t.write(1,o?1:0),o&&(t.o([[0,224],[0,512],[0,4096],[15,8]],o.O),t.o([[0,3],[0,4],[2,5],[8,9]],o.minLength),T(t,o._,8)),n.length>1&&Z(t,n),t.write(1,1);for(const o of r)T(t,o.config,15);for(const o of r){const n=o.code.M-1;if(n){const o=s(n);t.write(1,1),t.write(4,o),t.write(o,n-(1<<o))}else t.write(1,0)}for(const o of r)O(t,o.code)}const q=_(4),B=Object.freeze({O:224,minLength:7,_:q}),z=_(0);function Y(t,o){const n=[[3,0],[6,8],[10,72],[13,1096]];if("rct"===o.type)t.write(2,0),t.o(n,o.T),t.o([[0,6],[2,0],[4,2],[6,10]],o.D??6);else if("palette"===o.type)t.write(2,1),t.o(n,o.T),t.o([[0,1],[0,3],[0,4],[13,1]],o.P),t.o([[8,0],[10,256],[12,1280],[16,5376]],o.G),t.o([[0,0],[8,1],[10,257],[16,1281]],o.R??0),t.write(4,o.Z??0);else{if("squeeze"!==o.type)throw new Error("unknown transform "+o.type);{t.write(2,2);const r=o.j??[];t.o([[0,0],[4,1],[6,9],[8,41]],r.length);for(const o of r)t.write(1,o.q?1:0),t.write(1,o.B?1:0),t.o(n,o.T),t.o([[0,1],[0,2],[0,3],[4,4]],o.P)}}}function H(t,o,n,r,e,s,f=!1){if(v.channel?.(t,o,n,r,e,s,f))return;const c=s.Z,a=s.offset,l=s.Y,h=s.config||z,u=q;let w=0;const d=(n,r=h,e=0)=>{t?R(t,o,r,n,e):f&&!e?o[n]++:P(r,n,o,f?o.length-33:e)},y=()=>{if(w){if(w>=8)d(0),d(w-7-1,u,224);else for(let t=0;t<w;t++)d(0);w=0}},p=(t,o)=>{const r=n[t];let e;1===l?e=r-o-a:(e=Math.round((r-o-a)/l),n[t]=o+a+e*l),0!==e?(y(),d(i(e))):w++};for(let t=0,o=0;t<e;t++)for(let e=0;e<r;e++,o++){let i;if(0===c)i=0;else{const s=e?n[o-1]:t?n[o-r]:0,f=t?n[o-r]:s;if(1===c)i=s;else if(2===c)i=f;else if(3===c)i=(s+f)/2|0;else{const a=s+f-(e&&t?n[o-r-1]:s);if(5===c){const t=s<f?s:f,o=s<f?f:s;i=a<t?t:a>o?o:a}else{if(4!==c)throw new Error("predictor "+c+" is not coded here");i=Math.abs(a-s)<Math.abs(a-f)?s:f}}}p(o,i)}y()}const F=[_(0),_(1),_(2),_(3),_(4),_(4,1,1),_(5,1,1),_(2,0,1),_(3,0,1)],K=_(4,1,1);class Q{constructor(t){this.H=t,this.small=new Uint32Array(64*t),this.F=Array.from({length:t},()=>null),this.K=new Float64Array(t)}add(t,o){if(this.K[t]++,o<64)return void this.small[64*t+o]++;const n=this.F[t]||(this.F[t]=new Map);n.set(o,(n.get(o)||0)+1)}V(t,o,n=64){const r=new Uint32Array(n);for(const n of t){const t=64*n;for(let n=0;n<64;n++)this.small[t+n]&&(r[W(o,n)]+=this.small[t+n]);const e=this.F[n];if(e)for(const[t,n]of e)r[W(o,t)]+=n}return r}W(t,o){let n=ot(this.V(t,o));for(const r of t){const t=64*r;for(let r=o.L;r<64;r++)this.small[t+r]&&(n+=this.small[t+r]*(s(r)-o.C-o.J));const e=this.F[r];if(e)for(const[t,r]of e)n+=r*(s(t)-o.C-o.J)}return n}}const V=[0,0,0];function W(t,o){return D(t,o,V),V[0]}const $=[1];for(let t=1;t<32;t++)$.push($[t-1]/2);function tt(t){let o=0;for(t>=2&&t<4294967296&&(o=31-Math.clz32(t),t*=$[o]);t>=1.4142135623730951;)t/=2,o++;for(;t<.7071067811865476;)t*=2,o--;const n=(t-1)/(t+1),r=n*n;let e=n,i=n;for(let t=3;t<30;t+=2)i+=(e*=r)/t;return o+2.885390081777927*i}function ot(t){let o=0,n=0;for(const n of t)o+=n;for(const r of t)r&&(n+=r*tt(o/r));return n}function nt(t,{maxClusters:o=48,newClusterCost:n=320}={}){const r=[];for(let o=0;o<t.H;o++)t.K[o]>0&&r.push(o);r.sort((o,n)=>t.K[n]-t.K[o]);const e=[];for(const i of r){const r=t.V([i],K),s=ot(r);let f=-1,c=1/0;for(let t=0;t<e.length;t++){const o=e[t],n=new Uint32Array(64);for(let t=0;t<64;t++)n[t]=o.$[t]+r[t];const i=ot(n)-o.tt-s;i<c&&(c=i,f=t)}if(f<0||e.length<o&&c>n)e.push({H:[i],$:r,tt:s});else{const t=e[f];t.H.push(i);for(let o=0;o<64;o++)t.$[o]+=r[o];t.tt=ot(t.$)}}e.length||e.push({H:[],$:new Uint32Array(64),tt:0});const i=new Uint8Array(t.H);let s=2*t.H;const f=e.map((o,n)=>{for(const t of o.H)i[t]=n;let r=F[0],e=1/0;for(const n of F){const i=t.W(o.H,n);i<e&&(e=i,r=n)}const f=N(t.V(o.H,r,128));return s+=e+3*f.M+40,{config:r,code:f}});return{X:i,k:f,write:(t,o,n)=>{const r=f[i[o]];R(t,r.code,r.config,n)},tt:s}}const rt=[0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,15,16,16,17,17,18,18,19,19,20,20,21,21,22,22,23,23,23,23,24,24,24,24,25,25,25,25,26,26,26,26,27,27,27,27,28,28,28,28,29,29,29,29,30,30,30,30],et=[0,0,31,62,62,93,93,93,93,123,123,123,123,152,152,152,152,152,152,152,152,180,180,180,180,180,180,180,180,180,180,180,180,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206,206],it=a.map(t=>(7&t)<<3|t>>3),st=(t,o,n)=>2*(et[t]+rt[o])+n;function ft(t,o,n){const r=[];if(o>0){const n=new Uint32Array(2048);let e=0;for(const o of t)n[Math.min(2047,Math.max(0,o+1024))]++,e++;let i=0,s=e/(o+1);for(let t=0;t<2048&&r.length<o;t++)i+=n[t],i>s&&(r.push(t-1025),s=e*(r.length+1)/(o+1))}const e=r.length+1,i=new Uint8Array(39*e);for(let t=0;t<e;t++)for(let o=0;o<13;o++)i[(0+o)*e+t]=t,i[(13+o)*e+t]=n?e:e+(t>>1),i[(26+o)*e+t]=n?e:e+(e-1>>1)+1+(t>>1);let s=0;for(const t of i)s=Math.max(s,t+1);return{thresholds:r,ot:e,map:i,nt:s,rt:t=>{let o=0;for(const n of r)t>n&&o++;return o},et:(t,o)=>i[13*(t<2?1^t:2)*e+o],it:(t,o)=>(Math.min(t,64)<8?Math.min(t,64):4+(Math.min(t,64)>>1))*s+o,st:t=>37*s+458*t,H:495*s}}function ct(t,o,n){const r=o.map(()=>function(t,o=0,n=1){return{Z:t,offset:o,Y:n,context:-1}}(n)),e=r.map(()=>new Uint32Array(257));o.forEach((t,o)=>H(null,e[o],t.data,t.w,t.h,r[o])),function(t,{ft:o=!0,ct:n=[]}={}){t.write(1,o?1:0),t.write(1,1),t.o([[0,0],[0,1],[4,2],[8,18]],n.length);for(const o of n)Y(t,o)}(t,{ft:!1,ct:[]});const s=function(t,o){const n=[o],r=[],e=[];for(const t of n){if(t.left){r.push(t.lt+1,i(t.ht)),n.push(t.left,t.right);continue}t.context=e.length,e.push(t);const o=1===t.Y?0:31-Math.clz32(t.Y&-t.Y);r.push(0,t.Z,i(t.offset),o,(t.Y>>o)-1)}const s=new Uint32Array(64);for(const t of r)P(z,t,s);const f=N(s);j(t,{X:new Uint8Array(6),k:[{config:z,code:f}]});for(const o of r)R(t,f,z,o);return e}(t,function(t){return function(t,o){const n=(r,e)=>{if(r===e)return o?t[r].ut:t[r];const i=r+e>>1;return function(t,o,n,r){return{lt:t,ht:o,left:n,right:r}}(o,o?t[i].wt:i,n(i+1,e),n(r,i))};return n(0,t.length-1)}(t,0)}(r)),f=function(t,o,n,r=t=>t.context,e=()=>z){const i=new Uint8Array(o.length+1);for(const t of o)i[t.context]=r(t)+1;const s=new Uint32Array(2);s[1]=1;const f=[{config:z,code:N(s)}],c=Math.max(...i);for(let t=0;t<c;t++)f.push({config:e(t),code:N(n[t])});return j(t,{N:B,X:i,k:f}),f}(t,s,e,t=>r.indexOf(t));o.forEach((o,n)=>H(t,f[n+1].code,o.data,o.w,o.h,r[n]))}function*at(t,o={}){const{width:n,height:e,components:s,alpha:a}=t,h=1===s.length,u=t.quantScale||1;let w=t.quantFieldBase||1;for(;w/(2040*u)<1/16384;)w*=2;const d=t.ycbcr||h,y=h?[0,0,0]:d?[1,0,2]:[0,1,2],p=y.map(t=>s[t]),b=o.orders?y.map(t=>o.orders[t].map(t=>it[t])):[it,it,it],m=t=>1===t?0:2===t?1:-1,M=p.map(t=>m(t.h)),A=p.map(t=>m(t.v));if(M.includes(-1)||A.includes(-1))throw l("sampling factors other than one or two");const U=Math.max(...M),v=Math.max(...A),E=t=>U-M[t],S=t=>v-A[t];if(!d&&(U||v))throw l("an RGB JPEG with subsampling");const C=Math.ceil(n/(8<<U))<<U,J=Math.ceil(e/(8<<v))<<v,L=Math.ceil(n/I),X=Math.ceil(e/I),k=L*X,O=Math.ceil(C/256),T=O*Math.ceil(J/256),D=1===k,G=(t,o,n)=>{const r=p[t];return h&&1!==t?-1:64*(n*r.stride+o)},q=t=>{let o=1024;for(;t%o;)o>>=1;return o},B=p.map(t=>d?1:t.quant[0]/q(t.quant[0])),z=p.map(t=>d?0:1024/q(t.quant[0])),Y=new Int32Array(C*J);for(let t=0;t<J;t++)for(let o=0;o<C;o++)Y[t*C+o]=p[1].coeffs[G(1,o,t)]*B[1]+z[1];const H=p[1].quant,F=(H[8]+H[16]+H[24]+H[32]+H[40])/u,K=C*J,V=K<256?0:Math.max(1,Math.min(7,f(K)-f(F)-7));let W=ft(Y,V,h);const $=new r(256);if(function(t,o,n,r,e,{xyb:i=!1,orientation:s=1,colorSpace:f}={}){t.write(16,2815),t.write(1,0),x(t,n),t.write(3,0),x(t,o),t.write(1,0);const c=1!==s;t.write(1,c?1:0),c&&t.write(6,s-1),t.write(4,8),e?t.write(3,5):t.write(2,0),t.write(1,i?1:0),3===r&&"display-p3"===f?t.write(21,903568):3===r?t.write(1,1):t.write(15,14100),c&&t.write(1,1),t.write(2,0),t.write(1,1),t.i()}($,n,e,h?1:3,!!a,{orientation:t.orientation,colorSpace:t.colorSpace}),$.write(1,0),$.write(2,0),$.write(1,0),$.write(2,2),$.write(8,111),$.write(1,d?1:0),d)for(let t=0;t<3;t++)$.write(2,0===M[t]&&0===A[t]?0:1===M[t]&&1===A[t]?1:1===M[t]?2:3);$.write(2,0),a&&$.write(2,0),function(t,o){t.write(o?7:5,0),t.write(11,1)}($,a);const tt=[0,1,2].map(()=>new Int32Array(1024)),ot=(t,o)=>{const n=t%L*32,r=32*(t/L|0),e=Math.min(32,C-n),s=Math.min(32,J-r);for(let t=0;t<s;t++)for(let s=0;s<e;s++)for(const e of[1,0,2]){const f=E(e),c=S(e),a=s>>f,l=t>>c;if(a<<f!==s||l<<c!==t)continue;const h=G(e,(n>>f)+a,(r>>c)+l),u=p[e].coeffs;let w=0;if(h>=0)for(let t=1;t<64;t++)u[h+t]&&w++;const d=tt[e],y=0===a?0===l?32:d[32*(l-1)]:0===l?d[32*l+a-1]:d[32*(l-1)+a]+d[32*l+a-1]+1>>1;d[32*l+a]=w;const m=W.et(e,W.rt(Y[(r+t)*C+n+s]));o(W.it(y,m),w);const M=W.st(m);let g=w>4?0:1,A=w;for(let t=1;t<64&&A;t++){const n=u[h+b[e][t]];o(M+st(A,t,g),i(n)),g=n?1:0,A-=g}}},rt=(V>0?3:2)*k+T;let et=0;const at=function*(t){W=t;const n=new Q(t.H);for(let t=0;t<k;t++)ot(t,(t,o)=>n.add(t,o)),yield++et/rt;return(o.coding||nt)(n,o.clusters)};let lt=yield*at(W);if(V>0){const t=W,o=ft(Y,0,h),n=yield*at(o);n.tt<=lt.tt?lt=n:W=t}const ht=Array.from({length:D?1:2+T+k},()=>null),ut=t=>ht[D?0:t]||(ht[D?0:t]=new r(4096)),wt=new Uint32Array(ht.length);let dt=0;const yt=t=>{t=D?0:t;const o=Math.ceil(ht[t].u/8);dt+=o-wt[t],wt[t]=o,g(dt)},pt=ut(0);pt.write(1,0);const bt=(t,o)=>{const r=t*I,i=o*I,s=Math.min(I,n-r),f=Math.min(I,e-i),c=new Int32Array(s*f);for(let t=0;t<f;t++)for(let o=0;o<s;o++)c[t*s+o]=a[4*((i+t)*n+r+o)+3];return{w:s,h:f,data:c}};for(let t=0;t<3;t++)pt.write(16,c(p[t].quant[0]/B[t]/(2040*u)*128));pt.write(2,3),pt.write(16,57343),pt.write(2,1),pt.write(5,0),pt.write(1,0),pt.write(4,0),pt.write(4,W.thresholds.length);for(const t of W.thresholds)pt.o([[4,0],[8,16],[16,272],[32,65808]],i(t));pt.write(4,0),pt.write(4,0),Z(pt,W.map),pt.write(1,0),pt.write(2,0),pt.write(16,0),pt.write(16,0),pt.write(8,128),pt.write(8,128),pt.write(1,0),a&&ct(pt,[D?bt(0,0):{w:0,h:0,data:new Int32Array(0)}],5),yt(0);for(let o=0;o<T;o++){const n=ut(1+o),r=o%O*256,e=256*(o/O|0),i=Math.min(256,C-r),s=Math.min(256,J-e);n.write(2,0),ct(n,[1,0,2].map(t=>{const o=i>>E(t),n=s>>S(t),f=new Int32Array(o*n),c=B[t],a=z[t];for(let i=0;i<n;i++)for(let n=0;n<o;n++){const s=G(t,(r>>E(t))+n,(e>>S(t))+i);f[i*o+n]=s<0?0:p[t].coeffs[s]*c+a}return{w:o,h:n,data:f}}),5);const c=i*s,a=f(c);a&&n.write(a,c-1);const l=i+7>>3,h=s+7>>3,u=new Int32Array(2*c).fill(w-1,c);if(t.quantFields)for(let o=0;o<s;o++)for(let n=0;n<i;n++)u[c+o*i+n]=t.quantFields[(e+o)*C+r+n]-1;ct(n,[{w:l,h:h,data:new Int32Array(l*h)},{w:l,h:h,data:new Int32Array(l*h)},{w:c,h:2,data:u},{w:i,h:s,data:new Int32Array(c)}],w>1?5:0),yt(1+o),yield++et/rt}const mt=ut(1+T);mt.write(1,0),mt.write(3,7),mt.write(16,c(w/(2040*u))),ct(mt,[0,1,2].map(t=>{const o=new Int32Array(64),n=p[t].quant;for(let t=0;t<8;t++)for(let r=0;r<8;r++)o[8*r+t]=n[8*t+r];return{w:8,h:8,data:o}}),5);for(let t=1;t<17;t++)mt.write(3,0);if(k>1&&mt.write(f(k),0),o.orders){mt.o([[0,95],[0,19],[0,0],[13,0]],1);const t=[];for(const n of y){const r=Array.from({length:64},(t,o)=>o),e=o.orders[n].map(t=>{const o=r.indexOf(t);return r.splice(o,1),o});let i=64;for(;i>1&&!e[i-1];)i--;t.push(i-1,...e.slice(1,i))}const n=_(0),r=new Uint32Array(64);for(const o of t)P(n,o,r);const e=N(r);j(mt,{X:new Uint8Array(8),k:[{config:n,code:e}]});for(const o of t)R(mt,e,n,o)}else mt.write(2,2);lt.writeHistograms?lt.writeHistograms(mt):j(mt,{X:lt.X,k:lt.k}),yt(1+T);for(let t=0;t<k;t++){const o=ut(2+T+t);ot(t,(t,n)=>lt.write(o,t,n)),lt.flush&<.flush(o),a&&!D&&ct(o,[bt(t%L,Math.floor(t/L))],5),yt(2+T+t),yield++et/rt}return function(t,o){const n=o.map(t=>t.length);!function(t,o){t.write(1,0),t.i();for(const n of o)t.o([[10,0],[14,1024],[22,17408],[30,4211712]],n);t.i()}(t,n);const r=t.finish(),e=r.length+n.reduce((t,o)=>t+o,0);g(e);const i=new Uint8Array(e);i.set(r);let s=r.length;for(const t of o)i.set(t,s),s+=t.length;return i}($,function(t){return t.map(t=>t?t.finish():new Uint8Array(0))}(ht))}function*lt(t,o,n){if(o<3&&!n)return yield*at(t);let r=n;try{const n=at(t);let e,i;for(;!(e=n.next()).done;)if(i=yield e.value/2,i&&r&&e.value<1)return n.return(),r;if((!r||e.value.length<r.length)&&(r=e.value),i||o<3)return r;const s=o<4?1:3,f=at(t,{clusters:{maxClusters:32,newClusterCost:160}});for(;!(e=f.next()).done;)if(i=yield.5+e.value/(2*s),i&&e.value<1)return f.return(),r;if(e.value.length<r.length&&(r=e.value),i||o<4)return r;const c=function*(t){const o=a.map(t=>(7&t)<<3|t>>3),n=t.map(()=>new Uint32Array(64)),r=t.reduce((t,o)=>t+o.coeffs.length,0);let e=0;for(let i=0;i<t.length;i++){const{coeffs:s}=t[i],f=n[i];for(let t=0;t<s.length;t+=65536){const n=Math.min(t+65536,s.length);for(let r=t;r<n;r+=64)for(let t=1;t<64;t++)s[r+o[t]]&&f[t]++;if(e+=n-t,yield e/r)return null}}return n.map(t=>[0,...Array.from({length:63},(t,o)=>o+1).sort((o,n)=>Math.floor(t[n]/8)-Math.floor(t[o]/8)||o-n)])}(t.components);for(;!(e=c.next()).done;)if(yield.5+(1+e.value)/6)return c.return(),r;const l=at(t,{orders:e.value});for(;!(e=l.next()).done;)if(i=yield.5+(2+e.value)/6,i&&e.value<1)return l.return(),r;return e.value.length<r.length?e.value:r}catch(t){if(!r||(!(t instanceof RangeError)||t.code)&&"JXL_SIZE"!==t.code)throw t;return r}}const ht=[5,4,4,4,4,4,3,3,3,3,3,6,7],ut=[17,11,15,3,9,7,4,2,5,6,0,33,1],wt=196608;function dt(t,o){if(!o)return void t.write(1,0);const n=s(o);t.write(1,1),t.write(3,n),t.write(n,o-(1<<n))}function yt(t){let o=0,n=0;for(let r=0;r<t.length;r++)o+=t[r],t[r]&&(n=r+1);const r=new Uint16Array(n||1);if(!o)return r[0]=4096,r;let e=0;for(let i=0;i<n;i++)t[i]&&(e+=r[i]=Math.max(1,Math.round(4096*t[i]/o)));for(;4096!==e;){const i=e<4096?1:-1;let s=-1,f=-1/0;for(let e=0;e<n;e++)if(t[e]&&(i>0||r[e]>1)){const n=i*(4096*t[e]-r[e]*o);n>f&&(s=e,f=n)}r[s]+=i,e+=i}return r}function pt(t,o){const n=[];let r=0;for(let t=0;t<o.length;t++)o[t]&&n.push(t),o[t]>o[r]&&(r=t);if(n.length<=2){t.write(1,1),t.write(1,n.length-1);for(const o of n)dt(t,o);return void(2===n.length&&t.write(12,o[n[0]]))}t.write(1,0),t.write(1,0),t.write(3,7),t.write(3,5),dt(t,o.length-3);const e=new Uint8Array(o.length);let i=0;for(let t=0;t<o.length;t++)t!==r&&o[t]&&(e[t]=s(o[t])+1,i=Math.max(i,e[t]+(t<r?1:0)));e[r]=i;for(const o of e)t.write(ht[o],ut[o]);for(let n=0;n<o.length;n++)if(n!==r&&e[n]>1){const r=e[n]-1;t.write(r,o[n]-(1<<r))}}function bt(t,o){const n=1<<o,r=4096>>o,e=new Uint16Array(t.length+1),i=new Uint16Array(4096);let s=-1;for(let o=0;o<t.length;o++)e[o+1]=e[o]+t[o],4096===t[o]&&(s=o);if(s>=0){for(let t=0;t<4096;t++)i[t]=t;return{starts:e,reverse:i}}const f=new Int32Array(n),c=new Uint16Array(n),a=new Int32Array(n),l=[],h=[];f.set(t);for(let t=0;t<n;t++)f[t]<r?l.push(t):f[t]>r&&h.push(t);for(;h.length;){const t=h.pop(),o=l.pop(),n=r-f[o];f[t]-=n,c[o]=t,a[o]=f[t]-f[o],f[t]<r?l.push(t):f[t]>r&&h.push(t)}for(let t=0;t<n;t++)for(let o=0;o<r;o++){const n=o<f[t],s=n?t:c[t],l=n?o:o+a[t];i[e[s]+l]=t*r+o}return{starts:e,reverse:i}}function mt(t,o){const n=nt(t,o),e=n.k.map(()=>[]);for(let o=0;o<t.H;o++)t.K[o]&&e[n.X[o]].push(o);const i=n.k.map(({config:o},n)=>({config:o,counts:yt(t.V(e[n],o,256))})),s=Math.max(5,f(Math.max(...i.map(t=>t.counts.length))));for(const t of i)Object.assign(t,bt(t.counts,s));const c=new r;c.write(1,0),n.X.length>1&&Z(c,n.X),c.write(1,0),c.write(2,s-5);for(const t of i)T(c,t.config,s);for(const t of i)pt(c,t.counts);const a=new Uint32Array(wt),l=new Uint8Array(wt),h=new Uint16Array(wt),u=[0,0,0];let w=0;return{tt:n.tt,write:(t,o,r)=>{a[w]=r,l[w++]=n.X[o]},flush:t=>{let o=1245184;for(let t=w-1;t>=0;t--){const n=i[l[t]];D(n.config,a[t],u);const r=u[0],e=n.counts[r];a[t]=u[2],l[t]=u[1],o>>>20>=e&&(h[t]=65535&o,l[t]|=64,o>>>=16);const s=Math.floor(o/e);o=4096*s+n.reverse[n.starts[r]+o-s*e]}t.write(32,o);for(let o=0;o<w;o++){64&l[o]&&t.write(16,h[o]);const n=63&l[o];n&&t.write(n,a[o])}w=0},writeHistograms:t=>t.append(c)}}function*Mt(t,o,n){if(o<2)return yield*lt(t,o,n);let r=yield*function*(t){let o,n;for(;!(o=t.next(n)).done;)n=yield e(o.value,t=>(0+t)/2);return o.value}(lt(t,o,n));if(yield.5)return r;try{const o=at(t,{coding:mt});let n;for(;!(n=o.next()).done;)if((yield.5+n.value/2)&&n.value<1)return o.return(),r;n.value.length<r.length&&(r=n.value)}catch(t){if((!(t instanceof RangeError)||t.code)&&"JXL_SIZE"!==t.code)throw t}return r}function gt(t,o){return function(t){return function(t){let o;for(;!(o=t.next()).done;);o.value}(t),{bytes:t.bytes,width:t.width,height:t.height,orientation:t.orientation}}(At(t,o))}function At(t,o){return U(t,o,Mt)}export{o as LIMITS,gt as transcode,At as transcodeSteps};
|