@genome-spy/app 0.85.0 → 0.86.0
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/README.md +28 -0
- package/dist/{agentApi-Cz0hCnVp.js → agentApi-DgopQbMV.js} +5019 -6824
- package/dist/agentApi.es.js +2757 -2852
- package/dist/agentShared.es.js +15 -14
- package/dist/canvas2d-8uxuN_vx.js +619 -0
- package/dist/canvas2d-BtQC7Xr8.js +619 -0
- package/dist/{arrayUtils-LJpQOu-U.js → clipOptions-BQfNhxgP.js} +625 -561
- package/dist/{paramUtils-BYI4rwyL.js → clipOptions-taFzEljc.js} +192 -128
- package/dist/{debug-BvCZWumf.js → debug-Bzc3SoRg.js} +8 -8
- package/dist/{debug-CgDtmspT.js → debug-D_VtWQ6l.js} +8 -8
- package/dist/index.es.js +2992 -2915
- package/dist/index.js +2006 -2004
- package/dist/indexer-qiFctgR3.js +72 -0
- package/dist/indexer-qy_dq5l5.js +72 -0
- package/dist/layoutResult-D50MSHXR.js +97 -0
- package/dist/{nativeText-m5AUINMq.js → nativeText-DFV5XIx8.js} +247 -193
- package/dist/{nativeText-DMO8gLt7.js → nativeText-vT3AWE14.js} +244 -190
- package/dist/performanceProfiler-CPLEjApa.js +20 -0
- package/dist/rasterExport-B8pVoOsj.js +44 -0
- package/dist/rasterExport-C4r4xjQT.js +44 -0
- package/dist/rasterImage-B4rPLaW9.js +18 -0
- package/dist/rasterization-CFogVB3B.js +50 -0
- package/dist/rectangle-DKnrAmKs.js +142 -0
- package/dist/renderCanvas2D-BQrRWp2Z.js +271 -0
- package/dist/renderCanvas2D-CHVNfIUz.js +271 -0
- package/dist/schema.json +71 -131
- package/dist/{svg-CCu8kYy2.js → svg-C-Sw6E6G.js} +286 -277
- package/dist/{svg-yFj875aX.js → svg-CKHwwKRt.js} +278 -269
- package/dist/svgRasterizer-BgD72AmG.js +40 -0
- package/dist/svgRasterizer-BgSNqI3L.js +40 -0
- package/dist/vega-scale-CK0_al6O.js +2700 -0
- package/dist/vega-scale-D46-iCaL.js +2700 -0
- package/dist/viewError-BiR9VCgL.js +29 -0
- package/dist/{viewIdentityRegistry-D3oPbN4O.js → viewIdentityRegistry-B-VGlez1.js} +1 -1
- package/dist/{viewIdentityRegistry-BUdkK9zT.js → viewIdentityRegistry-CDtVktJD.js} +1 -1
- package/dist/viewSelectors-CKfxF_LM.js +1817 -0
- package/dist/viewSelectors-D_imtq5Z.js +1817 -0
- package/dist/viewUtils-nCJ7AoaI.js +5782 -0
- package/dist/webgl-BaA3jSa2.js +4128 -0
- package/dist/webgl-FP-4EsBL.js +4128 -0
- package/package.json +7 -6
- package/dist/bmFontMetrics-CuNB-kNN.js +0 -31
- package/dist/canvas2d-DoAXEiF9.js +0 -309
- package/dist/canvas2d-f5jl4A5D.js +0 -310
- package/dist/clipOptions-gqdb3fvW.js +0 -43
- package/dist/color-W5zffv-z.js +0 -335
- package/dist/framebufferReadback-CCLOjStu.js +0 -148
- package/dist/framebufferReadback-THWwFqs8.js +0 -1994
- package/dist/twgl-full.module-DB2UdP1k.js +0 -1849
- package/dist/viewRenderingContext-HtpqwS_x.js +0 -120
- package/dist/viewSelectors-DGCspRN3.js +0 -4198
- package/dist/viewSelectors-U5oLCLHV.js +0 -4195
- package/dist/viewUtils-Dg4RA40Q.js +0 -7503
- package/dist/warning-DRGdb6BF.js +0 -59
- package/dist/webgl-Ci6ZhCCf.js +0 -54
- package/dist/webgl-Dpz8a3TI.js +0 -53
|
@@ -0,0 +1,4128 @@
|
|
|
1
|
+
import { $ as e, At as t, E as n, H as r, J as i, Jt as a, K as o, Kt as s, Nt as c, O as l, Ot as u, W as d, Xt as f, Y as p, Z as m, en as h, et as g, h as _, jt as v, kt as ee, lt as y, n as b, nt as te, o as ne, rt as re, s as ie, tt as ae, u as x, w as oe, z as se } from "./clipOptions-taFzEljc.js";
|
|
2
|
+
import { A as ce, T as le, at as ue, b as S, g as de, v as C, x as fe, y as pe } from "./vega-scale-D46-iCaL.js";
|
|
3
|
+
import { i as me, n as he, p as ge, r as _e, t as ve } from "./indexer-qiFctgR3.js";
|
|
4
|
+
import { n as ye, t as be } from "./viewError-BiR9VCgL.js";
|
|
5
|
+
import { t as xe } from "./rectangle-DKnrAmKs.js";
|
|
6
|
+
import { n as Se, r as Ce } from "./performanceProfiler-CPLEjApa.js";
|
|
7
|
+
import { n as we, t as Te } from "./layoutResult-D50MSHXR.js";
|
|
8
|
+
import { t as Ee } from "./canvasSizeHelper-7h_8rOcx.js";
|
|
9
|
+
import { n as De, t as Oe } from "./rasterImage-B4rPLaW9.js";
|
|
10
|
+
//#region ../core/src/fonts/Lato-Regular.png
|
|
11
|
+
var ke = "data:image/png;base64,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", Ae = 5120, je = 5121, Me = 5122, Ne = 5123, Pe = 5124, Fe = 5125, Ie = 5126, Le = 32819, Re = 32820, ze = 33635, Be = 5131, Ve = 33640, He = 35899, Ue = 35902, We = 36269, Ge = 34042, Ke = {};
|
|
12
|
+
{
|
|
13
|
+
let e = Ke;
|
|
14
|
+
e[Ae] = Int8Array, e[je] = Uint8Array, e[Me] = Int16Array, e[Ne] = Uint16Array, e[Pe] = Int32Array, e[Fe] = Uint32Array, e[Ie] = Float32Array, e[Le] = Uint16Array, e[Re] = Uint16Array, e[ze] = Uint16Array, e[Be] = Uint16Array, e[Ve] = Uint32Array, e[He] = Uint32Array, e[Ue] = Uint32Array, e[We] = Uint32Array, e[Ge] = Uint32Array;
|
|
15
|
+
}
|
|
16
|
+
function qe(e) {
|
|
17
|
+
if (e instanceof Int8Array) return Ae;
|
|
18
|
+
if (e instanceof Uint8Array || e instanceof Uint8ClampedArray) return je;
|
|
19
|
+
if (e instanceof Int16Array) return Me;
|
|
20
|
+
if (e instanceof Uint16Array) return Ne;
|
|
21
|
+
if (e instanceof Int32Array) return Pe;
|
|
22
|
+
if (e instanceof Uint32Array) return Fe;
|
|
23
|
+
if (e instanceof Float32Array) return Ie;
|
|
24
|
+
throw Error("unsupported typed array type");
|
|
25
|
+
}
|
|
26
|
+
function Je(e) {
|
|
27
|
+
if (e === Int8Array) return Ae;
|
|
28
|
+
if (e === Uint8Array || e === Uint8ClampedArray) return je;
|
|
29
|
+
if (e === Int16Array) return Me;
|
|
30
|
+
if (e === Uint16Array) return Ne;
|
|
31
|
+
if (e === Int32Array) return Pe;
|
|
32
|
+
if (e === Uint32Array) return Fe;
|
|
33
|
+
if (e === Float32Array) return Ie;
|
|
34
|
+
throw Error("unsupported typed array type");
|
|
35
|
+
}
|
|
36
|
+
function Ye(e) {
|
|
37
|
+
let t = Ke[e];
|
|
38
|
+
if (!t) throw Error("unknown gl type");
|
|
39
|
+
return t;
|
|
40
|
+
}
|
|
41
|
+
var Xe = typeof SharedArrayBuffer < "u" ? function(e) {
|
|
42
|
+
return e && e.buffer && (e.buffer instanceof ArrayBuffer || e.buffer instanceof SharedArrayBuffer);
|
|
43
|
+
} : function(e) {
|
|
44
|
+
return e && e.buffer && e.buffer instanceof ArrayBuffer;
|
|
45
|
+
};
|
|
46
|
+
function Ze(...e) {
|
|
47
|
+
console.error(...e);
|
|
48
|
+
}
|
|
49
|
+
function Qe(...e) {
|
|
50
|
+
console.warn(...e);
|
|
51
|
+
}
|
|
52
|
+
function $e(e, t) {
|
|
53
|
+
return typeof WebGLBuffer < "u" && t instanceof WebGLBuffer;
|
|
54
|
+
}
|
|
55
|
+
function et(e, t) {
|
|
56
|
+
return typeof WebGLRenderbuffer < "u" && t instanceof WebGLRenderbuffer;
|
|
57
|
+
}
|
|
58
|
+
function tt(e, t) {
|
|
59
|
+
return typeof WebGLTexture < "u" && t instanceof WebGLTexture;
|
|
60
|
+
}
|
|
61
|
+
function nt(e, t) {
|
|
62
|
+
return typeof WebGLSampler < "u" && t instanceof WebGLSampler;
|
|
63
|
+
}
|
|
64
|
+
var rt = 35044, w = 34962, it = 34963, at = 34660, ot = 5120, st = 5121, ct = 5122, lt = 5123, ut = 5124, dt = 5125, ft = 5126, pt = { attribPrefix: "" };
|
|
65
|
+
function mt(e, t, n, r, i) {
|
|
66
|
+
e.bindBuffer(t, n), e.bufferData(t, r, i || rt);
|
|
67
|
+
}
|
|
68
|
+
function ht(e, t, n, r) {
|
|
69
|
+
if ($e(e, t)) return t;
|
|
70
|
+
n ||= w;
|
|
71
|
+
let i = e.createBuffer();
|
|
72
|
+
return mt(e, n, i, t, r), i;
|
|
73
|
+
}
|
|
74
|
+
function gt(e) {
|
|
75
|
+
return e === "indices";
|
|
76
|
+
}
|
|
77
|
+
function _t(e) {
|
|
78
|
+
return e instanceof Int8Array || e instanceof Uint8Array;
|
|
79
|
+
}
|
|
80
|
+
function vt(e) {
|
|
81
|
+
return e === Int8Array || e === Uint8Array;
|
|
82
|
+
}
|
|
83
|
+
function yt(e) {
|
|
84
|
+
return e.length ? e : e.data;
|
|
85
|
+
}
|
|
86
|
+
var bt = /coord|texture/i, xt = /color|colour/i;
|
|
87
|
+
function St(e, t) {
|
|
88
|
+
let n;
|
|
89
|
+
if (n = bt.test(e) ? 2 : xt.test(e) ? 4 : 3, t % n > 0) throw Error(`Can not guess numComponents for attribute '${e}'. Tried ${n} but ${t} values is not evenly divisible by ${n}. You should specify it.`);
|
|
90
|
+
return n;
|
|
91
|
+
}
|
|
92
|
+
function Ct(e, t) {
|
|
93
|
+
return e.numComponents || e.size || St(t, yt(e).length);
|
|
94
|
+
}
|
|
95
|
+
function wt(e, t) {
|
|
96
|
+
if (Xe(e)) return e;
|
|
97
|
+
if (Xe(e.data)) return e.data;
|
|
98
|
+
Array.isArray(e) && (e = { data: e });
|
|
99
|
+
let n = e.type;
|
|
100
|
+
return n ||= gt(t) ? Uint16Array : Float32Array, new n(e.data);
|
|
101
|
+
}
|
|
102
|
+
function Tt(e, t) {
|
|
103
|
+
let n = {};
|
|
104
|
+
return Object.keys(t).forEach(function(r) {
|
|
105
|
+
if (!gt(r)) {
|
|
106
|
+
let i = t[r], a = i.attrib || i.name || i.attribName || pt.attribPrefix + r;
|
|
107
|
+
if (i.value) {
|
|
108
|
+
if (!Array.isArray(i.value) && !Xe(i.value)) throw Error("array.value is not array or typedarray");
|
|
109
|
+
n[a] = { value: i.value };
|
|
110
|
+
} else {
|
|
111
|
+
let t, o, s, c;
|
|
112
|
+
if (i.buffer && i.buffer instanceof WebGLBuffer) t = i.buffer, c = i.numComponents || i.size, o = i.type, s = i.normalize;
|
|
113
|
+
else if (typeof i == "number" || typeof i.data == "number") {
|
|
114
|
+
let n = i.data || i, a = i.type || Float32Array, l = n * a.BYTES_PER_ELEMENT;
|
|
115
|
+
o = Je(a), s = i.normalize === void 0 ? vt(a) : i.normalize, c = i.numComponents || i.size || St(r, n), t = e.createBuffer(), e.bindBuffer(w, t), e.bufferData(w, l, i.drawType || rt);
|
|
116
|
+
} else {
|
|
117
|
+
let n = wt(i, r);
|
|
118
|
+
t = ht(e, n, void 0, i.drawType), o = qe(n), s = i.normalize === void 0 ? _t(n) : i.normalize, c = Ct(i, r);
|
|
119
|
+
}
|
|
120
|
+
n[a] = {
|
|
121
|
+
buffer: t,
|
|
122
|
+
numComponents: c,
|
|
123
|
+
type: o,
|
|
124
|
+
normalize: s,
|
|
125
|
+
stride: i.stride || 0,
|
|
126
|
+
offset: i.offset || 0,
|
|
127
|
+
divisor: i.divisor === void 0 ? void 0 : i.divisor,
|
|
128
|
+
drawType: i.drawType
|
|
129
|
+
};
|
|
130
|
+
}
|
|
131
|
+
}
|
|
132
|
+
}), e.bindBuffer(w, null), n;
|
|
133
|
+
}
|
|
134
|
+
function Et(e, t, n, r) {
|
|
135
|
+
n = wt(n), r === void 0 ? mt(e, w, t.buffer, n, t.drawType) : (e.bindBuffer(w, t.buffer), e.bufferSubData(w, r, n));
|
|
136
|
+
}
|
|
137
|
+
function Dt(e, t) {
|
|
138
|
+
return t === ot || t === st ? 1 : t === ct || t === lt ? 2 : t === ut || t === dt || t === ft ? 4 : 0;
|
|
139
|
+
}
|
|
140
|
+
var Ot = [
|
|
141
|
+
"position",
|
|
142
|
+
"positions",
|
|
143
|
+
"a_position"
|
|
144
|
+
];
|
|
145
|
+
function kt(e, t) {
|
|
146
|
+
let n, r;
|
|
147
|
+
for (r = 0; r < Ot.length && (n = Ot[r], !(n in t || (n = pt.attribPrefix + n, n in t))); ++r);
|
|
148
|
+
r === Ot.length && (n = Object.keys(t)[0]);
|
|
149
|
+
let i = t[n];
|
|
150
|
+
if (!i.buffer) return 1;
|
|
151
|
+
e.bindBuffer(w, i.buffer);
|
|
152
|
+
let a = e.getBufferParameter(w, at);
|
|
153
|
+
e.bindBuffer(w, null);
|
|
154
|
+
let o = a / Dt(e, i.type), s = i.numComponents || i.size, c = o / s;
|
|
155
|
+
if (c % 1 != 0) throw Error(`numComponents ${s} not correct for length ${length}`);
|
|
156
|
+
return c;
|
|
157
|
+
}
|
|
158
|
+
function At(e, t, n) {
|
|
159
|
+
let r = Tt(e, t), i = Object.assign({}, n || {});
|
|
160
|
+
i.attribs = Object.assign({}, n ? n.attribs : {}, r);
|
|
161
|
+
let a = t.indices;
|
|
162
|
+
if (a) {
|
|
163
|
+
let t = wt(a, "indices");
|
|
164
|
+
i.indices = ht(e, t, it), i.numElements = t.length, i.elementType = qe(t);
|
|
165
|
+
} else i.numElements ||= kt(e, i.attribs);
|
|
166
|
+
return i;
|
|
167
|
+
}
|
|
168
|
+
function T(e) {
|
|
169
|
+
return !!e.texStorage2D;
|
|
170
|
+
}
|
|
171
|
+
var jt = function() {
|
|
172
|
+
let e = {}, t = {};
|
|
173
|
+
function n(n) {
|
|
174
|
+
let r = n.constructor.name;
|
|
175
|
+
if (!e[r]) {
|
|
176
|
+
for (let e in n) if (typeof n[e] == "number") {
|
|
177
|
+
let r = t[n[e]];
|
|
178
|
+
t[n[e]] = r ? `${r} | ${e}` : e;
|
|
179
|
+
}
|
|
180
|
+
e[r] = !0;
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
return function(e, r) {
|
|
184
|
+
return n(e), t[r] || (typeof r == "number" ? `0x${r.toString(16)}` : r);
|
|
185
|
+
};
|
|
186
|
+
}(), E = {
|
|
187
|
+
textureColor: new Uint8Array([
|
|
188
|
+
128,
|
|
189
|
+
192,
|
|
190
|
+
255,
|
|
191
|
+
255
|
|
192
|
+
]),
|
|
193
|
+
textureOptions: {},
|
|
194
|
+
crossOrigin: void 0
|
|
195
|
+
}, Mt = Xe, Nt = function() {
|
|
196
|
+
let e;
|
|
197
|
+
return function() {
|
|
198
|
+
return e ||= typeof document < "u" && document.createElement ? document.createElement("canvas").getContext("2d") : null, e;
|
|
199
|
+
};
|
|
200
|
+
}(), Pt = 6406, D = 6407, O = 6408, Ft = 6409, It = 6410, k = 6402, Lt = 34041, Rt = 33071, zt = 9728, Bt = 9729, A = 3553, j = 34067, M = 32879, N = 35866, Vt = 34069, Ht = 34070, Ut = 34071, Wt = 34072, Gt = 34073, Kt = 34074, qt = 10241, Jt = 10240, Yt = 10242, Xt = 10243, Zt = 32882, Qt = 33082, $t = 33083, en = 33084, tn = 33085, nn = 3317, rn = 3314, an = 32878, on = 3316, sn = 3315, cn = 32877, ln = 37443, un = 37441, dn = 37440, fn = 33321, pn = 36756, mn = 33325, hn = 33326, gn = 33330, _n = 33329, vn = 33338, yn = 33337, bn = 33340, xn = 33339, Sn = 33323, Cn = 36757, wn = 33327, Tn = 33328, En = 33336, Dn = 33335, On = 33332, kn = 33331, An = 33334, jn = 33333, Mn = 32849, Nn = 35905, Pn = 36194, Fn = 36758, In = 35898, Ln = 35901, Rn = 34843, zn = 34837, Bn = 36221, Vn = 36239, Hn = 36215, Un = 36233, Wn = 36209, Gn = 36227, Kn = 32856, qn = 35907, Jn = 36759, Yn = 32855, Xn = 32854, Zn = 32857, Qn = 34842, $n = 34836, er = 36220, tr = 36238, nr = 36975, rr = 36214, ir = 36232, ar = 36226, or = 36208, sr = 33189, cr = 33190, lr = 36012, ur = 36013, dr = 35056, P = 5120, F = 5121, fr = 5122, pr = 5123, mr = 5124, I = 5125, L = 5126, hr = 32819, gr = 32820, _r = 33635, R = 5131, vr = 36193, yr = 33640, br = 35899, xr = 35902, Sr = 36269, Cr = 34042, wr = 33319, z = 33320, Tr = 6403, B = 36244, V = 36248, H = 36249, Er = {};
|
|
201
|
+
{
|
|
202
|
+
let e = Er;
|
|
203
|
+
e[Pt] = { numColorComponents: 1 }, e[Ft] = { numColorComponents: 1 }, e[It] = { numColorComponents: 2 }, e[D] = { numColorComponents: 3 }, e[O] = { numColorComponents: 4 }, e[Tr] = { numColorComponents: 1 }, e[B] = { numColorComponents: 1 }, e[wr] = { numColorComponents: 2 }, e[z] = { numColorComponents: 2 }, e[D] = { numColorComponents: 3 }, e[V] = { numColorComponents: 3 }, e[O] = { numColorComponents: 4 }, e[H] = { numColorComponents: 4 }, e[k] = { numColorComponents: 1 }, e[Lt] = { numColorComponents: 2 };
|
|
204
|
+
}
|
|
205
|
+
var Dr;
|
|
206
|
+
function Or(e) {
|
|
207
|
+
if (!Dr) {
|
|
208
|
+
let e = {};
|
|
209
|
+
e[Pt] = {
|
|
210
|
+
textureFormat: Pt,
|
|
211
|
+
colorRenderable: !0,
|
|
212
|
+
textureFilterable: !0,
|
|
213
|
+
bytesPerElement: [
|
|
214
|
+
1,
|
|
215
|
+
2,
|
|
216
|
+
2,
|
|
217
|
+
4
|
|
218
|
+
],
|
|
219
|
+
type: [
|
|
220
|
+
F,
|
|
221
|
+
R,
|
|
222
|
+
vr,
|
|
223
|
+
L
|
|
224
|
+
]
|
|
225
|
+
}, e[Ft] = {
|
|
226
|
+
textureFormat: Ft,
|
|
227
|
+
colorRenderable: !0,
|
|
228
|
+
textureFilterable: !0,
|
|
229
|
+
bytesPerElement: [
|
|
230
|
+
1,
|
|
231
|
+
2,
|
|
232
|
+
2,
|
|
233
|
+
4
|
|
234
|
+
],
|
|
235
|
+
type: [
|
|
236
|
+
F,
|
|
237
|
+
R,
|
|
238
|
+
vr,
|
|
239
|
+
L
|
|
240
|
+
]
|
|
241
|
+
}, e[It] = {
|
|
242
|
+
textureFormat: It,
|
|
243
|
+
colorRenderable: !0,
|
|
244
|
+
textureFilterable: !0,
|
|
245
|
+
bytesPerElement: [
|
|
246
|
+
2,
|
|
247
|
+
4,
|
|
248
|
+
4,
|
|
249
|
+
8
|
|
250
|
+
],
|
|
251
|
+
type: [
|
|
252
|
+
F,
|
|
253
|
+
R,
|
|
254
|
+
vr,
|
|
255
|
+
L
|
|
256
|
+
]
|
|
257
|
+
}, e[D] = {
|
|
258
|
+
textureFormat: D,
|
|
259
|
+
colorRenderable: !0,
|
|
260
|
+
textureFilterable: !0,
|
|
261
|
+
bytesPerElement: [
|
|
262
|
+
3,
|
|
263
|
+
6,
|
|
264
|
+
6,
|
|
265
|
+
12,
|
|
266
|
+
2
|
|
267
|
+
],
|
|
268
|
+
type: [
|
|
269
|
+
F,
|
|
270
|
+
R,
|
|
271
|
+
vr,
|
|
272
|
+
L,
|
|
273
|
+
_r
|
|
274
|
+
]
|
|
275
|
+
}, e[O] = {
|
|
276
|
+
textureFormat: O,
|
|
277
|
+
colorRenderable: !0,
|
|
278
|
+
textureFilterable: !0,
|
|
279
|
+
bytesPerElement: [
|
|
280
|
+
4,
|
|
281
|
+
8,
|
|
282
|
+
8,
|
|
283
|
+
16,
|
|
284
|
+
2,
|
|
285
|
+
2
|
|
286
|
+
],
|
|
287
|
+
type: [
|
|
288
|
+
F,
|
|
289
|
+
R,
|
|
290
|
+
vr,
|
|
291
|
+
L,
|
|
292
|
+
hr,
|
|
293
|
+
gr
|
|
294
|
+
]
|
|
295
|
+
}, e[k] = {
|
|
296
|
+
textureFormat: k,
|
|
297
|
+
colorRenderable: !0,
|
|
298
|
+
textureFilterable: !1,
|
|
299
|
+
bytesPerElement: [2, 4],
|
|
300
|
+
type: [I, pr]
|
|
301
|
+
}, e[fn] = {
|
|
302
|
+
textureFormat: Tr,
|
|
303
|
+
colorRenderable: !0,
|
|
304
|
+
textureFilterable: !0,
|
|
305
|
+
bytesPerElement: [1],
|
|
306
|
+
type: [F]
|
|
307
|
+
}, e[pn] = {
|
|
308
|
+
textureFormat: Tr,
|
|
309
|
+
colorRenderable: !1,
|
|
310
|
+
textureFilterable: !0,
|
|
311
|
+
bytesPerElement: [1],
|
|
312
|
+
type: [P]
|
|
313
|
+
}, e[mn] = {
|
|
314
|
+
textureFormat: Tr,
|
|
315
|
+
colorRenderable: !1,
|
|
316
|
+
textureFilterable: !0,
|
|
317
|
+
bytesPerElement: [4, 2],
|
|
318
|
+
type: [L, R]
|
|
319
|
+
}, e[hn] = {
|
|
320
|
+
textureFormat: Tr,
|
|
321
|
+
colorRenderable: !1,
|
|
322
|
+
textureFilterable: !1,
|
|
323
|
+
bytesPerElement: [4],
|
|
324
|
+
type: [L]
|
|
325
|
+
}, e[gn] = {
|
|
326
|
+
textureFormat: B,
|
|
327
|
+
colorRenderable: !0,
|
|
328
|
+
textureFilterable: !1,
|
|
329
|
+
bytesPerElement: [1],
|
|
330
|
+
type: [F]
|
|
331
|
+
}, e[_n] = {
|
|
332
|
+
textureFormat: B,
|
|
333
|
+
colorRenderable: !0,
|
|
334
|
+
textureFilterable: !1,
|
|
335
|
+
bytesPerElement: [1],
|
|
336
|
+
type: [P]
|
|
337
|
+
}, e[On] = {
|
|
338
|
+
textureFormat: B,
|
|
339
|
+
colorRenderable: !0,
|
|
340
|
+
textureFilterable: !1,
|
|
341
|
+
bytesPerElement: [2],
|
|
342
|
+
type: [pr]
|
|
343
|
+
}, e[kn] = {
|
|
344
|
+
textureFormat: B,
|
|
345
|
+
colorRenderable: !0,
|
|
346
|
+
textureFilterable: !1,
|
|
347
|
+
bytesPerElement: [2],
|
|
348
|
+
type: [fr]
|
|
349
|
+
}, e[An] = {
|
|
350
|
+
textureFormat: B,
|
|
351
|
+
colorRenderable: !0,
|
|
352
|
+
textureFilterable: !1,
|
|
353
|
+
bytesPerElement: [4],
|
|
354
|
+
type: [I]
|
|
355
|
+
}, e[jn] = {
|
|
356
|
+
textureFormat: B,
|
|
357
|
+
colorRenderable: !0,
|
|
358
|
+
textureFilterable: !1,
|
|
359
|
+
bytesPerElement: [4],
|
|
360
|
+
type: [mr]
|
|
361
|
+
}, e[Sn] = {
|
|
362
|
+
textureFormat: wr,
|
|
363
|
+
colorRenderable: !0,
|
|
364
|
+
textureFilterable: !0,
|
|
365
|
+
bytesPerElement: [2],
|
|
366
|
+
type: [F]
|
|
367
|
+
}, e[Cn] = {
|
|
368
|
+
textureFormat: wr,
|
|
369
|
+
colorRenderable: !1,
|
|
370
|
+
textureFilterable: !0,
|
|
371
|
+
bytesPerElement: [2],
|
|
372
|
+
type: [P]
|
|
373
|
+
}, e[wn] = {
|
|
374
|
+
textureFormat: wr,
|
|
375
|
+
colorRenderable: !1,
|
|
376
|
+
textureFilterable: !0,
|
|
377
|
+
bytesPerElement: [8, 4],
|
|
378
|
+
type: [L, R]
|
|
379
|
+
}, e[Tn] = {
|
|
380
|
+
textureFormat: wr,
|
|
381
|
+
colorRenderable: !1,
|
|
382
|
+
textureFilterable: !1,
|
|
383
|
+
bytesPerElement: [8],
|
|
384
|
+
type: [L]
|
|
385
|
+
}, e[En] = {
|
|
386
|
+
textureFormat: z,
|
|
387
|
+
colorRenderable: !0,
|
|
388
|
+
textureFilterable: !1,
|
|
389
|
+
bytesPerElement: [2],
|
|
390
|
+
type: [F]
|
|
391
|
+
}, e[Dn] = {
|
|
392
|
+
textureFormat: z,
|
|
393
|
+
colorRenderable: !0,
|
|
394
|
+
textureFilterable: !1,
|
|
395
|
+
bytesPerElement: [2],
|
|
396
|
+
type: [P]
|
|
397
|
+
}, e[vn] = {
|
|
398
|
+
textureFormat: z,
|
|
399
|
+
colorRenderable: !0,
|
|
400
|
+
textureFilterable: !1,
|
|
401
|
+
bytesPerElement: [4],
|
|
402
|
+
type: [pr]
|
|
403
|
+
}, e[yn] = {
|
|
404
|
+
textureFormat: z,
|
|
405
|
+
colorRenderable: !0,
|
|
406
|
+
textureFilterable: !1,
|
|
407
|
+
bytesPerElement: [4],
|
|
408
|
+
type: [fr]
|
|
409
|
+
}, e[bn] = {
|
|
410
|
+
textureFormat: z,
|
|
411
|
+
colorRenderable: !0,
|
|
412
|
+
textureFilterable: !1,
|
|
413
|
+
bytesPerElement: [8],
|
|
414
|
+
type: [I]
|
|
415
|
+
}, e[xn] = {
|
|
416
|
+
textureFormat: z,
|
|
417
|
+
colorRenderable: !0,
|
|
418
|
+
textureFilterable: !1,
|
|
419
|
+
bytesPerElement: [8],
|
|
420
|
+
type: [mr]
|
|
421
|
+
}, e[Mn] = {
|
|
422
|
+
textureFormat: D,
|
|
423
|
+
colorRenderable: !0,
|
|
424
|
+
textureFilterable: !0,
|
|
425
|
+
bytesPerElement: [3],
|
|
426
|
+
type: [F]
|
|
427
|
+
}, e[Nn] = {
|
|
428
|
+
textureFormat: D,
|
|
429
|
+
colorRenderable: !1,
|
|
430
|
+
textureFilterable: !0,
|
|
431
|
+
bytesPerElement: [3],
|
|
432
|
+
type: [F]
|
|
433
|
+
}, e[Pn] = {
|
|
434
|
+
textureFormat: D,
|
|
435
|
+
colorRenderable: !0,
|
|
436
|
+
textureFilterable: !0,
|
|
437
|
+
bytesPerElement: [3, 2],
|
|
438
|
+
type: [F, _r]
|
|
439
|
+
}, e[Fn] = {
|
|
440
|
+
textureFormat: D,
|
|
441
|
+
colorRenderable: !1,
|
|
442
|
+
textureFilterable: !0,
|
|
443
|
+
bytesPerElement: [3],
|
|
444
|
+
type: [P]
|
|
445
|
+
}, e[In] = {
|
|
446
|
+
textureFormat: D,
|
|
447
|
+
colorRenderable: !1,
|
|
448
|
+
textureFilterable: !0,
|
|
449
|
+
bytesPerElement: [
|
|
450
|
+
12,
|
|
451
|
+
6,
|
|
452
|
+
4
|
|
453
|
+
],
|
|
454
|
+
type: [
|
|
455
|
+
L,
|
|
456
|
+
R,
|
|
457
|
+
br
|
|
458
|
+
]
|
|
459
|
+
}, e[Ln] = {
|
|
460
|
+
textureFormat: D,
|
|
461
|
+
colorRenderable: !1,
|
|
462
|
+
textureFilterable: !0,
|
|
463
|
+
bytesPerElement: [
|
|
464
|
+
12,
|
|
465
|
+
6,
|
|
466
|
+
4
|
|
467
|
+
],
|
|
468
|
+
type: [
|
|
469
|
+
L,
|
|
470
|
+
R,
|
|
471
|
+
xr
|
|
472
|
+
]
|
|
473
|
+
}, e[Rn] = {
|
|
474
|
+
textureFormat: D,
|
|
475
|
+
colorRenderable: !1,
|
|
476
|
+
textureFilterable: !0,
|
|
477
|
+
bytesPerElement: [12, 6],
|
|
478
|
+
type: [L, R]
|
|
479
|
+
}, e[zn] = {
|
|
480
|
+
textureFormat: D,
|
|
481
|
+
colorRenderable: !1,
|
|
482
|
+
textureFilterable: !1,
|
|
483
|
+
bytesPerElement: [12],
|
|
484
|
+
type: [L]
|
|
485
|
+
}, e[Bn] = {
|
|
486
|
+
textureFormat: V,
|
|
487
|
+
colorRenderable: !1,
|
|
488
|
+
textureFilterable: !1,
|
|
489
|
+
bytesPerElement: [3],
|
|
490
|
+
type: [F]
|
|
491
|
+
}, e[Vn] = {
|
|
492
|
+
textureFormat: V,
|
|
493
|
+
colorRenderable: !1,
|
|
494
|
+
textureFilterable: !1,
|
|
495
|
+
bytesPerElement: [3],
|
|
496
|
+
type: [P]
|
|
497
|
+
}, e[Hn] = {
|
|
498
|
+
textureFormat: V,
|
|
499
|
+
colorRenderable: !1,
|
|
500
|
+
textureFilterable: !1,
|
|
501
|
+
bytesPerElement: [6],
|
|
502
|
+
type: [pr]
|
|
503
|
+
}, e[Un] = {
|
|
504
|
+
textureFormat: V,
|
|
505
|
+
colorRenderable: !1,
|
|
506
|
+
textureFilterable: !1,
|
|
507
|
+
bytesPerElement: [6],
|
|
508
|
+
type: [fr]
|
|
509
|
+
}, e[Wn] = {
|
|
510
|
+
textureFormat: V,
|
|
511
|
+
colorRenderable: !1,
|
|
512
|
+
textureFilterable: !1,
|
|
513
|
+
bytesPerElement: [12],
|
|
514
|
+
type: [I]
|
|
515
|
+
}, e[Gn] = {
|
|
516
|
+
textureFormat: V,
|
|
517
|
+
colorRenderable: !1,
|
|
518
|
+
textureFilterable: !1,
|
|
519
|
+
bytesPerElement: [12],
|
|
520
|
+
type: [mr]
|
|
521
|
+
}, e[Kn] = {
|
|
522
|
+
textureFormat: O,
|
|
523
|
+
colorRenderable: !0,
|
|
524
|
+
textureFilterable: !0,
|
|
525
|
+
bytesPerElement: [4],
|
|
526
|
+
type: [F]
|
|
527
|
+
}, e[qn] = {
|
|
528
|
+
textureFormat: O,
|
|
529
|
+
colorRenderable: !0,
|
|
530
|
+
textureFilterable: !0,
|
|
531
|
+
bytesPerElement: [4],
|
|
532
|
+
type: [F]
|
|
533
|
+
}, e[Jn] = {
|
|
534
|
+
textureFormat: O,
|
|
535
|
+
colorRenderable: !1,
|
|
536
|
+
textureFilterable: !0,
|
|
537
|
+
bytesPerElement: [4],
|
|
538
|
+
type: [P]
|
|
539
|
+
}, e[Yn] = {
|
|
540
|
+
textureFormat: O,
|
|
541
|
+
colorRenderable: !0,
|
|
542
|
+
textureFilterable: !0,
|
|
543
|
+
bytesPerElement: [
|
|
544
|
+
4,
|
|
545
|
+
2,
|
|
546
|
+
4
|
|
547
|
+
],
|
|
548
|
+
type: [
|
|
549
|
+
F,
|
|
550
|
+
gr,
|
|
551
|
+
yr
|
|
552
|
+
]
|
|
553
|
+
}, e[Xn] = {
|
|
554
|
+
textureFormat: O,
|
|
555
|
+
colorRenderable: !0,
|
|
556
|
+
textureFilterable: !0,
|
|
557
|
+
bytesPerElement: [4, 2],
|
|
558
|
+
type: [F, hr]
|
|
559
|
+
}, e[Zn] = {
|
|
560
|
+
textureFormat: O,
|
|
561
|
+
colorRenderable: !0,
|
|
562
|
+
textureFilterable: !0,
|
|
563
|
+
bytesPerElement: [4],
|
|
564
|
+
type: [yr]
|
|
565
|
+
}, e[Qn] = {
|
|
566
|
+
textureFormat: O,
|
|
567
|
+
colorRenderable: !1,
|
|
568
|
+
textureFilterable: !0,
|
|
569
|
+
bytesPerElement: [16, 8],
|
|
570
|
+
type: [L, R]
|
|
571
|
+
}, e[$n] = {
|
|
572
|
+
textureFormat: O,
|
|
573
|
+
colorRenderable: !1,
|
|
574
|
+
textureFilterable: !1,
|
|
575
|
+
bytesPerElement: [16],
|
|
576
|
+
type: [L]
|
|
577
|
+
}, e[er] = {
|
|
578
|
+
textureFormat: H,
|
|
579
|
+
colorRenderable: !0,
|
|
580
|
+
textureFilterable: !1,
|
|
581
|
+
bytesPerElement: [4],
|
|
582
|
+
type: [F]
|
|
583
|
+
}, e[tr] = {
|
|
584
|
+
textureFormat: H,
|
|
585
|
+
colorRenderable: !0,
|
|
586
|
+
textureFilterable: !1,
|
|
587
|
+
bytesPerElement: [4],
|
|
588
|
+
type: [P]
|
|
589
|
+
}, e[nr] = {
|
|
590
|
+
textureFormat: H,
|
|
591
|
+
colorRenderable: !0,
|
|
592
|
+
textureFilterable: !1,
|
|
593
|
+
bytesPerElement: [4],
|
|
594
|
+
type: [yr]
|
|
595
|
+
}, e[rr] = {
|
|
596
|
+
textureFormat: H,
|
|
597
|
+
colorRenderable: !0,
|
|
598
|
+
textureFilterable: !1,
|
|
599
|
+
bytesPerElement: [8],
|
|
600
|
+
type: [pr]
|
|
601
|
+
}, e[ir] = {
|
|
602
|
+
textureFormat: H,
|
|
603
|
+
colorRenderable: !0,
|
|
604
|
+
textureFilterable: !1,
|
|
605
|
+
bytesPerElement: [8],
|
|
606
|
+
type: [fr]
|
|
607
|
+
}, e[ar] = {
|
|
608
|
+
textureFormat: H,
|
|
609
|
+
colorRenderable: !0,
|
|
610
|
+
textureFilterable: !1,
|
|
611
|
+
bytesPerElement: [16],
|
|
612
|
+
type: [mr]
|
|
613
|
+
}, e[or] = {
|
|
614
|
+
textureFormat: H,
|
|
615
|
+
colorRenderable: !0,
|
|
616
|
+
textureFilterable: !1,
|
|
617
|
+
bytesPerElement: [16],
|
|
618
|
+
type: [I]
|
|
619
|
+
}, e[sr] = {
|
|
620
|
+
textureFormat: k,
|
|
621
|
+
colorRenderable: !0,
|
|
622
|
+
textureFilterable: !1,
|
|
623
|
+
bytesPerElement: [2, 4],
|
|
624
|
+
type: [pr, I]
|
|
625
|
+
}, e[cr] = {
|
|
626
|
+
textureFormat: k,
|
|
627
|
+
colorRenderable: !0,
|
|
628
|
+
textureFilterable: !1,
|
|
629
|
+
bytesPerElement: [4],
|
|
630
|
+
type: [I]
|
|
631
|
+
}, e[lr] = {
|
|
632
|
+
textureFormat: k,
|
|
633
|
+
colorRenderable: !0,
|
|
634
|
+
textureFilterable: !1,
|
|
635
|
+
bytesPerElement: [4],
|
|
636
|
+
type: [L]
|
|
637
|
+
}, e[dr] = {
|
|
638
|
+
textureFormat: Lt,
|
|
639
|
+
colorRenderable: !0,
|
|
640
|
+
textureFilterable: !1,
|
|
641
|
+
bytesPerElement: [4],
|
|
642
|
+
type: [Cr]
|
|
643
|
+
}, e[ur] = {
|
|
644
|
+
textureFormat: Lt,
|
|
645
|
+
colorRenderable: !0,
|
|
646
|
+
textureFilterable: !1,
|
|
647
|
+
bytesPerElement: [4],
|
|
648
|
+
type: [Sr]
|
|
649
|
+
}, Object.keys(e).forEach(function(t) {
|
|
650
|
+
let n = e[t];
|
|
651
|
+
n.bytesPerElementMap = {}, n.bytesPerElement.forEach(function(e, t) {
|
|
652
|
+
let r = n.type[t];
|
|
653
|
+
n.bytesPerElementMap[r] = e;
|
|
654
|
+
});
|
|
655
|
+
}), Dr = e;
|
|
656
|
+
}
|
|
657
|
+
return Dr[e];
|
|
658
|
+
}
|
|
659
|
+
function kr(e, t) {
|
|
660
|
+
let n = Or(e);
|
|
661
|
+
if (!n) throw "unknown internal format";
|
|
662
|
+
let r = n.bytesPerElementMap[t];
|
|
663
|
+
if (r === void 0) throw "unknown internal format";
|
|
664
|
+
return r;
|
|
665
|
+
}
|
|
666
|
+
function Ar(e) {
|
|
667
|
+
let t = Or(e);
|
|
668
|
+
if (!t) throw "unknown internal format";
|
|
669
|
+
return {
|
|
670
|
+
format: t.textureFormat,
|
|
671
|
+
type: t.type[0]
|
|
672
|
+
};
|
|
673
|
+
}
|
|
674
|
+
function jr(e) {
|
|
675
|
+
return (e & e - 1) == 0;
|
|
676
|
+
}
|
|
677
|
+
function Mr(e, t, n, r) {
|
|
678
|
+
if (!T(e)) return jr(t) && jr(n);
|
|
679
|
+
let i = Or(r);
|
|
680
|
+
if (!i) throw "unknown internal format";
|
|
681
|
+
return i.colorRenderable && i.textureFilterable;
|
|
682
|
+
}
|
|
683
|
+
function Nr(e) {
|
|
684
|
+
let t = Or(e);
|
|
685
|
+
if (!t) throw "unknown internal format";
|
|
686
|
+
return t.textureFilterable;
|
|
687
|
+
}
|
|
688
|
+
function Pr(e, t, n) {
|
|
689
|
+
return Mt(t) ? qe(t) : n || F;
|
|
690
|
+
}
|
|
691
|
+
function Fr(e, t, n, r, i) {
|
|
692
|
+
if (i % 1 != 0) throw "can't guess dimensions";
|
|
693
|
+
if (!n && !r) {
|
|
694
|
+
let e = Math.sqrt(i / (t === j ? 6 : 1));
|
|
695
|
+
e % 1 == 0 ? (n = e, r = e) : (n = i, r = 1);
|
|
696
|
+
} else if (!r) {
|
|
697
|
+
if (r = i / n, r % 1) throw "can't guess dimensions";
|
|
698
|
+
} else if (!n && (n = i / r, n % 1)) throw "can't guess dimensions";
|
|
699
|
+
return {
|
|
700
|
+
width: n,
|
|
701
|
+
height: r
|
|
702
|
+
};
|
|
703
|
+
}
|
|
704
|
+
function Ir(e, t) {
|
|
705
|
+
t.colorspaceConversion !== void 0 && e.pixelStorei(ln, t.colorspaceConversion), t.premultiplyAlpha !== void 0 && e.pixelStorei(un, t.premultiplyAlpha), t.flipY !== void 0 && e.pixelStorei(dn, t.flipY);
|
|
706
|
+
}
|
|
707
|
+
function Lr(e) {
|
|
708
|
+
e.pixelStorei(nn, 4), T(e) && (e.pixelStorei(rn, 0), e.pixelStorei(an, 0), e.pixelStorei(on, 0), e.pixelStorei(sn, 0), e.pixelStorei(cn, 0));
|
|
709
|
+
}
|
|
710
|
+
function Rr(e, t, n, r) {
|
|
711
|
+
r.minMag && (n.call(e, t, qt, r.minMag), n.call(e, t, Jt, r.minMag)), r.min && n.call(e, t, qt, r.min), r.mag && n.call(e, t, Jt, r.mag), r.wrap && (n.call(e, t, Yt, r.wrap), n.call(e, t, Xt, r.wrap), (t === M || nt(e, t)) && n.call(e, t, Zt, r.wrap)), r.wrapR && n.call(e, t, Zt, r.wrapR), r.wrapS && n.call(e, t, Yt, r.wrapS), r.wrapT && n.call(e, t, Xt, r.wrapT), r.minLod && n.call(e, t, Qt, r.minLod), r.maxLod && n.call(e, t, $t, r.maxLod), r.baseLevel && n.call(e, t, en, r.baseLevel), r.maxLevel && n.call(e, t, tn, r.maxLevel);
|
|
712
|
+
}
|
|
713
|
+
function zr(e, t, n) {
|
|
714
|
+
let r = n.target || A;
|
|
715
|
+
e.bindTexture(r, t), Rr(e, r, e.texParameteri, n);
|
|
716
|
+
}
|
|
717
|
+
function Br(e) {
|
|
718
|
+
return e ||= E.textureColor, Mt(e) ? e : new Uint8Array([
|
|
719
|
+
e[0] * 255,
|
|
720
|
+
e[1] * 255,
|
|
721
|
+
e[2] * 255,
|
|
722
|
+
e[3] * 255
|
|
723
|
+
]);
|
|
724
|
+
}
|
|
725
|
+
function Vr(e, t, n, r, i, a) {
|
|
726
|
+
n ||= E.textureOptions, a ||= O;
|
|
727
|
+
let o = n.target || A;
|
|
728
|
+
if (r ||= n.width, i ||= n.height, e.bindTexture(o, t), Mr(e, r, i, a)) e.generateMipmap(o);
|
|
729
|
+
else {
|
|
730
|
+
let t = Nr(a) ? Bt : zt;
|
|
731
|
+
e.texParameteri(o, qt, t), e.texParameteri(o, Jt, t), e.texParameteri(o, Yt, Rt), e.texParameteri(o, Xt, Rt);
|
|
732
|
+
}
|
|
733
|
+
}
|
|
734
|
+
function Hr(e) {
|
|
735
|
+
return e.auto === !0 || e.auto === void 0 && e.level === void 0;
|
|
736
|
+
}
|
|
737
|
+
function Ur(e, t) {
|
|
738
|
+
return t ||= {}, t.cubeFaceOrder || [
|
|
739
|
+
Vt,
|
|
740
|
+
Ht,
|
|
741
|
+
Ut,
|
|
742
|
+
Wt,
|
|
743
|
+
Gt,
|
|
744
|
+
Kt
|
|
745
|
+
];
|
|
746
|
+
}
|
|
747
|
+
function Wr(e, t) {
|
|
748
|
+
let n = Ur(e, t).map(function(e, t) {
|
|
749
|
+
return {
|
|
750
|
+
face: e,
|
|
751
|
+
ndx: t
|
|
752
|
+
};
|
|
753
|
+
});
|
|
754
|
+
return n.sort(function(e, t) {
|
|
755
|
+
return e.face - t.face;
|
|
756
|
+
}), n;
|
|
757
|
+
}
|
|
758
|
+
function Gr(e, t, n, r) {
|
|
759
|
+
r ||= E.textureOptions;
|
|
760
|
+
let i = r.target || A, a = r.level || 0, o = n.width, s = n.height, c = r.internalFormat || r.format || O, l = Ar(c), u = r.format || l.format, d = r.type || l.type;
|
|
761
|
+
if (Ir(e, r), e.bindTexture(i, t), i === j) {
|
|
762
|
+
let l = n.width, f = n.height, p, m;
|
|
763
|
+
if (l / 6 === f) p = f, m = [
|
|
764
|
+
0,
|
|
765
|
+
0,
|
|
766
|
+
1,
|
|
767
|
+
0,
|
|
768
|
+
2,
|
|
769
|
+
0,
|
|
770
|
+
3,
|
|
771
|
+
0,
|
|
772
|
+
4,
|
|
773
|
+
0,
|
|
774
|
+
5,
|
|
775
|
+
0
|
|
776
|
+
];
|
|
777
|
+
else if (f / 6 === l) p = l, m = [
|
|
778
|
+
0,
|
|
779
|
+
0,
|
|
780
|
+
0,
|
|
781
|
+
1,
|
|
782
|
+
0,
|
|
783
|
+
2,
|
|
784
|
+
0,
|
|
785
|
+
3,
|
|
786
|
+
0,
|
|
787
|
+
4,
|
|
788
|
+
0,
|
|
789
|
+
5
|
|
790
|
+
];
|
|
791
|
+
else if (l / 3 == f / 2) p = l / 3, m = [
|
|
792
|
+
0,
|
|
793
|
+
0,
|
|
794
|
+
1,
|
|
795
|
+
0,
|
|
796
|
+
2,
|
|
797
|
+
0,
|
|
798
|
+
0,
|
|
799
|
+
1,
|
|
800
|
+
1,
|
|
801
|
+
1,
|
|
802
|
+
2,
|
|
803
|
+
1
|
|
804
|
+
];
|
|
805
|
+
else if (l / 2 == f / 3) p = l / 2, m = [
|
|
806
|
+
0,
|
|
807
|
+
0,
|
|
808
|
+
1,
|
|
809
|
+
0,
|
|
810
|
+
0,
|
|
811
|
+
1,
|
|
812
|
+
1,
|
|
813
|
+
1,
|
|
814
|
+
0,
|
|
815
|
+
2,
|
|
816
|
+
1,
|
|
817
|
+
2
|
|
818
|
+
];
|
|
819
|
+
else throw "can't figure out cube map from element: " + (n.src ? n.src : n.nodeName);
|
|
820
|
+
let h = Nt();
|
|
821
|
+
h ? (h.canvas.width = p, h.canvas.height = p, o = p, s = p, Wr(e, r).forEach(function(t) {
|
|
822
|
+
let r = m[t.ndx * 2 + 0] * p, i = m[t.ndx * 2 + 1] * p;
|
|
823
|
+
h.drawImage(n, r, i, p, p, 0, 0, p, p), e.texImage2D(t.face, a, c, u, d, h.canvas);
|
|
824
|
+
}), h.canvas.width = 1, h.canvas.height = 1) : typeof createImageBitmap < "u" && (o = p, s = p, Wr(e, r).forEach(function(l) {
|
|
825
|
+
let f = m[l.ndx * 2 + 0] * p, h = m[l.ndx * 2 + 1] * p;
|
|
826
|
+
e.texImage2D(l.face, a, c, p, p, 0, u, d, null), createImageBitmap(n, f, h, p, p, {
|
|
827
|
+
premultiplyAlpha: "none",
|
|
828
|
+
colorSpaceConversion: "none"
|
|
829
|
+
}).then(function(n) {
|
|
830
|
+
Ir(e, r), e.bindTexture(i, t), e.texImage2D(l.face, a, c, u, d, n), Hr(r) && Vr(e, t, r, o, s, c);
|
|
831
|
+
});
|
|
832
|
+
}));
|
|
833
|
+
} else if (i === M || i === N) {
|
|
834
|
+
let t = Math.min(n.width, n.height), r = Math.max(n.width, n.height), o = r / t;
|
|
835
|
+
if (o % 1 != 0) throw "can not compute 3D dimensions of element";
|
|
836
|
+
let s = +(n.width === r), l = +(n.height === r);
|
|
837
|
+
e.pixelStorei(nn, 1), e.pixelStorei(rn, n.width), e.pixelStorei(an, 0), e.pixelStorei(cn, 0), e.texImage3D(i, a, c, t, t, t, 0, u, d, null);
|
|
838
|
+
for (let r = 0; r < o; ++r) {
|
|
839
|
+
let o = r * t * s, c = r * t * l;
|
|
840
|
+
e.pixelStorei(on, o), e.pixelStorei(sn, c), e.texSubImage3D(i, a, 0, 0, r, t, t, 1, u, d, n);
|
|
841
|
+
}
|
|
842
|
+
Lr(e);
|
|
843
|
+
} else e.texImage2D(i, a, c, u, d, n);
|
|
844
|
+
Hr(r) && Vr(e, t, r, o, s, c), zr(e, t, r);
|
|
845
|
+
}
|
|
846
|
+
function Kr() {}
|
|
847
|
+
function qr(e) {
|
|
848
|
+
if (typeof document < "u") {
|
|
849
|
+
let t = document.createElement("a");
|
|
850
|
+
return t.href = e, t.hostname === location.hostname && t.port === location.port && t.protocol === location.protocol;
|
|
851
|
+
} else {
|
|
852
|
+
let t = new URL(location.href).origin;
|
|
853
|
+
return new URL(e, location.href).origin === t;
|
|
854
|
+
}
|
|
855
|
+
}
|
|
856
|
+
function Jr(e, t) {
|
|
857
|
+
return t === void 0 && !qr(e) ? "anonymous" : t;
|
|
858
|
+
}
|
|
859
|
+
function Yr(e, t, n) {
|
|
860
|
+
n ||= Kr;
|
|
861
|
+
let r;
|
|
862
|
+
if (t = t === void 0 ? E.crossOrigin : t, t = Jr(e, t), typeof Image < "u") {
|
|
863
|
+
r = new Image(), t !== void 0 && (r.crossOrigin = t);
|
|
864
|
+
let i = function() {
|
|
865
|
+
r.removeEventListener("error", a), r.removeEventListener("load", o), r = null;
|
|
866
|
+
}, a = function() {
|
|
867
|
+
let t = "couldn't load image: " + e;
|
|
868
|
+
Ze(t), n(t, r), i();
|
|
869
|
+
}, o = function() {
|
|
870
|
+
n(null, r), i();
|
|
871
|
+
};
|
|
872
|
+
return r.addEventListener("error", a), r.addEventListener("load", o), r.src = e, r;
|
|
873
|
+
} else if (typeof ImageBitmap < "u") {
|
|
874
|
+
let i, a, o = function() {
|
|
875
|
+
n(i, a);
|
|
876
|
+
}, s = {};
|
|
877
|
+
t && (s.mode = "cors"), fetch(e, s).then(function(e) {
|
|
878
|
+
if (!e.ok) throw e;
|
|
879
|
+
return e.blob();
|
|
880
|
+
}).then(function(e) {
|
|
881
|
+
return createImageBitmap(e, {
|
|
882
|
+
premultiplyAlpha: "none",
|
|
883
|
+
colorSpaceConversion: "none"
|
|
884
|
+
});
|
|
885
|
+
}).then(function(e) {
|
|
886
|
+
a = e, setTimeout(o);
|
|
887
|
+
}).catch(function(e) {
|
|
888
|
+
i = e, setTimeout(o);
|
|
889
|
+
}), r = null;
|
|
890
|
+
}
|
|
891
|
+
return r;
|
|
892
|
+
}
|
|
893
|
+
function Xr(e) {
|
|
894
|
+
return typeof ImageBitmap < "u" && e instanceof ImageBitmap || typeof ImageData < "u" && e instanceof ImageData || typeof HTMLElement < "u" && e instanceof HTMLElement;
|
|
895
|
+
}
|
|
896
|
+
function Zr(e, t, n) {
|
|
897
|
+
return Xr(e) ? (setTimeout(function() {
|
|
898
|
+
n(null, e);
|
|
899
|
+
}), e) : Yr(e, t, n);
|
|
900
|
+
}
|
|
901
|
+
function Qr(e, t, n) {
|
|
902
|
+
n ||= E.textureOptions;
|
|
903
|
+
let r = n.target || A;
|
|
904
|
+
if (e.bindTexture(r, t), n.color === !1) return;
|
|
905
|
+
let i = Br(n.color);
|
|
906
|
+
if (r === j) for (let t = 0; t < 6; ++t) e.texImage2D(Vt + t, 0, O, 1, 1, 0, O, F, i);
|
|
907
|
+
else r === M || r === N ? e.texImage3D(r, 0, O, 1, 1, 1, 0, O, F, i) : e.texImage2D(r, 0, O, 1, 1, 0, O, F, i);
|
|
908
|
+
}
|
|
909
|
+
function $r(e, t, n, r) {
|
|
910
|
+
return r ||= Kr, n ||= E.textureOptions, Qr(e, t, n), n = Object.assign({}, n), Zr(n.src, n.crossOrigin, function(i, a) {
|
|
911
|
+
i ? r(i, t, a) : (Gr(e, t, a, n), r(null, t, a));
|
|
912
|
+
});
|
|
913
|
+
}
|
|
914
|
+
function ei(e, t, n, r) {
|
|
915
|
+
r ||= Kr;
|
|
916
|
+
let i = n.src;
|
|
917
|
+
if (i.length !== 6) throw "there must be 6 urls for a cubemap";
|
|
918
|
+
let a = n.level || 0, o = n.internalFormat || n.format || O, s = Ar(o), c = n.format || s.format, l = n.type || F, u = n.target || A;
|
|
919
|
+
if (u !== j) throw "target must be TEXTURE_CUBE_MAP";
|
|
920
|
+
Qr(e, t, n), n = Object.assign({}, n);
|
|
921
|
+
let d = 6, f = [], p = Ur(e, n), m;
|
|
922
|
+
function h(i) {
|
|
923
|
+
return function(s, p) {
|
|
924
|
+
--d, s ? f.push(s) : p.width === p.height ? (Ir(e, n), e.bindTexture(u, t), d === 5 ? Ur().forEach(function(t) {
|
|
925
|
+
e.texImage2D(t, a, o, c, l, p);
|
|
926
|
+
}) : e.texImage2D(i, a, o, c, l, p), Hr(n) && e.generateMipmap(u)) : f.push("cubemap face img is not a square: " + p.src), d === 0 && r(f.length ? f : void 0, t, m);
|
|
927
|
+
};
|
|
928
|
+
}
|
|
929
|
+
m = i.map(function(e, t) {
|
|
930
|
+
return Zr(e, n.crossOrigin, h(p[t]));
|
|
931
|
+
});
|
|
932
|
+
}
|
|
933
|
+
function ti(e, t, n, r) {
|
|
934
|
+
r ||= Kr;
|
|
935
|
+
let i = n.src, a = n.internalFormat || n.format || O, o = Ar(a), s = n.format || o.format, c = n.type || F, l = n.target || N;
|
|
936
|
+
if (l !== M && l !== N) throw "target must be TEXTURE_3D or TEXTURE_2D_ARRAY";
|
|
937
|
+
Qr(e, t, n), n = Object.assign({}, n);
|
|
938
|
+
let u = i.length, d = [], f, p = n.level || 0, m = n.width, h = n.height, g = i.length, _ = !0;
|
|
939
|
+
function v(i) {
|
|
940
|
+
return function(o, v) {
|
|
941
|
+
if (--u, o) d.push(o);
|
|
942
|
+
else {
|
|
943
|
+
if (Ir(e, n), e.bindTexture(l, t), _) {
|
|
944
|
+
_ = !1, m = n.width || v.width, h = n.height || v.height, e.texImage3D(l, p, a, m, h, g, 0, s, c, null);
|
|
945
|
+
for (let t = 0; t < g; ++t) e.texSubImage3D(l, p, 0, 0, t, m, h, 1, s, c, v);
|
|
946
|
+
} else {
|
|
947
|
+
let t = v, n;
|
|
948
|
+
(v.width !== m || v.height !== h) && (n = Nt(), t = n.canvas, n.canvas.width = m, n.canvas.height = h, n.drawImage(v, 0, 0, m, h)), e.texSubImage3D(l, p, 0, 0, i, m, h, 1, s, c, t), n && t === n.canvas && (n.canvas.width = 0, n.canvas.height = 0);
|
|
949
|
+
}
|
|
950
|
+
Hr(n) && e.generateMipmap(l);
|
|
951
|
+
}
|
|
952
|
+
u === 0 && r(d.length ? d : void 0, t, f);
|
|
953
|
+
};
|
|
954
|
+
}
|
|
955
|
+
f = i.map(function(e, t) {
|
|
956
|
+
return Zr(e, n.crossOrigin, v(t));
|
|
957
|
+
});
|
|
958
|
+
}
|
|
959
|
+
function ni(e, t, n, r) {
|
|
960
|
+
r ||= E.textureOptions;
|
|
961
|
+
let i = r.target || A;
|
|
962
|
+
e.bindTexture(i, t);
|
|
963
|
+
let a = r.width, o = r.height, s = r.depth, c = r.level || 0, l = r.internalFormat || r.format || O, u = Ar(l), d = r.format || u.format, f = r.type || Pr(e, n, u.type);
|
|
964
|
+
Mt(n) ? n instanceof Uint8ClampedArray && (n = new Uint8Array(n.buffer)) : n = new (Ye(f))(n);
|
|
965
|
+
let p = kr(l, f), m = n.byteLength / p;
|
|
966
|
+
if (m % 1) throw "length wrong size for format: " + jt(e, d);
|
|
967
|
+
let h;
|
|
968
|
+
if (i === M || i === N) if (!a && !o && !s) {
|
|
969
|
+
let e = Math.cbrt(m);
|
|
970
|
+
if (e % 1 != 0) throw "can't guess cube size of array of numElements: " + m;
|
|
971
|
+
a = e, o = e, s = e;
|
|
972
|
+
} else a && (!o || !s) ? (h = Fr(e, i, o, s, m / a), o = h.width, s = h.height) : o && (!a || !s) ? (h = Fr(e, i, a, s, m / o), a = h.width, s = h.height) : (h = Fr(e, i, a, o, m / s), a = h.width, o = h.height);
|
|
973
|
+
else h = Fr(e, i, a, o, m), a = h.width, o = h.height;
|
|
974
|
+
if (Lr(e), e.pixelStorei(nn, r.unpackAlignment || 1), Ir(e, r), i === j) {
|
|
975
|
+
let t = p / n.BYTES_PER_ELEMENT, i = m / 6 * t;
|
|
976
|
+
Wr(e, r).forEach((t) => {
|
|
977
|
+
let r = i * t.ndx, s = n.subarray(r, r + i);
|
|
978
|
+
e.texImage2D(t.face, c, l, a, o, 0, d, f, s);
|
|
979
|
+
});
|
|
980
|
+
} else i === M || i === N ? e.texImage3D(i, c, l, a, o, s, 0, d, f, n) : e.texImage2D(i, c, l, a, o, 0, d, f, n);
|
|
981
|
+
return {
|
|
982
|
+
width: a,
|
|
983
|
+
height: o,
|
|
984
|
+
depth: s,
|
|
985
|
+
type: f
|
|
986
|
+
};
|
|
987
|
+
}
|
|
988
|
+
function ri(e, t, n) {
|
|
989
|
+
let r = n.target || A;
|
|
990
|
+
e.bindTexture(r, t);
|
|
991
|
+
let i = n.level || 0, a = n.internalFormat || n.format || O, o = Ar(a), s = n.format || o.format, c = n.type || o.type;
|
|
992
|
+
if (Ir(e, n), r === j) for (let t = 0; t < 6; ++t) e.texImage2D(Vt + t, i, a, n.width, n.height, 0, s, c, null);
|
|
993
|
+
else r === M || r === N ? e.texImage3D(r, i, a, n.width, n.height, n.depth, 0, s, c, null) : e.texImage2D(r, i, a, n.width, n.height, 0, s, c, null);
|
|
994
|
+
}
|
|
995
|
+
function ii(e, t, n) {
|
|
996
|
+
n ||= Kr, t ||= E.textureOptions;
|
|
997
|
+
let r = e.createTexture(), i = t.target || A, a = t.width || 1, o = t.height || 1, s = t.internalFormat || O;
|
|
998
|
+
e.bindTexture(i, r), i === j && (e.texParameteri(i, Yt, Rt), e.texParameteri(i, Xt, Rt));
|
|
999
|
+
let c = t.src;
|
|
1000
|
+
if (c) if (typeof c == "function" && (c = c(e, t)), typeof c == "string") $r(e, r, t, n);
|
|
1001
|
+
else if (Mt(c) || Array.isArray(c) && (typeof c[0] == "number" || Array.isArray(c[0]) || Mt(c[0]))) {
|
|
1002
|
+
let n = ni(e, r, c, t);
|
|
1003
|
+
a = n.width, o = n.height;
|
|
1004
|
+
} else Array.isArray(c) && (typeof c[0] == "string" || Xr(c[0])) ? i === j ? ei(e, r, t, n) : ti(e, r, t, n) : (Gr(e, r, c, t), a = c.width, o = c.height);
|
|
1005
|
+
else ri(e, r, t);
|
|
1006
|
+
return Hr(t) && Vr(e, r, t, a, o, s), zr(e, r, t), r;
|
|
1007
|
+
}
|
|
1008
|
+
function ai(e, t, n, r, i, a) {
|
|
1009
|
+
r ||= n.width, i ||= n.height, a ||= n.depth;
|
|
1010
|
+
let o = n.target || A;
|
|
1011
|
+
e.bindTexture(o, t);
|
|
1012
|
+
let s = n.level || 0, c = n.internalFormat || n.format || O, l = Ar(c), u = n.format || l.format, d, f = n.src;
|
|
1013
|
+
if (d = f && (Mt(f) || Array.isArray(f) && typeof f[0] == "number") ? n.type || Pr(e, f, l.type) : n.type || l.type, o === j) for (let t = 0; t < 6; ++t) e.texImage2D(Vt + t, s, c, r, i, 0, u, d, null);
|
|
1014
|
+
else o === M || o === N ? e.texImage3D(o, s, c, r, i, a, 0, u, d, null) : e.texImage2D(o, s, c, r, i, 0, u, d, null);
|
|
1015
|
+
}
|
|
1016
|
+
var oi = Qe, si = 33984, ci = 35048, li = 34962, ui = 34963, di = 35345, fi = 35718, pi = 35721, mi = 35971, hi = 35382, gi = 35396, _i = 35398, vi = 35392, yi = 35395, bi = 5126, xi = 35664, Si = 35665, Ci = 35666, wi = 5124, Ti = 35667, Ei = 35668, Di = 35669, Oi = 35670, ki = 35671, Ai = 35672, ji = 35673, Mi = 35674, Ni = 35675, Pi = 35676, Fi = 35678, Ii = 35680, Li = 35679, Ri = 35682, zi = 35685, Bi = 35686, Vi = 35687, Hi = 35688, Ui = 35689, Wi = 35690, Gi = 36289, Ki = 36292, qi = 36293, Ji = 5125, Yi = 36294, Xi = 36295, Zi = 36296, Qi = 36298, $i = 36299, ea = 36300, ta = 36303, na = 36306, ra = 36307, ia = 36308, aa = 36311, oa = 3553, sa = 34067, ca = 32879, la = 35866, U = {};
|
|
1017
|
+
function ua(e, t) {
|
|
1018
|
+
return U[t].bindPoint;
|
|
1019
|
+
}
|
|
1020
|
+
function da(e, t) {
|
|
1021
|
+
return function(n) {
|
|
1022
|
+
e.uniform1f(t, n);
|
|
1023
|
+
};
|
|
1024
|
+
}
|
|
1025
|
+
function fa(e, t) {
|
|
1026
|
+
return function(n) {
|
|
1027
|
+
e.uniform1fv(t, n);
|
|
1028
|
+
};
|
|
1029
|
+
}
|
|
1030
|
+
function pa(e, t) {
|
|
1031
|
+
return function(n) {
|
|
1032
|
+
e.uniform2fv(t, n);
|
|
1033
|
+
};
|
|
1034
|
+
}
|
|
1035
|
+
function ma(e, t) {
|
|
1036
|
+
return function(n) {
|
|
1037
|
+
e.uniform3fv(t, n);
|
|
1038
|
+
};
|
|
1039
|
+
}
|
|
1040
|
+
function ha(e, t) {
|
|
1041
|
+
return function(n) {
|
|
1042
|
+
e.uniform4fv(t, n);
|
|
1043
|
+
};
|
|
1044
|
+
}
|
|
1045
|
+
function ga(e, t) {
|
|
1046
|
+
return function(n) {
|
|
1047
|
+
e.uniform1i(t, n);
|
|
1048
|
+
};
|
|
1049
|
+
}
|
|
1050
|
+
function _a(e, t) {
|
|
1051
|
+
return function(n) {
|
|
1052
|
+
e.uniform1iv(t, n);
|
|
1053
|
+
};
|
|
1054
|
+
}
|
|
1055
|
+
function va(e, t) {
|
|
1056
|
+
return function(n) {
|
|
1057
|
+
e.uniform2iv(t, n);
|
|
1058
|
+
};
|
|
1059
|
+
}
|
|
1060
|
+
function ya(e, t) {
|
|
1061
|
+
return function(n) {
|
|
1062
|
+
e.uniform3iv(t, n);
|
|
1063
|
+
};
|
|
1064
|
+
}
|
|
1065
|
+
function ba(e, t) {
|
|
1066
|
+
return function(n) {
|
|
1067
|
+
e.uniform4iv(t, n);
|
|
1068
|
+
};
|
|
1069
|
+
}
|
|
1070
|
+
function xa(e, t) {
|
|
1071
|
+
return function(n) {
|
|
1072
|
+
e.uniform1ui(t, n);
|
|
1073
|
+
};
|
|
1074
|
+
}
|
|
1075
|
+
function Sa(e, t) {
|
|
1076
|
+
return function(n) {
|
|
1077
|
+
e.uniform1uiv(t, n);
|
|
1078
|
+
};
|
|
1079
|
+
}
|
|
1080
|
+
function Ca(e, t) {
|
|
1081
|
+
return function(n) {
|
|
1082
|
+
e.uniform2uiv(t, n);
|
|
1083
|
+
};
|
|
1084
|
+
}
|
|
1085
|
+
function wa(e, t) {
|
|
1086
|
+
return function(n) {
|
|
1087
|
+
e.uniform3uiv(t, n);
|
|
1088
|
+
};
|
|
1089
|
+
}
|
|
1090
|
+
function Ta(e, t) {
|
|
1091
|
+
return function(n) {
|
|
1092
|
+
e.uniform4uiv(t, n);
|
|
1093
|
+
};
|
|
1094
|
+
}
|
|
1095
|
+
function Ea(e, t) {
|
|
1096
|
+
return function(n) {
|
|
1097
|
+
e.uniformMatrix2fv(t, !1, n);
|
|
1098
|
+
};
|
|
1099
|
+
}
|
|
1100
|
+
function Da(e, t) {
|
|
1101
|
+
return function(n) {
|
|
1102
|
+
e.uniformMatrix3fv(t, !1, n);
|
|
1103
|
+
};
|
|
1104
|
+
}
|
|
1105
|
+
function Oa(e, t) {
|
|
1106
|
+
return function(n) {
|
|
1107
|
+
e.uniformMatrix4fv(t, !1, n);
|
|
1108
|
+
};
|
|
1109
|
+
}
|
|
1110
|
+
function ka(e, t) {
|
|
1111
|
+
return function(n) {
|
|
1112
|
+
e.uniformMatrix2x3fv(t, !1, n);
|
|
1113
|
+
};
|
|
1114
|
+
}
|
|
1115
|
+
function Aa(e, t) {
|
|
1116
|
+
return function(n) {
|
|
1117
|
+
e.uniformMatrix3x2fv(t, !1, n);
|
|
1118
|
+
};
|
|
1119
|
+
}
|
|
1120
|
+
function ja(e, t) {
|
|
1121
|
+
return function(n) {
|
|
1122
|
+
e.uniformMatrix2x4fv(t, !1, n);
|
|
1123
|
+
};
|
|
1124
|
+
}
|
|
1125
|
+
function Ma(e, t) {
|
|
1126
|
+
return function(n) {
|
|
1127
|
+
e.uniformMatrix4x2fv(t, !1, n);
|
|
1128
|
+
};
|
|
1129
|
+
}
|
|
1130
|
+
function Na(e, t) {
|
|
1131
|
+
return function(n) {
|
|
1132
|
+
e.uniformMatrix3x4fv(t, !1, n);
|
|
1133
|
+
};
|
|
1134
|
+
}
|
|
1135
|
+
function Pa(e, t) {
|
|
1136
|
+
return function(n) {
|
|
1137
|
+
e.uniformMatrix4x3fv(t, !1, n);
|
|
1138
|
+
};
|
|
1139
|
+
}
|
|
1140
|
+
function W(e, t, n, r) {
|
|
1141
|
+
let i = ua(e, t);
|
|
1142
|
+
return T(e) ? function(t) {
|
|
1143
|
+
let a, o;
|
|
1144
|
+
tt(e, t) ? (a = t, o = null) : (a = t.texture, o = t.sampler), e.uniform1i(r, n), e.activeTexture(si + n), e.bindTexture(i, a), e.bindSampler(n, o);
|
|
1145
|
+
} : function(t) {
|
|
1146
|
+
e.uniform1i(r, n), e.activeTexture(si + n), e.bindTexture(i, t);
|
|
1147
|
+
};
|
|
1148
|
+
}
|
|
1149
|
+
function G(e, t, n, r, i) {
|
|
1150
|
+
let a = ua(e, t), o = new Int32Array(i);
|
|
1151
|
+
for (let e = 0; e < i; ++e) o[e] = n + e;
|
|
1152
|
+
return T(e) ? function(t) {
|
|
1153
|
+
e.uniform1iv(r, o), t.forEach(function(t, r) {
|
|
1154
|
+
e.activeTexture(si + o[r]);
|
|
1155
|
+
let i, s;
|
|
1156
|
+
tt(e, t) ? (i = t, s = null) : (i = t.texture, s = t.sampler), e.bindSampler(n, s), e.bindTexture(a, i);
|
|
1157
|
+
});
|
|
1158
|
+
} : function(t) {
|
|
1159
|
+
e.uniform1iv(r, o), t.forEach(function(t, n) {
|
|
1160
|
+
e.activeTexture(si + o[n]), e.bindTexture(a, t);
|
|
1161
|
+
});
|
|
1162
|
+
};
|
|
1163
|
+
}
|
|
1164
|
+
U[bi] = {
|
|
1165
|
+
Type: Float32Array,
|
|
1166
|
+
size: 4,
|
|
1167
|
+
setter: da,
|
|
1168
|
+
arraySetter: fa
|
|
1169
|
+
}, U[xi] = {
|
|
1170
|
+
Type: Float32Array,
|
|
1171
|
+
size: 8,
|
|
1172
|
+
setter: pa,
|
|
1173
|
+
cols: 2
|
|
1174
|
+
}, U[Si] = {
|
|
1175
|
+
Type: Float32Array,
|
|
1176
|
+
size: 12,
|
|
1177
|
+
setter: ma,
|
|
1178
|
+
cols: 3
|
|
1179
|
+
}, U[Ci] = {
|
|
1180
|
+
Type: Float32Array,
|
|
1181
|
+
size: 16,
|
|
1182
|
+
setter: ha,
|
|
1183
|
+
cols: 4
|
|
1184
|
+
}, U[wi] = {
|
|
1185
|
+
Type: Int32Array,
|
|
1186
|
+
size: 4,
|
|
1187
|
+
setter: ga,
|
|
1188
|
+
arraySetter: _a
|
|
1189
|
+
}, U[Ti] = {
|
|
1190
|
+
Type: Int32Array,
|
|
1191
|
+
size: 8,
|
|
1192
|
+
setter: va,
|
|
1193
|
+
cols: 2
|
|
1194
|
+
}, U[Ei] = {
|
|
1195
|
+
Type: Int32Array,
|
|
1196
|
+
size: 12,
|
|
1197
|
+
setter: ya,
|
|
1198
|
+
cols: 3
|
|
1199
|
+
}, U[Di] = {
|
|
1200
|
+
Type: Int32Array,
|
|
1201
|
+
size: 16,
|
|
1202
|
+
setter: ba,
|
|
1203
|
+
cols: 4
|
|
1204
|
+
}, U[Ji] = {
|
|
1205
|
+
Type: Uint32Array,
|
|
1206
|
+
size: 4,
|
|
1207
|
+
setter: xa,
|
|
1208
|
+
arraySetter: Sa
|
|
1209
|
+
}, U[Yi] = {
|
|
1210
|
+
Type: Uint32Array,
|
|
1211
|
+
size: 8,
|
|
1212
|
+
setter: Ca,
|
|
1213
|
+
cols: 2
|
|
1214
|
+
}, U[Xi] = {
|
|
1215
|
+
Type: Uint32Array,
|
|
1216
|
+
size: 12,
|
|
1217
|
+
setter: wa,
|
|
1218
|
+
cols: 3
|
|
1219
|
+
}, U[Zi] = {
|
|
1220
|
+
Type: Uint32Array,
|
|
1221
|
+
size: 16,
|
|
1222
|
+
setter: Ta,
|
|
1223
|
+
cols: 4
|
|
1224
|
+
}, U[Oi] = {
|
|
1225
|
+
Type: Uint32Array,
|
|
1226
|
+
size: 4,
|
|
1227
|
+
setter: ga,
|
|
1228
|
+
arraySetter: _a
|
|
1229
|
+
}, U[ki] = {
|
|
1230
|
+
Type: Uint32Array,
|
|
1231
|
+
size: 8,
|
|
1232
|
+
setter: va,
|
|
1233
|
+
cols: 2
|
|
1234
|
+
}, U[Ai] = {
|
|
1235
|
+
Type: Uint32Array,
|
|
1236
|
+
size: 12,
|
|
1237
|
+
setter: ya,
|
|
1238
|
+
cols: 3
|
|
1239
|
+
}, U[ji] = {
|
|
1240
|
+
Type: Uint32Array,
|
|
1241
|
+
size: 16,
|
|
1242
|
+
setter: ba,
|
|
1243
|
+
cols: 4
|
|
1244
|
+
}, U[Mi] = {
|
|
1245
|
+
Type: Float32Array,
|
|
1246
|
+
size: 32,
|
|
1247
|
+
setter: Ea,
|
|
1248
|
+
rows: 2,
|
|
1249
|
+
cols: 2
|
|
1250
|
+
}, U[Ni] = {
|
|
1251
|
+
Type: Float32Array,
|
|
1252
|
+
size: 48,
|
|
1253
|
+
setter: Da,
|
|
1254
|
+
rows: 3,
|
|
1255
|
+
cols: 3
|
|
1256
|
+
}, U[Pi] = {
|
|
1257
|
+
Type: Float32Array,
|
|
1258
|
+
size: 64,
|
|
1259
|
+
setter: Oa,
|
|
1260
|
+
rows: 4,
|
|
1261
|
+
cols: 4
|
|
1262
|
+
}, U[zi] = {
|
|
1263
|
+
Type: Float32Array,
|
|
1264
|
+
size: 32,
|
|
1265
|
+
setter: ka,
|
|
1266
|
+
rows: 2,
|
|
1267
|
+
cols: 3
|
|
1268
|
+
}, U[Bi] = {
|
|
1269
|
+
Type: Float32Array,
|
|
1270
|
+
size: 32,
|
|
1271
|
+
setter: ja,
|
|
1272
|
+
rows: 2,
|
|
1273
|
+
cols: 4
|
|
1274
|
+
}, U[Vi] = {
|
|
1275
|
+
Type: Float32Array,
|
|
1276
|
+
size: 48,
|
|
1277
|
+
setter: Aa,
|
|
1278
|
+
rows: 3,
|
|
1279
|
+
cols: 2
|
|
1280
|
+
}, U[Hi] = {
|
|
1281
|
+
Type: Float32Array,
|
|
1282
|
+
size: 48,
|
|
1283
|
+
setter: Na,
|
|
1284
|
+
rows: 3,
|
|
1285
|
+
cols: 4
|
|
1286
|
+
}, U[Ui] = {
|
|
1287
|
+
Type: Float32Array,
|
|
1288
|
+
size: 64,
|
|
1289
|
+
setter: Ma,
|
|
1290
|
+
rows: 4,
|
|
1291
|
+
cols: 2
|
|
1292
|
+
}, U[Wi] = {
|
|
1293
|
+
Type: Float32Array,
|
|
1294
|
+
size: 64,
|
|
1295
|
+
setter: Pa,
|
|
1296
|
+
rows: 4,
|
|
1297
|
+
cols: 3
|
|
1298
|
+
}, U[Fi] = {
|
|
1299
|
+
Type: null,
|
|
1300
|
+
size: 0,
|
|
1301
|
+
setter: W,
|
|
1302
|
+
arraySetter: G,
|
|
1303
|
+
bindPoint: oa
|
|
1304
|
+
}, U[Ii] = {
|
|
1305
|
+
Type: null,
|
|
1306
|
+
size: 0,
|
|
1307
|
+
setter: W,
|
|
1308
|
+
arraySetter: G,
|
|
1309
|
+
bindPoint: sa
|
|
1310
|
+
}, U[Li] = {
|
|
1311
|
+
Type: null,
|
|
1312
|
+
size: 0,
|
|
1313
|
+
setter: W,
|
|
1314
|
+
arraySetter: G,
|
|
1315
|
+
bindPoint: ca
|
|
1316
|
+
}, U[Ri] = {
|
|
1317
|
+
Type: null,
|
|
1318
|
+
size: 0,
|
|
1319
|
+
setter: W,
|
|
1320
|
+
arraySetter: G,
|
|
1321
|
+
bindPoint: oa
|
|
1322
|
+
}, U[Gi] = {
|
|
1323
|
+
Type: null,
|
|
1324
|
+
size: 0,
|
|
1325
|
+
setter: W,
|
|
1326
|
+
arraySetter: G,
|
|
1327
|
+
bindPoint: la
|
|
1328
|
+
}, U[Ki] = {
|
|
1329
|
+
Type: null,
|
|
1330
|
+
size: 0,
|
|
1331
|
+
setter: W,
|
|
1332
|
+
arraySetter: G,
|
|
1333
|
+
bindPoint: la
|
|
1334
|
+
}, U[qi] = {
|
|
1335
|
+
Type: null,
|
|
1336
|
+
size: 0,
|
|
1337
|
+
setter: W,
|
|
1338
|
+
arraySetter: G,
|
|
1339
|
+
bindPoint: sa
|
|
1340
|
+
}, U[Qi] = {
|
|
1341
|
+
Type: null,
|
|
1342
|
+
size: 0,
|
|
1343
|
+
setter: W,
|
|
1344
|
+
arraySetter: G,
|
|
1345
|
+
bindPoint: oa
|
|
1346
|
+
}, U[$i] = {
|
|
1347
|
+
Type: null,
|
|
1348
|
+
size: 0,
|
|
1349
|
+
setter: W,
|
|
1350
|
+
arraySetter: G,
|
|
1351
|
+
bindPoint: ca
|
|
1352
|
+
}, U[ea] = {
|
|
1353
|
+
Type: null,
|
|
1354
|
+
size: 0,
|
|
1355
|
+
setter: W,
|
|
1356
|
+
arraySetter: G,
|
|
1357
|
+
bindPoint: sa
|
|
1358
|
+
}, U[ta] = {
|
|
1359
|
+
Type: null,
|
|
1360
|
+
size: 0,
|
|
1361
|
+
setter: W,
|
|
1362
|
+
arraySetter: G,
|
|
1363
|
+
bindPoint: la
|
|
1364
|
+
}, U[na] = {
|
|
1365
|
+
Type: null,
|
|
1366
|
+
size: 0,
|
|
1367
|
+
setter: W,
|
|
1368
|
+
arraySetter: G,
|
|
1369
|
+
bindPoint: oa
|
|
1370
|
+
}, U[ra] = {
|
|
1371
|
+
Type: null,
|
|
1372
|
+
size: 0,
|
|
1373
|
+
setter: W,
|
|
1374
|
+
arraySetter: G,
|
|
1375
|
+
bindPoint: ca
|
|
1376
|
+
}, U[ia] = {
|
|
1377
|
+
Type: null,
|
|
1378
|
+
size: 0,
|
|
1379
|
+
setter: W,
|
|
1380
|
+
arraySetter: G,
|
|
1381
|
+
bindPoint: sa
|
|
1382
|
+
}, U[aa] = {
|
|
1383
|
+
Type: null,
|
|
1384
|
+
size: 0,
|
|
1385
|
+
setter: W,
|
|
1386
|
+
arraySetter: G,
|
|
1387
|
+
bindPoint: la
|
|
1388
|
+
};
|
|
1389
|
+
function Fa(e, t) {
|
|
1390
|
+
return function(n) {
|
|
1391
|
+
if (n.value) switch (e.disableVertexAttribArray(t), n.value.length) {
|
|
1392
|
+
case 4:
|
|
1393
|
+
e.vertexAttrib4fv(t, n.value);
|
|
1394
|
+
break;
|
|
1395
|
+
case 3:
|
|
1396
|
+
e.vertexAttrib3fv(t, n.value);
|
|
1397
|
+
break;
|
|
1398
|
+
case 2:
|
|
1399
|
+
e.vertexAttrib2fv(t, n.value);
|
|
1400
|
+
break;
|
|
1401
|
+
case 1:
|
|
1402
|
+
e.vertexAttrib1fv(t, n.value);
|
|
1403
|
+
break;
|
|
1404
|
+
default: throw Error("the length of a float constant value must be between 1 and 4!");
|
|
1405
|
+
}
|
|
1406
|
+
else e.bindBuffer(li, n.buffer), e.enableVertexAttribArray(t), e.vertexAttribPointer(t, n.numComponents || n.size, n.type || bi, n.normalize || !1, n.stride || 0, n.offset || 0), n.divisor !== void 0 && e.vertexAttribDivisor(t, n.divisor);
|
|
1407
|
+
};
|
|
1408
|
+
}
|
|
1409
|
+
function K(e, t) {
|
|
1410
|
+
return function(n) {
|
|
1411
|
+
if (n.value) if (e.disableVertexAttribArray(t), n.value.length === 4) e.vertexAttrib4iv(t, n.value);
|
|
1412
|
+
else throw Error("The length of an integer constant value must be 4!");
|
|
1413
|
+
else e.bindBuffer(li, n.buffer), e.enableVertexAttribArray(t), e.vertexAttribIPointer(t, n.numComponents || n.size, n.type || wi, n.stride || 0, n.offset || 0), n.divisor !== void 0 && e.vertexAttribDivisor(t, n.divisor);
|
|
1414
|
+
};
|
|
1415
|
+
}
|
|
1416
|
+
function Ia(e, t) {
|
|
1417
|
+
return function(n) {
|
|
1418
|
+
if (n.value) if (e.disableVertexAttribArray(t), n.value.length === 4) e.vertexAttrib4uiv(t, n.value);
|
|
1419
|
+
else throw Error("The length of an unsigned integer constant value must be 4!");
|
|
1420
|
+
else e.bindBuffer(li, n.buffer), e.enableVertexAttribArray(t), e.vertexAttribIPointer(t, n.numComponents || n.size, n.type || Ji, n.stride || 0, n.offset || 0), n.divisor !== void 0 && e.vertexAttribDivisor(t, n.divisor);
|
|
1421
|
+
};
|
|
1422
|
+
}
|
|
1423
|
+
function La(e, t, n) {
|
|
1424
|
+
let r = n.size, i = n.count;
|
|
1425
|
+
return function(n) {
|
|
1426
|
+
e.bindBuffer(li, n.buffer);
|
|
1427
|
+
let a = n.size || n.numComponents || r, o = a / i, s = n.type || bi, c = U[s].size * a, l = n.normalize || !1, u = n.offset || 0, d = c / i;
|
|
1428
|
+
for (let r = 0; r < i; ++r) e.enableVertexAttribArray(t + r), e.vertexAttribPointer(t + r, o, s, l, c, u + d * r), n.divisor !== void 0 && e.vertexAttribDivisor(t + r, n.divisor);
|
|
1429
|
+
};
|
|
1430
|
+
}
|
|
1431
|
+
var q = {};
|
|
1432
|
+
q[bi] = {
|
|
1433
|
+
size: 4,
|
|
1434
|
+
setter: Fa
|
|
1435
|
+
}, q[xi] = {
|
|
1436
|
+
size: 8,
|
|
1437
|
+
setter: Fa
|
|
1438
|
+
}, q[Si] = {
|
|
1439
|
+
size: 12,
|
|
1440
|
+
setter: Fa
|
|
1441
|
+
}, q[Ci] = {
|
|
1442
|
+
size: 16,
|
|
1443
|
+
setter: Fa
|
|
1444
|
+
}, q[wi] = {
|
|
1445
|
+
size: 4,
|
|
1446
|
+
setter: K
|
|
1447
|
+
}, q[Ti] = {
|
|
1448
|
+
size: 8,
|
|
1449
|
+
setter: K
|
|
1450
|
+
}, q[Ei] = {
|
|
1451
|
+
size: 12,
|
|
1452
|
+
setter: K
|
|
1453
|
+
}, q[Di] = {
|
|
1454
|
+
size: 16,
|
|
1455
|
+
setter: K
|
|
1456
|
+
}, q[Ji] = {
|
|
1457
|
+
size: 4,
|
|
1458
|
+
setter: Ia
|
|
1459
|
+
}, q[Yi] = {
|
|
1460
|
+
size: 8,
|
|
1461
|
+
setter: Ia
|
|
1462
|
+
}, q[Xi] = {
|
|
1463
|
+
size: 12,
|
|
1464
|
+
setter: Ia
|
|
1465
|
+
}, q[Zi] = {
|
|
1466
|
+
size: 16,
|
|
1467
|
+
setter: Ia
|
|
1468
|
+
}, q[Oi] = {
|
|
1469
|
+
size: 4,
|
|
1470
|
+
setter: K
|
|
1471
|
+
}, q[ki] = {
|
|
1472
|
+
size: 8,
|
|
1473
|
+
setter: K
|
|
1474
|
+
}, q[Ai] = {
|
|
1475
|
+
size: 12,
|
|
1476
|
+
setter: K
|
|
1477
|
+
}, q[ji] = {
|
|
1478
|
+
size: 16,
|
|
1479
|
+
setter: K
|
|
1480
|
+
}, q[Mi] = {
|
|
1481
|
+
size: 4,
|
|
1482
|
+
setter: La,
|
|
1483
|
+
count: 2
|
|
1484
|
+
}, q[Ni] = {
|
|
1485
|
+
size: 9,
|
|
1486
|
+
setter: La,
|
|
1487
|
+
count: 3
|
|
1488
|
+
}, q[Pi] = {
|
|
1489
|
+
size: 16,
|
|
1490
|
+
setter: La,
|
|
1491
|
+
count: 4
|
|
1492
|
+
};
|
|
1493
|
+
function Ra(e) {
|
|
1494
|
+
let t = e.name;
|
|
1495
|
+
return t.startsWith("gl_") || t.startsWith("webgl_");
|
|
1496
|
+
}
|
|
1497
|
+
var za = /(\.|\[|]|\w+)/g, Ba = (e) => e >= "0" && e <= "9";
|
|
1498
|
+
function Va(e, t, n, r) {
|
|
1499
|
+
let i = e.split(za).filter((e) => e !== ""), a = 0, o = "";
|
|
1500
|
+
for (;;) {
|
|
1501
|
+
let e = i[a++];
|
|
1502
|
+
o += e;
|
|
1503
|
+
let s = Ba(e[0]), c = s ? parseInt(e) : e;
|
|
1504
|
+
if (s && (o += i[a++]), a === i.length) {
|
|
1505
|
+
n[c] = t;
|
|
1506
|
+
break;
|
|
1507
|
+
} else {
|
|
1508
|
+
let e = i[a++], t = e === "[", s = n[c] || (t ? [] : {});
|
|
1509
|
+
n[c] = s, n = s, r[o] = r[o] || function(e) {
|
|
1510
|
+
return function(t) {
|
|
1511
|
+
$a(e, t);
|
|
1512
|
+
};
|
|
1513
|
+
}(s), o += e;
|
|
1514
|
+
}
|
|
1515
|
+
}
|
|
1516
|
+
}
|
|
1517
|
+
function Ha(e, t) {
|
|
1518
|
+
let n = 0;
|
|
1519
|
+
function r(t, r, i) {
|
|
1520
|
+
let a = r.name.endsWith("[0]"), o = r.type, s = U[o];
|
|
1521
|
+
if (!s) throw Error(`unknown type: 0x${o.toString(16)}`);
|
|
1522
|
+
let c;
|
|
1523
|
+
if (s.bindPoint) {
|
|
1524
|
+
let t = n;
|
|
1525
|
+
n += r.size, c = a ? s.arraySetter(e, o, t, i, r.size) : s.setter(e, o, t, i, r.size);
|
|
1526
|
+
} else c = s.arraySetter && a ? s.arraySetter(e, i) : s.setter(e, i);
|
|
1527
|
+
return c.location = i, c;
|
|
1528
|
+
}
|
|
1529
|
+
let i = {}, a = {}, o = e.getProgramParameter(t, fi);
|
|
1530
|
+
for (let n = 0; n < o; ++n) {
|
|
1531
|
+
let o = e.getActiveUniform(t, n);
|
|
1532
|
+
if (Ra(o)) continue;
|
|
1533
|
+
let s = o.name;
|
|
1534
|
+
s.endsWith("[0]") && (s = s.substr(0, s.length - 3));
|
|
1535
|
+
let c = e.getUniformLocation(t, o.name);
|
|
1536
|
+
if (c) {
|
|
1537
|
+
let e = r(t, o, c);
|
|
1538
|
+
i[s] = e, Va(s, e, a, i);
|
|
1539
|
+
}
|
|
1540
|
+
}
|
|
1541
|
+
return i;
|
|
1542
|
+
}
|
|
1543
|
+
function Ua(e, t) {
|
|
1544
|
+
let n = {}, r = e.getProgramParameter(t, mi);
|
|
1545
|
+
for (let i = 0; i < r; ++i) {
|
|
1546
|
+
let r = e.getTransformFeedbackVarying(t, i);
|
|
1547
|
+
n[r.name] = {
|
|
1548
|
+
index: i,
|
|
1549
|
+
type: r.type,
|
|
1550
|
+
size: r.size
|
|
1551
|
+
};
|
|
1552
|
+
}
|
|
1553
|
+
return n;
|
|
1554
|
+
}
|
|
1555
|
+
function Wa(e, t) {
|
|
1556
|
+
let n = e.getProgramParameter(t, fi), r = [], i = [];
|
|
1557
|
+
for (let a = 0; a < n; ++a) {
|
|
1558
|
+
i.push(a), r.push({});
|
|
1559
|
+
let n = e.getActiveUniform(t, a);
|
|
1560
|
+
r[a].name = n.name;
|
|
1561
|
+
}
|
|
1562
|
+
[
|
|
1563
|
+
["UNIFORM_TYPE", "type"],
|
|
1564
|
+
["UNIFORM_SIZE", "size"],
|
|
1565
|
+
["UNIFORM_BLOCK_INDEX", "blockNdx"],
|
|
1566
|
+
["UNIFORM_OFFSET", "offset"]
|
|
1567
|
+
].forEach(function(n) {
|
|
1568
|
+
let a = n[0], o = n[1];
|
|
1569
|
+
e.getActiveUniforms(t, i, e[a]).forEach(function(e, t) {
|
|
1570
|
+
r[t][o] = e;
|
|
1571
|
+
});
|
|
1572
|
+
});
|
|
1573
|
+
let a = {}, o = e.getProgramParameter(t, hi);
|
|
1574
|
+
for (let n = 0; n < o; ++n) {
|
|
1575
|
+
let r = e.getActiveUniformBlockName(t, n), i = {
|
|
1576
|
+
index: e.getUniformBlockIndex(t, r),
|
|
1577
|
+
usedByVertexShader: e.getActiveUniformBlockParameter(t, n, gi),
|
|
1578
|
+
usedByFragmentShader: e.getActiveUniformBlockParameter(t, n, _i),
|
|
1579
|
+
size: e.getActiveUniformBlockParameter(t, n, vi),
|
|
1580
|
+
uniformIndices: e.getActiveUniformBlockParameter(t, n, yi)
|
|
1581
|
+
};
|
|
1582
|
+
i.used = i.usedByVertexShader || i.usedByFragmentShader, a[r] = i;
|
|
1583
|
+
}
|
|
1584
|
+
return {
|
|
1585
|
+
blockSpecs: a,
|
|
1586
|
+
uniformData: r
|
|
1587
|
+
};
|
|
1588
|
+
}
|
|
1589
|
+
var Ga = /\[\d+\]\.$/, Ka = (e, t) => ((e + (t - 1)) / t | 0) * t;
|
|
1590
|
+
function qa(e, t, n, r) {
|
|
1591
|
+
if (t || n) {
|
|
1592
|
+
r ||= 1;
|
|
1593
|
+
let t = e.length / 4;
|
|
1594
|
+
return function(n) {
|
|
1595
|
+
let i = 0, a = 0;
|
|
1596
|
+
for (let o = 0; o < t; ++o) {
|
|
1597
|
+
for (let t = 0; t < r; ++t) e[i++] = n[a++];
|
|
1598
|
+
i += 4 - r;
|
|
1599
|
+
}
|
|
1600
|
+
};
|
|
1601
|
+
} else return function(t) {
|
|
1602
|
+
t.length ? e.set(t) : e[0] = t;
|
|
1603
|
+
};
|
|
1604
|
+
}
|
|
1605
|
+
function Ja(e, t, n, r) {
|
|
1606
|
+
let i = n.blockSpecs, a = n.uniformData, o = i[r];
|
|
1607
|
+
if (!o) return oi("no uniform block object named:", r), {
|
|
1608
|
+
name: r,
|
|
1609
|
+
uniforms: {}
|
|
1610
|
+
};
|
|
1611
|
+
let s = new ArrayBuffer(o.size), c = e.createBuffer(), l = o.index;
|
|
1612
|
+
e.bindBuffer(di, c), e.uniformBlockBinding(t, o.index, l);
|
|
1613
|
+
let u = r + ".";
|
|
1614
|
+
Ga.test(u) && (u = u.replace(Ga, "."));
|
|
1615
|
+
let d = {}, f = {}, p = {};
|
|
1616
|
+
return o.uniformIndices.forEach(function(e) {
|
|
1617
|
+
let t = a[e], n = t.name;
|
|
1618
|
+
n.startsWith(u) && (n = n.substr(u.length));
|
|
1619
|
+
let r = n.endsWith("[0]");
|
|
1620
|
+
r && (n = n.substr(0, n.length - 3));
|
|
1621
|
+
let i = U[t.type], o = i.Type, c = r ? Ka(i.size, 16) * t.size : i.size * t.size, l = new o(s, t.offset, c / o.BYTES_PER_ELEMENT);
|
|
1622
|
+
d[n] = l;
|
|
1623
|
+
let m = qa(l, r, i.rows, i.cols);
|
|
1624
|
+
f[n] = m, Va(n, m, p, f);
|
|
1625
|
+
}), {
|
|
1626
|
+
name: r,
|
|
1627
|
+
array: s,
|
|
1628
|
+
asFloat: new Float32Array(s),
|
|
1629
|
+
buffer: c,
|
|
1630
|
+
uniforms: d,
|
|
1631
|
+
setters: f
|
|
1632
|
+
};
|
|
1633
|
+
}
|
|
1634
|
+
function Ya(e, t, n) {
|
|
1635
|
+
return Ja(e, t.program, t.uniformBlockSpec, n);
|
|
1636
|
+
}
|
|
1637
|
+
function Xa(e, t, n) {
|
|
1638
|
+
let r = (t.uniformBlockSpec || t).blockSpecs[n.name];
|
|
1639
|
+
if (r) {
|
|
1640
|
+
let t = r.index;
|
|
1641
|
+
return e.bindBufferRange(di, t, n.buffer, n.offset || 0, n.array.byteLength), !0;
|
|
1642
|
+
}
|
|
1643
|
+
return !1;
|
|
1644
|
+
}
|
|
1645
|
+
function Za(e, t, n) {
|
|
1646
|
+
Xa(e, t, n) && e.bufferData(di, n.array, ci);
|
|
1647
|
+
}
|
|
1648
|
+
function Qa(e, t) {
|
|
1649
|
+
let n = e.setters;
|
|
1650
|
+
for (let e in t) {
|
|
1651
|
+
let r = n[e];
|
|
1652
|
+
if (r) {
|
|
1653
|
+
let n = t[e];
|
|
1654
|
+
r(n);
|
|
1655
|
+
}
|
|
1656
|
+
}
|
|
1657
|
+
}
|
|
1658
|
+
function $a(e, t) {
|
|
1659
|
+
for (let n in t) {
|
|
1660
|
+
let r = e[n];
|
|
1661
|
+
typeof r == "function" ? r(t[n]) : $a(e[n], t[n]);
|
|
1662
|
+
}
|
|
1663
|
+
}
|
|
1664
|
+
function J(e, ...t) {
|
|
1665
|
+
let n = e.uniformSetters || e, r = t.length;
|
|
1666
|
+
for (let e = 0; e < r; ++e) {
|
|
1667
|
+
let r = t[e];
|
|
1668
|
+
if (Array.isArray(r)) {
|
|
1669
|
+
let e = r.length;
|
|
1670
|
+
for (let t = 0; t < e; ++t) J(n, r[t]);
|
|
1671
|
+
} else for (let e in r) {
|
|
1672
|
+
let t = n[e];
|
|
1673
|
+
t && t(r[e]);
|
|
1674
|
+
}
|
|
1675
|
+
}
|
|
1676
|
+
}
|
|
1677
|
+
function eo(e, t) {
|
|
1678
|
+
let n = {}, r = e.getProgramParameter(t, pi);
|
|
1679
|
+
for (let i = 0; i < r; ++i) {
|
|
1680
|
+
let r = e.getActiveAttrib(t, i);
|
|
1681
|
+
if (Ra(r)) continue;
|
|
1682
|
+
let a = e.getAttribLocation(t, r.name), o = q[r.type], s = o.setter(e, a, o);
|
|
1683
|
+
s.location = a, n[r.name] = s;
|
|
1684
|
+
}
|
|
1685
|
+
return n;
|
|
1686
|
+
}
|
|
1687
|
+
function to(e, t) {
|
|
1688
|
+
for (let n in t) {
|
|
1689
|
+
let r = e[n];
|
|
1690
|
+
r && r(t[n]);
|
|
1691
|
+
}
|
|
1692
|
+
}
|
|
1693
|
+
function Y(e, t, n) {
|
|
1694
|
+
n.vertexArrayObject ? e.bindVertexArray(n.vertexArrayObject) : (to(t.attribSetters || t, n.attribs), n.indices && e.bindBuffer(ui, n.indices));
|
|
1695
|
+
}
|
|
1696
|
+
function no(e, t) {
|
|
1697
|
+
let n = {
|
|
1698
|
+
program: t,
|
|
1699
|
+
uniformSetters: Ha(e, t),
|
|
1700
|
+
attribSetters: eo(e, t)
|
|
1701
|
+
};
|
|
1702
|
+
return T(e) && (n.uniformBlockSpec = Wa(e, t), n.transformFeedbackInfo = Ua(e, t)), n;
|
|
1703
|
+
}
|
|
1704
|
+
var ro = 4, io = 5123;
|
|
1705
|
+
function ao(e, t, n, r, i, a) {
|
|
1706
|
+
n = n === void 0 ? ro : n;
|
|
1707
|
+
let o = t.indices, s = t.elementType, c = r === void 0 ? t.numElements : r;
|
|
1708
|
+
i = i === void 0 ? 0 : i, s || o ? a === void 0 ? e.drawElements(n, c, s === void 0 ? io : t.elementType, i) : e.drawElementsInstanced(n, c, s === void 0 ? io : t.elementType, i, a) : a === void 0 ? e.drawArrays(n, i, c) : e.drawArraysInstanced(n, i, c, a);
|
|
1709
|
+
}
|
|
1710
|
+
var oo = 36160, X = 36161, so = 3553, co = 5121, lo = 6402, uo = 6408, fo = 33190, po = 36012, mo = 35056, ho = 36013, go = 32854, _o = 32855, vo = 36194, yo = 33189, bo = 6401, xo = 36168, So = 34041, Co = 36064, wo = 36096, To = 36128, Eo = 33306, Do = 33071, Oo = 9729, ko = [{
|
|
1711
|
+
format: uo,
|
|
1712
|
+
type: co,
|
|
1713
|
+
min: Oo,
|
|
1714
|
+
wrap: Do
|
|
1715
|
+
}, { format: So }], Z = {};
|
|
1716
|
+
Z[So] = Eo, Z[bo] = To, Z[xo] = To, Z[lo] = wo, Z[yo] = wo, Z[fo] = wo, Z[po] = wo, Z[mo] = Eo, Z[ho] = Eo;
|
|
1717
|
+
function Ao(e, t) {
|
|
1718
|
+
return Z[e] || Z[t];
|
|
1719
|
+
}
|
|
1720
|
+
var Q = {};
|
|
1721
|
+
Q[go] = !0, Q[_o] = !0, Q[vo] = !0, Q[So] = !0, Q[yo] = !0, Q[bo] = !0, Q[xo] = !0;
|
|
1722
|
+
function jo(e) {
|
|
1723
|
+
return Q[e];
|
|
1724
|
+
}
|
|
1725
|
+
function Mo(e) {
|
|
1726
|
+
return e >= Co && e < 36096;
|
|
1727
|
+
}
|
|
1728
|
+
function No(e, t, n, r) {
|
|
1729
|
+
let i = oo, a = e.createFramebuffer();
|
|
1730
|
+
e.bindFramebuffer(i, a), n ||= e.drawingBufferWidth, r ||= e.drawingBufferHeight, t ||= ko;
|
|
1731
|
+
let o = [], s = {
|
|
1732
|
+
framebuffer: a,
|
|
1733
|
+
attachments: [],
|
|
1734
|
+
width: n,
|
|
1735
|
+
height: r
|
|
1736
|
+
};
|
|
1737
|
+
return t.forEach(function(t, a) {
|
|
1738
|
+
let c = t.attachment, l = t.samples, u = t.format, d = t.attachmentPoint || Ao(u, t.internalFormat);
|
|
1739
|
+
if (d ||= Co + a, Mo(d) && o.push(d), !c) if (l !== void 0 || jo(u)) c = e.createRenderbuffer(), e.bindRenderbuffer(X, c), l > 1 ? e.renderbufferStorageMultisample(X, l, u, n, r) : e.renderbufferStorage(X, u, n, r);
|
|
1740
|
+
else {
|
|
1741
|
+
let i = Object.assign({}, t);
|
|
1742
|
+
i.width = n, i.height = r, i.auto === void 0 && (i.auto = !1, i.min = i.min || i.minMag || Oo, i.mag = i.mag || i.minMag || Oo, i.wrapS = i.wrapS || i.wrap || Do, i.wrapT = i.wrapT || i.wrap || Do), c = ii(e, i);
|
|
1743
|
+
}
|
|
1744
|
+
if (et(e, c)) e.framebufferRenderbuffer(i, d, X, c);
|
|
1745
|
+
else if (tt(e, c)) t.layer === void 0 ? e.framebufferTexture2D(i, d, t.target || so, c, t.level || 0) : e.framebufferTextureLayer(i, d, c, t.level || 0, t.layer);
|
|
1746
|
+
else throw Error("unknown attachment type");
|
|
1747
|
+
s.attachments.push(c);
|
|
1748
|
+
}), e.drawBuffers && e.drawBuffers(o), s;
|
|
1749
|
+
}
|
|
1750
|
+
function Po(e, t, n, r, i) {
|
|
1751
|
+
r ||= e.drawingBufferWidth, i ||= e.drawingBufferHeight, t.width = r, t.height = i, n ||= ko, n.forEach(function(n, a) {
|
|
1752
|
+
let o = t.attachments[a], s = n.format, c = n.samples;
|
|
1753
|
+
if (c !== void 0 || et(e, o)) e.bindRenderbuffer(X, o), c > 1 ? e.renderbufferStorageMultisample(X, c, s, r, i) : e.renderbufferStorage(X, s, r, i);
|
|
1754
|
+
else if (tt(e, o)) ai(e, o, n, r, i);
|
|
1755
|
+
else throw Error("unknown attachment type");
|
|
1756
|
+
});
|
|
1757
|
+
}
|
|
1758
|
+
function Fo(e, t, n) {
|
|
1759
|
+
let r = e.createVertexArray();
|
|
1760
|
+
return e.bindVertexArray(r), t.length || (t = [t]), t.forEach(function(t) {
|
|
1761
|
+
Y(e, t, n);
|
|
1762
|
+
}), e.bindVertexArray(null), {
|
|
1763
|
+
numElements: n.numElements,
|
|
1764
|
+
elementType: n.elementType,
|
|
1765
|
+
vertexArrayObject: r
|
|
1766
|
+
};
|
|
1767
|
+
}
|
|
1768
|
+
var Io = { addExtensionsToContext: !0 }, Lo = /^(.*?)_/;
|
|
1769
|
+
function Ro(e, t) {
|
|
1770
|
+
jt(e, 0);
|
|
1771
|
+
let n = e.getExtension(t);
|
|
1772
|
+
if (n) {
|
|
1773
|
+
let r = {}, i = Lo.exec(t)[1], a = "_" + i;
|
|
1774
|
+
for (let t in n) {
|
|
1775
|
+
let o = n[t], s = typeof o == "function", c = s ? i : a, l = t;
|
|
1776
|
+
t.endsWith(c) && (l = t.substring(0, t.length - c.length)), e[l] === void 0 ? s ? e[l] = function(e) {
|
|
1777
|
+
return function() {
|
|
1778
|
+
return e.apply(n, arguments);
|
|
1779
|
+
};
|
|
1780
|
+
}(o) : (e[l] = o, r[l] = o) : !s && e[l] !== o && Qe(l, e[l], o, t);
|
|
1781
|
+
}
|
|
1782
|
+
r.constructor = { name: n.constructor.name }, jt(r, 0);
|
|
1783
|
+
}
|
|
1784
|
+
return n;
|
|
1785
|
+
}
|
|
1786
|
+
var zo = [
|
|
1787
|
+
"ANGLE_instanced_arrays",
|
|
1788
|
+
"EXT_blend_minmax",
|
|
1789
|
+
"EXT_color_buffer_float",
|
|
1790
|
+
"EXT_color_buffer_half_float",
|
|
1791
|
+
"EXT_disjoint_timer_query",
|
|
1792
|
+
"EXT_disjoint_timer_query_webgl2",
|
|
1793
|
+
"EXT_frag_depth",
|
|
1794
|
+
"EXT_sRGB",
|
|
1795
|
+
"EXT_shader_texture_lod",
|
|
1796
|
+
"EXT_texture_filter_anisotropic",
|
|
1797
|
+
"OES_element_index_uint",
|
|
1798
|
+
"OES_standard_derivatives",
|
|
1799
|
+
"OES_texture_float",
|
|
1800
|
+
"OES_texture_float_linear",
|
|
1801
|
+
"OES_texture_half_float",
|
|
1802
|
+
"OES_texture_half_float_linear",
|
|
1803
|
+
"OES_vertex_array_object",
|
|
1804
|
+
"WEBGL_color_buffer_float",
|
|
1805
|
+
"WEBGL_compressed_texture_atc",
|
|
1806
|
+
"WEBGL_compressed_texture_etc1",
|
|
1807
|
+
"WEBGL_compressed_texture_pvrtc",
|
|
1808
|
+
"WEBGL_compressed_texture_s3tc",
|
|
1809
|
+
"WEBGL_compressed_texture_s3tc_srgb",
|
|
1810
|
+
"WEBGL_depth_texture",
|
|
1811
|
+
"WEBGL_draw_buffers"
|
|
1812
|
+
];
|
|
1813
|
+
function Bo(e) {
|
|
1814
|
+
for (let t = 0; t < zo.length; ++t) Ro(e, zo[t]);
|
|
1815
|
+
}
|
|
1816
|
+
function Vo(e, t) {
|
|
1817
|
+
let n = [
|
|
1818
|
+
"webgl2",
|
|
1819
|
+
"webgl",
|
|
1820
|
+
"experimental-webgl"
|
|
1821
|
+
], r = null;
|
|
1822
|
+
for (let i = 0; i < n.length; ++i) if (r = e.getContext(n[i], t), r) {
|
|
1823
|
+
Io.addExtensionsToContext && Bo(r);
|
|
1824
|
+
break;
|
|
1825
|
+
}
|
|
1826
|
+
return r;
|
|
1827
|
+
}
|
|
1828
|
+
function Ho(e, t) {
|
|
1829
|
+
return Vo(e, t);
|
|
1830
|
+
}
|
|
1831
|
+
//#endregion
|
|
1832
|
+
//#region ../core/src/rendering/webgl/gl/colorUtils.js
|
|
1833
|
+
function Uo(e, n, r, i, a = !1) {
|
|
1834
|
+
let o = c(e) ? e : e.name, s = !c(e) && e.extent || [0, 1];
|
|
1835
|
+
if (r === void 0 && !c(e) && (r = e.count), o) {
|
|
1836
|
+
let e = le(o);
|
|
1837
|
+
if (t(e)) {
|
|
1838
|
+
let t = qo(e, {
|
|
1839
|
+
extent: s,
|
|
1840
|
+
count: r,
|
|
1841
|
+
reverse: a
|
|
1842
|
+
});
|
|
1843
|
+
return Vs(n, {
|
|
1844
|
+
minMag: n.LINEAR,
|
|
1845
|
+
format: n.RGB,
|
|
1846
|
+
height: 1,
|
|
1847
|
+
wrap: n.CLAMP_TO_EDGE
|
|
1848
|
+
}, t, i);
|
|
1849
|
+
} else if (u(e)) return Ko(a ? Array.from(e).reverse() : e, n, r, i);
|
|
1850
|
+
else throw Error("Unknown scheme: " + o);
|
|
1851
|
+
}
|
|
1852
|
+
}
|
|
1853
|
+
function Wo(e, t = "rgb", n, r) {
|
|
1854
|
+
let i = qo(de(e, c(t) ? t : t.type, c(t) ? void 0 : t.gamma));
|
|
1855
|
+
return Vs(n, {
|
|
1856
|
+
minMag: n.LINEAR,
|
|
1857
|
+
format: n.RGB,
|
|
1858
|
+
height: 1,
|
|
1859
|
+
wrap: n.CLAMP_TO_EDGE
|
|
1860
|
+
}, i, r);
|
|
1861
|
+
}
|
|
1862
|
+
function Go(e, t, n, r) {
|
|
1863
|
+
let i = Math.max(e.length, n || 0), a = new Float32Array(i);
|
|
1864
|
+
for (let t = 0; t < i; t++) a[t] = e[t % e.length];
|
|
1865
|
+
return Vs(t, {
|
|
1866
|
+
minMag: t.NEAREST,
|
|
1867
|
+
format: t.RED,
|
|
1868
|
+
internalFormat: t.R32F,
|
|
1869
|
+
height: 1
|
|
1870
|
+
}, a, r);
|
|
1871
|
+
}
|
|
1872
|
+
function Ko(e, t, n, r) {
|
|
1873
|
+
let i = Jo(e, n);
|
|
1874
|
+
return Vs(t, {
|
|
1875
|
+
minMag: t.NEAREST,
|
|
1876
|
+
format: t.RGB,
|
|
1877
|
+
height: 1
|
|
1878
|
+
}, i, r);
|
|
1879
|
+
}
|
|
1880
|
+
function qo(e, { extent: t = [0, 1], reverse: n = !1, count: r = 256 } = {}) {
|
|
1881
|
+
let i = t[0], o = a(t) - i, s = h(r).map((e) => e / (r - 1)).map((e) => i + e / o).map(e);
|
|
1882
|
+
return n && s.reverse(), Jo(s);
|
|
1883
|
+
}
|
|
1884
|
+
function Jo(e, t) {
|
|
1885
|
+
let n = Math.max(e.length, t || 0), r = new Uint8Array(n * 3);
|
|
1886
|
+
for (let t = 0; t < n; t++) {
|
|
1887
|
+
let n = e[t % e.length], i = ce(n);
|
|
1888
|
+
if (!i) throw Error(`Invalid color "${n}" in the scheme ${JSON.stringify(e)}!`);
|
|
1889
|
+
let a = i.rgb();
|
|
1890
|
+
r[t * 3 + 0] = a.r, r[t * 3 + 1] = a.g, r[t * 3 + 2] = a.b;
|
|
1891
|
+
}
|
|
1892
|
+
return r;
|
|
1893
|
+
}
|
|
1894
|
+
function Yo(e) {
|
|
1895
|
+
let t = ce(e).rgb();
|
|
1896
|
+
return [
|
|
1897
|
+
t.r,
|
|
1898
|
+
t.g,
|
|
1899
|
+
t.b
|
|
1900
|
+
].map((e) => e / 255);
|
|
1901
|
+
}
|
|
1902
|
+
//#endregion
|
|
1903
|
+
//#region ../core/src/rendering/webgl/gl/glslScaleGenerator.js
|
|
1904
|
+
var Xo = "attr_", Zo = "uDomain_", Qo = "range_", $o = "accessor_", es = "scale_", ts = "getScaled_", ns = "uRangeTexture_", rs = "uParam_", is = "checkSelection_";
|
|
1905
|
+
function as(e) {
|
|
1906
|
+
let t = e.match(/^(?:(\w+)-)?(\w+)$/);
|
|
1907
|
+
if (!t) throw Error("Not a scale type: " + e);
|
|
1908
|
+
return {
|
|
1909
|
+
family: t[1] || "continuous",
|
|
1910
|
+
transform: t[2]
|
|
1911
|
+
};
|
|
1912
|
+
}
|
|
1913
|
+
function os(e) {
|
|
1914
|
+
return e.type === "quantize" ? e.thresholds() : e.domain();
|
|
1915
|
+
}
|
|
1916
|
+
function ss(e) {
|
|
1917
|
+
return e.type === "quantize" ? e.range().length : e.type === "threshold" ? e.domain().length + 1 : e.domain().length;
|
|
1918
|
+
}
|
|
1919
|
+
function cs(e, t) {
|
|
1920
|
+
return `${$o}${e}_${t}`;
|
|
1921
|
+
}
|
|
1922
|
+
function ls(t, n, r) {
|
|
1923
|
+
let i;
|
|
1924
|
+
if (ae(t)) i = $(d(t)(r));
|
|
1925
|
+
else if (c(r)) if (e(t)) i = vs(r);
|
|
1926
|
+
else throw Error(`String values are not supported on the "${t}" channel: ${r}`);
|
|
1927
|
+
else if (ee(r)) i = $(+!!r);
|
|
1928
|
+
else if (r === null) if (e(t)) i = $([
|
|
1929
|
+
0,
|
|
1930
|
+
0,
|
|
1931
|
+
0
|
|
1932
|
+
]);
|
|
1933
|
+
else throw Error(`null value is not supported on the "${t}" chanel.`);
|
|
1934
|
+
else i = $(r);
|
|
1935
|
+
let a = cs(t, n);
|
|
1936
|
+
return {
|
|
1937
|
+
channel: t,
|
|
1938
|
+
accessorGlsl: `
|
|
1939
|
+
${i.type} ${a}() {
|
|
1940
|
+
// Constant value
|
|
1941
|
+
return ${i};
|
|
1942
|
+
}`,
|
|
1943
|
+
accessorFunctionName: a
|
|
1944
|
+
};
|
|
1945
|
+
}
|
|
1946
|
+
function us(t, n) {
|
|
1947
|
+
let r = "float", i = (e) => e;
|
|
1948
|
+
e(t) ? (r = "vec3", i = (e) => Yo(e)) : ae(t) && (i = d(t));
|
|
1949
|
+
let a = `u${Os(t)}_${n}`, o = ` // Dynamic value\n uniform ${r} ${a};`, s = cs(t, n);
|
|
1950
|
+
return {
|
|
1951
|
+
channel: t,
|
|
1952
|
+
uniformName: a,
|
|
1953
|
+
uniformGlsl: o,
|
|
1954
|
+
accessorGlsl: `
|
|
1955
|
+
${r} ${s}() {
|
|
1956
|
+
// Dynamic value
|
|
1957
|
+
return ${a};
|
|
1958
|
+
}`,
|
|
1959
|
+
accessorFunctionName: s,
|
|
1960
|
+
adjuster: i
|
|
1961
|
+
};
|
|
1962
|
+
}
|
|
1963
|
+
function ds(e, t, n, r = [e]) {
|
|
1964
|
+
let { attributeType: i } = xs(t, e), a = Ds(r), o = `in highp ${i} ${a};`, s = cs(e, n);
|
|
1965
|
+
return {
|
|
1966
|
+
channel: e,
|
|
1967
|
+
attributeName: a,
|
|
1968
|
+
attributeGlsl: o,
|
|
1969
|
+
accessorGlsl: `
|
|
1970
|
+
${i} ${s}() {
|
|
1971
|
+
return ${a};
|
|
1972
|
+
}`,
|
|
1973
|
+
accessorFunctionName: s
|
|
1974
|
+
};
|
|
1975
|
+
}
|
|
1976
|
+
function fs(e, t, n) {
|
|
1977
|
+
let { attributeType: r } = xs(t, e), i = Ds(e), a = ` uniform highp ${r} ${i};`, o = cs(e, n);
|
|
1978
|
+
return {
|
|
1979
|
+
channel: e,
|
|
1980
|
+
uniformName: i,
|
|
1981
|
+
uniformGlsl: a,
|
|
1982
|
+
accessorGlsl: `
|
|
1983
|
+
${r} ${o}() {
|
|
1984
|
+
return ${i};
|
|
1985
|
+
}`,
|
|
1986
|
+
accessorFunctionName: o
|
|
1987
|
+
};
|
|
1988
|
+
}
|
|
1989
|
+
function ps(t, n, r) {
|
|
1990
|
+
n ??= he();
|
|
1991
|
+
let a = i(t), o = Zo + a, s = Qo + a, { hp: c, attributeType: l } = xs(n, t), u = n.domain ? S(n.type) ? os(n).length : n.domain().length : void 0, d, f = [];
|
|
1992
|
+
f.push(""), f.push("/".repeat(70)), f.push(`// Channel: ${t}`), f.push("");
|
|
1993
|
+
let { transform: p } = as(n.type), m = (e, ...t) => bs.apply(null, [
|
|
1994
|
+
e,
|
|
1995
|
+
"value",
|
|
1996
|
+
...t
|
|
1997
|
+
]), h;
|
|
1998
|
+
switch (p) {
|
|
1999
|
+
case "linear":
|
|
2000
|
+
h = m("scaleLinear", "domain", s);
|
|
2001
|
+
break;
|
|
2002
|
+
case "log":
|
|
2003
|
+
h = m("scaleLog", "domain", s, n.base());
|
|
2004
|
+
break;
|
|
2005
|
+
case "symlog":
|
|
2006
|
+
h = m("scaleSymlog", "domain", s, n.constant());
|
|
2007
|
+
break;
|
|
2008
|
+
case "pow":
|
|
2009
|
+
case "sqrt":
|
|
2010
|
+
h = m("scalePow", "domain", s, n.exponent());
|
|
2011
|
+
break;
|
|
2012
|
+
case "index":
|
|
2013
|
+
case "locus":
|
|
2014
|
+
h = m("scaleBandHp", "domain", s, n.paddingInner(), n.paddingOuter(), n.align(), r.band ?? .5);
|
|
2015
|
+
break;
|
|
2016
|
+
case "point":
|
|
2017
|
+
case "band":
|
|
2018
|
+
h = m("scaleBand", "domain", s, n.paddingInner(), n.paddingOuter(), n.align(), r.band ?? .5);
|
|
2019
|
+
break;
|
|
2020
|
+
case "ordinal":
|
|
2021
|
+
case "null":
|
|
2022
|
+
case "identity":
|
|
2023
|
+
h = m("scaleIdentity");
|
|
2024
|
+
break;
|
|
2025
|
+
case "threshold":
|
|
2026
|
+
case "quantize": break;
|
|
2027
|
+
default: throw Error(`Unsupported scale type: ${n.type}! ${t}: ${JSON.stringify(r)}`);
|
|
2028
|
+
}
|
|
2029
|
+
let g = ks(n, t), _;
|
|
2030
|
+
if (g && t == a) {
|
|
2031
|
+
let e = n.props.range ?? [];
|
|
2032
|
+
if (x(e) || e.some(x)) {
|
|
2033
|
+
if (g.length < 1 || g.length > 4) throw Error(`A range with ExprRefs must have 1-4 elements, not ${g.length}! Range: ${JSON.stringify(g)}`);
|
|
2034
|
+
_ = ` uniform ${gs(g.length)} ${s};`;
|
|
2035
|
+
} else if (g.length && g.every(v)) {
|
|
2036
|
+
let e = ys(g);
|
|
2037
|
+
f.push(`const ${e.type} ${s} = ${e};`);
|
|
2038
|
+
}
|
|
2039
|
+
}
|
|
2040
|
+
let ee = _s(t), y;
|
|
2041
|
+
if (e(t)) {
|
|
2042
|
+
let e = ns + a;
|
|
2043
|
+
if (t == a && f.push(`uniform sampler2D ${e};`), C(n.type)) y = `getInterpolatedColor(${e}, transformed)`;
|
|
2044
|
+
else if (pe(n.type) || S(n.type)) y = `getDiscreteColor(${e}, int(transformed))`;
|
|
2045
|
+
else throw Error("Problem with color scale!");
|
|
2046
|
+
} else if (n.type === "ordinal" || S(n.type)) {
|
|
2047
|
+
let e = ns + a;
|
|
2048
|
+
t == a && f.push(`uniform sampler2D ${e};`), y = `getDiscreteColor(${e}, int(transformed)).r`;
|
|
2049
|
+
}
|
|
2050
|
+
let b = [], te = C(n.type) && u > 2, ne = S(n.type) || te;
|
|
2051
|
+
if (b.push("int slot = 0;"), ne) {
|
|
2052
|
+
let e = o;
|
|
2053
|
+
b.push(te ? `while (slot < ${e}.length() - 2 && value >= ${e}[slot + 1]) { slot++; }` : `while (slot < ${e}.length() && value >= ${e}[slot]) { slot++; }`);
|
|
2054
|
+
}
|
|
2055
|
+
let re = C(n.type) || S(n.type) || ["band", "point"].includes(n.type);
|
|
2056
|
+
if (h) {
|
|
2057
|
+
let e = o;
|
|
2058
|
+
re && (c ? b.push(`vec3 domain = ${e};`) : b.push(`vec2 domain = vec2(${e}[slot], ${e}[slot + 1]);`)), b.push(`float transformed = ${h};`), te && b.push(`transformed = (float(slot) + transformed) / (float(${e}.length() - 1));`);
|
|
2059
|
+
} else b.push("float transformed = float(slot);");
|
|
2060
|
+
"clamp" in n && n.clamp() && b.push(`transformed = clampToRange(transformed, ${ys(g)});`), b.push(`return ${y ?? "transformed"};`), f.push(`
|
|
2061
|
+
${ee} ${es}${t}(${l} value) {
|
|
2062
|
+
${b.map((e) => ` ${e}\n`).join("")}
|
|
2063
|
+
}`);
|
|
2064
|
+
let ie = f.join("\n");
|
|
2065
|
+
if (re && t == a) {
|
|
2066
|
+
let e = C(n.type) || S(n.type) ? u : 2;
|
|
2067
|
+
d = c ? ` highp vec3 ${o};` : ` mediump float ${o}[${e}];`;
|
|
2068
|
+
}
|
|
2069
|
+
return {
|
|
2070
|
+
glsl: ie,
|
|
2071
|
+
domainUniformName: o,
|
|
2072
|
+
domainUniform: d,
|
|
2073
|
+
rangeUniformName: s,
|
|
2074
|
+
rangeUniform: _
|
|
2075
|
+
};
|
|
2076
|
+
}
|
|
2077
|
+
function ms(e, t) {
|
|
2078
|
+
let n = _s(e), r = [], i = [];
|
|
2079
|
+
for (let n = 0; n < t.length; n++) {
|
|
2080
|
+
let { accessor: a, predicate: o } = t[n], s = cs(e, n), { param: c, empty: l } = o;
|
|
2081
|
+
r.push(c ? `${is}${c}(${!!l})` : null), i.push(a.scaleChannel ? `return ${es}${e}(${s}());` : `return ${s}();`);
|
|
2082
|
+
}
|
|
2083
|
+
return `${n} ${ts}${e}() {
|
|
2084
|
+
${As(r, i)}
|
|
2085
|
+
}
|
|
2086
|
+
|
|
2087
|
+
#define ${e}_DEFINED`;
|
|
2088
|
+
}
|
|
2089
|
+
function hs(e) {
|
|
2090
|
+
if (!v(e)) throw Error(`Not a number: ${e}`);
|
|
2091
|
+
if (e == Infinity) return "3.402823466e+38";
|
|
2092
|
+
if (e == -Infinity) return "-3.402823466e+38";
|
|
2093
|
+
{
|
|
2094
|
+
let t = `${e}`;
|
|
2095
|
+
return /^(-)?\d+$/.test(t) && (t += ".0"), t;
|
|
2096
|
+
}
|
|
2097
|
+
}
|
|
2098
|
+
function $(e) {
|
|
2099
|
+
typeof e == "number" && (e = [e]);
|
|
2100
|
+
let t = e.length;
|
|
2101
|
+
if (t < 1 || t > 4) throw Error("Invalid number of components: " + t);
|
|
2102
|
+
let n = gs(t), r = `${n}(${e.map(hs).join(", ")})`;
|
|
2103
|
+
return Object.assign(r, {
|
|
2104
|
+
type: n,
|
|
2105
|
+
numComponents: t
|
|
2106
|
+
});
|
|
2107
|
+
}
|
|
2108
|
+
function gs(e) {
|
|
2109
|
+
switch (e) {
|
|
2110
|
+
case 1: return "float";
|
|
2111
|
+
case 2: return "vec2";
|
|
2112
|
+
case 3: return "vec3";
|
|
2113
|
+
case 4: return "vec4";
|
|
2114
|
+
default: throw Error("Invalid number of components: " + e);
|
|
2115
|
+
}
|
|
2116
|
+
}
|
|
2117
|
+
function _s(t) {
|
|
2118
|
+
return e(t) ? "vec3" : t == "uniqueId" ? "uint" : "float";
|
|
2119
|
+
}
|
|
2120
|
+
function vs(e) {
|
|
2121
|
+
return $(Yo(e));
|
|
2122
|
+
}
|
|
2123
|
+
function ys(e) {
|
|
2124
|
+
return $([e[0], a(e)]);
|
|
2125
|
+
}
|
|
2126
|
+
function bs(e, ...t) {
|
|
2127
|
+
let n = [];
|
|
2128
|
+
for (let e of t) v(e) ? n.push(hs(e)) : u(e) ? n.push($(e)) : n.push(e);
|
|
2129
|
+
return `${e}(${n.join(", ")})`;
|
|
2130
|
+
}
|
|
2131
|
+
function xs(e, t) {
|
|
2132
|
+
let n = e && pe(e.type), r = e && _e(e.type), i = r && me(e.domain()), a = i ? {
|
|
2133
|
+
attributeType: "uvec2",
|
|
2134
|
+
arrayConstructor: Uint32Array
|
|
2135
|
+
} : r ? {
|
|
2136
|
+
attributeType: "uint",
|
|
2137
|
+
arrayConstructor: Uint32Array
|
|
2138
|
+
} : n ? {
|
|
2139
|
+
attributeType: "uint",
|
|
2140
|
+
arrayConstructor: Uint16Array
|
|
2141
|
+
} : t == "uniqueId" ? {
|
|
2142
|
+
attributeType: "uint",
|
|
2143
|
+
arrayConstructor: Uint32Array
|
|
2144
|
+
} : {
|
|
2145
|
+
attributeType: "float",
|
|
2146
|
+
arrayConstructor: Float32Array
|
|
2147
|
+
};
|
|
2148
|
+
return Object.assign(a, {
|
|
2149
|
+
numComponents: +(a.attributeType.match(/^(?:u)?vec([234])$/)?.[1] ?? 1),
|
|
2150
|
+
discrete: n,
|
|
2151
|
+
hp: r,
|
|
2152
|
+
largeHp: i
|
|
2153
|
+
});
|
|
2154
|
+
}
|
|
2155
|
+
var Ss = 2 ** 12;
|
|
2156
|
+
Ss - 1;
|
|
2157
|
+
function Cs(e, t = []) {
|
|
2158
|
+
let n = e % Ss;
|
|
2159
|
+
return t[0] = (e - n) / Ss, t[1] = n, t;
|
|
2160
|
+
}
|
|
2161
|
+
function ws(e) {
|
|
2162
|
+
let t = e % Ss;
|
|
2163
|
+
return [e - t, t];
|
|
2164
|
+
}
|
|
2165
|
+
function Ts(e) {
|
|
2166
|
+
return [...ws(e[0]), e[1] - e[0]];
|
|
2167
|
+
}
|
|
2168
|
+
function Es(e) {
|
|
2169
|
+
let t = new ue([], JSON.stringify);
|
|
2170
|
+
for (let [n, r] of Object.entries(e)) {
|
|
2171
|
+
let e = r.channelDef;
|
|
2172
|
+
if (re(e)) {
|
|
2173
|
+
let i = [e.field, r.scale ? (C(r.scale.type) || S(r.scale.type)) ?? !1 : !1];
|
|
2174
|
+
t.set(i, [...t.get(i) ?? [], n]);
|
|
2175
|
+
}
|
|
2176
|
+
}
|
|
2177
|
+
return t;
|
|
2178
|
+
}
|
|
2179
|
+
function Ds(e) {
|
|
2180
|
+
return Xo + s(e).toSorted().join("_");
|
|
2181
|
+
}
|
|
2182
|
+
function Os(e) {
|
|
2183
|
+
return e[0].toUpperCase() + e.slice(1);
|
|
2184
|
+
}
|
|
2185
|
+
var ks = (t, n) => fe(t.type) || C(t.type) && e(n) ? [0, 1] : t.range ? t.range() : void 0;
|
|
2186
|
+
function As(e, t) {
|
|
2187
|
+
if (e.length != t.length) throw Error("Unequal array lengths");
|
|
2188
|
+
let n = e.length;
|
|
2189
|
+
if (n == 0) return "";
|
|
2190
|
+
if (n == 1 && e[0] == null) return t[0];
|
|
2191
|
+
let r = [];
|
|
2192
|
+
for (let i = 0; i < n; i++) {
|
|
2193
|
+
let a = e[i], o = i == 0 ? `if (${a})` : a == null && i == n - 1 ? "else" : `else if (${a})`;
|
|
2194
|
+
r.push(` ${o} {
|
|
2195
|
+
${t[i]}
|
|
2196
|
+
}`);
|
|
2197
|
+
}
|
|
2198
|
+
return r.join("\n");
|
|
2199
|
+
}
|
|
2200
|
+
//#endregion
|
|
2201
|
+
//#region ../core/src/rendering/webgl/gl/hashTable.js
|
|
2202
|
+
var js = 4294967295, Ms = 4294967295;
|
|
2203
|
+
function Ns(e) {
|
|
2204
|
+
let t = e >>> 0;
|
|
2205
|
+
return t ^= t >>> 16, t = Math.imul(t, 2146121005), t ^= t >>> 15, t = Math.imul(t, 2221713035), t ^= t >>> 16, t >>> 0;
|
|
2206
|
+
}
|
|
2207
|
+
function Ps(e, t = {}) {
|
|
2208
|
+
let n = Array.from(e, (e) => Is(e, "key")), r = n.length, i = t.maxLoadFactor ?? .6;
|
|
2209
|
+
if (!(i > 0 && i < 1)) throw Error("maxLoadFactor must be between 0 and 1.");
|
|
2210
|
+
let a = t.capacity ?? Ls(Math.ceil(r / i));
|
|
2211
|
+
if (!Number.isSafeInteger(a) || a < 1) throw Error("capacity must be a positive power of two.");
|
|
2212
|
+
if (a & a - 1) throw Error("capacity must be a power of two.");
|
|
2213
|
+
let o = new Uint32Array(a);
|
|
2214
|
+
o.fill(js);
|
|
2215
|
+
let s = a - 1;
|
|
2216
|
+
for (let e of n) {
|
|
2217
|
+
if (e === 4294967295) throw Error("Hash table keys must not equal the empty sentinel (0xffffffff).");
|
|
2218
|
+
let t = Ns(e) & s, n = !1;
|
|
2219
|
+
for (let r = 0; r < a; r += 1) {
|
|
2220
|
+
let r = o[t];
|
|
2221
|
+
if (r === 4294967295 || r === e) {
|
|
2222
|
+
o[t] = e, n = !0;
|
|
2223
|
+
break;
|
|
2224
|
+
}
|
|
2225
|
+
t = t + 1 & s;
|
|
2226
|
+
}
|
|
2227
|
+
if (!n) throw Error("Hash table insertion failed. Increase capacity or lower load factor.");
|
|
2228
|
+
}
|
|
2229
|
+
return {
|
|
2230
|
+
table: o,
|
|
2231
|
+
capacity: a,
|
|
2232
|
+
size: r
|
|
2233
|
+
};
|
|
2234
|
+
}
|
|
2235
|
+
function Fs(e, t) {
|
|
2236
|
+
if (!Number.isSafeInteger(e) || e < 1) throw Error("capacity must be a positive integer.");
|
|
2237
|
+
if (e & e - 1) throw Error("capacity must be a power of two.");
|
|
2238
|
+
if (!Number.isSafeInteger(t) || t < 1) throw Error("maxTextureSize must be a positive integer.");
|
|
2239
|
+
if (e > t * t) throw Error("Selection hash table exceeds maximum texture capacity.");
|
|
2240
|
+
let n = 1 << Math.floor(Math.log2(t)), r = Math.min(e, n), i = e / r;
|
|
2241
|
+
if (i > t) throw Error("Selection hash table dimensions exceed maximum texture size.");
|
|
2242
|
+
return {
|
|
2243
|
+
width: r,
|
|
2244
|
+
height: i
|
|
2245
|
+
};
|
|
2246
|
+
}
|
|
2247
|
+
function Is(e, t) {
|
|
2248
|
+
if (!Number.isSafeInteger(e) || e < 0 || e > Ms) throw Error(t + " must be a non-negative u32.");
|
|
2249
|
+
return e >>> 0;
|
|
2250
|
+
}
|
|
2251
|
+
function Ls(e) {
|
|
2252
|
+
let t = Math.max(1, e);
|
|
2253
|
+
return --t, t |= t >>> 1, t |= t >>> 2, t |= t >>> 4, t |= t >>> 8, t |= t >>> 16, t + 1;
|
|
2254
|
+
}
|
|
2255
|
+
//#endregion
|
|
2256
|
+
//#region ../core/src/rendering/webgl/gl/webGLHelper.js
|
|
2257
|
+
var Rs = class {
|
|
2258
|
+
#e = !1;
|
|
2259
|
+
#t = () => {};
|
|
2260
|
+
_ownedTextures = /* @__PURE__ */ new Set();
|
|
2261
|
+
_placementDisposers = /* @__PURE__ */ new Set();
|
|
2262
|
+
constructor(e, t, n = {}, r) {
|
|
2263
|
+
let i = t ?? (() => ({
|
|
2264
|
+
width: void 0,
|
|
2265
|
+
height: void 0
|
|
2266
|
+
}));
|
|
2267
|
+
this._canvasSizeHelper = void 0, this._appliedCanvasSize = void 0, this._onCanvasResize = r ?? (() => {}), this._shaderCache = /* @__PURE__ */ new Map(), this.rangeTextures = /* @__PURE__ */ new WeakMap(), this.placementTextures = /* @__PURE__ */ new WeakMap(), this.selectionTextures = /* @__PURE__ */ new WeakMap();
|
|
2268
|
+
let a = document.createElement("canvas"), o = Ho(a, {
|
|
2269
|
+
antialias: !0,
|
|
2270
|
+
depth: !1,
|
|
2271
|
+
premultipliedAlpha: !0,
|
|
2272
|
+
...n
|
|
2273
|
+
});
|
|
2274
|
+
if (!o) throw Error("Unable to initialize WebGL. Your browser or machine may not support it.");
|
|
2275
|
+
if (!T(o)) throw Error("Your web browser does not support WebGL 2.0. Chrome, Firefox, and Safari Tech Preview should work.");
|
|
2276
|
+
Bo(o);
|
|
2277
|
+
let s = o.getExtension("WEBGL_provoking_vertex");
|
|
2278
|
+
s && s.provokingVertexWEBGL(s.FIRST_VERTEX_CONVENTION_WEBGL), o.blendFunc(o.ONE, o.ONE_MINUS_SRC_ALPHA), this.canvas = a, this.gl = o, this._pickingAttachmentOptions = [{
|
|
2279
|
+
format: o.RGBA,
|
|
2280
|
+
type: o.UNSIGNED_BYTE,
|
|
2281
|
+
minMag: o.LINEAR,
|
|
2282
|
+
wrap: o.CLAMP_TO_EDGE
|
|
2283
|
+
}], this._pickingBufferInfo = No(o, this._pickingAttachmentOptions), o.bindFramebuffer(o.FRAMEBUFFER, null), e.appendChild(a);
|
|
2284
|
+
try {
|
|
2285
|
+
this._canvasSizeHelper = new Ee(e, a, i, () => {
|
|
2286
|
+
this.adjustGl() && this._onCanvasResize();
|
|
2287
|
+
}), this.adjustGl();
|
|
2288
|
+
} catch (e) {
|
|
2289
|
+
throw this._canvasSizeHelper?.finalize(), a.remove(), e;
|
|
2290
|
+
}
|
|
2291
|
+
}
|
|
2292
|
+
getPlacementTexture(e) {
|
|
2293
|
+
let t = e.getSnapshot(), n = this.placementTextures.get(e);
|
|
2294
|
+
if (n?.geometryRevision === t.geometryRevision) return n.texture;
|
|
2295
|
+
let r = n?.data.length === t.rectangles.length / 2 ? n.data : new Float32Array(t.rectangles.length / 2);
|
|
2296
|
+
for (let e = 0; e < t.rectangles.length / 4; e++) r[e * 2] = t.rectangles[e * 4 + 1], r[e * 2 + 1] = t.rectangles[e * 4 + 3];
|
|
2297
|
+
let i = Vs(this.gl, {
|
|
2298
|
+
internalFormat: this.gl.RG32F,
|
|
2299
|
+
format: this.gl.RG,
|
|
2300
|
+
height: 1
|
|
2301
|
+
}, r, n?.texture);
|
|
2302
|
+
if (this.placementTextures.set(e, {
|
|
2303
|
+
texture: i,
|
|
2304
|
+
geometryRevision: t.geometryRevision,
|
|
2305
|
+
data: r
|
|
2306
|
+
}), this._ownedTextures.add(i), !n) {
|
|
2307
|
+
let t;
|
|
2308
|
+
t = e.onDispose(() => {
|
|
2309
|
+
this._placementDisposers.delete(t);
|
|
2310
|
+
let n = this.placementTextures.get(e);
|
|
2311
|
+
n && (this._ownedTextures.delete(n.texture) && this.gl.deleteTexture(n.texture), this.placementTextures.delete(e));
|
|
2312
|
+
}), this._placementDisposers.add(t);
|
|
2313
|
+
}
|
|
2314
|
+
return i;
|
|
2315
|
+
}
|
|
2316
|
+
invalidateSize() {
|
|
2317
|
+
return this._canvasSizeHelper.invalidate(), this.adjustGl();
|
|
2318
|
+
}
|
|
2319
|
+
compileShader(e, t) {
|
|
2320
|
+
u(t) && (t = t.join("\n\n"));
|
|
2321
|
+
let n = this.gl, r = t.replaceAll(/ {2,}|^\s*\/\/.*$/gm, ""), i = this._shaderCache.get(r);
|
|
2322
|
+
if (!i) {
|
|
2323
|
+
let a = [
|
|
2324
|
+
"#version 300 es",
|
|
2325
|
+
"precision mediump float;",
|
|
2326
|
+
t
|
|
2327
|
+
].join("\n\n");
|
|
2328
|
+
i = n.createShader(e), n.shaderSource(i, a), n.compileShader(i), this._shaderCache.set(r, i);
|
|
2329
|
+
}
|
|
2330
|
+
return i;
|
|
2331
|
+
}
|
|
2332
|
+
adjustGl() {
|
|
2333
|
+
let e = this.getLogicalCanvasSize(), t = this.getPhysicalCanvasSize(e);
|
|
2334
|
+
return this._appliedCanvasSize && this._appliedCanvasSize.logicalWidth == e.width && this._appliedCanvasSize.logicalHeight == e.height && this._appliedCanvasSize.physicalWidth == t.width && this._appliedCanvasSize.physicalHeight == t.height ? !1 : (this.canvas.style.width = `${e.width}px`, this.canvas.style.height = `${e.height}px`, this.canvas.width = t.width, this.canvas.height = t.height, Po(this.gl, this._pickingBufferInfo, this._pickingAttachmentOptions), this._appliedCanvasSize = {
|
|
2335
|
+
logicalWidth: e.width,
|
|
2336
|
+
logicalHeight: e.height,
|
|
2337
|
+
physicalWidth: t.width,
|
|
2338
|
+
physicalHeight: t.height
|
|
2339
|
+
}, !0);
|
|
2340
|
+
}
|
|
2341
|
+
finalize() {
|
|
2342
|
+
if (!this.#e) {
|
|
2343
|
+
this.#e = !0, this.#t();
|
|
2344
|
+
for (let e of this._placementDisposers) e();
|
|
2345
|
+
this._placementDisposers.clear();
|
|
2346
|
+
for (let e of this._ownedTextures) this.gl.deleteTexture(e);
|
|
2347
|
+
this._ownedTextures.clear();
|
|
2348
|
+
for (let e of this._shaderCache.values()) this.gl.deleteShader(e);
|
|
2349
|
+
this._shaderCache.clear();
|
|
2350
|
+
for (let e of this._pickingBufferInfo.attachments) this.gl.deleteTexture(e);
|
|
2351
|
+
this.gl.deleteFramebuffer(this._pickingBufferInfo.framebuffer), this._canvasSizeHelper.finalize(), this.canvas.remove();
|
|
2352
|
+
}
|
|
2353
|
+
}
|
|
2354
|
+
setResourceFinalizer(e) {
|
|
2355
|
+
this.#t = e;
|
|
2356
|
+
}
|
|
2357
|
+
getPhysicalCanvasSize(e) {
|
|
2358
|
+
return this._canvasSizeHelper.getPhysicalCanvasSize(e);
|
|
2359
|
+
}
|
|
2360
|
+
getDevicePixelRatio(e) {
|
|
2361
|
+
return this._canvasSizeHelper.getDevicePixelRatio(e);
|
|
2362
|
+
}
|
|
2363
|
+
getLogicalCanvasSize() {
|
|
2364
|
+
return this._canvasSizeHelper.getLogicalCanvasSize();
|
|
2365
|
+
}
|
|
2366
|
+
createRangeTexture(t, n = !1) {
|
|
2367
|
+
let r = this.rangeTextures.get(t.getScale());
|
|
2368
|
+
if (!n && r) return;
|
|
2369
|
+
function i(e, t) {
|
|
2370
|
+
return pe(t.type) ? t.domain().length : t.type == "threshold" || t.type == "quantize" ? ss(t) : t.type == "quantile" ? e ?? 4 : e;
|
|
2371
|
+
}
|
|
2372
|
+
let a = t.channel;
|
|
2373
|
+
if (e(a)) {
|
|
2374
|
+
let e = t.getScale(), n = e.props, a = e.range(), o;
|
|
2375
|
+
if (n.scheme) if (pe(e.type) || S(e.type)) o = Ko(a, this.gl, ss(e), r);
|
|
2376
|
+
else {
|
|
2377
|
+
let t = c(n.scheme) ? void 0 : n.scheme.count;
|
|
2378
|
+
t = i(t, e), o = Uo(n.scheme, this.gl, t, r, !!n.reverse);
|
|
2379
|
+
}
|
|
2380
|
+
else o = fe(e.type) || C(e.type) && a.length > 1 ? Wo(a, n.interpolate, this.gl, r) : Ko(a, this.gl, S(e.type) ? ss(e) : e.domain().length, r);
|
|
2381
|
+
this.rangeTextures.set(e, o), this._ownedTextures.add(o);
|
|
2382
|
+
} else {
|
|
2383
|
+
let e = t.getScale();
|
|
2384
|
+
if (e.type === "ordinal" || S(e.type)) {
|
|
2385
|
+
let t = ae(a) ? d(a) : (e) => e, n = Go(e.range().map(t), this.gl, S(e.type) ? ss(e) : e.domain().length, r);
|
|
2386
|
+
this.rangeTextures.set(e, n), this._ownedTextures.add(n);
|
|
2387
|
+
}
|
|
2388
|
+
}
|
|
2389
|
+
}
|
|
2390
|
+
createSelectionTexture(e, t = !0) {
|
|
2391
|
+
if (!n(e)) throw Error("Not a multi-point selection, cannot create texture");
|
|
2392
|
+
let { table: r, capacity: i } = Ps(e.data.keys()), { width: a, height: o } = Fs(i, this.gl.getParameter(this.gl.MAX_TEXTURE_SIZE)), s = this.selectionTextures.get(e), c = this.gl, l = Vs(this.gl, {
|
|
2393
|
+
auto: !1,
|
|
2394
|
+
level: 0,
|
|
2395
|
+
min: c.NEAREST,
|
|
2396
|
+
mag: c.NEAREST,
|
|
2397
|
+
format: c.RED_INTEGER,
|
|
2398
|
+
internalFormat: c.R32UI,
|
|
2399
|
+
width: a,
|
|
2400
|
+
height: o
|
|
2401
|
+
}, r, t ? s : !1);
|
|
2402
|
+
c.bindTexture(c.TEXTURE_2D, l), c.texParameteri(c.TEXTURE_2D, c.TEXTURE_BASE_LEVEL, 0), c.texParameteri(c.TEXTURE_2D, c.TEXTURE_MAX_LEVEL, 0), c.bindTexture(c.TEXTURE_2D, null), this.selectionTextures.set(e, l), this._ownedTextures.add(l);
|
|
2403
|
+
}
|
|
2404
|
+
};
|
|
2405
|
+
function zs(e, t = "", n = 0) {
|
|
2406
|
+
let r = [...t.matchAll(/ERROR:\s*\d+:(\d+)/gi)], i = new Map(r.map((e, n) => {
|
|
2407
|
+
let i = parseInt(e[1]), a = r[n + 1], o = a ? a.index : t.length, s = t.substring(e.index, o);
|
|
2408
|
+
return [i - 1, s];
|
|
2409
|
+
}));
|
|
2410
|
+
return e.split("\n").map((e, t) => {
|
|
2411
|
+
let r = i.get(t);
|
|
2412
|
+
return `${t + 1 + n}: ${e}${r ? `\n\n^^^ ${r}` : ""}`;
|
|
2413
|
+
}).join("\n");
|
|
2414
|
+
}
|
|
2415
|
+
function Bs(e, t, n) {
|
|
2416
|
+
let r = e.createProgram();
|
|
2417
|
+
e.attachShader(r, t), e.attachShader(r, n), e.linkProgram(r);
|
|
2418
|
+
function i() {
|
|
2419
|
+
let i, a;
|
|
2420
|
+
if (!e.getProgramParameter(r, e.LINK_STATUS)) {
|
|
2421
|
+
i = e.getProgramInfoLog(r);
|
|
2422
|
+
for (let r of [t, n]) e.getShaderParameter(r, e.COMPILE_STATUS) || (i = e.getShaderInfoLog(r), a = zs(e.getShaderSource(r), i, 0) + `\nError compiling: ${i}`, e.deleteShader(r));
|
|
2423
|
+
e.deleteProgram(r);
|
|
2424
|
+
}
|
|
2425
|
+
if (i) return {
|
|
2426
|
+
message: i,
|
|
2427
|
+
detail: a
|
|
2428
|
+
};
|
|
2429
|
+
}
|
|
2430
|
+
return {
|
|
2431
|
+
program: r,
|
|
2432
|
+
getProgramErrors: i
|
|
2433
|
+
};
|
|
2434
|
+
}
|
|
2435
|
+
function Vs(e, t, n, r) {
|
|
2436
|
+
return r ? ni(e, r, n, t) : r = ii(e, {
|
|
2437
|
+
...t,
|
|
2438
|
+
src: n
|
|
2439
|
+
}), r;
|
|
2440
|
+
}
|
|
2441
|
+
function Hs(e, t, n, r) {
|
|
2442
|
+
let { height: i, framebuffer: a } = t, o = /* @__PURE__ */ new Uint8Array(4);
|
|
2443
|
+
return e.bindFramebuffer(e.FRAMEBUFFER, a), e.readPixels(n, i - r - 1, 1, 1, e.RGBA, e.UNSIGNED_BYTE, o), e.bindFramebuffer(e.FRAMEBUFFER, null), o;
|
|
2444
|
+
}
|
|
2445
|
+
//#endregion
|
|
2446
|
+
//#region ../core/src/rendering/webgl/bufferedViewRenderingContext.js
|
|
2447
|
+
var Us = class extends we {
|
|
2448
|
+
#e = [
|
|
2449
|
+
0,
|
|
2450
|
+
0,
|
|
2451
|
+
0,
|
|
2452
|
+
0
|
|
2453
|
+
];
|
|
2454
|
+
#t;
|
|
2455
|
+
#n = [];
|
|
2456
|
+
#r;
|
|
2457
|
+
#i;
|
|
2458
|
+
#a;
|
|
2459
|
+
#o = /* @__PURE__ */ new Set();
|
|
2460
|
+
#s = /* @__PURE__ */ new Set();
|
|
2461
|
+
#c;
|
|
2462
|
+
#l = void 0;
|
|
2463
|
+
#u = 1;
|
|
2464
|
+
#d = {
|
|
2465
|
+
width: 0,
|
|
2466
|
+
height: 0
|
|
2467
|
+
};
|
|
2468
|
+
#f;
|
|
2469
|
+
constructor(e, t) {
|
|
2470
|
+
if (super(e), this.#i = t.webGLHelper, this.#a = t.markAdapter, this.#r = t.framebufferInfo, this.#u = t.devicePixelRatio, this.#d = t.canvasSize, this.#c = t.markPredicate ?? (() => !0), this.#f = t.pixelOffset, t.clearColor) {
|
|
2471
|
+
let e = ce(t.clearColor).rgb();
|
|
2472
|
+
this.#e = [
|
|
2473
|
+
e.r / 255,
|
|
2474
|
+
e.g / 255,
|
|
2475
|
+
e.b / 255,
|
|
2476
|
+
e.opacity
|
|
2477
|
+
];
|
|
2478
|
+
}
|
|
2479
|
+
}
|
|
2480
|
+
getDevicePixelRatio() {
|
|
2481
|
+
return this.#u;
|
|
2482
|
+
}
|
|
2483
|
+
pushView(e, t) {
|
|
2484
|
+
this.#s.add(e), this.#l = t;
|
|
2485
|
+
}
|
|
2486
|
+
renderMark(e, t) {
|
|
2487
|
+
if (!this.#c(e) || this.globalOptions.picking && !e.isPickingParticipant()) return;
|
|
2488
|
+
let n = ne(t);
|
|
2489
|
+
this.#n.push({
|
|
2490
|
+
mark: e,
|
|
2491
|
+
options: t,
|
|
2492
|
+
coords: this.#l,
|
|
2493
|
+
placement: t.placement,
|
|
2494
|
+
clip: ie(n, e.properties.clip, this.#l),
|
|
2495
|
+
cullClip: n
|
|
2496
|
+
});
|
|
2497
|
+
}
|
|
2498
|
+
render() {
|
|
2499
|
+
if (this.finish(), this.#a.synchronize(this.#o), this.#t.length == 0) return;
|
|
2500
|
+
let e = this.#i.gl, t = this.#r;
|
|
2501
|
+
t ? (e.bindFramebuffer(e.FRAMEBUFFER, t.framebuffer), e.viewport(0, 0, t.width, t.height)) : e.viewport(0, 0, e.drawingBufferWidth, e.drawingBufferHeight), e.disable(e.SCISSOR_TEST), e.clearColor(...this.#e), e.clear(e.COLOR_BUFFER_BIT);
|
|
2502
|
+
for (let e of this.#s) e.onBeforeRender();
|
|
2503
|
+
for (let e of this.#t) e();
|
|
2504
|
+
this.#r && e.bindFramebuffer(e.FRAMEBUFFER, null);
|
|
2505
|
+
}
|
|
2506
|
+
finish() {
|
|
2507
|
+
if (!this.#t) {
|
|
2508
|
+
let e = this.#n.map((e) => e.mark);
|
|
2509
|
+
this.#a.prepareMarks(e), this.#a.synchronize(e.map((e) => this.#a.getMarkEntry(e)).filter((e) => e)), this.#p();
|
|
2510
|
+
}
|
|
2511
|
+
}
|
|
2512
|
+
#p() {
|
|
2513
|
+
this.#t = [];
|
|
2514
|
+
let e = !0, t = !0, n = (t) => () => {
|
|
2515
|
+
e && t();
|
|
2516
|
+
}, r = (n) => () => {
|
|
2517
|
+
e && t && n();
|
|
2518
|
+
}, i = ge(this.#n.reverse(), (e) => e.mark);
|
|
2519
|
+
for (let [a, o] of [...i.entries()].reverse()) {
|
|
2520
|
+
let i = this.#a.getMarkEntry(a);
|
|
2521
|
+
if (!i) continue;
|
|
2522
|
+
let s = i.graphics;
|
|
2523
|
+
if (!this.#a.isEntryDrawable(i)) continue;
|
|
2524
|
+
this.#o.add(i);
|
|
2525
|
+
let c = o.map((e) => ({
|
|
2526
|
+
...e,
|
|
2527
|
+
callback: s.render(e.options)
|
|
2528
|
+
})).filter((e) => e.callback);
|
|
2529
|
+
if (c.length == 0) continue;
|
|
2530
|
+
this.#t.push(() => {
|
|
2531
|
+
e = this.#a.isEntryDrawable(i) && a.unitView.getEffectiveOpacity() > 0;
|
|
2532
|
+
});
|
|
2533
|
+
let l = c[0].placement, u = l ? {
|
|
2534
|
+
...this.globalOptions,
|
|
2535
|
+
placement: l
|
|
2536
|
+
} : this.globalOptions;
|
|
2537
|
+
this.#t.push(...s.prepareRender(u).map((e) => n(e)));
|
|
2538
|
+
let d, f, p;
|
|
2539
|
+
for (let e of c) {
|
|
2540
|
+
let i = e.coords;
|
|
2541
|
+
(!i.equals(d) || !b(e.clip, f) || !b(e.cullClip, p)) && this.#t.push(n(() => {
|
|
2542
|
+
t = s.setViewport(this.#d, this.#u, i, e.clip, e.cullClip, this.#f);
|
|
2543
|
+
})), this.#t.push(r(e.callback)), d = e.coords, f = e.clip, p = e.cullClip;
|
|
2544
|
+
}
|
|
2545
|
+
}
|
|
2546
|
+
}
|
|
2547
|
+
}, Ws = class extends we {
|
|
2548
|
+
constructor(...e) {
|
|
2549
|
+
super({}), this.contexts = e;
|
|
2550
|
+
}
|
|
2551
|
+
beginSampleFacetBatch() {
|
|
2552
|
+
for (let e of this.contexts) e.beginSampleFacetBatch();
|
|
2553
|
+
}
|
|
2554
|
+
endSampleFacetBatch() {
|
|
2555
|
+
for (let e of this.contexts) e.endSampleFacetBatch();
|
|
2556
|
+
}
|
|
2557
|
+
pushView(e, t) {
|
|
2558
|
+
for (let n of this.contexts) n.pushView(e, t);
|
|
2559
|
+
}
|
|
2560
|
+
popView(e) {
|
|
2561
|
+
for (let t of this.contexts) t.popView(e);
|
|
2562
|
+
}
|
|
2563
|
+
renderMark(e, t) {
|
|
2564
|
+
for (let n of this.contexts) n.renderMark(e, t);
|
|
2565
|
+
}
|
|
2566
|
+
}, Gs = class {
|
|
2567
|
+
#e;
|
|
2568
|
+
#t;
|
|
2569
|
+
#n;
|
|
2570
|
+
#r;
|
|
2571
|
+
#i;
|
|
2572
|
+
#a;
|
|
2573
|
+
#o;
|
|
2574
|
+
#s;
|
|
2575
|
+
#c;
|
|
2576
|
+
constructor({ viewRoot: e, glHelper: t, markAdapter: n, getBackground: r, broadcast: i, onLayoutComputed: a }) {
|
|
2577
|
+
this.#e = e, this.#t = t, this.#n = n, this.#r = r, this.#i = i, this.#a = a, this.#o = void 0, this.#s = void 0, this.#c = !1;
|
|
2578
|
+
}
|
|
2579
|
+
computeLayout() {
|
|
2580
|
+
if (!this.#e) return;
|
|
2581
|
+
this.#i("layout"), this.#t.invalidateSize();
|
|
2582
|
+
let e = 5;
|
|
2583
|
+
for (;;) {
|
|
2584
|
+
let t = this.#l();
|
|
2585
|
+
if (!t) return;
|
|
2586
|
+
if (!this.#t.invalidateSize()) {
|
|
2587
|
+
this.#u(t), this.#a(), this.#i("layoutComputed");
|
|
2588
|
+
return;
|
|
2589
|
+
}
|
|
2590
|
+
if (e--, e == 0) throw Error("Layout did not settle: canvas size kept changing.");
|
|
2591
|
+
}
|
|
2592
|
+
}
|
|
2593
|
+
#l() {
|
|
2594
|
+
let e = this.#e, t = this.#t.getLogicalCanvasSize();
|
|
2595
|
+
if (isNaN(t.width) || isNaN(t.height)) return console.log(`NaN in canvas size: ${t.width}x${t.height}. Skipping computeLayout().`), !1;
|
|
2596
|
+
let n = this.#t.getDevicePixelRatio(t);
|
|
2597
|
+
return {
|
|
2598
|
+
layoutResult: Ce("layout", () => Te(e, xe.create(0, 0, t.width, t.height), { devicePixelRatio: n })),
|
|
2599
|
+
canvasSize: t,
|
|
2600
|
+
devicePixelRatio: n
|
|
2601
|
+
};
|
|
2602
|
+
}
|
|
2603
|
+
#u({ layoutResult: e, canvasSize: t, devicePixelRatio: n }) {
|
|
2604
|
+
let r = {
|
|
2605
|
+
webGLHelper: this.#t,
|
|
2606
|
+
markAdapter: this.#n,
|
|
2607
|
+
canvasSize: t,
|
|
2608
|
+
devicePixelRatio: n
|
|
2609
|
+
}, i = new Us({ picking: !1 }, {
|
|
2610
|
+
...r,
|
|
2611
|
+
clearColor: this.#r()
|
|
2612
|
+
}), a = new Us({ picking: !0 }, {
|
|
2613
|
+
...r,
|
|
2614
|
+
framebufferInfo: this.#t._pickingBufferInfo
|
|
2615
|
+
});
|
|
2616
|
+
Ce("layoutReplay", () => e.collectRenderCommands(new Ws(i, a))), i.finish(), a.finish(), this.#o = i, this.#s = a;
|
|
2617
|
+
}
|
|
2618
|
+
renderAll() {
|
|
2619
|
+
let e = Se();
|
|
2620
|
+
e?.beginFrame("webgl"), Ce("render", () => this.#o?.render()), this.#c = !0, e?.endFrame();
|
|
2621
|
+
}
|
|
2622
|
+
renderPickingFramebuffer() {
|
|
2623
|
+
if (!this.#c) return;
|
|
2624
|
+
let e = Se();
|
|
2625
|
+
e?.beginFrame("webgl", "picking"), Ce("picking", () => this.#s.render()), this.#c = !1, e?.endFrame();
|
|
2626
|
+
}
|
|
2627
|
+
};
|
|
2628
|
+
//#endregion
|
|
2629
|
+
//#region ../core/src/rendering/webgl/gl/framebufferReadback.js
|
|
2630
|
+
function Ks(e, t, n = {}) {
|
|
2631
|
+
let r = n.x ?? 0, i = n.y ?? 0, a = n.width ?? t.width, o = n.height ?? t.height;
|
|
2632
|
+
Zs(t, r, i, a, o);
|
|
2633
|
+
let s = new Uint8Array(a * o * 4);
|
|
2634
|
+
e.bindFramebuffer(e.FRAMEBUFFER, t.framebuffer);
|
|
2635
|
+
try {
|
|
2636
|
+
e.readPixels(r, t.height - i - o, a, o, e.RGBA, e.UNSIGNED_BYTE, s);
|
|
2637
|
+
} finally {
|
|
2638
|
+
e.bindFramebuffer(e.FRAMEBUFFER, null);
|
|
2639
|
+
}
|
|
2640
|
+
return {
|
|
2641
|
+
pixels: Xs(s, a, o, n.unpremultiplyAlpha ?? !1),
|
|
2642
|
+
width: a,
|
|
2643
|
+
height: o
|
|
2644
|
+
};
|
|
2645
|
+
}
|
|
2646
|
+
function qs(e, t, n = "image/png", r = {}) {
|
|
2647
|
+
return Ys(e, t, r).toDataURL(n);
|
|
2648
|
+
}
|
|
2649
|
+
function Js(e, t, n = "image/png", r = {}) {
|
|
2650
|
+
let i = Ys(e, t, r);
|
|
2651
|
+
return new Promise((e, t) => {
|
|
2652
|
+
i.toBlob((r) => {
|
|
2653
|
+
r ? e(r) : t(/* @__PURE__ */ Error(`Could not encode framebuffer as ${n}.`));
|
|
2654
|
+
}, n);
|
|
2655
|
+
});
|
|
2656
|
+
}
|
|
2657
|
+
function Ys(e, t, n) {
|
|
2658
|
+
let { pixels: r, width: i, height: a } = Ks(e, t, n), o = document.createElement("canvas");
|
|
2659
|
+
o.width = i, o.height = a;
|
|
2660
|
+
let s = o.getContext("2d"), c = s.createImageData(i, a);
|
|
2661
|
+
return c.data.set(r), s.putImageData(c, 0, 0), o;
|
|
2662
|
+
}
|
|
2663
|
+
function Xs(e, t, n, r) {
|
|
2664
|
+
let i = new Uint8ClampedArray(e.length), a = t * 4;
|
|
2665
|
+
for (let t = 0; t < n; t++) {
|
|
2666
|
+
let r = (n - t - 1) * a, o = t * a;
|
|
2667
|
+
i.set(e.subarray(r, r + a), o);
|
|
2668
|
+
}
|
|
2669
|
+
if (r) for (let e = 0; e < i.length; e += 4) {
|
|
2670
|
+
let t = i[e + 3];
|
|
2671
|
+
if (t == 0) i[e] = 0, i[e + 1] = 0, i[e + 2] = 0;
|
|
2672
|
+
else if (t < 255) {
|
|
2673
|
+
let n = 255 / t;
|
|
2674
|
+
i[e] = Math.round(i[e] * n), i[e + 1] = Math.round(i[e + 1] * n), i[e + 2] = Math.round(i[e + 2] * n);
|
|
2675
|
+
}
|
|
2676
|
+
}
|
|
2677
|
+
return i;
|
|
2678
|
+
}
|
|
2679
|
+
function Zs(e, t, n, r, i) {
|
|
2680
|
+
if (![
|
|
2681
|
+
t,
|
|
2682
|
+
n,
|
|
2683
|
+
r,
|
|
2684
|
+
i
|
|
2685
|
+
].every(Number.isInteger)) throw RangeError("Framebuffer readback bounds must be integers.");
|
|
2686
|
+
if (t < 0 || n < 0 || r <= 0 || i <= 0 || t + r > e.width || n + i > e.height) throw RangeError("Framebuffer readback bounds are out of range.");
|
|
2687
|
+
}
|
|
2688
|
+
//#endregion
|
|
2689
|
+
//#region ../core/src/rendering/webgl/canvasExport.js
|
|
2690
|
+
function Qs({ glHelper: e, markAdapter: t, viewRoot: n, logicalWidth: r, logicalHeight: i, devicePixelRatio: a, clearColor: o = "white" }) {
|
|
2691
|
+
let { gl: s, framebufferInfo: c } = ec({
|
|
2692
|
+
glHelper: e,
|
|
2693
|
+
markAdapter: t,
|
|
2694
|
+
viewRoot: n,
|
|
2695
|
+
logicalWidth: r,
|
|
2696
|
+
logicalHeight: i,
|
|
2697
|
+
pixelRatio: a,
|
|
2698
|
+
clearColor: o
|
|
2699
|
+
});
|
|
2700
|
+
try {
|
|
2701
|
+
return qs(s, c, "image/png");
|
|
2702
|
+
} finally {
|
|
2703
|
+
tc(s, c);
|
|
2704
|
+
}
|
|
2705
|
+
}
|
|
2706
|
+
async function $s({ glHelper: e, markAdapter: t, viewRoot: n, logicalWidth: r, logicalHeight: i, pixelRatio: a, clearColor: o = "white", mimeType: s = "image/png" }) {
|
|
2707
|
+
if (s != "image/png") throw Error(`Unsupported raster export MIME type: ${s}`);
|
|
2708
|
+
let { gl: c, framebufferInfo: l } = ec({
|
|
2709
|
+
glHelper: e,
|
|
2710
|
+
markAdapter: t,
|
|
2711
|
+
viewRoot: n,
|
|
2712
|
+
logicalWidth: r,
|
|
2713
|
+
logicalHeight: i,
|
|
2714
|
+
pixelRatio: a,
|
|
2715
|
+
clearColor: o
|
|
2716
|
+
});
|
|
2717
|
+
try {
|
|
2718
|
+
return await Js(c, l, s);
|
|
2719
|
+
} finally {
|
|
2720
|
+
tc(c, l);
|
|
2721
|
+
}
|
|
2722
|
+
}
|
|
2723
|
+
function ec({ glHelper: e, markAdapter: t, viewRoot: n, logicalWidth: r, logicalHeight: i, pixelRatio: a, clearColor: o }) {
|
|
2724
|
+
r ??= e.getLogicalCanvasSize().width, i ??= e.getLogicalCanvasSize().height, a ??= window.devicePixelRatio ?? 1;
|
|
2725
|
+
let s = e.gl, c = Math.floor(r * a), l = Math.floor(i * a), u = No(s, [{
|
|
2726
|
+
format: s.RGBA,
|
|
2727
|
+
type: s.UNSIGNED_BYTE,
|
|
2728
|
+
minMag: s.LINEAR,
|
|
2729
|
+
wrap: s.CLAMP_TO_EDGE
|
|
2730
|
+
}], c, l), d;
|
|
2731
|
+
try {
|
|
2732
|
+
d = No(s, [{
|
|
2733
|
+
format: s.RGBA8,
|
|
2734
|
+
samples: Math.min(4, s.getParameter(s.MAX_SAMPLES))
|
|
2735
|
+
}], c, l);
|
|
2736
|
+
let f = new Us({ picking: !1 }, {
|
|
2737
|
+
webGLHelper: e,
|
|
2738
|
+
markAdapter: t,
|
|
2739
|
+
canvasSize: {
|
|
2740
|
+
width: r,
|
|
2741
|
+
height: i
|
|
2742
|
+
},
|
|
2743
|
+
devicePixelRatio: a,
|
|
2744
|
+
clearColor: o,
|
|
2745
|
+
framebufferInfo: d
|
|
2746
|
+
});
|
|
2747
|
+
return Te(n, xe.create(0, 0, r, i), { devicePixelRatio: a }).collectRenderCommands(f), f.finish(), f.render(), s.disable(s.SCISSOR_TEST), s.bindFramebuffer(s.READ_FRAMEBUFFER, d.framebuffer), s.bindFramebuffer(s.DRAW_FRAMEBUFFER, u.framebuffer), s.blitFramebuffer(0, 0, c, l, 0, 0, c, l, s.COLOR_BUFFER_BIT, s.NEAREST), {
|
|
2748
|
+
gl: s,
|
|
2749
|
+
framebufferInfo: u
|
|
2750
|
+
};
|
|
2751
|
+
} catch (e) {
|
|
2752
|
+
throw tc(s, u), e;
|
|
2753
|
+
} finally {
|
|
2754
|
+
d && (s.deleteRenderbuffer(d.attachments[0]), s.deleteFramebuffer(d.framebuffer));
|
|
2755
|
+
}
|
|
2756
|
+
}
|
|
2757
|
+
function tc(e, t) {
|
|
2758
|
+
e.deleteTexture(t.attachments[0]), e.deleteFramebuffer(t.framebuffer);
|
|
2759
|
+
}
|
|
2760
|
+
//#endregion
|
|
2761
|
+
//#region ../core/src/rendering/webgl/marks/arrow.vertex.glsl
|
|
2762
|
+
var nc = "flat out lowp vec4 vFillColor;\nflat out lowp vec4 vStrokeColor;\nflat out float vHalfStrokeWidth;\nflat out float vArrowHalfLengthInPixels;\nflat out float vHeadHalfWidth;\nflat out float vStemHalfWidth;\nflat out float vHeadStrokeWidth;\nflat out float vRHeadSlope;\nflat out float vRHeadNotchSlope;\nflat out float vRStartNotchSlope;\nflat out float vHeadRepeatFootprintLength;\nflat out float vHeadSpacing;\nflat out float vDirection;\n\nout vec2 vPosInPixels;\n\n/** Position along the arrow centerline. */\nin float pos;\n\n/** Which side of the extruded strip: -0.5 or 0.5. */\nin float side;\n\nfloat resolveStemHalfWidth(float arrowSize) {\n if (uStem) {\n return arrowSize * 0.5;\n } else {\n // The negative sign hides stem geometry; the magnitude remains\n // available for open-head thickness.\n return -arrowSize * 0.5;\n }\n}\n\nfloat resolveHeadHalfWidth(float arrowSize) {\n float headWidth = uHeadWidth * arrowSize;\n return max(headWidth, 0.0) * 0.5;\n}\n\n// Width along the arrow axis needed by one repeated head, including stroke.\nfloat headRepeatFootprintLength(\n float halfWidth,\n float rHeadSlope,\n float headStrokeWidth,\n float halfStrokeWidth\n) {\n float headAxisLength = halfWidth * rHeadSlope;\n float headStrokeLength = headStrokeWidth / length(vec2(rHeadSlope, 1.0));\n return headAxisLength + headStrokeLength + halfStrokeWidth * 2.0;\n}\n\n// Distance from the head tip to its centerline notch/join point.\nfloat headNotchOffset(\n float headHalfWidth,\n float rHeadSlope,\n float rHeadNotchSlope,\n float headStrokeWidth\n) {\n if (headHalfWidth <= 0.0) {\n return 0.0;\n }\n\n float headAxisLength = headHalfWidth * rHeadSlope;\n vec2 topOuter = vec2(headAxisLength, headHalfWidth);\n vec2 normalOffset = headStrokeWidth\n * normalize(vec2(headHalfWidth, -headAxisLength));\n vec2 topInner = topOuter + normalOffset;\n return topInner.x - topInner.y * rHeadNotchSlope;\n}\n\n// Distance from the arrow tip to where the stem outer edge meets a filled\n// triangle head's notch edge. This is the effective occupied head length for\n// deciding when a short inside arrow needs to blunt its head angle.\nfloat triangleHeadStemJoinLength(\n float stemHalfWidth,\n float headHalfWidth,\n float rHeadSlope,\n float rHeadNotchSlope\n) {\n float clampedRHeadNotchSlope = min(rHeadNotchSlope, rHeadSlope);\n return headHalfWidth * rHeadSlope\n - (headHalfWidth - stemHalfWidth) * clampedRHeadNotchSlope;\n}\n\n// Blunt non-repeated heads toward 90 degrees to preserve visible stem length.\nfloat effectiveHeadSlope(\n float halfLength,\n float headHalfWidth,\n float stemHalfWidth,\n float configuredRHeadSlope,\n float configuredRHeadNotchSlope,\n bool headRepeat\n) {\n if (\n headRepeat ||\n stemHalfWidth < 0.0\n ) {\n return configuredRHeadSlope;\n }\n\n if (uHeadPlacement == HEAD_PLACEMENT_OUTSIDE) {\n if (!uStartNotch || stemHalfWidth <= 0.0) {\n return configuredRHeadSlope;\n }\n\n // Outside heads start at the encoded endpoint. The preserved length is\n // therefore the encoded arrow length minus the start notch depth.\n float maxStartNotchLength = max(\n halfLength * 2.0 - uMinStemLength,\n 0.0\n );\n return min(\n configuredRHeadSlope,\n maxStartNotchLength / stemHalfWidth\n );\n }\n\n if (uHeadShape != HEAD_SHAPE_TRIANGLE) {\n return configuredRHeadSlope;\n }\n\n float maxJoinLength = max(\n halfLength * 2.0 - uMinStemLength,\n 0.0\n );\n float configuredJoinLength = triangleHeadStemJoinLength(\n stemHalfWidth,\n headHalfWidth,\n configuredRHeadSlope,\n configuredRHeadNotchSlope\n );\n\n if (configuredJoinLength <= maxJoinLength) {\n return configuredRHeadSlope;\n }\n\n float boundaryJoinLength = stemHalfWidth * configuredRHeadNotchSlope;\n if (maxJoinLength < boundaryJoinLength) {\n return stemHalfWidth > 0.0\n ? clamp(maxJoinLength / stemHalfWidth, 0.0, configuredRHeadSlope)\n : 0.0;\n } else {\n return clamp(\n (\n maxJoinLength +\n (headHalfWidth - stemHalfWidth) * configuredRHeadNotchSlope\n ) / headHalfWidth,\n 0.0,\n configuredRHeadSlope\n );\n }\n}\n\n// Outside placement extends the vertex quad so the head can protrude past the\n// encoded interval while its notch/join point stays on the endpoint.\nfloat getOutsideHeadOffset(\n float headHalfWidth,\n float rHeadSlope,\n float rHeadNotchSlope,\n float headStrokeWidth\n) {\n if (uHeadPlacement != HEAD_PLACEMENT_OUTSIDE) {\n return 0.0;\n }\n\n return headNotchOffset(\n headHalfWidth,\n rHeadSlope,\n rHeadNotchSlope,\n headStrokeWidth\n );\n}\n\nvec2 getOutsideHeadExpansion(float outsideHeadOffset, float direction) {\n // Expansion is stored as negative/positive arrow-axis growth. In the\n // canonical reverse direction, the head is on the negative side.\n return direction == DIRECTION_REVERSE\n ? vec2(outsideHeadOffset, 0.0)\n : vec2(0.0, outsideHeadOffset);\n}\n\nvoid main(void) {\n vec2 a = applyOffset(\n applySampleFacet(vec2(getScaled_x(), getScaled_y())),\n vec2(getScaled_xOffset(), getScaled_yOffset())\n );\n vec2 b = applyOffset(\n applySampleFacet(vec2(getScaled_x2(), getScaled_y2())),\n vec2(getScaled_x2Offset(), getScaled_y2Offset())\n );\n float direction = getScaled_direction();\n\n vec2 segmentInPixels = (b - a) * uViewportSize;\n float segmentLength = length(segmentInPixels);\n if (segmentLength <= 0.0) {\n gl_Position = vec4(0.0, 0.0, 0.0, 1.0);\n return;\n }\n\n float strokeWidth = getScaled_strokeWidth();\n float strokeOpacity = getScaled_strokeOpacity() * uViewOpacity;\n vHalfStrokeWidth = strokeWidth / 2.0;\n\n float arrowSize = max(getScaled_size(), uMinSize);\n float headHalfWidth = resolveHeadHalfWidth(arrowSize);\n float stemHalfWidth = resolveStemHalfWidth(arrowSize);\n float physicalStemHalfWidth = abs(stemHalfWidth);\n float headStrokeWidth = uHeadShape == HEAD_SHAPE_OPEN\n ? physicalStemHalfWidth * 2.0\n : 0.0;\n float configuredRHeadSlope = 1.0 / uHeadSlope;\n float configuredRHeadNotchSlope = 1.0 / uHeadNotchSlope;\n float rHeadSlope = effectiveHeadSlope(\n segmentLength * 0.5,\n headHalfWidth,\n stemHalfWidth,\n configuredRHeadSlope,\n configuredRHeadNotchSlope,\n uHeadSpacing >= 0.0\n );\n float rHeadNotchSlope = uHeadShape == HEAD_SHAPE_OPEN\n ? rHeadSlope\n : min(configuredRHeadNotchSlope, rHeadSlope);\n\n // Grow only the head side of the vertex quad for outside placement.\n float outsideHeadOffset = getOutsideHeadOffset(\n headHalfWidth,\n rHeadSlope,\n rHeadNotchSlope,\n headStrokeWidth\n );\n vec2 outsideHeadExpansion = getOutsideHeadExpansion(\n outsideHeadOffset,\n direction\n );\n\n float aaPadding = 1.0 / uDevicePixelRatio;\n float stripHalfWidth = max(headHalfWidth, physicalStemHalfWidth)\n + vHalfStrokeWidth\n + aaPadding;\n\n float reverseExpansion = outsideHeadExpansion.x;\n float forwardExpansion = outsideHeadExpansion.y;\n float geometryStart = -segmentLength * 0.5 - reverseExpansion;\n float geometryEnd = segmentLength * 0.5 + forwardExpansion;\n float geometryCenter = (geometryStart + geometryEnd) * 0.5;\n float geometryHalfLength = (geometryEnd - geometryStart) * 0.5;\n\n // The SDF geometry still uses the encoded arrow length, but the vertex\n // strip needs room for stroke and antialiasing beyond both endpoints.\n float axisPadding = vHalfStrokeWidth + aaPadding;\n float drawStart = geometryStart - axisPadding;\n float drawEnd = geometryEnd + axisPadding;\n float localAxisPosition = mix(drawStart, drawEnd, pos);\n float localX = localAxisPosition - geometryCenter;\n float localY = side * stripHalfWidth * 2.0;\n\n vec2 tangentInPixels = segmentInPixels / segmentLength;\n vec2 normalInPixels = vec2(-tangentInPixels.y, tangentInPixels.x);\n vec2 segmentCenter = (a + b) * 0.5;\n vec2 p = segmentCenter\n + (tangentInPixels * localAxisPosition + normalInPixels * localY)\n / uViewportSize;\n\n vPosInPixels = vec2(localX, localY);\n vArrowHalfLengthInPixels = geometryHalfLength;\n\n // These flat varyings are per-arrow geometry constants used by the fragment\n // SDF. Keeping them here avoids repeating this math per fragment.\n vHeadHalfWidth = headHalfWidth;\n vStemHalfWidth = stemHalfWidth;\n vHeadStrokeWidth = headStrokeWidth;\n vRHeadSlope = rHeadSlope;\n vRHeadNotchSlope = rHeadNotchSlope;\n vRStartNotchSlope = uStartNotch ? vRHeadSlope : 0.0;\n vDirection = direction;\n vHeadRepeatFootprintLength = headRepeatFootprintLength(\n vHeadHalfWidth,\n vRHeadSlope,\n vHeadStrokeWidth,\n vHalfStrokeWidth\n );\n vHeadSpacing = uHeadSpacing >= 0.0 ? uHeadSpacing * arrowSize : -1.0;\n vStrokeColor = vec4(getScaled_stroke() * strokeOpacity, strokeOpacity);\n\n gl_Position = unitToNdc(p);\n\n float fillOpacity = getScaled_fillOpacity() * uViewOpacity;\n vFillColor = vec4(getScaled_fill() * fillOpacity, fillOpacity);\n\n setupPicking();\n}\n", rc = "in vec2 vPosInPixels;\n\nflat in lowp vec4 vFillColor;\nflat in lowp vec4 vStrokeColor;\nflat in float vHalfStrokeWidth;\nflat in float vArrowHalfLengthInPixels;\nflat in float vHeadHalfWidth;\nflat in float vStemHalfWidth;\nflat in float vHeadStrokeWidth;\nflat in float vRHeadSlope;\nflat in float vRHeadNotchSlope;\nflat in float vRStartNotchSlope;\nflat in float vHeadRepeatFootprintLength;\nflat in float vHeadSpacing;\nflat in float vDirection;\n\nout lowp vec4 fragColor;\n\nconst int N = 6;\nconst float FAR_OUTSIDE = 1e20;\n\n// Adapted from: https://iquilezles.org/articles/distfunctions2d/\nfloat sdPolygon(vec2[N] v, vec2 p) {\n float d = dot(p-v[0],p-v[0]);\n float s = 1.0;\n for( int i=0, j=N-1; i<N; j=i, i++ ) {\n vec2 e = v[j] - v[i];\n vec2 w = p - v[i];\n vec2 b = w - e*clamp( dot(w,e)/dot(e,e), 0.0, 1.0 );\n d = min( d, dot(b,b) );\n bvec3 c = bvec3(p.y>=v[i].y,p.y<v[j].y,e.x*w.y>e.y*w.x);\n if( all(c) || all(not(c)) ) s*=-1.0; \n }\n return s*sqrt(d);\n}\n\nfloat sdStem(\n vec2 p,\n float halfLength,\n float halfWidth,\n float rHeadSlope,\n float rStartNotchSlope\n) {\n if (halfWidth < 0.0) {\n return FAR_OUTSIDE;\n }\n\n float headSideLength = halfWidth * rHeadSlope;\n float startNotchLength = halfWidth * rStartNotchSlope;\n vec2 vertices[6] = vec2[6](\n vec2(-halfLength, 0.0),\n vec2(-halfLength + headSideLength, halfWidth),\n vec2(halfLength, halfWidth),\n vec2(halfLength - startNotchLength, 0.0),\n vec2(halfLength, -halfWidth),\n vec2(-halfLength + headSideLength, -halfWidth)\n );\n\n return sdPolygon(vertices, p);\n}\n\n// Inner corner of an open head, offset perpendicular to the outer edge.\nvec2 headInnerCorner(float halfWidth, float rHeadSlope, float headStrokeWidth) {\n float headAxisLength = halfWidth * rHeadSlope;\n vec2 topOuter = vec2(headAxisLength, halfWidth);\n vec2 normalOffset = headStrokeWidth\n * normalize(vec2(halfWidth, -headAxisLength));\n return topOuter + normalOffset;\n}\n\n// X coordinate where the arrowhead notch edge crosses the centerline.\nfloat headNotchX(\n float halfWidth,\n float rHeadSlope,\n float rHeadNotchSlope,\n float headStrokeWidth\n) {\n vec2 topInner = headInnerCorner(halfWidth, rHeadSlope, headStrokeWidth);\n return topInner.x - topInner.y * rHeadNotchSlope;\n}\n\nfloat sdArrowHead(\n vec2 p,\n float halfWidth,\n float rHeadSlope,\n float rHeadNotchSlope,\n float headStrokeWidth\n) {\n float headAxisLength = halfWidth * rHeadSlope;\n vec2 topOuter = vec2(headAxisLength, halfWidth);\n vec2 bottomOuter = vec2(headAxisLength, -halfWidth);\n vec2 topInner = headInnerCorner(halfWidth, rHeadSlope, headStrokeWidth);\n vec2 normalOffset = topInner - topOuter;\n vec2 bottomInner = bottomOuter + vec2(normalOffset.x, -normalOffset.y);\n float notchX = headNotchX(\n halfWidth,\n rHeadSlope,\n rHeadNotchSlope,\n headStrokeWidth\n );\n\n vec2 vertices[6] = vec2[6](\n vec2(0.0, 0.0),\n topOuter,\n topInner,\n vec2(notchX, 0.0),\n bottomInner,\n bottomOuter\n );\n\n return sdPolygon(vertices, p);\n}\n\nfloat repeat(float x, float spacing) {\n return x >= spacing ? x - floor(x / spacing) * spacing : x;\n}\n\nfloat sdArrow(vec2 arrowPos, float arrowHalfLength) {\n float stemDistance = sdStem(\n arrowPos,\n arrowHalfLength,\n vStemHalfWidth,\n vRHeadSlope,\n vRStartNotchSlope\n );\n\n bool headRepeat = vHeadSpacing >= 0.0;\n float spacing = headRepeat\n ? max(vHeadSpacing, vHeadRepeatFootprintLength)\n : 1.0 / 0.0;\n float distanceFromStart = arrowPos.x + arrowHalfLength;\n\n // Keep the stroked tip inside the repeated head's local window.\n float arrowHeadX = repeat(\n distanceFromStart + vHalfStrokeWidth,\n spacing\n ) - vHalfStrokeWidth;\n\n float headDistance = sdArrowHead(\n vec2(arrowHeadX, arrowPos.y),\n vHeadHalfWidth,\n vRHeadSlope,\n vRHeadNotchSlope,\n vHeadStrokeWidth\n );\n\n if (headRepeat) {\n // Cull heads that would be partially clipped.\n float headTipDistance = distanceFromStart - arrowHeadX;\n float headEndDistance = headTipDistance\n + vHeadRepeatFootprintLength\n - vHalfStrokeWidth;\n\n if (headTipDistance > 0.0 && headEndDistance > arrowHalfLength * 2.0) {\n headDistance = FAR_OUTSIDE;\n }\n }\n\n return min(stemDistance, headDistance);\n}\n\nvoid main(void) {\n vec2 arrowPos = vPosInPixels;\n if (vDirection == DIRECTION_FORWARD) {\n arrowPos.x = -arrowPos.x;\n }\n float d = sdArrow(arrowPos, vArrowHalfLengthInPixels);\n\n fragColor = distanceToColor(\n d,\n vFillColor,\n vStrokeColor,\n vec4(0.0),\n vHalfStrokeWidth\n );\n\n if (uPickingEnabled) {\n if (d < vHalfStrokeWidth) {\n fragColor = vPickingColor;\n }\n } else if (fragColor.a == 0.0) {\n discard;\n }\n}\n", ic = "layout(std140) uniform Mark {\n uniform int uHeadShape;\n\n uniform float uHeadSlope;\n uniform float uHeadNotchSlope;\n\n uniform float uMinSize;\n uniform float uHeadWidth;\n uniform bool uStartNotch;\n uniform float uMinStemLength;\n uniform float uHeadSpacing;\n uniform bool uStem;\n\n uniform int uHeadPlacement;\n\n#pragma markUniforms\n};\n\nconst float DIRECTION_FORWARD = 0.0;\nconst float DIRECTION_REVERSE = 1.0;\n\nconst int HEAD_SHAPE_TRIANGLE = 0;\nconst int HEAD_SHAPE_OPEN = 1;\n\nconst int HEAD_PLACEMENT_INSIDE = 0;\nconst int HEAD_PLACEMENT_OUTSIDE = 1;\n\n// Arrow space uses x for arrow length and y for width perpendicular to it.\n// Negative x points toward the arrowhead in the canonical \"reverse\" direction.\n", ac = 1e4, oc = class {
|
|
2763
|
+
#e = !1;
|
|
2764
|
+
constructor(e) {
|
|
2765
|
+
this.size = e, this.arrays = {}, this.pushers = [], this.dataUpdaters = [], this.vertexCount = 0;
|
|
2766
|
+
}
|
|
2767
|
+
configure() {
|
|
2768
|
+
if (this.#e) throw Error("Already configured!");
|
|
2769
|
+
this.#t(), this.#n(), this.#e = !0;
|
|
2770
|
+
}
|
|
2771
|
+
addConverter(e, t) {
|
|
2772
|
+
let n = this.createUpdater(e, t.numComponents || 1, t.targetArrayType ?? Float32Array, t.arrayReference), r = t.f;
|
|
2773
|
+
this.dataUpdaters.push((t.arrayReference, (e) => n(r(e))));
|
|
2774
|
+
}
|
|
2775
|
+
createUpdater(e, t, n = Float32Array, r = void 0) {
|
|
2776
|
+
if (!v(this.size)) throw Error("The number of vertices must be defined!");
|
|
2777
|
+
let i, a, o = 0, s = new n(this.size * t);
|
|
2778
|
+
if (this.arrays[e] = {
|
|
2779
|
+
data: s,
|
|
2780
|
+
numComponents: t
|
|
2781
|
+
}, t == 1) {
|
|
2782
|
+
let e = 0;
|
|
2783
|
+
i = () => {
|
|
2784
|
+
s[o++] = e;
|
|
2785
|
+
}, a = (t) => {
|
|
2786
|
+
e = +t;
|
|
2787
|
+
};
|
|
2788
|
+
} else {
|
|
2789
|
+
let e = r ?? [0], n = r ? (e) => {} : (t) => {
|
|
2790
|
+
e = t;
|
|
2791
|
+
};
|
|
2792
|
+
switch (t) {
|
|
2793
|
+
case 1: break;
|
|
2794
|
+
case 2:
|
|
2795
|
+
i = () => {
|
|
2796
|
+
s[o++] = e[0], s[o++] = e[1];
|
|
2797
|
+
}, a = n;
|
|
2798
|
+
break;
|
|
2799
|
+
case 3:
|
|
2800
|
+
i = () => {
|
|
2801
|
+
s[o++] = e[0], s[o++] = e[1], s[o++] = e[2];
|
|
2802
|
+
}, a = n;
|
|
2803
|
+
break;
|
|
2804
|
+
case 4:
|
|
2805
|
+
i = () => {
|
|
2806
|
+
s[o++] = e[0], s[o++] = e[1], s[o++] = e[2], s[o++] = e[3];
|
|
2807
|
+
}, a = n;
|
|
2808
|
+
break;
|
|
2809
|
+
default: throw Error("Invalid numComponents: " + t);
|
|
2810
|
+
}
|
|
2811
|
+
}
|
|
2812
|
+
return this.pushers.push(i), a;
|
|
2813
|
+
}
|
|
2814
|
+
pushAll() {
|
|
2815
|
+
throw Error("Call configure() first!");
|
|
2816
|
+
}
|
|
2817
|
+
updateFromDatum(e) {
|
|
2818
|
+
throw Error("Call configure() first!");
|
|
2819
|
+
}
|
|
2820
|
+
#t() {
|
|
2821
|
+
if (this.size > ac) {
|
|
2822
|
+
let e = this.pushers.map((e, t) => `const p${t} = that.pushers[${t}];`).join("\n"), t = this.pushers.map((e, t) => ` p${t}();`).join("\n");
|
|
2823
|
+
this.pushAll = Function("that", `${e}
|
|
2824
|
+
return function unrolledPushAll() {
|
|
2825
|
+
${t}
|
|
2826
|
+
that.vertexCount++;
|
|
2827
|
+
};`)(this);
|
|
2828
|
+
} else this.pushAll = () => {
|
|
2829
|
+
for (let e = 0; e < this.pushers.length; e++) this.pushers[e]();
|
|
2830
|
+
this.vertexCount++;
|
|
2831
|
+
};
|
|
2832
|
+
}
|
|
2833
|
+
#n() {
|
|
2834
|
+
if (this.size > ac) {
|
|
2835
|
+
let e = this.dataUpdaters.map((e, t) => `const u${t} = that.dataUpdaters[${t}];`).join("\n"), t = this.dataUpdaters.map((e, t) => ` u${t}(datum);`).join("\n");
|
|
2836
|
+
this.updateFromDatum = Function("that", "datum", `${e}
|
|
2837
|
+
return function unrolledUpdateFromDatum(datum) {
|
|
2838
|
+
${t}
|
|
2839
|
+
};`)(this);
|
|
2840
|
+
} else this.updateFromDatum = (e) => {
|
|
2841
|
+
for (let t = 0; t < this.dataUpdaters.length; t++) this.dataUpdaters[t](e);
|
|
2842
|
+
};
|
|
2843
|
+
}
|
|
2844
|
+
pushFromDatum(e) {
|
|
2845
|
+
this.updateFromDatum(e), this.pushAll();
|
|
2846
|
+
}
|
|
2847
|
+
}, sc = 2 ** 31 - 1, cc = -(2 ** 31);
|
|
2848
|
+
function lc(e, t, n, r = n, i = 0, a = i) {
|
|
2849
|
+
if (a <= i || t[1] <= t[0]) return;
|
|
2850
|
+
let o = n === r, s = Array(e);
|
|
2851
|
+
s.fill(sc);
|
|
2852
|
+
let c = Array(e);
|
|
2853
|
+
c.fill(0);
|
|
2854
|
+
let l = t[0], u = (t[1] - t[0]) / e, d = (t, n) => {
|
|
2855
|
+
let r = (t - l) / u, i = Math.floor(r);
|
|
2856
|
+
return se(n && i == r ? i - 1 : i, 0, e - 1);
|
|
2857
|
+
}, f = cc, p = -Infinity, m = !1, h = (e, t, n = [0, 0]) => {
|
|
2858
|
+
let r = d(e, !1), i = d(t, !0), a = s[r], o = Math.max(c[i], a);
|
|
2859
|
+
return n[0] = a, n[1] = o, n;
|
|
2860
|
+
};
|
|
2861
|
+
for (let e = i; e < a;) {
|
|
2862
|
+
let t = e, i = n(e), l = r(e);
|
|
2863
|
+
for (e += 1; e < a && n(e) === i && r(e) === l;) e += 1;
|
|
2864
|
+
if (t > f) f = t;
|
|
2865
|
+
else {
|
|
2866
|
+
m = !0;
|
|
2867
|
+
break;
|
|
2868
|
+
}
|
|
2869
|
+
if (i < p || !o && l < i) {
|
|
2870
|
+
m = !0;
|
|
2871
|
+
break;
|
|
2872
|
+
}
|
|
2873
|
+
p = i;
|
|
2874
|
+
let u = d(i, !1), h = o ? u : d(l, !0);
|
|
2875
|
+
for (let n = u; n <= h; n++) s[n] > t && (s[n] = t), c[n] < e && (c[n] = e);
|
|
2876
|
+
}
|
|
2877
|
+
if (m) return;
|
|
2878
|
+
for (let e = 1; e < c.length; e++) c[e] < c[e - 1] && (c[e] = c[e - 1]);
|
|
2879
|
+
let g = !0;
|
|
2880
|
+
for (let e = s.length - 1; e > 0; e--) g && s[e] == sc ? (s[e] = c[e], g = !1) : s[e - 1] > s[e] && (s[e - 1] = s[e]);
|
|
2881
|
+
return h;
|
|
2882
|
+
}
|
|
2883
|
+
//#endregion
|
|
2884
|
+
//#region ../core/src/rendering/webgl/gl/dataToVertices.js
|
|
2885
|
+
var uc = class {
|
|
2886
|
+
constructor({ encoders: e, numVertices: t = void 0, attributes: n = [] }) {
|
|
2887
|
+
this.encoders = e, this.variableEncoders = Object.fromEntries(Object.entries(e).filter(([e, t]) => n.includes(e) && t && !t.constant));
|
|
2888
|
+
let r = [...Es(e).entries()].filter(([e, t]) => e[1] && t.length > 1).map(([e, t]) => t);
|
|
2889
|
+
this.allocatedVertices = t, this.variableBuilder = new oc(t), this.attributeNames = {};
|
|
2890
|
+
for (let [e, t] of Object.entries(this.variableEncoders)) {
|
|
2891
|
+
let n = o(t);
|
|
2892
|
+
if (!n) continue;
|
|
2893
|
+
let i = r.find((t) => t.find((t) => t == e)), a = n.asNumberAccessor(), s = t.scale, { largeHp: c, arrayConstructor: l, discrete: u, numComponents: d } = xs(s, e), f = [0, 0], p;
|
|
2894
|
+
if (s && u) if ("props" in s && s.props.domainIndexer) p = s.props.domainIndexer;
|
|
2895
|
+
else if ("domain" in s) p = ve(), p.addAll(s.domain());
|
|
2896
|
+
else throw Error("Missing domain indexer for discrete scale.");
|
|
2897
|
+
let m = p ? (e) => p(n(e)) : c ? (e) => Cs(a(e), f) : a, h = Ds(i ?? e);
|
|
2898
|
+
for (let t of i ?? [e]) this.attributeNames[t] = h;
|
|
2899
|
+
i && e != i[0] || this.variableBuilder.addConverter(h, {
|
|
2900
|
+
f: m,
|
|
2901
|
+
numComponents: d,
|
|
2902
|
+
arrayReference: c ? f : void 0,
|
|
2903
|
+
targetArrayType: l
|
|
2904
|
+
});
|
|
2905
|
+
}
|
|
2906
|
+
let i = this.variableEncoders.x, a = this.variableEncoders.x2, s = this.encoders.x?.channelDef, c = i?.scale;
|
|
2907
|
+
if (s?.buildIndex && i && c && C(c.type)) {
|
|
2908
|
+
let e = this.attributeNames.x;
|
|
2909
|
+
if (!e) throw Error("Missing x attribute for x indexing.");
|
|
2910
|
+
let t = a?.scale && C(a.scale.type) ? this.attributeNames.x2 ?? e : e;
|
|
2911
|
+
this.xIndexConfig = {
|
|
2912
|
+
domain: [c.domain()[0], c.domain()[1]],
|
|
2913
|
+
xAttributeName: e,
|
|
2914
|
+
x2AttributeName: t
|
|
2915
|
+
};
|
|
2916
|
+
} else this.xIndexConfig = void 0;
|
|
2917
|
+
this.lastOffset = 0, this.rangeMap = new ue([], JSON.stringify);
|
|
2918
|
+
}
|
|
2919
|
+
registerBatch(e) {
|
|
2920
|
+
let t = this.lastOffset, n = this.variableBuilder.vertexCount, r = n - t;
|
|
2921
|
+
r && this.rangeMap.set(e, {
|
|
2922
|
+
offset: t,
|
|
2923
|
+
count: r,
|
|
2924
|
+
xIndex: this.createXIndex(t, n)
|
|
2925
|
+
}), this.lastOffset = n;
|
|
2926
|
+
}
|
|
2927
|
+
addBatches(e) {
|
|
2928
|
+
for (let [t, n] of e) this.addBatch(t, n);
|
|
2929
|
+
}
|
|
2930
|
+
addBatch(e, t, n = 0, r = t.length) {
|
|
2931
|
+
for (let e = n; e < r; e++) {
|
|
2932
|
+
let n = t[e];
|
|
2933
|
+
this.variableBuilder.pushFromDatum(n);
|
|
2934
|
+
}
|
|
2935
|
+
this.registerBatch(e);
|
|
2936
|
+
}
|
|
2937
|
+
createXIndex(e, t) {
|
|
2938
|
+
let n = this.xIndexConfig;
|
|
2939
|
+
if (!n) return;
|
|
2940
|
+
let r = (e) => {
|
|
2941
|
+
let { data: t, numComponents: n } = this.variableBuilder.arrays[e];
|
|
2942
|
+
return n == 2 ? (e) => {
|
|
2943
|
+
let r = e * n;
|
|
2944
|
+
return t[r] * Ss + t[r + 1];
|
|
2945
|
+
} : (e) => t[e * n];
|
|
2946
|
+
}, i = r(n.xAttributeName), a = n.x2AttributeName == n.xAttributeName ? i : r(n.x2AttributeName);
|
|
2947
|
+
return lc(50, n.domain, i, a, e, t);
|
|
2948
|
+
}
|
|
2949
|
+
toArrays() {
|
|
2950
|
+
return {
|
|
2951
|
+
arrays: this.variableBuilder.arrays,
|
|
2952
|
+
vertexCount: this.variableBuilder.vertexCount,
|
|
2953
|
+
allocatedVertices: this.allocatedVertices,
|
|
2954
|
+
rangeMap: this.rangeMap
|
|
2955
|
+
};
|
|
2956
|
+
}
|
|
2957
|
+
}, dc = class extends uc {
|
|
2958
|
+
constructor({ encoders: e, attributes: t, numItems: n }) {
|
|
2959
|
+
super({
|
|
2960
|
+
encoders: e,
|
|
2961
|
+
attributes: t,
|
|
2962
|
+
numVertices: n * 6
|
|
2963
|
+
}), this.variableBuilder.configure();
|
|
2964
|
+
let r = this.variableBuilder.pushAll;
|
|
2965
|
+
this.pushAllSixTimes = n > 500 ? Function("pushAll", "return function unrolledPushAllSixTimes() {\n pushAll(); pushAll(); pushAll(); pushAll(); pushAll(); pushAll();\n};")(r) : function() {
|
|
2966
|
+
r(), r(), r(), r(), r(), r();
|
|
2967
|
+
};
|
|
2968
|
+
}
|
|
2969
|
+
addBatch(e, t, n = 0, r = t.length) {
|
|
2970
|
+
if (!(r <= n)) {
|
|
2971
|
+
for (let e = n; e < r; e++) {
|
|
2972
|
+
let n = t[e];
|
|
2973
|
+
this.variableBuilder.updateFromDatum(n), this.pushAllSixTimes();
|
|
2974
|
+
}
|
|
2975
|
+
this.registerBatch(e);
|
|
2976
|
+
}
|
|
2977
|
+
}
|
|
2978
|
+
}, fc = class extends uc {
|
|
2979
|
+
constructor({ encoders: e, attributes: t, tessellationThreshold: n = Infinity, visibleRange: r = [-Infinity, Infinity], numItems: i }) {
|
|
2980
|
+
super({
|
|
2981
|
+
encoders: e,
|
|
2982
|
+
attributes: t,
|
|
2983
|
+
numVertices: n == Infinity ? i * 6 : void 0
|
|
2984
|
+
}), this.visibleRange = r, this.tessellationThreshold = n || Infinity, this.updateSide = this.variableBuilder.createUpdater("side", 1), this.updatePos = this.variableBuilder.createUpdater("pos", 1), this.variableBuilder.configure();
|
|
2985
|
+
}
|
|
2986
|
+
addBatch(e, t, n = 0, r = t.length) {
|
|
2987
|
+
for (let e = n; e < r; e++) {
|
|
2988
|
+
let n = t[e];
|
|
2989
|
+
this.variableBuilder.updateFromDatum(n), this.updateSide(-.5), this.updatePos(0), this.variableBuilder.pushAll();
|
|
2990
|
+
for (let e = 0; e <= 1; e++) this.updatePos(e / 1), this.updateSide(-.5), this.variableBuilder.pushAll(), this.updateSide(.5), this.variableBuilder.pushAll();
|
|
2991
|
+
this.variableBuilder.pushAll();
|
|
2992
|
+
}
|
|
2993
|
+
this.registerBatch(e);
|
|
2994
|
+
}
|
|
2995
|
+
}, pc = class extends uc {
|
|
2996
|
+
constructor({ encoders: e, attributes: t, numItems: n = void 0 }) {
|
|
2997
|
+
super({
|
|
2998
|
+
encoders: e,
|
|
2999
|
+
attributes: t,
|
|
3000
|
+
numVertices: n
|
|
3001
|
+
}), this.variableBuilder.configure();
|
|
3002
|
+
}
|
|
3003
|
+
addBatch(e, t, n = 0, r = t.length) {
|
|
3004
|
+
for (let e = n; e < r; e++) {
|
|
3005
|
+
let n = t[e];
|
|
3006
|
+
this.variableBuilder.pushFromDatum(n);
|
|
3007
|
+
}
|
|
3008
|
+
this.registerBatch(e);
|
|
3009
|
+
}
|
|
3010
|
+
}, mc = class extends uc {
|
|
3011
|
+
constructor({ encoders: e, attributes: t, numItems: n = void 0 }) {
|
|
3012
|
+
super({
|
|
3013
|
+
encoders: e,
|
|
3014
|
+
attributes: t,
|
|
3015
|
+
numVertices: n
|
|
3016
|
+
}), this.variableBuilder.configure();
|
|
3017
|
+
}
|
|
3018
|
+
addBatch(e, t, n = 0, r = t.length) {
|
|
3019
|
+
for (let e = n; e < r; e++) {
|
|
3020
|
+
let n = t[e];
|
|
3021
|
+
this.variableBuilder.pushFromDatum(n);
|
|
3022
|
+
}
|
|
3023
|
+
this.registerBatch(e);
|
|
3024
|
+
}
|
|
3025
|
+
toArrays() {
|
|
3026
|
+
let e = this.variableBuilder.arrays;
|
|
3027
|
+
for (let t of Object.values(e)) t.divisor = 1;
|
|
3028
|
+
return super.toArrays();
|
|
3029
|
+
}
|
|
3030
|
+
}, hc = class extends uc {
|
|
3031
|
+
constructor({ encoders: e, attributes: t, fontMetrics: n, properties: r, numCharacters: i = void 0 }) {
|
|
3032
|
+
super({
|
|
3033
|
+
encoders: e,
|
|
3034
|
+
attributes: t,
|
|
3035
|
+
numVertices: i * 6
|
|
3036
|
+
}), this.metadata = n, this.metrics = n, this.properties = r;
|
|
3037
|
+
let a = e.text.channelDef;
|
|
3038
|
+
this.numberFormat = !y(a) && "format" in a && a.format ? f(a.format) : (e) => e, this.updateVertexCoord = this.variableBuilder.createUpdater("vertexCoord", 2), this.updateTextureCoord = this.variableBuilder.createUpdater("textureCoord", 2), this.updateWidth = this.variableBuilder.createUpdater("width", 1), this.variableBuilder.configure();
|
|
3039
|
+
}
|
|
3040
|
+
addBatch(e, t, n = 0, r = t.length) {
|
|
3041
|
+
let i = this.properties.align || "left", a = this.properties.logoLetters ?? !1, o = this.metadata.common.base, s = this.metadata.common.scaleH, l = -5;
|
|
3042
|
+
switch (this.properties.baseline) {
|
|
3043
|
+
case "top":
|
|
3044
|
+
l += this.metrics.capHeight;
|
|
3045
|
+
break;
|
|
3046
|
+
case "middle":
|
|
3047
|
+
l += this.metrics.capHeight / 2;
|
|
3048
|
+
break;
|
|
3049
|
+
case "bottom":
|
|
3050
|
+
l -= this.metrics.descent;
|
|
3051
|
+
break;
|
|
3052
|
+
default:
|
|
3053
|
+
}
|
|
3054
|
+
let u = this.encoders.text, d = [0, 0];
|
|
3055
|
+
this.updateVertexCoord(d);
|
|
3056
|
+
let f = [0, 0];
|
|
3057
|
+
this.updateTextureCoord(f);
|
|
3058
|
+
for (let e = n; e < r; e++) {
|
|
3059
|
+
let n = t[e], r = this.numberFormat(u(n)), p = c(r) ? r : r === null ? "" : "" + r;
|
|
3060
|
+
if (p.length == 0) continue;
|
|
3061
|
+
this.variableBuilder.updateFromDatum(n);
|
|
3062
|
+
let m = a ? p.length : this.metrics.measureWidth(p);
|
|
3063
|
+
this.updateWidth(m);
|
|
3064
|
+
let h = i == "right" ? -m : i == "center" ? -m / 2 : 0;
|
|
3065
|
+
if (!a) {
|
|
3066
|
+
let e = this.metrics.getCharByCode(p.charCodeAt(0));
|
|
3067
|
+
h -= (e.width - e.xadvance) / o / 2;
|
|
3068
|
+
}
|
|
3069
|
+
let g, _, v;
|
|
3070
|
+
for (let e = 0; e < p.length; e++) {
|
|
3071
|
+
let t = this.metrics.getCharByCode(p.charCodeAt(e)), n = a ? 1 : t.xadvance / o;
|
|
3072
|
+
if (t.id == 32) {
|
|
3073
|
+
h += n;
|
|
3074
|
+
continue;
|
|
3075
|
+
}
|
|
3076
|
+
a ? (v = (t.width + 10) / t.width, h = -v / 2, _ = (t.height + 10) / t.height, g = -.5 - 5 / t.height) : (_ = t.height / o, g = -(t.height + t.yoffset + l) / o, v = t.width / o);
|
|
3077
|
+
let r = t.x, i = t.y;
|
|
3078
|
+
d[0] = h, d[1] = g + _, f[0] = r / s, f[1] = i / s, this.variableBuilder.pushAll(), d[0] = h + v, d[1] = g + _, f[0] = (r + t.width) / s, f[1] = i / s, this.variableBuilder.pushAll(), d[0] = h, d[1] = g, f[0] = r / s, f[1] = (i + t.height) / s, this.variableBuilder.pushAll(), d[0] = h + v, d[1] = g + _, f[0] = (r + t.width) / s, f[1] = i / s, this.variableBuilder.pushAll(), d[0] = h, d[1] = g, f[0] = r / s, f[1] = (i + t.height) / s, this.variableBuilder.pushAll(), d[0] = h + v, d[1] = g, f[0] = (r + t.width) / s, f[1] = (i + t.height) / s, this.variableBuilder.pushAll(), h += n;
|
|
3079
|
+
}
|
|
3080
|
+
}
|
|
3081
|
+
this.registerBatch(e);
|
|
3082
|
+
}
|
|
3083
|
+
}, gc = "#define PI 3.141593\n\nuniform View {\n /** Offset in \"unit\" units */\n mediump vec2 uViewOffset;\n mediump vec2 uViewScale;\n /** Size of the logical viewport in pixels, i.e., the view */\n mediump vec2 uViewportSize;\n mediump vec4 uLogicalVisibleRect;\n lowp vec2 uCullByVisibleRange;\n lowp float uDevicePixelRatio;\n // TODO: Views with opacity less than 1.0 should be rendered into a texture\n // that is rendered with the specified opacity.\n lowp float uViewOpacity;\n bool uPickingEnabled;\n};\n\n\n/**\n * Maps a coordinate on the unit scale to a normalized device coordinate.\n * (0, 0) is at the bottom left corner.\n */\nvec4 unitToNdc(vec2 coord) {\n return vec4((coord * uViewScale + uViewOffset) * 2.0 - 1.0, 0.0, 1.0);\n}\n\nvec4 unitToNdc(float x, float y) {\n return unitToNdc(vec2(x, y));\n}\n\nvec4 pixelsToNdc(vec2 coord) {\n return unitToNdc(coord / uViewportSize);\n}\n\nvec4 pixelsToNdc(float x, float y) {\n return pixelsToNdc(vec2(x, y));\n}\n\n/** Applies logical pixel offsets to a position in unit coordinates. */\nvec2 applyOffset(vec2 pos, vec2 offset) {\n return pos + vec2(offset.x, -offset.y) / uViewportSize;\n}\n\nbool isOutsideVisibleRange(vec2 pos) {\n return (uCullByVisibleRange.x > 0.5 &&\n (pos.x < uLogicalVisibleRect.x ||\n pos.x > uLogicalVisibleRect.z)) ||\n (uCullByVisibleRange.y > 0.5 &&\n (pos.y < uLogicalVisibleRect.y ||\n pos.y > uLogicalVisibleRect.w));\n}\n\nfloat linearstep(float edge0, float edge1, float x) {\n return clamp((x - edge0) / (edge1 - edge0), 0.0, 1.0);\n}\n\nconst highp uint HASH_EMPTY_KEY = 0xffffffffu;\n\nhighp uint hash32(highp uint key) {\n highp uint v = key;\n v ^= v >> 16u;\n v *= 0x7feb352du;\n v ^= v >> 15u;\n v *= 0x846ca68bu;\n v ^= v >> 16u;\n return v;\n}\n\nbool isEmptyHashTexture(highp usampler2D s) {\n // Empty selections are encoded as a single empty hash slot.\n ivec2 texSize = textureSize(s, 0);\n return texSize.x == 1 && texSize.y == 1 && texelFetch(s, ivec2(0, 0), 0).r == HASH_EMPTY_KEY;\n}\n\nbool hashContainsTexture(highp usampler2D s, highp uint value) {\n ivec2 texSize = textureSize(s, 0);\n highp uint width = uint(texSize.x);\n highp uint size = width * uint(texSize.y);\n highp uint mask = size - 1u;\n highp uint index = hash32(value) & mask;\n\n for (highp uint probe = 0u; probe < size; probe += 1u) {\n ivec2 coord = ivec2(int(index % width), int(index / width));\n highp uint entry = texelFetch(s, coord, 0).r;\n if (entry == value) {\n return true;\n }\n if (entry == HASH_EMPTY_KEY) {\n return false;\n }\n index = (index + 1u) & mask;\n }\n\n return false;\n}\n\n/**\n * Calculates a gamma for antialiasing opacity based on the color.\n */\nfloat getGammaForColor(vec3 rgb) {\n return mix(\n 1.25,\n 0.75,\n // RGB should be linearized but this is good enough for now\n smoothstep(0.0, 1.0, dot(rgb, vec3(0.299, 0.587, 0.114))));\n}\n\n// Fragment shader stuff ////////////////////////////////////////////////////////\n\n// TODO: include the following only in fragment shaders\n\n/**\n * Specialized linearstep for doing antialiasing\n */\nfloat distanceToRatio(float d) {\n return clamp(d * uDevicePixelRatio + 0.5, 0.0, 1.0);\n}\n\nvec4 distanceToColor(float d, vec4 fill, vec4 stroke, vec4 background, float halfStrokeWidth) {\n if (halfStrokeWidth > 0.0) {\n // Distance to stroke's edge. Negative inside the stroke.\n float sd = abs(d) - halfStrokeWidth;\n return mix(\n stroke,\n d <= 0.0 ? fill : background,\n distanceToRatio(sd));\n } else {\n return mix(background, fill, distanceToRatio(-d));\n }\n}\n", _c = "uniform highp float uZero;\n\n// Utils ------------\n\nvec3 getDiscreteColor(sampler2D s, int index) {\n return texelFetch(s, ivec2(index % textureSize(s, 0).x, 0), 0).rgb;\n}\n\nvec3 getInterpolatedColor(sampler2D s, float unitValue) {\n return texture(s, vec2(unitValue, 0.0)).rgb;\n}\n\nfloat clampToRange(float value, vec2 range) {\n return clamp(value, min(range[0], range[1]), max(range[0], range[1]));\n}\n\n// Scales ------------\n// Based on d3 scales: https://github.com/d3/d3-scale\n\nfloat scaleIdentity(float value) {\n return value;\n}\n\nfloat scaleIdentity(uint value) {\n return float(value);\n}\n\nfloat scaleLinear(float value, vec2 domain, vec2 range) {\n float domainSpan = domain[1] - domain[0];\n float rangeSpan = range[1] - range[0];\n return (value - domain[0]) / domainSpan * rangeSpan + range[0];\n}\n\nfloat scaleLog(float value, vec2 domain, vec2 range, float base) {\n // y = m log(x) + b \n // TODO: Perf optimization: precalculate log domain in js.\n // TODO: Reversed domain, etc\n return scaleLinear(log(value) / log(base), log(domain) / log(base), range);\n}\n\nfloat symlog(float value, float constant) {\n // WARNING: emulating log1p with log(x + 1). Small numbers are likely to\n // have significant precision problems.\n return sign(value) * log(abs(value / constant) + 1.0);\n}\n\nfloat scaleSymlog(float value, vec2 domain, vec2 range, float constant) {\n return scaleLinear(\n symlog(value, constant),\n vec2(symlog(domain[0], constant), symlog(domain[1], constant)),\n range\n );\n}\n\nfloat scalePow(float value, vec2 domain, vec2 range, float exponent) {\n // y = mx^k + b\n // TODO: Perf optimization: precalculate pow domain in js.\n // TODO: Reversed domain, etc\n return scaleLinear(\n pow(abs(value), exponent) * sign(value),\n pow(abs(domain), vec2(exponent)) * sign(domain),\n range\n );\n}\n\n// TODO: scaleThreshold\n// TODO: scaleQuantile (special case of threshold scale)\n\n// TODO: domainExtent should be uint\nfloat scaleBand(uint value, vec2 domainExtent, vec2 range,\n float paddingInner, float paddingOuter,\n float align, float band) {\n\n // TODO: reverse\n float start = range[0];\n float stop = range[1];\n float rangeSpan = stop - start;\n\n float n = domainExtent[1] - domainExtent[0];\n\n // This fix departs from Vega and d3: https://github.com/vega/vega/issues/3357#issuecomment-1063253596\n paddingInner = int(n) > 1 ? paddingInner : 0.0;\n\n // Adapted from: https://github.com/d3/d3-scale/blob/master/src/band.js\n float step = rangeSpan / max(1.0, n - paddingInner + paddingOuter * 2.0);\n start += (rangeSpan - step * (n - paddingInner)) * align;\n float bandwidth = step * (1.0 - paddingInner);\n\n return start + (float(value) - domainExtent[0]) * step + bandwidth * band;\n}\n\nconst int lowBits = 12;\nconst float lowDivisor = pow(2.0, float(lowBits));\nconst uint lowMask = uint(lowDivisor - 1.0);\n\nvec2 splitUint(uint value) {\n uint valueLo = value & lowMask;\n uint valueHi = value - valueLo;\n return vec2(float(valueHi), float(valueLo));\n}\n\n/**\n * High precision variant of scaleBand for index/locus scales\n */\nfloat scaleBandHp(uint value, vec3 domainExtent, vec2 range,\n float paddingInner, float paddingOuter,\n float align, float band) {\n\n // TODO: reverse\n float start = range[0];\n float stop = range[1];\n float rangeSpan = stop - start;\n\n vec2 domainStart = domainExtent.xy;\n float n = domainExtent[2];\n\n // The following computation is identical for every vertex. Could be done on the JS side.\n float step = rangeSpan / max(1.0, n - paddingInner + paddingOuter * 2.0);\n start += (rangeSpan - step * (n - paddingInner)) * align;\n float bandwidth = step * (1.0 - paddingInner);\n\n // Split into to values with each having a reduced number of significant digits\n // to mitigate the lack of precision in float32 calculations.\n vec2 splitValue = splitUint(value);\n\n // Using max to prevent the shader compiler from wrecking the precision.\n // Othwewise the compiler could optimize the sum of the four terms into\n // some equivalent form that does premature rounding.\n float inf = 1.0 / uZero;\n float hi = max(splitValue[0] - domainStart[0], -inf);\n float lo = max(splitValue[1] - domainStart[1], -inf);\n\n return dot(vec4(start, hi, lo, bandwidth), vec4(1.0, step, step, band));\n}\n\n/**\n * High precision variant of scaleBand for index/locus scales for large\n * domains where 32bit uints are not sufficient to represent the domain.\n */\nfloat scaleBandHp(uvec2 value, vec3 domainExtent, vec2 range,\n float paddingInner, float paddingOuter,\n float align, float band) {\n\n // TODO: reverse\n float start = range[0];\n float stop = range[1];\n float rangeSpan = stop - start;\n\n vec2 domainStart = domainExtent.xy;\n float n = domainExtent[2];\n\n // The following computation is identical for every vertex. Could be done on the JS side.\n float step = rangeSpan / max(1.0, n - paddingInner + paddingOuter * 2.0);\n start += (rangeSpan - step * (n - paddingInner)) * align;\n float bandwidth = step * (1.0 - paddingInner);\n\n // Split into to values with each having a reduced number of significant digits\n // to mitigate the lack of precision in float32 calculations.\n vec2 splitValue = vec2(float(value[0]) * lowDivisor, float(value[1]));\n\n // Using max to prevent the shader compiler from wrecking the precision.\n // Othwewise the compiler could optimize the sum of the four terms into\n // some equivalent form that does premature rounding.\n float inf = 1.0 / uZero;\n float hi = max(splitValue[0] - domainStart[0], -inf);\n float lo = max(splitValue[1] - domainStart[1], -inf);\n\n return dot(vec4(start, hi, lo, bandwidth), vec4(1.0, step, step, band));\n}\n", vc = "\n/** Describes where a sample facet should be shown. */\nstruct SampleFacetPosition {\n float pos;\n float height;\n};\n\n// ----------------------------------------------------------------------------\n\n#if !defined(SAMPLE_FACET_UNIFORM) && !defined(SAMPLE_FACET_TEXTURE)\n\nSampleFacetPosition getSampleFacetPos() {\n return SampleFacetPosition(0.0, 1.0);\n}\n\n#elif defined(SAMPLE_FACET_UNIFORM)\n\n/**\n * Location and height of the band on the Y axis on a normalized [0, 1] scale.\n * Elements: position, height\n */\nuniform vec2 uSampleFacet;\n\nSampleFacetPosition getSampleFacetPos() {\n return SampleFacetPosition(\n 1.0 - uSampleFacet.x - uSampleFacet.y,\n uSampleFacet.y\n );\n}\n\n#elif defined(SAMPLE_FACET_TEXTURE)\n\nuniform sampler2D uSampleFacetTexture;\n\nSampleFacetPosition getSampleFacetPos() {\n vec2 texel = texelFetch(\n uSampleFacetTexture,\n ivec2(int(attr_facetIndex), 0),\n 0\n ).rg;\n return SampleFacetPosition(\n 1.0 - texel.x - texel.y,\n texel.y\n );\n}\n\n#endif\n\nvec2 applySampleFacet(vec2 pos) {\n SampleFacetPosition facetPos = getSampleFacetPos();\n return vec2(pos.x, facetPos.pos + pos.y * facetPos.height);\n}\n", yc = "/*\n * Based on concepts presented at:\n * https://webglfundamentals.org/webgl/lessons/webgl-picking.html\n * https://deck.gl/docs/developer-guide/custom-layers/picking\n */\n\nout highp vec4 vPickingColor;\n\n/**\n * Passes the unique id to the fragment shader as a color if picking is enabled.\n * Returns true if picking is enabled.\n */\nbool setupPicking() {\n if (uPickingEnabled) {\n#ifdef uniqueId_DEFINED\n uint id = attr_uniqueId;\n vPickingColor = vec4(\n ivec4(id >> 0, id >> 8, id >> 16, id >> 24) & 0xFF\n ) / float(0xFF);\n#else\n vPickingColor = vec4(1.0);\n#endif\n return true;\n }\n return false;\n}\n", bc = "in highp vec4 vPickingColor;\n", xc = .5, Sc = "SAMPLE_FACET_UNIFORM", Cc = "SAMPLE_FACET_TEXTURE", wc = "uSelectionTexture_", Tc = class {
|
|
3084
|
+
#e = [];
|
|
3085
|
+
#t = !1;
|
|
3086
|
+
constructor(e, t, n) {
|
|
3087
|
+
this.mark = e, this._glHelper = t, this._rendererResources = n, this.bufferInfo = void 0, this.bytesPerElement = /* @__PURE__ */ new Map(), this.programInfo = void 0, this.vertexArrayInfo = void 0, this.viewUniformInfo = void 0, this.markUniformInfo = void 0, this.markUniformsAltered = !0, this.selectionTextureOps = [], this.scaleResolutionDisposers = [], this.rangeMap = new Ec();
|
|
3088
|
+
}
|
|
3089
|
+
get unitView() {
|
|
3090
|
+
return this.mark.unitView;
|
|
3091
|
+
}
|
|
3092
|
+
get encoders() {
|
|
3093
|
+
return this.mark.encoders;
|
|
3094
|
+
}
|
|
3095
|
+
get encoding() {
|
|
3096
|
+
return this.mark.encoding;
|
|
3097
|
+
}
|
|
3098
|
+
get properties() {
|
|
3099
|
+
return this.mark.properties;
|
|
3100
|
+
}
|
|
3101
|
+
get font() {
|
|
3102
|
+
return this.mark.font;
|
|
3103
|
+
}
|
|
3104
|
+
get opaque() {
|
|
3105
|
+
return !1;
|
|
3106
|
+
}
|
|
3107
|
+
get defaultHitTestMode() {
|
|
3108
|
+
return this.mark.defaultHitTestMode;
|
|
3109
|
+
}
|
|
3110
|
+
getType() {
|
|
3111
|
+
return this.mark.getType();
|
|
3112
|
+
}
|
|
3113
|
+
getAttributes() {
|
|
3114
|
+
throw Error("Not implemented.");
|
|
3115
|
+
}
|
|
3116
|
+
initializeGraphics() {
|
|
3117
|
+
this.#n();
|
|
3118
|
+
}
|
|
3119
|
+
getSampleFacetMode() {
|
|
3120
|
+
if (this.encoders.facetIndex) return Cc;
|
|
3121
|
+
if (this.unitView.usesSampleFacetRendering()) return Sc;
|
|
3122
|
+
}
|
|
3123
|
+
createAndLinkShaders(e, t, i = []) {
|
|
3124
|
+
let a = this.getAttributes(), o = this.encoders, s = this.getSampleFacetMode(), c = !!this.properties.cullByVisibleRange;
|
|
3125
|
+
s && i.push(`#define ${s}`), c && i.push("#define VISIBLE_RANGE_CULLING");
|
|
3126
|
+
let u = "// view: " + this.unitView.getPathString(), d = [], f = /* @__PURE__ */ new Set(), h = Es(o), v = [], ee = Object.values(o).flatMap((e) => e.branches ?? []).map((e) => e.predicate).filter((e) => e.param), b = /* @__PURE__ */ new Map();
|
|
3127
|
+
for (let e of ee) {
|
|
3128
|
+
let t = e.param, r = this.unitView.paramRuntime, i = r.findValue(t);
|
|
3129
|
+
if (!i) throw Error(`Cannot infer selection type as the parameter "${t}" has no value. Please ensure that the parameter is properly defined!`);
|
|
3130
|
+
let a = Ds("uniqueId");
|
|
3131
|
+
if (l(i)) {
|
|
3132
|
+
if (!b.has(t)) {
|
|
3133
|
+
b.set(t, "single");
|
|
3134
|
+
let e = rs + _(t);
|
|
3135
|
+
v.push(" // Selection parameter"), v.push(` uniform highp uint ${e};`), this.#e.push(() => {
|
|
3136
|
+
this.registerMarkUniformValue(e, { expr: t }, (e) => e.uniqueId ?? 0);
|
|
3137
|
+
}), d.push(`bool ${is}${t}(bool empty) {\n return ${rs}${t} == ${a} || (empty && ${rs}${t} == 0u);\n}`);
|
|
3138
|
+
}
|
|
3139
|
+
} else if (n(i)) {
|
|
3140
|
+
if (!b.has(t)) {
|
|
3141
|
+
b.set(t, "multi");
|
|
3142
|
+
let e = wc + _(t);
|
|
3143
|
+
d.push(`// Selection texture\nuniform highp usampler2D ${e};`);
|
|
3144
|
+
let n = this.glHelper, o = n.selectionTextures;
|
|
3145
|
+
this.selectionTextureOps.push(() => {
|
|
3146
|
+
let n = r.getValue(t), i = o.get(n);
|
|
3147
|
+
if (!i) throw Error(`Bug: no selection texture found for "${t}"!`);
|
|
3148
|
+
J(this.programInfo, { [e]: i });
|
|
3149
|
+
});
|
|
3150
|
+
let s = wc + t;
|
|
3151
|
+
d.push(`bool ${is}${t}(bool empty) {\n return hashContainsTexture(${s}, ${a}) || (empty && isEmptyHashTexture(${s}));\n}`), n.createSelectionTexture(i), r.watchExpression(t, () => {
|
|
3152
|
+
let e = r.getValue(t);
|
|
3153
|
+
n.createSelectionTexture(e), this.unitView.context.animator.requestRender();
|
|
3154
|
+
});
|
|
3155
|
+
}
|
|
3156
|
+
} else if (oe(i) && !b.has(t)) {
|
|
3157
|
+
b.set(t, "interval");
|
|
3158
|
+
let e = [], n = [];
|
|
3159
|
+
for (let r of Object.keys(i.intervals)) {
|
|
3160
|
+
if (!["x", "y"].includes(r)) continue;
|
|
3161
|
+
let i = rs + _(t) + `_${r}`, { attributeType: a } = xs(this.unitView.getScaleResolution(r).getScale(), r);
|
|
3162
|
+
v.push(" // Selection parameter"), v.push(` uniform highp ${a}[2] ${i};`), this.#e.push(() => {
|
|
3163
|
+
this.registerMarkUniformValue(i, { expr: t }, (e) => e.intervals[r] ?? [1, 0]);
|
|
3164
|
+
});
|
|
3165
|
+
let o = (e) => {
|
|
3166
|
+
for (let [t, n] of h.entries()) if (t[1] && n.includes(e)) return Ds(n);
|
|
3167
|
+
return Ds(e);
|
|
3168
|
+
}, s = o(r), c = i + "[0]", l = i + "[1]", u = p(r);
|
|
3169
|
+
if (this.encoding[u]) {
|
|
3170
|
+
let t = o(u), n = this.defaultHitTestMode;
|
|
3171
|
+
if (n == "endpoints") e.push(`((${c} <= ${s} && ${s} <= ${l}) || (${c} <= ${t} && ${t} <= ${l}))`);
|
|
3172
|
+
else if (n == "encloses") e.push(`(${c} <= ${s} && ${t} <= ${l})`);
|
|
3173
|
+
else if (n == "intersects") e.push(`(${c} <= ${t} && ${s} <= ${l})`);
|
|
3174
|
+
else throw new be(`Unsupported hit test mode "${n}" for interval selection!`, this.unitView);
|
|
3175
|
+
} else e.push(`(${c} <= ${s} && ${s} <= ${l})`);
|
|
3176
|
+
n.push(`${c} > ${l}`);
|
|
3177
|
+
}
|
|
3178
|
+
d.push(`bool ${is}${t}(bool empty) {\n return ${e.join(" && ")} || (empty && (${n.join(" || ")}));\n}`);
|
|
3179
|
+
}
|
|
3180
|
+
}
|
|
3181
|
+
let ne = (e, t, n, r) => {
|
|
3182
|
+
let i = t.channelDef;
|
|
3183
|
+
if (y(i)) if (x(i.value)) {
|
|
3184
|
+
let { uniformName: t, uniformGlsl: r, accessorGlsl: a, adjuster: o } = us(e, n);
|
|
3185
|
+
d.push(a), v.push(r), this.#e.push(() => {
|
|
3186
|
+
this.registerMarkUniformValue(t, i.value, o);
|
|
3187
|
+
});
|
|
3188
|
+
} else d.push(ls(e, n, i.value).accessorGlsl);
|
|
3189
|
+
else if (g(i)) {
|
|
3190
|
+
let { uniformName: t, uniformGlsl: a, accessorGlsl: o } = fs(e, r, n);
|
|
3191
|
+
v.push(a), d.push(o);
|
|
3192
|
+
let { largeHp: s, discrete: c } = xs(r, e), l = c && "domain" in r ? (e) => r.domain().indexOf(e) : s ? Cs : (e) => +e;
|
|
3193
|
+
this.#e.push(() => {
|
|
3194
|
+
this.registerMarkUniformValue(t, i.datum, l);
|
|
3195
|
+
});
|
|
3196
|
+
} else if (re(i)) {
|
|
3197
|
+
let t = h.get([i.field, !0]), { attributeGlsl: a, accessorGlsl: o } = ds(e, r, n, t?.includes(e) ? t : void 0);
|
|
3198
|
+
f.add(a), d.push(o);
|
|
3199
|
+
} else if (te(i)) {
|
|
3200
|
+
let { attributeGlsl: t, accessorGlsl: i } = ds(e, r, n);
|
|
3201
|
+
f.add(t), d.push(i);
|
|
3202
|
+
} else throw new be(`Unsupported channel definition: ${JSON.stringify(i)}`, this.unitView);
|
|
3203
|
+
};
|
|
3204
|
+
for (let [e, t] of Object.entries(o)) {
|
|
3205
|
+
if (!a.includes(e)) continue;
|
|
3206
|
+
let { branches: n, channelDef: i, scale: o } = t;
|
|
3207
|
+
for (let t = 0; t < n.length; t++) ne(e, n[t].accessor, t, o);
|
|
3208
|
+
if (o) {
|
|
3209
|
+
let t = r(i), n = t && t.resolutionChannel || e, a = m(n) ? this.unitView.getScaleResolution(n) : null, { glsl: s, domainUniform: c, domainUniformName: l, rangeUniform: u, rangeUniformName: f } = ps(e, o, i);
|
|
3210
|
+
d.push(s), v.push(c), v.push(u), u && this.#e.push(() => {
|
|
3211
|
+
let t = this.createMarkUniformSetter(f), n = () => t(ks(o, e));
|
|
3212
|
+
this.registerScaleResolutionListener(a, "range", n), n();
|
|
3213
|
+
}), c && this.#e.push(() => {
|
|
3214
|
+
let e = this.createMarkUniformSetter(l), t = () => {
|
|
3215
|
+
let t;
|
|
3216
|
+
t = pe(o.type) ? [0, o.domain().length] : S(o.type) ? os(o) : o.domain(), e(_e(o.type) ? Ts(t) : t);
|
|
3217
|
+
};
|
|
3218
|
+
this.registerScaleResolutionListener(a, "domain", t), t();
|
|
3219
|
+
});
|
|
3220
|
+
}
|
|
3221
|
+
d.push(ms(e, n));
|
|
3222
|
+
}
|
|
3223
|
+
let ie = [...b.keys()].map((e) => `${is}${e}(false)`);
|
|
3224
|
+
d.push("bool isPointSelected() {\n" + (this.encoders.uniqueId && ie.length > 0 ? ` return ${ie.join(" || ")};` : " return false;") + "\n}");
|
|
3225
|
+
let ae = "precision highp float;\nprecision highp int;", se = (e) => e.replace("#pragma markUniforms", v.join("\n"));
|
|
3226
|
+
i = i.map(se), e = se(e), t = se(t);
|
|
3227
|
+
let ce = [
|
|
3228
|
+
ae,
|
|
3229
|
+
u,
|
|
3230
|
+
...i,
|
|
3231
|
+
gc,
|
|
3232
|
+
_c,
|
|
3233
|
+
[...f].join("\n"),
|
|
3234
|
+
...d,
|
|
3235
|
+
vc,
|
|
3236
|
+
yc,
|
|
3237
|
+
e
|
|
3238
|
+
], le = [
|
|
3239
|
+
ae,
|
|
3240
|
+
u,
|
|
3241
|
+
...i,
|
|
3242
|
+
gc,
|
|
3243
|
+
bc,
|
|
3244
|
+
t
|
|
3245
|
+
], ue = this.gl;
|
|
3246
|
+
this.programStatus = Bs(ue, this.glHelper.compileShader(ue.VERTEX_SHADER, ce), this.glHelper.compileShader(ue.FRAGMENT_SHADER, le));
|
|
3247
|
+
}
|
|
3248
|
+
finalizeGraphicsInitialization() {
|
|
3249
|
+
if (this.#n(), this.programInfo) return;
|
|
3250
|
+
if (!this.programStatus) throw Error("No program status found! " + this.unitView.getPathString());
|
|
3251
|
+
let e = this.programStatus.getProgramErrors();
|
|
3252
|
+
if (e) {
|
|
3253
|
+
e.detail && console.warn(e.detail);
|
|
3254
|
+
let t = /* @__PURE__ */ Error("Cannot create shader program: " + e.message);
|
|
3255
|
+
throw t.view = this.unitView, t;
|
|
3256
|
+
}
|
|
3257
|
+
this.programInfo = no(this.gl, this.programStatus.program), delete this.programStatus, this.viewUniformInfo = Ya(this.gl, this.programInfo, "View"), this.markUniformInfo = Ya(this.gl, this.programInfo, "Mark"), this.gl.useProgram(this.programInfo.program), J(this.programInfo, {
|
|
3258
|
+
uSampleFacet: [0, 1],
|
|
3259
|
+
uZero: 0
|
|
3260
|
+
});
|
|
3261
|
+
for (let e of this.#e) e();
|
|
3262
|
+
this.#e = void 0;
|
|
3263
|
+
}
|
|
3264
|
+
createMarkUniformSetter(e) {
|
|
3265
|
+
let t = this.markUniformInfo.setters[e];
|
|
3266
|
+
if (!t) throw Error(`Uniform "${e}" not found int the Mark block!`);
|
|
3267
|
+
return (e) => {
|
|
3268
|
+
t(e), this.markUniformsAltered = !0, this.unitView.context.animator.requestRender();
|
|
3269
|
+
};
|
|
3270
|
+
}
|
|
3271
|
+
registerMarkUniformValue(e, t, n = (e) => e) {
|
|
3272
|
+
let r = this.createMarkUniformSetter(e), i = (n) => {
|
|
3273
|
+
if (n == null) throw Error(`Trying to set null/undefined value for uniform: ${e}${x(t) ? `Expr: ${t.expr}` : ""}`);
|
|
3274
|
+
r(n);
|
|
3275
|
+
};
|
|
3276
|
+
if (x(t)) {
|
|
3277
|
+
let e, r = () => i(n(e(null)));
|
|
3278
|
+
e = this.unitView.paramRuntime.watchExpression(t.expr, r), r();
|
|
3279
|
+
} else i(n(t));
|
|
3280
|
+
}
|
|
3281
|
+
deleteGraphicsData() {
|
|
3282
|
+
let e = this.gl;
|
|
3283
|
+
this.vertexArrayInfo &&= (this.gl.bindVertexArray(null), e.deleteVertexArray(this.vertexArrayInfo.vertexArrayObject), void 0), this.bufferInfo &&= (Object.values(this.bufferInfo.attribs).forEach((e) => this.gl.deleteBuffer(e.buffer)), this.bufferInfo.indices && this.gl.deleteBuffer(this.bufferInfo.indices), void 0);
|
|
3284
|
+
}
|
|
3285
|
+
registerScaleResolutionListener(e, t, n) {
|
|
3286
|
+
e.addEventListener(t, n), this.scaleResolutionDisposers.push(() => e.removeEventListener(t, n));
|
|
3287
|
+
}
|
|
3288
|
+
dispose() {
|
|
3289
|
+
if (this.#t) return;
|
|
3290
|
+
this.#t = !0;
|
|
3291
|
+
for (let e of this.scaleResolutionDisposers) e();
|
|
3292
|
+
this.scaleResolutionDisposers.length = 0, this.deleteGraphicsData(), this.viewUniformInfo &&= (this.gl.deleteBuffer(this.viewUniformInfo.buffer), void 0), this.markUniformInfo &&= (this.gl.deleteBuffer(this.markUniformInfo.buffer), void 0);
|
|
3293
|
+
let e = this.programInfo?.program ?? this.programStatus?.program;
|
|
3294
|
+
e && this.gl.deleteProgram(e), this.programInfo = void 0, this.programStatus = void 0;
|
|
3295
|
+
}
|
|
3296
|
+
#n() {
|
|
3297
|
+
if (this.#t) throw Error("WebGL mark resources have been disposed.");
|
|
3298
|
+
}
|
|
3299
|
+
updateBufferInfo(e) {
|
|
3300
|
+
if (this.gl.bindVertexArray(null), this.bufferInfo && e.vertexCount <= this.bufferInfo.allocatedVertices) for (let [t, n] of Object.entries(e.arrays)) n.data && Et(this.gl, this.bufferInfo.attribs[t], n.data, 0);
|
|
3301
|
+
else {
|
|
3302
|
+
this.deleteGraphicsData(), this.bufferInfo = At(this.gl, e.arrays, { numElements: e.vertexCount }), this.bufferInfo.allocatedVertices = e.allocatedVertices;
|
|
3303
|
+
for (let [t, n] of Object.entries(e.arrays)) this.bytesPerElement.set(t, n.data.BYTES_PER_ELEMENT);
|
|
3304
|
+
}
|
|
3305
|
+
}
|
|
3306
|
+
get glHelper() {
|
|
3307
|
+
return this._glHelper;
|
|
3308
|
+
}
|
|
3309
|
+
get rendererResources() {
|
|
3310
|
+
if (!this._rendererResources) throw Error("WebGL renderer resources are not available.");
|
|
3311
|
+
return this._rendererResources;
|
|
3312
|
+
}
|
|
3313
|
+
get gl() {
|
|
3314
|
+
return this.glHelper.gl;
|
|
3315
|
+
}
|
|
3316
|
+
isReady() {
|
|
3317
|
+
return !!(this.bufferInfo && this.programInfo);
|
|
3318
|
+
}
|
|
3319
|
+
isPickingParticipant() {
|
|
3320
|
+
return this.mark.isPickingParticipant();
|
|
3321
|
+
}
|
|
3322
|
+
getDebugState() {
|
|
3323
|
+
return {
|
|
3324
|
+
markUniformsAltered: this.markUniformsAltered,
|
|
3325
|
+
vertexCount: this.bufferInfo?.numElements,
|
|
3326
|
+
allocatedVertices: this.bufferInfo?.allocatedVertices,
|
|
3327
|
+
rangeCount: this.rangeMap.size
|
|
3328
|
+
};
|
|
3329
|
+
}
|
|
3330
|
+
bindOrSetMarkUniformBlock() {
|
|
3331
|
+
this.markUniformsAltered ? (Za(this.gl, this.programInfo, this.markUniformInfo), this.markUniformsAltered = !1) : Xa(this.gl, this.programInfo, this.markUniformInfo);
|
|
3332
|
+
}
|
|
3333
|
+
prepareRender(e) {
|
|
3334
|
+
let t = this.glHelper, n = this.gl, r = [];
|
|
3335
|
+
r.push(() => {
|
|
3336
|
+
this.vertexArrayInfo ||= Fo(this.gl, this.programInfo, this.bufferInfo), n.useProgram(this.programInfo.program);
|
|
3337
|
+
});
|
|
3338
|
+
for (let [e, n] of Object.entries(this.encoders)) {
|
|
3339
|
+
let i = t.rangeTextures.get(n.scale);
|
|
3340
|
+
i && r.push(() => J(this.programInfo, { [ns + e]: i }));
|
|
3341
|
+
}
|
|
3342
|
+
r.push(...this.selectionTextureOps), this.getSampleFacetMode() == Cc && r.push(() => {
|
|
3343
|
+
let t = e.placement?.source;
|
|
3344
|
+
if (!t) throw Error("No placement source available.");
|
|
3345
|
+
J(this.programInfo, { uSampleFacetTexture: this.glHelper.getPlacementTexture(t) });
|
|
3346
|
+
});
|
|
3347
|
+
let i = (e.picking ?? !1) && this.isPickingParticipant();
|
|
3348
|
+
return r.push(() => Qa(this.viewUniformInfo, {
|
|
3349
|
+
uViewOpacity: this.unitView.getEffectiveOpacity(),
|
|
3350
|
+
uPickingEnabled: i
|
|
3351
|
+
})), this.opaque || e.picking ? r.push(() => n.disable(n.BLEND)) : r.push(() => n.enable(n.BLEND)), r;
|
|
3352
|
+
}
|
|
3353
|
+
prepareSampleFacetRendering(e) {
|
|
3354
|
+
let t = e.sampleFacetRenderingOptions, n = this.programInfo.uniformSetters.uSampleFacet;
|
|
3355
|
+
if (t && n) {
|
|
3356
|
+
let e = t.pixelToUnit, r = t.locSize.location * e, i = t.locSize.size * e;
|
|
3357
|
+
if (r > 1 || r + i < 0) return !1;
|
|
3358
|
+
this.gl.uniform2f(n.location, r, i);
|
|
3359
|
+
}
|
|
3360
|
+
return !0;
|
|
3361
|
+
}
|
|
3362
|
+
render(e) {}
|
|
3363
|
+
createRenderCallback(e, t) {
|
|
3364
|
+
if (!this.bufferInfo) return () => void 0;
|
|
3365
|
+
let n = this, r, i = this.unitView.getScaleResolution("x")?.getScale(), a = i && C(i.type), o = ["index", "locus"].includes(i?.type) ? -1 : 0, s = [0, 0];
|
|
3366
|
+
r = (t) => {
|
|
3367
|
+
if (a && t.xIndex) {
|
|
3368
|
+
let n = i.domain(), r = Math.abs(n[1] - n[0]), a = t.xIndex(n[0] + o - r, n[1] + r, s), c = a[0], l = a[1] - c;
|
|
3369
|
+
l > 0 && e(c, l);
|
|
3370
|
+
} else e(t.offset, t.count);
|
|
3371
|
+
};
|
|
3372
|
+
let c = this.rangeMap.get(void 0).count == 0 ? t.facetId : void 0, l = this.rangeMap.get(c);
|
|
3373
|
+
return t.sampleFacetRenderingOptions ? function() {
|
|
3374
|
+
l.count && n.prepareSampleFacetRendering(t) && r(l);
|
|
3375
|
+
} : function() {
|
|
3376
|
+
l.count && r(l);
|
|
3377
|
+
};
|
|
3378
|
+
}
|
|
3379
|
+
setViewport(e, t, n, r, i, a = xc) {
|
|
3380
|
+
n = n.flatten();
|
|
3381
|
+
let o = this.gl, s = this.properties, c = a, l = a, u, d = Dc(e, n, s.clip === "never" ? void 0 : r, !1), f = d.coords;
|
|
3382
|
+
if (d.requiresScissor) {
|
|
3383
|
+
if (!f.isDefined()) return !1;
|
|
3384
|
+
let r = [
|
|
3385
|
+
f.x,
|
|
3386
|
+
e.height - f.y2,
|
|
3387
|
+
f.width,
|
|
3388
|
+
f.height
|
|
3389
|
+
].map((e) => e * t), i = r.map((e) => Math.floor(e)), a = r[0] - i[0], s = r[1] - i[1];
|
|
3390
|
+
o.viewport(...i), o.scissor(...i), o.enable(o.SCISSOR_TEST), u = {
|
|
3391
|
+
uViewOffset: [(n.x - f.x + c + a / t) / f.width, (f.y2 - n.y2 - l + s / t) / f.height],
|
|
3392
|
+
uViewScale: [n.width / f.width, n.height / f.height]
|
|
3393
|
+
};
|
|
3394
|
+
} else {
|
|
3395
|
+
if (!n.isDefined()) return !1;
|
|
3396
|
+
o.viewport(0, 0, Math.round(e.width * t), Math.round(e.height * t)), o.disable(o.SCISSOR_TEST), u = {
|
|
3397
|
+
uViewOffset: [(n.x + c) / e.width, (e.height - n.y - l - n.height) / e.height],
|
|
3398
|
+
uViewScale: [n.width / e.width, n.height / e.height]
|
|
3399
|
+
};
|
|
3400
|
+
}
|
|
3401
|
+
return Qa(this.viewUniformInfo, {
|
|
3402
|
+
...u,
|
|
3403
|
+
uViewportSize: [n.width, n.height],
|
|
3404
|
+
uLogicalVisibleRect: Oc(n, i),
|
|
3405
|
+
uCullByVisibleRange: [+(s.cullByVisibleRange === !0 || s.cullByVisibleRange === "x"), +(s.cullByVisibleRange === !0 || s.cullByVisibleRange === "y")],
|
|
3406
|
+
uDevicePixelRatio: t
|
|
3407
|
+
}), Za(this.gl, this.programInfo, this.viewUniformInfo), !0;
|
|
3408
|
+
}
|
|
3409
|
+
}, Ec = class extends ue {
|
|
3410
|
+
constructor() {
|
|
3411
|
+
super([], JSON.stringify);
|
|
3412
|
+
}
|
|
3413
|
+
get(e) {
|
|
3414
|
+
let t = super.get(e);
|
|
3415
|
+
return t === void 0 && (t = {
|
|
3416
|
+
offset: 0,
|
|
3417
|
+
count: 0,
|
|
3418
|
+
xIndex: void 0
|
|
3419
|
+
}, super.set(e, t)), t;
|
|
3420
|
+
}
|
|
3421
|
+
migrateEntries(e) {
|
|
3422
|
+
for (let [t, n] of this.entries()) e.has(t) || (n.offset = 0, n.count = 0, n.xIndex = void 0);
|
|
3423
|
+
for (let [t, n] of e.entries()) Object.assign(this.get(t), n);
|
|
3424
|
+
}
|
|
3425
|
+
};
|
|
3426
|
+
function Dc(e, t, n, r = !0) {
|
|
3427
|
+
if (!n || !n.clipX && !n.clipY) return {
|
|
3428
|
+
requiresScissor: !1,
|
|
3429
|
+
coords: t
|
|
3430
|
+
};
|
|
3431
|
+
let i = r ? t.intersect(n.rect) : n.rect;
|
|
3432
|
+
return n.clipX || (i = i.modify({
|
|
3433
|
+
x: 0,
|
|
3434
|
+
width: e.width
|
|
3435
|
+
})), n.clipY || (i = i.modify({
|
|
3436
|
+
y: 0,
|
|
3437
|
+
height: e.height
|
|
3438
|
+
})), {
|
|
3439
|
+
requiresScissor: !0,
|
|
3440
|
+
coords: i.flatten()
|
|
3441
|
+
};
|
|
3442
|
+
}
|
|
3443
|
+
function Oc(e, t) {
|
|
3444
|
+
let n = t?.clipX ? (t.rect.x - e.x) / e.width : 0, r = t?.clipX ? (t.rect.x2 - e.x) / e.width : 1;
|
|
3445
|
+
return [
|
|
3446
|
+
n,
|
|
3447
|
+
t?.clipY ? (e.y2 - t.rect.y2) / e.height : 0,
|
|
3448
|
+
r,
|
|
3449
|
+
t?.clipY ? (e.y2 - t.rect.y) / e.height : 1
|
|
3450
|
+
];
|
|
3451
|
+
}
|
|
3452
|
+
//#endregion
|
|
3453
|
+
//#region ../core/src/rendering/webgl/marks/arrow.js
|
|
3454
|
+
var kc = Math.PI / 180, Ac = 1e-6, jc = 1, Mc = 90, Nc = ["triangle", "open"], Pc = ["inside", "outside"], Fc = class extends Tc {
|
|
3455
|
+
getAttributes() {
|
|
3456
|
+
return [
|
|
3457
|
+
"uniqueId",
|
|
3458
|
+
"facetIndex",
|
|
3459
|
+
"x",
|
|
3460
|
+
"x2",
|
|
3461
|
+
"y",
|
|
3462
|
+
"y2",
|
|
3463
|
+
"xOffset",
|
|
3464
|
+
"yOffset",
|
|
3465
|
+
"x2Offset",
|
|
3466
|
+
"y2Offset",
|
|
3467
|
+
"fill",
|
|
3468
|
+
"stroke",
|
|
3469
|
+
"fillOpacity",
|
|
3470
|
+
"strokeOpacity",
|
|
3471
|
+
"strokeWidth",
|
|
3472
|
+
"size",
|
|
3473
|
+
"direction"
|
|
3474
|
+
];
|
|
3475
|
+
}
|
|
3476
|
+
initializeGraphics() {
|
|
3477
|
+
super.initializeGraphics(), this.createAndLinkShaders(nc, rc, [ic]);
|
|
3478
|
+
}
|
|
3479
|
+
finalizeGraphicsInitialization() {
|
|
3480
|
+
super.finalizeGraphicsInitialization(), this.gl.useProgram(this.programInfo.program);
|
|
3481
|
+
let e = this.properties;
|
|
3482
|
+
this.registerMarkUniformValue("uHeadSlope", e.headAngle, Lc), this.registerMarkUniformValue("uHeadNotchSlope", e.headNotchAngle, Lc), this.registerMarkUniformValue("uHeadShape", e.headShape, (e) => Ic(Nc, e)), this.registerMarkUniformValue("uMinSize", e.minSize), this.registerMarkUniformValue("uHeadWidth", e.headWidth), this.registerMarkUniformValue("uStartNotch", e.startNotch), this.registerMarkUniformValue("uMinStemLength", e.minStemLength), this.registerMarkUniformValue("uHeadSpacing", e.headSpacing ?? -1, Rc), this.registerMarkUniformValue("uStem", e.stem), this.registerMarkUniformValue("uHeadPlacement", e.headPlacement, (e) => Ic(Pc, e));
|
|
3483
|
+
}
|
|
3484
|
+
updateGraphicsData(e) {
|
|
3485
|
+
let t = e.getItemCount(), n = new fc({
|
|
3486
|
+
encoders: this.encoders,
|
|
3487
|
+
attributes: this.getAttributes(),
|
|
3488
|
+
numItems: t
|
|
3489
|
+
});
|
|
3490
|
+
n.addBatches(e.facetBatches);
|
|
3491
|
+
let r = n.toArrays();
|
|
3492
|
+
this.rangeMap.migrateEntries(r.rangeMap), this.updateBufferInfo(r);
|
|
3493
|
+
}
|
|
3494
|
+
prepareRender(e) {
|
|
3495
|
+
let t = super.prepareRender(e);
|
|
3496
|
+
return t.push(() => this.bindOrSetMarkUniformBlock()), t.push(() => Y(this.gl, this.programInfo, this.vertexArrayInfo)), t;
|
|
3497
|
+
}
|
|
3498
|
+
render(e) {
|
|
3499
|
+
let t = this.gl;
|
|
3500
|
+
return this.createRenderCallback((e, n) => {
|
|
3501
|
+
ao(t, this.vertexArrayInfo, t.TRIANGLE_STRIP, n, e);
|
|
3502
|
+
}, e);
|
|
3503
|
+
}
|
|
3504
|
+
};
|
|
3505
|
+
function Ic(e, t) {
|
|
3506
|
+
let n = e.indexOf(t);
|
|
3507
|
+
if (n < 0) throw Error(`Unsupported arrow mark value: ${t}`);
|
|
3508
|
+
return n;
|
|
3509
|
+
}
|
|
3510
|
+
function Lc(e) {
|
|
3511
|
+
return Math.max(Math.tan(Math.min(Math.max(e, jc), Mc) * kc), Ac);
|
|
3512
|
+
}
|
|
3513
|
+
function Rc(e) {
|
|
3514
|
+
return e ?? -1;
|
|
3515
|
+
}
|
|
3516
|
+
//#endregion
|
|
3517
|
+
//#region ../core/src/rendering/webgl/marks/link.vertex.glsl
|
|
3518
|
+
var zc = "flat out vec4 vColor;\n\n/** Stroke width */\nflat out float vSize;\n\n/** The distance from the line center to the direction of normal in pixels */\nout float vNormalLengthInPixels;\n\nflat out float vGamma;\n\nconst int SHAPE_ARC = 0;\nconst int SHAPE_DOME = 1;\nconst int SHAPE_DIAGONAL = 2;\nconst int SHAPE_LINE = 3;\nconst int ORIENT_VERTICAL = 0;\nconst int ORIENT_HORIZONTAL = 1;\n\nfloat distanceFromLine(vec2 pointOnLine1, vec2 pointOnLine2, vec2 point) {\n vec2 a = point - pointOnLine1;\n vec2 b = pointOnLine2 - pointOnLine1;\n vec2 proj = dot(a, b) / dot(b, b) * b;\n return length(a - proj);\n}\n\nbool isInsideViewport(vec2 point, float marginFactor) {\n vec2 margin = uViewportSize * vec2(marginFactor);\n return point.x >= -margin.x\n && point.x <= uViewportSize.x + margin.x\n && point.y >= -margin.y\n && point.y <= uViewportSize.y + margin.y;\n}\n\nfloat inverseSmoothstep(float t) {\n t = clamp(t, 0.0, 1.0);\n // The chord-axis coordinate of ARC/DOME follows the smoothstep curve.\n return 0.5 - sin(asin(1.0 - 2.0 * t) / 3.0);\n}\n\n/**\n * Remaps the parameter t to concentrate vertices to the part that is visible in the viewport.\n * This keeps the tightly bent endpoints smooth even when zooming in very close.\n */\nfloat remapVisibleChordParameter(\n float stripT,\n float chordStart,\n float chordEnd,\n float viewportLength\n) {\n // Concentrate samples in the viewport-visible chord interval without dropping the rest.\n float chordMin = min(chordStart, chordEnd);\n float chordMax = max(chordStart, chordEnd);\n float chordSpan = chordMax - chordMin;\n\n if (chordSpan <= 0.0) {\n return 0.0;\n }\n\n float visibleChordMin = max(chordMin, 0.0);\n float visibleChordMax = min(chordMax, viewportLength);\n\n if (visibleChordMax <= visibleChordMin) {\n return stripT;\n }\n\n float visibleTMin = inverseSmoothstep((visibleChordMin - chordMin) / chordSpan);\n float visibleTMax = inverseSmoothstep((visibleChordMax - chordMin) / chordSpan);\n float visibleTSpan = visibleTMax - visibleTMin;\n float offscreenTSpan = visibleTMin + (1.0 - visibleTMax);\n\n if (offscreenTSpan <= 0.0) {\n return stripT;\n }\n\n float visibleShare = clamp(0.75 + (1.0 - visibleTSpan) * 0.2, 0.75, 0.95);\n float offscreenShare = 1.0 - visibleShare;\n float leftShare = offscreenShare * visibleTMin / offscreenTSpan;\n float rightShare = offscreenShare * (1.0 - visibleTMax) / offscreenTSpan;\n\n if (stripT <= leftShare) {\n return leftShare > 0.0 ? mix(0.0, visibleTMin, stripT / leftShare) : visibleTMin;\n }\n\n float visibleStart = leftShare;\n float visibleEnd = visibleStart + visibleShare;\n\n if (stripT <= visibleEnd) {\n return visibleShare > 0.0\n ? mix(visibleTMin, visibleTMax, (stripT - visibleStart) / visibleShare)\n : visibleTMin;\n }\n\n return rightShare > 0.0\n ? mix(visibleTMax, 1.0, (stripT - visibleEnd) / rightShare)\n : visibleTMax;\n}\n\nvoid clampChordToViewport(inout vec2 p1, inout vec2 p4, inout float chordLength) {\n if (chordLength > uMaxChordLength) {\n vec2 chordVector = p4 - p1;\n vec2 unitChordVector = normalize(chordVector);\n\n if (isInsideViewport(p1, 2.0)) {\n chordLength = uMaxChordLength;\n p4 = p1 + unitChordVector * uMaxChordLength;\n } else if (isInsideViewport(p4, 2.0)) {\n chordLength = uMaxChordLength;\n p1 = p4 - unitChordVector * uMaxChordLength;\n }\n }\n}\n\nvoid clampDomeApex(inout vec2 p1, inout vec2 p4, int orient) {\n if (orient == ORIENT_VERTICAL) {\n if (p4.x > 0.0) {\n p1.x = max(p1.x, -p4.x);\n }\n if (p1.x < uViewportSize.x) {\n p4.x = min(p4.x, 2.0 * uViewportSize.x - p1.x);\n }\n } else {\n if (p4.y > 0.0) {\n p1.y = max(p1.y, -p4.y);\n }\n if (p1.y < uViewportSize.y) {\n p4.y = min(p4.y, 2.0 * uViewportSize.y - p1.y);\n }\n }\n}\n\nvoid main(void) {\n float pixelSize = 1.0 / uDevicePixelRatio;\n float opacity = getScaled_opacity() * uViewOpacity;\n\n // The bezier's control points\n vec2 p1, p2, p3, p4;\n\n vec2 a = applyOffset(\n applySampleFacet(vec2(getScaled_x(), getScaled_y())),\n vec2(getScaled_xOffset(), getScaled_yOffset())\n ) * uViewportSize;\n vec2 b = applyOffset(\n applySampleFacet(vec2(getScaled_x2(), getScaled_y2())),\n vec2(getScaled_x2Offset(), getScaled_y2Offset())\n ) * uViewportSize;\n\n if (uShape <= SHAPE_DOME) {\n if (uShape == SHAPE_DOME) {\n vec2 height = vec2(0.0);\n if (uOrient == ORIENT_VERTICAL) {\n p1 = vec2(min(a.x, b.x), b.y);\n p4 = vec2(max(a.x, b.x), b.y);\n height = vec2(0.0, a.y - b.y);\n\n float chordLength = length(p4 - p1);\n clampChordToViewport(p1, p4, chordLength);\n if (uClampApex) {\n clampDomeApex(p1, p4, ORIENT_VERTICAL);\n }\n\n } else {\n p1 = vec2(b.x, min(a.y, b.y));\n p4 = vec2(b.x, max(a.y, b.y));\n height = vec2(a.x - b.x, 0.0);\n\n float chordLength = length(p4 - p1);\n clampChordToViewport(p1, p4, chordLength);\n if (uClampApex) {\n clampDomeApex(p1, p4, ORIENT_HORIZONTAL);\n }\n }\n\n vec2 controlOffset = height / 0.75;\n p2 = p1 + controlOffset;\n p3 = p4 + controlOffset;\n\n } if (uShape == SHAPE_ARC) {\n p1 = a;\n p4 = b;\n\n vec2 chordVector = p4 - p1;\n vec2 unitChordVector = normalize(chordVector);\n vec2 chordNormal = vec2(-unitChordVector.y, unitChordVector.x);\n float chordLength = length(chordVector);\n clampChordToViewport(p1, p4, chordLength);\n\n float height = max(\n chordLength / 2.0 * uArcHeightFactor,\n uMinArcHeight\n );\n\n // This is a bit poor approximation of a circular arc, but it's probably enough for most purposes.\n // TODO: Consider a more sophisticated approach: https://stackoverflow.com/a/44829356/1547896\n vec2 controlOffset = chordNormal * height / 0.75;\n p2 = p1 + controlOffset;\n p3 = p4 + controlOffset;\n }\n\n } else if (uShape == SHAPE_DIAGONAL) {\n if (uOrient == ORIENT_VERTICAL) {\n p1 = a;\n p2 = vec2(a.x, (a.y + b.y) / 2.0);\n p3 = vec2(b.x, (a.y + b.y) / 2.0);\n p4 = b;\n } else {\n p1 = a;\n p2 = vec2((a.x + b.x) / 2.0, a.y);\n p3 = vec2((a.x + b.x) / 2.0, b.y);\n p4 = b;\n }\n } else if (uShape == SHAPE_LINE) {\n p1 = a;\n p2 = (a + b) / 2.0;\n p3 = p2;\n p4 = b;\n }\n\n vec2 strip = vec2(\n float(gl_VertexID / 2) / float(uSegmentBreaks),\n float(gl_VertexID % 2) - 0.5\n );\n\n float t = strip.x;\n\n if (uShape == SHAPE_DOME) {\n if (uOrient == ORIENT_VERTICAL) {\n t = remapVisibleChordParameter(strip.x, p1.x, p4.x, uViewportSize.x);\n } else {\n t = remapVisibleChordParameter(strip.x, p1.y, p4.y, uViewportSize.y);\n }\n } else if (uShape == SHAPE_ARC) {\n if (a.y == b.y) {\n t = remapVisibleChordParameter(strip.x, p1.x, p4.x, uViewportSize.x);\n } else if (a.x == b.x) {\n t = remapVisibleChordParameter(strip.x, p1.y, p4.y, uViewportSize.y);\n }\n }\n\n vec2 p;\n vec2 tangent;\n\n // de Casteljau evaluation keeps the cubic stable for long chords.\n vec2 q1 = mix(p1, p2, t);\n vec2 q2 = mix(p2, p3, t);\n vec2 q3 = mix(p3, p4, t);\n\n vec2 r1 = mix(q1, q2, t);\n vec2 r2 = mix(q2, q3, t);\n\n p = mix(r1, r2, t);\n tangent = 3.0 * (r2 - r1);\n\n tangent = normalize(tangent);\n vec2 normal = vec2(-tangent.y, tangent.x);\n\n float size = getScaled_size();\n\n // Avoid artifacts in very thin lines by clamping the size and adjusting opacity respectively\n if (size < pixelSize) {\n opacity *= size / pixelSize;\n size = pixelSize;\n }\n\n // Handle minimum picking size or add an extra pixel to the stroke width to accommodate edge antialiasing\n float paddedSize = uPickingEnabled\n ? max(size, uMinPickingSize)\n : size + pixelSize;\n\n vNormalLengthInPixels = strip.y * paddedSize;\n \n if (uShape == SHAPE_ARC &&\n uArcFadingDistance[0] > 0.0 &&\n uArcFadingDistance[1] > 0.0 &&\n (!uNoFadingOnPointSelection || !isPointSelected()))\n {\n float d = distanceFromLine(p1, p4, p);\n float distanceOpacity = smoothstep(uArcFadingDistance[1], uArcFadingDistance[0], d); \n\n // Fade out\n opacity *= distanceOpacity;\n\n // Collapse fully transparent triangles to skip fragment processing \n if (distanceOpacity <= 0.0) {\n vNormalLengthInPixels = 0.0;\n }\n }\n\n // Extrude\n p += normal * vNormalLengthInPixels;\n\n gl_Position = pixelsToNdc(p);\n\n vec3 color = getScaled_color();\n\n vColor = vec4(color * opacity, opacity);\n\n vGamma = getGammaForColor(color);\n\n vSize = paddedSize;\n\n setupPicking();\n}\n", Bc = "flat in vec4 vColor;\nflat in float vSize;\nin float vNormalLengthInPixels;\nflat in float vGamma;\n\nout lowp vec4 fragColor;\n\nvoid main(void) {\n float dpr = uDevicePixelRatio;\n\n float distance = abs(vNormalLengthInPixels);\n float opacity = clamp(((vSize / 2.0 - distance) * dpr), 0.0, 1.0);\n\n opacity = pow(opacity, vGamma);\n\n fragColor = vColor * opacity;\n\n if (uPickingEnabled) {\n fragColor = vPickingColor;\n }\n}\n", Vc = "layout(std140) uniform Mark {\n uniform float uArcHeightFactor;\n\n /** Make very small arcs visible */\n uniform float uMinArcHeight;\n\n /** The minimum stroke width in pixels when rendering into the picking buffer */\n uniform float uMinPickingSize;\n\n uniform int uShape;\n uniform int uOrient;\n uniform bool uClampApex;\n\n // In pixels\n uniform float uMaxChordLength;\n // In pixels\n uniform vec2 uArcFadingDistance;\n uniform bool uNoFadingOnPointSelection;\n\n uniform int uSegmentBreaks;\n\n#pragma markUniforms\n};\n", Hc = [
|
|
3519
|
+
"arc",
|
|
3520
|
+
"dome",
|
|
3521
|
+
"diagonal",
|
|
3522
|
+
"line"
|
|
3523
|
+
], Uc = ["vertical", "horizontal"], Wc = class extends Tc {
|
|
3524
|
+
constructor(e, t, n) {
|
|
3525
|
+
super(e, t, n), this._baseInstanceExt = void 0;
|
|
3526
|
+
}
|
|
3527
|
+
getAttributes() {
|
|
3528
|
+
return [
|
|
3529
|
+
"uniqueId",
|
|
3530
|
+
"facetIndex",
|
|
3531
|
+
"x",
|
|
3532
|
+
"x2",
|
|
3533
|
+
"y",
|
|
3534
|
+
"y2",
|
|
3535
|
+
"xOffset",
|
|
3536
|
+
"yOffset",
|
|
3537
|
+
"x2Offset",
|
|
3538
|
+
"y2Offset",
|
|
3539
|
+
"size",
|
|
3540
|
+
"color",
|
|
3541
|
+
"opacity"
|
|
3542
|
+
];
|
|
3543
|
+
}
|
|
3544
|
+
initializeGraphics() {
|
|
3545
|
+
super.initializeGraphics(), this._baseInstanceExt = this.gl.getExtension("WEBGL_draw_instanced_base_vertex_base_instance"), this.createAndLinkShaders(zc, Bc, [Vc]);
|
|
3546
|
+
}
|
|
3547
|
+
finalizeGraphicsInitialization() {
|
|
3548
|
+
super.finalizeGraphicsInitialization(), this.gl.useProgram(this.programInfo.program);
|
|
3549
|
+
let e = this.properties;
|
|
3550
|
+
this.registerMarkUniformValue("uArcFadingDistance", e.arcFadingDistance, (e) => e || [0, 0]), this.registerMarkUniformValue("uArcHeightFactor", e.arcHeightFactor), this.registerMarkUniformValue("uMinArcHeight", e.minArcHeight), this.registerMarkUniformValue("uMinPickingSize", e.minPickingSize), this.registerMarkUniformValue("uShape", e.linkShape, (e) => Hc.indexOf(e)), this.registerMarkUniformValue("uOrient", e.orient, (e) => Uc.indexOf(e)), this.registerMarkUniformValue("uClampApex", e.clampApex, (e) => !!e), this.registerMarkUniformValue("uMaxChordLength", e.maxChordLength), this.registerMarkUniformValue("uSegmentBreaks", e.segments, (e) => e), this.registerMarkUniformValue("uNoFadingOnPointSelection", e.noFadingOnPointSelection, (e) => !!e);
|
|
3551
|
+
}
|
|
3552
|
+
updateGraphicsData(e) {
|
|
3553
|
+
let t = e.getItemCount(), n = new mc({
|
|
3554
|
+
encoders: this.encoders,
|
|
3555
|
+
attributes: this.getAttributes(),
|
|
3556
|
+
numItems: t
|
|
3557
|
+
});
|
|
3558
|
+
n.addBatches(e.facetBatches);
|
|
3559
|
+
let r = n.toArrays();
|
|
3560
|
+
this.rangeMap.migrateEntries(r.rangeMap), this.arrays = Object.fromEntries(Object.entries(r.arrays).map(([e, t]) => [e, {
|
|
3561
|
+
...t,
|
|
3562
|
+
data: void 0
|
|
3563
|
+
}])), this.updateBufferInfo(r);
|
|
3564
|
+
}
|
|
3565
|
+
prepareRender(e) {
|
|
3566
|
+
let t = super.prepareRender(e);
|
|
3567
|
+
return t.push(() => this.bindOrSetMarkUniformBlock()), this._baseInstanceExt ? t.push(() => Y(this.gl, this.programInfo, this.vertexArrayInfo)) : t.push(() => this.gl.bindVertexArray(null)), t;
|
|
3568
|
+
}
|
|
3569
|
+
render(e) {
|
|
3570
|
+
let t = this.gl, n = () => (this.markUniformInfo.uniforms.uSegmentBreaks[0] + 1) * 2;
|
|
3571
|
+
return this._baseInstanceExt ? this.createRenderCallback((e, r) => {
|
|
3572
|
+
this._baseInstanceExt.drawArraysInstancedBaseInstanceWEBGL(t.TRIANGLE_STRIP, 0, n(), r, e);
|
|
3573
|
+
}, e) : this.createRenderCallback((e, r) => {
|
|
3574
|
+
for (let t of Object.entries(this.bufferInfo.attribs)) {
|
|
3575
|
+
let [n, r] = t;
|
|
3576
|
+
r.buffer && r.numComponents && r.divisor && (r.offset = e * this.arrays[n].numComponents * this.bytesPerElement.get(n));
|
|
3577
|
+
}
|
|
3578
|
+
Y(t, this.programInfo, this.bufferInfo), t.drawArraysInstanced(t.TRIANGLE_STRIP, 0, n(), r);
|
|
3579
|
+
}, e);
|
|
3580
|
+
}
|
|
3581
|
+
}, Gc = "flat out float vRadius;\nflat out float vRadiusWithPadding;\nflat out lowp vec4 vFillColor;\nflat out lowp vec4 vStrokeColor;\nflat out lowp float vShape;\nflat out lowp float vHalfStrokeWidth;\nflat out mat2 vRotationMatrix;\n\n// Copypaste from fragment shader\nconst float CIRCLE = 0.0;\nconst float SQUARE = 1.0;\nconst float CROSS = 2.0;\nconst float DIAMOND = 3.0;\nconst float TRIANGLE_UP = 4.0;\nconst float TRIANGLE_RIGHT = 5.0;\nconst float TRIANGLE_DOWN = 6.0;\nconst float TRIANGLE_LEFT = 7.0;\nconst float TICK_UP = 8.0;\nconst float TICK_RIGHT = 9.0;\nconst float TICK_DOWN = 10.0;\nconst float TICK_LEFT = 11.0;\nconst float X = 12.0;\nconst float PLUS = 13.0;\n\nfloat computeSemanticThresholdFactor() {\n // TODO: add smooth transition\n return getScaled_semanticScore() >= uSemanticThreshold ? 1.0 : 0.0;\n}\n\n// TODO: Move this into common.glsl or something\nvec2 getDxDy() {\n#if defined(dx_DEFINED) || defined(dy_DEFINED)\n return vec2(getScaled_dx(), getScaled_dy()) / uViewportSize;\n#else\n return vec2(0.0, 0.0);\n#endif\n}\n\nvoid main(void) {\n float shapeAngle = 0.0;\n\n // Selected points should always be visible\n float semanticThresholdFactor = isPointSelected()\n ? 1.0\n : computeSemanticThresholdFactor();\n\n if (semanticThresholdFactor <= 0.0) {\n gl_PointSize = 0.0;\n // Place the vertex outside the viewport. The default (0, 0) makes this super-slow\n // on Apple Silicon. Probably related to the tile-based GPU architecture.\n gl_Position = vec4(100.0, 0.0, 0.0, 0.0);\n // Exit early. MAY prevent some unnecessary calculations.\n return;\n }\n\n float size = getScaled_size();\n vec2 pos = vec2(getScaled_x(), getScaled_y()) + getDxDy();\n vec2 facetedPos = applyOffset(\n applySampleFacet(pos),\n vec2(getScaled_xOffset(), getScaled_yOffset())\n );\n\n#ifdef VISIBLE_RANGE_CULLING\n if (isOutsideVisibleRange(facetedPos)) {\n gl_PointSize = 0.0;\n gl_Position = vec4(100.0, 0.0, 0.0, 0.0);\n return;\n }\n#endif\n\n gl_Position = unitToNdc(facetedPos);\n\n float strokeWidth = getScaled_strokeWidth();\n float strokeOpacity = getScaled_strokeOpacity();\n vShape = getScaled_shape();\n\n // Line-only shapes use their width even when the stroke falls back to the\n // fill color. An invisible stroke must not inset other filled shapes.\n if (strokeOpacity <= 0.0 && vShape != X && vShape != PLUS) {\n strokeWidth = 0.0;\n }\n\n float diameter = sqrt(size) *\n uScaleFactor *\n semanticThresholdFactor;\n\n // Clamp minimum size and adjust opacity instead. Yields more pleasing result,\n // no flickering etc.\n float opacity = uViewOpacity;\n if (strokeWidth <= 0.0 || uInwardStroke) {\n float minDiameter = 1.0 / uDevicePixelRatio;\n if (diameter < minDiameter) {\n // We do some \"cheap\" gamma correction here. It breaks on dark background, though.\n // First we take a square of the size and then apply \"gamma\" of 1.5.\n opacity *= pow(diameter / minDiameter, 2.5);\n diameter = minDiameter;\n }\n }\n\n float fillOpa = getScaled_fillOpacity() * opacity;\n float strokeOpa = strokeOpacity * opacity;\n\n // Circle doesn't have sharp corners. Do some special optimizations to minimize the point size.\n bool circle = vShape == 0.0;\n\n if (vShape > TICK_UP && vShape <= TICK_LEFT) {\n shapeAngle = (vShape - TICK_UP) * 90.0;\n vShape = TICK_UP;\n } else if (vShape > TRIANGLE_UP && vShape <= TRIANGLE_LEFT) {\n shapeAngle = (vShape - TRIANGLE_UP) * 90.0;\n vShape = TRIANGLE_UP;\n } else if (vShape == X) {\n // The x shape reuses the perpendicular stroke geometry of plus.\n shapeAngle = -45.0;\n }\n\n float angleInDegrees = getScaled_angle();\n float angle = -(shapeAngle + angleInDegrees) * PI / 180.0;\n float sinTheta = sin(angle);\n float cosTheta = cos(angle);\n vRotationMatrix = mat2(cosTheta, sinTheta, -sinTheta, cosTheta);\n\n // Not needed if we would draw rotated quads instead of gl.POINTS\n float roomForRotation = circle ? 1.0 : sin(mod(angle, PI / 2.0) + PI / 4.0) / sin(PI / 4.0);\n\n float aaPadding = 1.0 / uDevicePixelRatio;\n float rotationPadding = (diameter * roomForRotation) - diameter;\n // sqrt(3.0) ensures that the angles of equilateral triangles have enough room\n float strokePadding = uInwardStroke ? 0.0 : strokeWidth * (circle ? 1.0 : sqrt(3.0));\n float padding = rotationPadding + strokePadding + aaPadding;\n\n gl_PointSize = max(\n (diameter + padding),\n uPickingEnabled ? uMinPickingSize : 0.0\n ) * uDevicePixelRatio;\n\n vRadius = diameter / 2.0;\n vRadiusWithPadding = vRadius + padding / 2.0;\n\n vHalfStrokeWidth = strokeWidth / 2.0;\n\n vFillColor = vec4(getScaled_fill() * fillOpa, fillOpa);\n vStrokeColor = vec4(getScaled_stroke() * strokeOpa, strokeOpa);\n\n setupPicking();\n}\n", Kc = "const lowp vec4 white = vec4(1.0);\nconst lowp vec4 black = vec4(0.0, 0.0, 0.0, 1.0);\n\nflat in float vRadius;\nflat in float vRadiusWithPadding;\n\nflat in lowp vec4 vFillColor;\nflat in lowp vec4 vStrokeColor;\nflat in lowp float vShape;\nflat in lowp float vHalfStrokeWidth;\n\nflat in mat2 vRotationMatrix;\n\nout lowp vec4 fragColor;\n\n// Copypaste from vertex shader\nconst float CIRCLE = 0.0;\nconst float SQUARE = 1.0;\nconst float CROSS = 2.0;\nconst float DIAMOND = 3.0;\nconst float TRIANGLE_UP = 4.0;\nconst float TICK_UP = 8.0;\nconst float X = 12.0;\nconst float PLUS = 13.0;\n\n// The distance functions are inspired by:\n// http://www.iquilezles.org/www/articles/distfunctions2d/distfunctions2d.htm\n// However, these are not true distance functions, because the corners need to be sharp.\n\nfloat circle(vec2 p, float r) {\n return length(p) - r;\n}\n\nfloat square(vec2 p, float r) {\n p = abs(p);\n return max(p.x, p.y) - r;\n}\n\nfloat tickUp(vec2 p, float r) {\n float halfR = r * 0.5;\n p.y += halfR;\n p = abs(p);\n return max(p.x - r * 0.15, p.y - halfR);\n}\n\nfloat equilateralTriangle(vec2 p, float r) {\n p.y = -p.y;\n float k = sqrt(3.0);\n float kr = k * r;\n p.y -= kr / 2.0;\n return max((abs(p.x) * k + p.y) / 2.0, -p.y - kr);\n}\n\nfloat crossShape(vec2 p, float r, float armHalfWidth) {\n p = abs(p);\n\n vec2 b = vec2(armHalfWidth, r);\n vec2 v = abs(p) - b.xy;\n vec2 h = abs(p) - b.yx;\n return min(max(v.x, v.y), max(h.x, h.y));\n}\n\nfloat diamond(vec2 p, float r) {\n p = abs(p);\n return (max(abs(p.x - p.y), abs(p.x + p.y)) - r) / sqrt(2.0);\n}\n\nvoid main() {\n float d;\n bool lineShape = false;\n\n /** Normalized point coord */\n vec2 p = vRotationMatrix * (2.0 * gl_PointCoord - 1.0) * vRadiusWithPadding;\n float r = vRadius;\n\n // We could also use textures here. Could even be faster, because we have plenty of branching here.\n if (vShape == CIRCLE) {\n d = circle(p, r);\n\n } else if (vShape == SQUARE) {\n d = square(p, r);\n\n } else if (vShape == CROSS) {\n d = crossShape(p, r, r * 0.4);\n\n } else if (vShape == DIAMOND) {\n d = diamond(p, r);\n\n } else if (vShape == TRIANGLE_UP) {\n d = equilateralTriangle(p, r);\n\n } else if (vShape == TICK_UP) {\n d = tickUp(p, r);\n\n } else if (vShape == X || vShape == PLUS) {\n float lineLength = vShape == X ? r * sqrt(2.0) : r;\n d = crossShape(p, lineLength, vHalfStrokeWidth);\n lineShape = true;\n\n } else {\n d = 0.0;\n }\n\n if (!uPickingEnabled) {\n lowp vec4 fillColor = lineShape\n ? (vStrokeColor.a > 0.0 ? vStrokeColor : vFillColor)\n : mix(vFillColor, white, -d * uGradientStrength / vRadius);\n\n fragColor = distanceToColor(\n d + (!lineShape && uInwardStroke ? vHalfStrokeWidth : 0.0),\n fillColor,\n vStrokeColor,\n vec4(0.0),\n lineShape ? 0.0 : vHalfStrokeWidth);\n\n } else if (d - (lineShape ? 0.0 : vHalfStrokeWidth) <= 0.0) {\n fragColor = vPickingColor;\n\n } else {\n discard;\n }\n}\n", qc = "layout(std140) uniform Mark {\n /**\n * The stroke should only grow inwards, e.g, the diameter/outline is not affected by the stroke width.\n * Thus, a point that has a zero size has no visible stroke. This allows strokes to be used with\n * geometric zoom, etc.\n */\n uniform bool uInwardStroke;\n\n /** The minimum point size in pixels when rendering into the picking buffer */\n uniform float uMinPickingSize;\n\n /** Scale factor for geometric zoom */\n uniform mediump float uScaleFactor;\n\n uniform mediump float uZoomLevel;\n uniform highp float uSemanticThreshold;\n\n uniform mediump float uGradientStrength;\n\n#pragma markUniforms\n};\n", Jc = class extends Tc {
|
|
3582
|
+
getAttributes() {
|
|
3583
|
+
return [
|
|
3584
|
+
"uniqueId",
|
|
3585
|
+
"facetIndex",
|
|
3586
|
+
"x",
|
|
3587
|
+
"y",
|
|
3588
|
+
"xOffset",
|
|
3589
|
+
"yOffset",
|
|
3590
|
+
"size",
|
|
3591
|
+
"semanticScore",
|
|
3592
|
+
"shape",
|
|
3593
|
+
"strokeWidth",
|
|
3594
|
+
"dx",
|
|
3595
|
+
"dy",
|
|
3596
|
+
"fill",
|
|
3597
|
+
"stroke",
|
|
3598
|
+
"fillOpacity",
|
|
3599
|
+
"strokeOpacity",
|
|
3600
|
+
"angle"
|
|
3601
|
+
];
|
|
3602
|
+
}
|
|
3603
|
+
initializeGraphics() {
|
|
3604
|
+
super.initializeGraphics(), this.createAndLinkShaders(Gc, Kc, [qc]);
|
|
3605
|
+
}
|
|
3606
|
+
finalizeGraphicsInitialization() {
|
|
3607
|
+
super.finalizeGraphicsInitialization(), this.gl.useProgram(this.programInfo.program);
|
|
3608
|
+
let e = this.properties;
|
|
3609
|
+
this.registerMarkUniformValue("uInwardStroke", e.inwardStroke, (e) => !!e), this.registerMarkUniformValue("uGradientStrength", e.fillGradientStrength), this.registerMarkUniformValue("uMinPickingSize", e.minPickingSize);
|
|
3610
|
+
}
|
|
3611
|
+
updateGraphicsData(e) {
|
|
3612
|
+
let t = e.getItemCount(), n = new pc({
|
|
3613
|
+
encoders: this.encoders,
|
|
3614
|
+
attributes: this.getAttributes(),
|
|
3615
|
+
numItems: t
|
|
3616
|
+
});
|
|
3617
|
+
n.addBatches(e.facetBatches);
|
|
3618
|
+
let r = n.toArrays();
|
|
3619
|
+
this.rangeMap.migrateEntries(r.rangeMap), this.updateBufferInfo(r);
|
|
3620
|
+
}
|
|
3621
|
+
#e() {
|
|
3622
|
+
let e = 2 ** (this.properties.geometricZoomBound || 0);
|
|
3623
|
+
return Math.min(1, this.unitView.getZoomLevel() / e) ** (1 / 3);
|
|
3624
|
+
}
|
|
3625
|
+
prepareRender(e) {
|
|
3626
|
+
let t = super.prepareRender(e);
|
|
3627
|
+
return t.push(() => {
|
|
3628
|
+
Qa(this.markUniformInfo, {
|
|
3629
|
+
uScaleFactor: this.#e(),
|
|
3630
|
+
uSemanticThreshold: this.mark.getSemanticThreshold()
|
|
3631
|
+
}), this.markUniformsAltered = !0;
|
|
3632
|
+
}), t.push(() => this.bindOrSetMarkUniformBlock()), t.push(() => Y(this.gl, this.programInfo, this.vertexArrayInfo)), t;
|
|
3633
|
+
}
|
|
3634
|
+
render(e) {
|
|
3635
|
+
let t = this.gl;
|
|
3636
|
+
return this.createRenderCallback((e, n) => {
|
|
3637
|
+
n && ao(t, this.vertexArrayInfo, t.POINTS, n, e);
|
|
3638
|
+
}, e);
|
|
3639
|
+
}
|
|
3640
|
+
}, Yc = "flat out lowp vec4 vFillColor;\nflat out lowp vec4 vStrokeColor;\nflat out float vHalfStrokeWidth;\nflat out vec4 vCornerRadii;\n\n#if defined(ROUNDED_CORNERS) || defined(STROKED) || defined(SHADOW)\n/** Position for SDF-strokes */\nout vec2 vPosInPixels;\n#endif\n\n/** Size of the rect in pixels */\nflat out vec2 vHalfSizeInPixels;\n\n/**\n * Adjusts the vertex position to ensure that the rectangle is at least `minSpan`\n * wide or high. Returns a value that reflects the amount of clamping and can be\n * used to adjust the opacity of the rectangle.\n *\n * pos: vertex position\n * frac: vertex position within the rectangle, [0, 1]\n * size: width or height of the rectangle\n * minSize: minimum width or height of the rectangle\n */\nfloat clampMinSize(inout float pos, float frac, float size, float minSize) {\n if (minSize > 0.0 && size < minSize) {\n pos += (frac - 0.5) * (minSize - size);\n return size / minSize;\n }\n\n return 1.0;\n}\n\nvoid sort(inout float a, inout float b) {\n if (a > b) {\n float tmp = b;\n b = a;\n a = tmp;\n }\n}\n\n/**\n * The vertex position wrt the rectangle specified by (x, x2, y, y2).\n * [0, 0] = [x, y], [1, 1] = [x2, y2]. \n * The x or y component may contain fractional values if the rectangle \n * have been tessellated.\n */\nvec2 getVertexPos() {\n int index = gl_VertexID % 6;\n return vec2(\n index == 0 || index == 1 || index == 3 ? 0.0 : 1.0,\n index == 0 || index == 1 || index == 2 ? 0.0 : 1.0\n );\n \n}\n\nvoid main(void) {\n vec2 frac = getVertexPos();\n\n vec2 normalizedMinSize = vec2(uMinWidth, uMinHeight) / uViewportSize;\n vec4 cornerRadii = vec4(\n uCornerRadiusTopRight,\n uCornerRadiusBottomRight,\n uCornerRadiusTopLeft,\n uCornerRadiusBottomLeft\n );\n\n SampleFacetPosition sampleFacetPos = getSampleFacetPos();\n if (sampleFacetPos.height == 0.0) {\n // Filtered samples have no facet height. Cull them before minimum-size\n // clamping can expand their rectangles at the viewport boundary.\n gl_Position = vec4(100.0, 0.0, 0.0, 0.0);\n return;\n }\n\n vec2 pos1 = applyOffset(\n applySampleFacet(vec2(getScaled_x(), getScaled_y())),\n vec2(getScaled_xOffset(), getScaled_yOffset())\n );\n vec2 pos2 = applyOffset(\n applySampleFacet(vec2(getScaled_x2(), getScaled_y2())),\n vec2(getScaled_x2Offset(), getScaled_y2Offset())\n );\n\n sort(pos1.x, pos2.x);\n sort(pos1.y, pos2.y);\n\n // Clamp x to prevent precision artifacts when the scale is zoomed very close.\n // TODO: clamp y as well\n float clampMargin = 1.0;\n pos1.x = clamp(pos1.x, 0.0 - clampMargin, 1.0 + clampMargin);\n pos2.x = clamp(pos2.x, 0.0 - clampMargin, 1.0 + clampMargin);\n\n vec2 size = pos2 - pos1;\n\n if (size.x < 0.0 || size.y < 0.0) {\n // Keep zero-sized rects alive so min-size clamping can stabilize them.\n gl_Position = vec4(0.0, 0.0, 0.0, 1.0);\n return;\n }\n\n vec2 pos = pos1 + frac * size;\n\n // Clamp to minimum size, optionally compensate with opacity\n float opaFactor = uViewOpacity * max(uMinOpacity,\n clampMinSize(pos.x, frac.x, size.x, normalizedMinSize.x) *\n clampMinSize(pos.y, frac.y, size.y, normalizedMinSize.y));\n\n size = max(size, normalizedMinSize);\n\n#if defined(ROUNDED_CORNERS) || defined(STROKED) || defined(SHADOW)\n // Add an extra pixel to the stroke width to accommodate edge antialiasing\n float aaPadding = 1.0 / uDevicePixelRatio;\n\n // TODO: Only expand to the offset direction. Now high offsets result in\n // a large expansion in all directions.\n float shadowPadding = uShadowBlur + max(abs(uShadowOffsetX), abs(uShadowOffsetY));\n\n float strokeWidth = getScaled_strokeWidth();\n float strokeOpacity = getScaled_strokeOpacity() * opaFactor;\n\n vec2 centeredFrac = frac - 0.5;\n vec2 expand = centeredFrac * (strokeWidth + aaPadding + shadowPadding * 2.0) / uViewportSize;\n pos += expand;\n\n vec2 sizeInPixels = size * uViewportSize;\n vPosInPixels = (centeredFrac + expand / size) * sizeInPixels;\n\n vHalfSizeInPixels = sizeInPixels / 2.0;\n\n vCornerRadii = min(cornerRadii, min(vHalfSizeInPixels.x, vHalfSizeInPixels.y));\n vHalfStrokeWidth = strokeWidth / 2.0;\n vStrokeColor = vec4(getScaled_stroke() * strokeOpacity, strokeOpacity);\n#endif\n\n gl_Position = unitToNdc(pos);\n\n float fillOpacity = getScaled_fillOpacity() * opaFactor;\n vFillColor = vec4(getScaled_fill() * fillOpacity, fillOpacity);\n\n setupPicking();\n}\n", Xc = "#if defined(ROUNDED_CORNERS) || defined(STROKED) || defined(SHADOW)\nin vec2 vPosInPixels;\n#endif\n\nflat in vec2 vHalfSizeInPixels;\n\nflat in lowp vec4 vFillColor;\nflat in lowp vec4 vStrokeColor;\nflat in float vHalfStrokeWidth;\nflat in vec4 vCornerRadii;\n\nout lowp vec4 fragColor;\n\n// ----------------------------------------------------------------------------\n// Shadow source: https://madebyevan.com/shaders/fast-rounded-rectangle-shadows/\n// License: CC0 (http://creativecommons.org/publicdomain/zero/1.0/)\n\n#ifdef SHADOW\n\n// A standard gaussian function, used for weighting samples\nfloat gaussian(float x, float sigma) {\n const float pi = 3.141592653589793;\n return exp(-(x * x) / (2.0 * sigma * sigma)) / (sqrt(2.0 * pi) * sigma);\n}\n\n// This approximates the error function, needed for the gaussian integral\nvec2 erf(vec2 x) {\n vec2 s = sign(x), a = abs(x);\n x = 1.0 + (0.278393 + (0.230389 + 0.078108 * (a * a)) * a) * a;\n x *= x;\n return s - s / (x * x);\n}\n\n// Return the blurred mask along the x dimension\nfloat roundedBoxShadowX(float x, float y, float sigma, float corner, vec2 halfSize) {\n float delta = min(halfSize.y - corner - abs(y), 0.0);\n float curved = halfSize.x - corner + sqrt(max(0.0, corner * corner - delta * delta));\n vec2 integral = 0.5 + 0.5 * erf((x + vec2(-curved, curved)) * (sqrt(0.5) / sigma));\n return integral.y - integral.x;\n}\n\n// Return the mask for the shadow of a box from lower to upper\nfloat roundedBoxShadow(vec2 lower, vec2 upper, vec2 point, float sigma, float corner) {\n // Center everything to make the math easier\n vec2 center = (lower + upper) * 0.5;\n vec2 halfSize = (upper - lower) * 0.5;\n point -= center;\n\n // The signal is only non-zero in a limited range, so don't waste samples\n float low = point.y - halfSize.y;\n float high = point.y + halfSize.y;\n float start = clamp(-3.0 * sigma, low, high);\n float end = clamp(3.0 * sigma, low, high);\n\n // Accumulate samples (we can get away with surprisingly few samples)\n float step = (end - start) / 4.0;\n float y = start + step * 0.5;\n float value = 0.0;\n for (int i = 0; i < 4; i++) {\n value += roundedBoxShadowX(point.x, point.y - y, sigma, corner, halfSize) * gaussian(y, sigma) * step;\n y += step;\n }\n\n return value;\n}\n\n// ----------------------------------------------------------------------------\n\n#endif\n\n// Source: https://www.iquilezles.org/www/articles/distfunctions2d/distfunctions2d.htm\nfloat sdRoundedBox(vec2 p, vec2 b, vec4 r) {\n r.xy = p.x > 0.0 ? r.xy : r.zw;\n r.x = p.y > 0.0 ? r.x : r.y;\n vec2 q = abs(p) - b + r.x;\n return min(max(q.x, q.y), 0.0) + length(max(q, 0.0)) - r.x;\n}\n\n// Not a true SDF. Makes the corners of strokes sharp and is faster.\nfloat sdSharpBox(vec2 p, vec2 b) {\n vec2 q = abs(p) - b;\n return max(q.x, q.y);\n}\n\nfloat diagonalPattern(vec2 uv, float spacing) {\n // Using 1.5 to approximate sqrt(2.0) to reduce aliasing artifacts.\n float divisor = spacing * vHalfStrokeWidth * 2.0 * 1.5;\n return abs(mod(uv.x - uv.y, divisor) - 0.5 * divisor) / 1.5;\n}\n\nfloat verticalPattern(float x, float spacing) {\n float divisor = spacing * vHalfStrokeWidth * 2.0;\n return abs(mod(x, divisor)) / 2.0;\n}\n\nfloat circle(vec2 p, float r) {\n return length(p) - r;\n}\n\nfloat masonryCirclePattern(vec2 uv, float spacing, float radius) {\n float halfSpacing = 0.5 * spacing;\n\n float row = floor(uv.y / spacing);\n float shift = mod(row, 2.0) * halfSpacing;\n\n vec2 shifted = vec2(uv.x + shift, uv.y + halfSpacing);\n vec2 cell = mod(shifted + 0.5 * spacing, spacing) - halfSpacing;\n\n return abs(circle(cell, radius));\n}\n\n/**\n * Patterns:\n * 0 none\n * 1 diagonal (/)\n * 2 antiDiagonal (\\)\n * 3 cross (X)\n * 4 vertical (|)\n * 5 horizontal (-)\n * 6 grid (+)\n * 7 dots (.)\n * 8 rings (o)\n * 9 ringsLarge (O)\n */\nfloat pattern() {\n#ifdef STROKED\n int patternType = uHatchPattern;\n vec2 uv = vPosInPixels;\n float spacing = 4.0;\n\n switch (patternType) {\n case 1:\n return diagonalPattern(vec2(uv.x, -uv.y), spacing);\n case 2:\n return diagonalPattern(uv, spacing);\n case 3:\n return min(\n diagonalPattern(uv, spacing),\n diagonalPattern(vec2(uv.x, -uv.y), spacing)\n );\n case 4:\n return verticalPattern(uv.x, spacing);\n case 5:\n return verticalPattern(uv.y, spacing);\n case 6:\n return min(\n verticalPattern(uv.x, spacing),\n verticalPattern(uv.y, spacing)\n );\n case 7:\n case 8:\n case 9: {\n float spacing = vHalfStrokeWidth * 14.0;\n float radius = spacing * (\n patternType == 8 ? 0.2 :\n patternType == 9 ? 0.35 :\n 0.07\n );\n return masonryCirclePattern(uv, spacing, radius);\n }\n default:\n break;\n }\n#endif\n return 1.0 / 0.0; // Infinity\n}\n\nvoid main(void) {\n\n#if defined(ROUNDED_CORNERS) || defined(STROKED) || defined(SHADOW)\n#ifdef ROUNDED_CORNERS\n // Distance from rectangle's edge in pixels. Negative inside the rectangle.\n float d = sdRoundedBox(vPosInPixels, vHalfSizeInPixels, vCornerRadii);\n#else\n float d = sdSharpBox(vPosInPixels, vHalfSizeInPixels);\n#endif\n\n vec4 backgroundColor = vec4(0.0, 0.0, 0.0, 0.0);\n\n#ifdef SHADOW\n float maxCornerRadius = max(vCornerRadii.x, max(vCornerRadii.y, max(vCornerRadii.z, vCornerRadii.w)));\n\n float shadow = 0.0;\n // Only calculate shadow for the region outside the stroke.\n if (d >= vHalfStrokeWidth - 1.0 && uShadowOpacity > 0.0) {\n shadow = roundedBoxShadow(\n -vHalfSizeInPixels - vHalfStrokeWidth,\n vHalfSizeInPixels + vHalfStrokeWidth,\n vPosInPixels - vec2(uShadowOffsetX, -uShadowOffsetY),\n max(uShadowBlur / 2.5, 0.25),\n maxCornerRadius + vHalfStrokeWidth\n ) * uShadowOpacity * uViewOpacity;\n }\n backgroundColor = vec4(uShadowColor * shadow, shadow);\n#endif\n\n if (vHalfStrokeWidth > 0.0 && uHatchPattern > 0) {\n d = max(d, -pattern());\n }\n\n fragColor = distanceToColor(\n d,\n vFillColor,\n vStrokeColor,\n backgroundColor,\n vHalfStrokeWidth\n );\n\n if (uPickingEnabled) {\n if (d < vHalfStrokeWidth) {\n fragColor = vPickingColor;\n }\n } else if (fragColor.a == 0.0) {\n discard;\n }\n#else\n // The trivial, non-decorated case\n fragColor = vFillColor;\n if (uPickingEnabled) {\n fragColor = vPickingColor;\n }\n#endif\n}\n", Zc = "layout(std140) uniform Mark {\n /** Minimum size (width, height) of the displayed rectangle in pixels */\n uniform float uMinWidth;\n uniform float uMinHeight;\n\n /** Minimum opacity for the size clamping */\n uniform float uMinOpacity;\n\n uniform float uCornerRadiusTopRight;\n uniform float uCornerRadiusBottomRight;\n uniform float uCornerRadiusTopLeft;\n uniform float uCornerRadiusBottomLeft;\n\n uniform int uHatchPattern;\n\n uniform vec3 uShadowColor;\n uniform float uShadowOpacity;\n uniform float uShadowBlur;\n uniform float uShadowOffsetX;\n uniform float uShadowOffsetY;\n\n#pragma markUniforms\n};\n", Qc = [
|
|
3641
|
+
"none",
|
|
3642
|
+
"diagonal",
|
|
3643
|
+
"antiDiagonal",
|
|
3644
|
+
"cross",
|
|
3645
|
+
"vertical",
|
|
3646
|
+
"horizontal",
|
|
3647
|
+
"grid",
|
|
3648
|
+
"dots",
|
|
3649
|
+
"rings",
|
|
3650
|
+
"ringsLarge"
|
|
3651
|
+
], $c = class extends Tc {
|
|
3652
|
+
get opaque() {
|
|
3653
|
+
return ye(this, "opaque", () => !this.#e() && !this.#t() && !this.properties.shadowOpacity && y(this.encoding.fillOpacity) && this.encoding.fillOpacity.value == 1 && this.properties.minOpacity == 1) && this.unitView.getEffectiveOpacity() == 1;
|
|
3654
|
+
}
|
|
3655
|
+
getAttributes() {
|
|
3656
|
+
return [
|
|
3657
|
+
"uniqueId",
|
|
3658
|
+
"facetIndex",
|
|
3659
|
+
"x",
|
|
3660
|
+
"x2",
|
|
3661
|
+
"y",
|
|
3662
|
+
"y2",
|
|
3663
|
+
"xOffset",
|
|
3664
|
+
"yOffset",
|
|
3665
|
+
"x2Offset",
|
|
3666
|
+
"y2Offset",
|
|
3667
|
+
"fill",
|
|
3668
|
+
"stroke",
|
|
3669
|
+
"fillOpacity",
|
|
3670
|
+
"strokeOpacity",
|
|
3671
|
+
"strokeWidth"
|
|
3672
|
+
];
|
|
3673
|
+
}
|
|
3674
|
+
#e() {
|
|
3675
|
+
let e = this.properties;
|
|
3676
|
+
return e.cornerRadius || e.cornerRadiusBottomLeft || e.cornerRadiusBottomRight || e.cornerRadiusTopLeft || e.cornerRadiusTopRight;
|
|
3677
|
+
}
|
|
3678
|
+
#t() {
|
|
3679
|
+
let e = this.encoding.strokeWidth;
|
|
3680
|
+
return !(y(e) && !e.value) || "condition" in e;
|
|
3681
|
+
}
|
|
3682
|
+
initializeGraphics() {
|
|
3683
|
+
super.initializeGraphics();
|
|
3684
|
+
let e = [];
|
|
3685
|
+
this.#e() && e.push("ROUNDED_CORNERS"), this.#t() && e.push("STROKED"), this.properties.shadowOpacity && e.push("SHADOW"), this.createAndLinkShaders(Yc, Xc, [Zc, ...e.map((e) => "#define " + e)]);
|
|
3686
|
+
}
|
|
3687
|
+
finalizeGraphicsInitialization() {
|
|
3688
|
+
super.finalizeGraphicsInitialization(), this.gl.useProgram(this.programInfo.program);
|
|
3689
|
+
let e = this.properties;
|
|
3690
|
+
this.registerMarkUniformValue("uMinWidth", e.minWidth), this.registerMarkUniformValue("uMinHeight", e.minHeight), this.registerMarkUniformValue("uMinOpacity", e.minOpacity), this.registerMarkUniformValue("uCornerRadiusTopRight", e.cornerRadiusTopRight ?? e.cornerRadius ?? 0), this.registerMarkUniformValue("uCornerRadiusBottomRight", e.cornerRadiusBottomRight ?? e.cornerRadius ?? 0), this.registerMarkUniformValue("uCornerRadiusTopLeft", e.cornerRadiusTopLeft ?? e.cornerRadius ?? 0), this.registerMarkUniformValue("uCornerRadiusBottomLeft", e.cornerRadiusBottomLeft ?? e.cornerRadius ?? 0), this.registerMarkUniformValue("uHatchPattern", e.hatch, (e) => Math.max(0, Qc.indexOf(e ?? "none"))), this.registerMarkUniformValue("uShadowBlur", e.shadowBlur ?? 0), this.registerMarkUniformValue("uShadowOpacity", e.shadowOpacity ?? 0), this.registerMarkUniformValue("uShadowOffsetX", e.shadowOffsetX ?? 0), this.registerMarkUniformValue("uShadowOffsetY", e.shadowOffsetY ?? 0), this.registerMarkUniformValue("uShadowColor", e.shadowColor ?? "black", Yo);
|
|
3691
|
+
}
|
|
3692
|
+
updateGraphicsData(e) {
|
|
3693
|
+
let t = e.getItemCount(), n = new dc({
|
|
3694
|
+
encoders: this.encoders,
|
|
3695
|
+
attributes: this.getAttributes(),
|
|
3696
|
+
numItems: t
|
|
3697
|
+
});
|
|
3698
|
+
n.addBatches(e.facetBatches);
|
|
3699
|
+
let r = n.toArrays();
|
|
3700
|
+
this.rangeMap.migrateEntries(r.rangeMap), this.updateBufferInfo(r);
|
|
3701
|
+
}
|
|
3702
|
+
prepareRender(e) {
|
|
3703
|
+
let t = super.prepareRender(e);
|
|
3704
|
+
return t.push(() => this.bindOrSetMarkUniformBlock()), t.push(() => Y(this.gl, this.programInfo, this.vertexArrayInfo)), t;
|
|
3705
|
+
}
|
|
3706
|
+
render(e) {
|
|
3707
|
+
let t = this.gl;
|
|
3708
|
+
return this.createRenderCallback((e, n) => {
|
|
3709
|
+
ao(t, this.vertexArrayInfo, t.TRIANGLE_STRIP, n, e);
|
|
3710
|
+
}, e);
|
|
3711
|
+
}
|
|
3712
|
+
}, el = "// Line caps\nconst int BUTT = 0;\nconst int SQUARE = 1;\nconst int ROUND = 2;\n\n/** Position along the rule */\nin float pos;\n\n/** Which side of the stroke: -0.5 or 0.5 */\nin float side;\n\nflat out vec4 vColor;\n\n/** Stroke width */\nflat out float vSize;\n\n/** The distance from the line center to the direction of normal in pixels */\nout float vNormalLengthInPixels;\n\n/** Distances from the line endings. Used for rendering the round caps and dashes */\nout highp vec2 vPosInPixels;\n\n\nvoid main(void) {\n float pixelSize = 1.0 / uDevicePixelRatio;\n\n // Stroke width in pixels\n float size = getScaled_size();\n float opacity = getScaled_opacity() * uViewOpacity;\n\n // Avoid artifacts in very thin lines by clamping the size and adjusting opacity respectively\n if (size < pixelSize) {\n opacity *= size / pixelSize;\n size = pixelSize;\n }\n\n vec2 a = applyOffset(\n applySampleFacet(vec2(getScaled_x(), getScaled_y())),\n vec2(getScaled_xOffset(), getScaled_yOffset())\n );\n vec2 b = applyOffset(\n applySampleFacet(vec2(getScaled_x2(), getScaled_y2())),\n vec2(getScaled_x2Offset(), getScaled_y2Offset())\n );\n\n vec2 tangent = b - a;\n\n float offset = 0.0;\n float relativeDiff = 0.0;\n if (uMinLength > 0.0 || uStrokeCap != BUTT) {\n float len = length(tangent * uViewportSize);\n\n // Elongate to reach the minimum length.\n // The length difference in pixels\n float diff = max(0.0, uMinLength - len);\n\n // Add line caps\n if (uStrokeCap != BUTT) {\n diff += size;\n }\n\n relativeDiff = diff / len;\n offset = relativeDiff * (pos - 0.5);\n }\n\n // Apply caps and minimum length by spreading the vertices along the tangent\n vec2 p = pos < 1.0\n ? a + tangent * (pos + offset)\n : b + tangent * offset;\n\n // Add an extra pixel to stroke width to accommodate edge antialiasing\n float aaPadding = pixelSize;\n\n // Extrude\n vec2 normal = normalize(vec2(-tangent.y, tangent.x) / uViewportSize);\n p += normal * side * (size + aaPadding) / uViewportSize;\n\n gl_Position = unitToNdc(p);\n\n vColor = vec4(getScaled_color() * opacity, opacity);\n vSize = size;\n vNormalLengthInPixels = side * (size + aaPadding);\n\n // TODO: Here's a precision problem that breaks round caps when zoomed in enough\n vPosInPixels = vec2(pos, (1.0 - pos)) * (1.0 + relativeDiff) * length(tangent * uViewportSize) -\n vec2(uStrokeCap != BUTT ? size / 2.0 : 0.0);\n \n setupPicking();\n}\n", tl = "// Line ending\nconst int BUTT = 0;\nconst int SQUARE = 1;\nconst int ROUND = 2;\n\nuniform sampler2D uDashTexture;\n\nflat in vec4 vColor;\nflat in float vSize;\n\n/** Position on the rule along its length in pixels */\nin vec2 vPosInPixels;\nin float vNormalLengthInPixels;\n\nout lowp vec4 fragColor;\n\nvoid main(void) {\n float dpr = uDevicePixelRatio;\n\n float distanceFromEnd = -min(vPosInPixels[0], vPosInPixels[1]);\n float distance; // from the rule centerline or end\n if (distanceFromEnd > 0.0 && uStrokeCap == ROUND) {\n // round cap\n distance = length(vec2(distanceFromEnd, vNormalLengthInPixels));\n } else {\n distance = abs(vNormalLengthInPixels);\n }\n\n // Use a signed distance field to implement edge antialiasing\n float opacity = clamp(((vSize / 2.0 - distance) * dpr), -0.5, 0.5) + 0.5;\n\n if (uDashTextureSize > 0.0) {\n float pos = (vPosInPixels[0] + uStrokeDashOffset) * dpr;\n float floored = floor(pos);\n vec2 texelPositions = (floored + vec2(0.5, 1.5)) / dpr / uDashTextureSize;\n \n // Do antialiasing\n opacity *= mix(\n texture(uDashTexture, vec2(texelPositions[0], 0)).r,\n texture(uDashTexture, vec2(texelPositions[1], 0)).r,\n clamp((pos - floored), 0.0, 1.0));\n }\n\n fragColor = vColor * opacity;\n\n if (uPickingEnabled) {\n fragColor = vPickingColor;\n }\n}\n", nl = "layout(std140) uniform Mark {\n /** Minimum rule length in pixels */\n uniform mediump float uMinLength;\n\n uniform mediump float uDashTextureSize;\n uniform lowp int uStrokeCap;\n uniform mediump float uStrokeDashOffset;\n\n#pragma markUniforms\n};\n", rl = class extends Tc {
|
|
3713
|
+
constructor(e, t, n) {
|
|
3714
|
+
super(e, t, n), this.dashTexture = void 0, this.dashTextureSize = 0;
|
|
3715
|
+
}
|
|
3716
|
+
getAttributes() {
|
|
3717
|
+
return [
|
|
3718
|
+
"uniqueId",
|
|
3719
|
+
"facetIndex",
|
|
3720
|
+
"x",
|
|
3721
|
+
"x2",
|
|
3722
|
+
"y",
|
|
3723
|
+
"y2",
|
|
3724
|
+
"xOffset",
|
|
3725
|
+
"yOffset",
|
|
3726
|
+
"x2Offset",
|
|
3727
|
+
"y2Offset",
|
|
3728
|
+
"size",
|
|
3729
|
+
"color",
|
|
3730
|
+
"opacity"
|
|
3731
|
+
];
|
|
3732
|
+
}
|
|
3733
|
+
initializeGraphics() {
|
|
3734
|
+
super.initializeGraphics();
|
|
3735
|
+
let e = this.gl, t = il(this.properties.strokeDash);
|
|
3736
|
+
this.dashTexture = ii(e, {
|
|
3737
|
+
level: 0,
|
|
3738
|
+
mag: e.NEAREST,
|
|
3739
|
+
min: e.NEAREST,
|
|
3740
|
+
internalFormat: e.R8,
|
|
3741
|
+
format: e.RED,
|
|
3742
|
+
src: t,
|
|
3743
|
+
height: 1
|
|
3744
|
+
}), this.dashTextureSize = t.length, this.createAndLinkShaders(el, tl, [nl]);
|
|
3745
|
+
}
|
|
3746
|
+
finalizeGraphicsInitialization() {
|
|
3747
|
+
super.finalizeGraphicsInitialization(), this.gl.useProgram(this.programInfo.program);
|
|
3748
|
+
let e = this.properties;
|
|
3749
|
+
this.registerMarkUniformValue("uMinLength", e.minLength), this.registerMarkUniformValue("uStrokeCap", e.strokeCap ?? "butt", (e) => [
|
|
3750
|
+
"butt",
|
|
3751
|
+
"square",
|
|
3752
|
+
"round"
|
|
3753
|
+
].indexOf(e)), Qa(this.markUniformInfo, { uDashTextureSize: +this.dashTextureSize }), this.markUniformsAltered = !0;
|
|
3754
|
+
}
|
|
3755
|
+
updateGraphicsData(e) {
|
|
3756
|
+
let t = e.getItemCount(), n = new fc({
|
|
3757
|
+
encoders: this.encoders,
|
|
3758
|
+
attributes: this.getAttributes(),
|
|
3759
|
+
numItems: t
|
|
3760
|
+
});
|
|
3761
|
+
n.addBatches(e.facetBatches);
|
|
3762
|
+
let r = n.toArrays();
|
|
3763
|
+
this.rangeMap.migrateEntries(r.rangeMap), this.updateBufferInfo(r);
|
|
3764
|
+
}
|
|
3765
|
+
prepareRender(e) {
|
|
3766
|
+
let t = super.prepareRender(e);
|
|
3767
|
+
return t.push(() => this.bindOrSetMarkUniformBlock()), t.push(() => J(this.programInfo, { uDashTexture: this.dashTexture })), t.push(() => Y(this.gl, this.programInfo, this.vertexArrayInfo)), t;
|
|
3768
|
+
}
|
|
3769
|
+
render(e) {
|
|
3770
|
+
let t = this.gl;
|
|
3771
|
+
return this.createRenderCallback((e, n) => ao(t, this.vertexArrayInfo, t.TRIANGLE_STRIP, n, e), e);
|
|
3772
|
+
}
|
|
3773
|
+
dispose() {
|
|
3774
|
+
this.dashTexture &&= (this.gl.deleteTexture(this.dashTexture), void 0), super.dispose();
|
|
3775
|
+
}
|
|
3776
|
+
};
|
|
3777
|
+
function il(e) {
|
|
3778
|
+
if (!e) return /* @__PURE__ */ new Uint8Array();
|
|
3779
|
+
if (e.length == 0 || e.length % 2 || e.findIndex((e) => Math.round(e) != e || e < 1 || e > 1e3) >= 0) throw Error("Invalid stroke dash pattern: " + JSON.stringify(e));
|
|
3780
|
+
let t = e.reduce((e, t) => e + t), n = new Uint8Array(t), r = !0, i = 0;
|
|
3781
|
+
for (let t of e) {
|
|
3782
|
+
for (; t;) n[i++] = r && 255 || 0, t--;
|
|
3783
|
+
r = !r;
|
|
3784
|
+
}
|
|
3785
|
+
return n;
|
|
3786
|
+
}
|
|
3787
|
+
//#endregion
|
|
3788
|
+
//#region ../core/src/rendering/webgl/marks/text.vertex.glsl
|
|
3789
|
+
var al = "in mediump vec2 vertexCoord;\nin lowp vec2 textureCoord;\n\n// Width of the text (all letters)\nin float width;\n\nout vec2 vTexCoord;\nout float vEdgeFadeOpacity;\nflat out vec4 vColor;\nflat out float vSlope;\nflat out float vGamma;\n\nstruct RangeResult {\n float pos;\n float scale;\n};\n\nfloat minValue(vec4 v) {\n return min(min(v.x, v.y), min(v.z, v.w));\n}\n\nfloat maxValue(vec4 v) {\n return max(max(v.x, v.y), max(v.z, v.w));\n}\n\n/**\n * All measures are in [0, 1]\n */\nRangeResult positionInsideRange(float a, float b, float width, float padding,\n int align, bool flush) {\n float span = b - a;\n float paddedWidth = width + 2.0 * padding;\n\n // Is the text clearly outside the viewport\n if (a > 1.0 || b < 0.0) {\n return RangeResult(0.0, 0.0);\n }\n\n // How much extra space we have for adjusting the position so that the\n // text stays inside the range.\n float extra = max(0.0, span - paddedWidth);\n\n float pos;\n\n // Align the text and try to keep it inside the range and the viewport\n if (align == 0) {\n float centre = a + b;\n\n if (flush) {\n float leftOver = max(0.0, paddedWidth - centre);\n centre += min(leftOver, extra);\n\n float rightOver = max(0.0, paddedWidth + centre - 2.0);\n centre -= min(rightOver, extra);\n }\n\n pos = centre / 2.0;\n\n } else if (align < 0) {\n float edge = a;\n\n if (flush) {\n float over = max(0.0, -edge);\n edge += min(over, extra);\n }\n\n pos = edge + padding;\n\n } else {\n float edge = b;\n\n if (flush) {\n float over = max(0.0, edge - 1.0);\n edge -= min(over, extra);\n }\n\n // TODO: If the text spans the whole viewport, try to keep it centered if possible.\n\n pos = edge - padding;\n }\n\n // How the text should be scaled to make it fit inside the range (if it didn't fit).\n float scale = clamp((span - padding) / paddedWidth, 0.0, 1.0);\n\n // TODO: Fix padding in scale factor. Padding should stay constant\n return RangeResult(pos, scale);\n}\n\nvec2 calculateRotatedDimensions(float width, mat2 rotationMatrix) {\n vec2 a = abs(rotationMatrix * vec2(width / 2.0, 0.5));\n vec2 b = abs(rotationMatrix * vec2(width / 2.0, -0.5));\n return vec2(max(a.x, b.x), max(a.y, b.y)) * 2.0;\n}\n\n/** Needed when using ranged text */\nivec2 fixAlignForAngle(ivec2 align, float angleInDegrees) {\n float a = mod(angleInDegrees + 45.0, 360.0);\n int x = align.x;\n int y = -align.y;\n\n // TODO: Optimize by avoiding branching\n if (a < 90.0) {\n return ivec2(x, y);\n } else if (a < 180.0) {\n return ivec2(y, -x);\n } else if (a < 270.0) {\n return ivec2(-x, y);\n } else {\n return ivec2(-y, x);\n }\n}\n\nvoid main(void) {\n float opacity = getScaled_opacity() * uViewOpacity;\n vec2 size = vec2(getScaled_size());\n float x = getScaled_x() + getScaled_xOffset() / uViewportSize.x;\n float y = getScaled_y();\n\n float scale = 1.0;\n\n float angleInDegrees = getScaled_angle();\n float angle = -angleInDegrees * PI / 180.0;\n \n float sinTheta = sin(angle);\n float cosTheta = cos(angle);\n mat2 rotationMatrix = mat2(cosTheta, sinTheta, -sinTheta, cosTheta);\n\n vec2 flushSize = calculateRotatedDimensions(width, rotationMatrix);\n\n#if defined(x2_DEFINED) || defined(y2_DEFINED)\n ivec2 align = fixAlignForAngle(uAlign, angleInDegrees);\n#else\n ivec2 align = uAlign;\n#endif\n\n#ifdef x2_DEFINED\n float x2 = getScaled_x2() + getScaled_x2Offset() / uViewportSize.x;\n\n if (uLogoLetter) {\n size.x = (x2 - x) * uViewportSize.x;\n x += (x2 - x) / 2.0;\n\n } else {\n RangeResult result = positionInsideRange(\n min(x, x2), max(x, x2),\n size.x * scale * flushSize.x / uViewportSize.x, uPaddingX / uViewportSize.x,\n align.x, uFlushX);\n \n x = result.pos;\n scale *= result.scale;\n }\n#endif\n\n // Position of the text origo \n vec2 pos = applyOffset(\n applySampleFacet(vec2(x, y)),\n vec2(0.0, getScaled_yOffset())\n );\n\n#ifdef y2_DEFINED\n float y2 = getScaled_y2();\n vec2 pos2 = applyOffset(\n applySampleFacet(vec2(x, y2)),\n vec2(0.0, getScaled_y2Offset())\n );\n\n if (uLogoLetter) {\n size.y = (pos2.y - pos.y) * uViewportSize.y;\n pos.y += (pos2.y - pos.y) / 2.0;\n\n } else {\n RangeResult result = positionInsideRange(\n min(pos.y, pos2.y), max(pos.y, pos2.y),\n size.y * scale * flushSize.y / uViewportSize.y, uPaddingY / uViewportSize.y,\n align.y, uFlushY);\n \n pos.y = result.pos;\n scale *= result.scale;\n }\n#endif\n\n#ifdef VISIBLE_RANGE_CULLING\n if (isOutsideVisibleRange(pos)) {\n gl_Position = vec4(0.0);\n return;\n }\n#endif\n\n if (scale < 1.0) {\n if (uSqueeze) {\n vec2 scaleFadeExtent = vec2(3.0, 6.0) / size;\n\n if (scale < scaleFadeExtent[0]) {\n gl_Position = vec4(0.0);\n return;\n }\n\n size *= scale;\n opacity *= linearstep(scaleFadeExtent[0], scaleFadeExtent[1], scale);\n\n } else if (scale < 1.0) {\n // Eliminate the text\n gl_Position = vec4(0.0);\n return;\n }\n }\n\n // Position of the character vertex in relation to the text origo\n vec2 charPos = rotationMatrix * (vertexCoord * size + uD);\n\n // Position of the character vertex inside the unit viewport\n vec2 unitPos = pos + charPos / uViewportSize;\n\n gl_Position = unitToNdc(unitPos);\n\n // Controls antialiasing of the SDF\n vSlope = max(1.0, min(size.x, size.y) / uSdfNumerator * uDevicePixelRatio);\n\n vec3 color = getScaled_color();\n\n // Premultiply alpha\n vColor = vec4(color * opacity, opacity);\n\n // Do something like gamma correction for text when the color is close to black or white.\n vGamma = getGammaForColor(color);\n\n vTexCoord = textureCoord;\n\n // Edge fading. The implementation is simplistic and fails with primitives that\n // span the whole viewport. However, it works just fine with reasonable font sizes.\n // x: top, y: right, z: bottom, w: left\n if (maxValue(uViewportEdgeFadeDistance) > -pow(10.0, 10.0)) { // -Infinity would be nice\n vEdgeFadeOpacity = minValue(\n ((vec4(1.0, 1.0, 0.0, 0.0) + vec4(-1.0, -1.0, 1.0, 1.0) * unitPos.yxyx) *\n uViewportSize.yxyx - uViewportEdgeFadeDistance) / uViewportEdgeFadeWidth);\n } else {\n vEdgeFadeOpacity = 1.0;\n }\n\n setupPicking();\n}\n", ol = "uniform sampler2D uTexture;\n\nin vec2 vTexCoord;\nin float vEdgeFadeOpacity;\nflat in vec4 vColor;\nflat in float vSlope;\nflat in float vGamma;\n\nout lowp vec4 fragColor;\n\nfloat median(float r, float g, float b) {\n return max(min(r, g), min(max(r, g), b));\n}\n\nfloat getDist(vec2 uv) {\n vec3 c = texture(uTexture, uv).rgb;\n return 1.0 - median(c.r, c.g, c.b);\n}\n\n/**\n * Calculates the super-sampled distance to the edge.\n * This is used to avoid aliasing when rendering small text,\n * as mip-mapping cannot be used here.\n * The distance is averaged over a grid of n x n samples.\n */\nfloat getSuperDist(vec2 uv) {\n vec2 dx = dFdx(uv);\n vec2 dy = dFdy(uv);\n\n float n = 2.0;\n\n float sum = 0.0;\n for (float x = 0.5; x < n; x++){\n for (float y = 0.5; y < n; y++) {\n sum += getDist(\n uv +\n x / n * dx +\n y / n * dy\n ); \n }\n }\n\n return sum / (n * n);\n}\n\nvoid main() {\n float sigDist = getSuperDist(vTexCoord);\n\n float slope = vSlope;\n if (uLogoLetter) {\n // Using screen-space derivatives for logo letters because skewed aspect ratios\n // result in blurry edges otherwise. However, use of screen-space derivatives\n // results in crappy looking text with regular letters text.\n slope = 0.7 / length(vec2(dFdy(sigDist), dFdx(sigDist)));\n }\n\n float opa = clamp((sigDist - 0.5) * slope + 0.5, 0.0, 1.0);\n opa *= clamp(vEdgeFadeOpacity, 0.0, 1.0);\n\n opa = pow(opa, vGamma);\n\n fragColor = vColor * opa;\n\n if (uPickingEnabled) {\n fragColor = vPickingColor;\n }\n}\n", sl = "layout(std140) uniform Mark {\n uniform mediump float uSdfNumerator;\n\n uniform mediump vec2 uD; // dx & dy\n\n uniform mediump vec4 uViewportEdgeFadeWidth;\n uniform mediump vec4 uViewportEdgeFadeDistance;\n \n uniform bool uSqueeze;\n uniform bool uLogoLetter;\n\n // x: -1, 0, 1 = left, center, right\n // y: -1, 0, 1 = top, middle, bottom \n uniform lowp ivec2 uAlign;\n\n uniform mediump float uPaddingX;\n uniform bool uFlushX;\n uniform mediump float uPaddingY;\n uniform bool uFlushY;\n\n#pragma markUniforms\n};\n", cl = 1024, ll = {
|
|
3790
|
+
left: -1,
|
|
3791
|
+
center: 0,
|
|
3792
|
+
right: 1
|
|
3793
|
+
}, ul = {
|
|
3794
|
+
top: -1,
|
|
3795
|
+
middle: 0,
|
|
3796
|
+
bottom: 1,
|
|
3797
|
+
alphabetic: 1,
|
|
3798
|
+
baseline: 1
|
|
3799
|
+
}, dl = {
|
|
3800
|
+
point: Jc,
|
|
3801
|
+
rect: $c,
|
|
3802
|
+
arrow: Fc,
|
|
3803
|
+
rule: rl,
|
|
3804
|
+
tick: rl,
|
|
3805
|
+
link: Wc,
|
|
3806
|
+
text: class extends Tc {
|
|
3807
|
+
getAttributes() {
|
|
3808
|
+
return [
|
|
3809
|
+
"uniqueId",
|
|
3810
|
+
"facetIndex",
|
|
3811
|
+
"x",
|
|
3812
|
+
"x2",
|
|
3813
|
+
"y",
|
|
3814
|
+
"y2",
|
|
3815
|
+
"xOffset",
|
|
3816
|
+
"yOffset",
|
|
3817
|
+
"x2Offset",
|
|
3818
|
+
"y2Offset",
|
|
3819
|
+
"color",
|
|
3820
|
+
"size",
|
|
3821
|
+
"opacity",
|
|
3822
|
+
"angle"
|
|
3823
|
+
];
|
|
3824
|
+
}
|
|
3825
|
+
initializeGraphics() {
|
|
3826
|
+
super.initializeGraphics(), this.createAndLinkShaders(al, ol, [sl]);
|
|
3827
|
+
}
|
|
3828
|
+
finalizeGraphicsInitialization() {
|
|
3829
|
+
super.finalizeGraphicsInitialization(), this.gl.useProgram(this.programInfo.program);
|
|
3830
|
+
let e = this.properties;
|
|
3831
|
+
this.registerMarkUniformValue("uPaddingX", e.paddingX), this.registerMarkUniformValue("uPaddingY", e.paddingY), this.registerMarkUniformValue("uFlushX", e.flushX, (e) => !!e), this.registerMarkUniformValue("uFlushY", e.flushY, (e) => !!e), this.registerMarkUniformValue("uSqueeze", e.squeeze, (e) => !!e), this.registerMarkUniformValue("uLogoLetter", e.logoLetters, (e) => !!e), this.registerMarkUniformValue("uSdfNumerator", e.logoLetters, (e) => this.font.metrics.common.base * .35 * (e ? .5 : 1)), this.registerMarkUniformVector("uViewportEdgeFadeWidth", [
|
|
3832
|
+
e.viewportEdgeFadeWidthTop,
|
|
3833
|
+
e.viewportEdgeFadeWidthRight,
|
|
3834
|
+
e.viewportEdgeFadeWidthBottom,
|
|
3835
|
+
e.viewportEdgeFadeWidthLeft
|
|
3836
|
+
]), this.registerMarkUniformVector("uViewportEdgeFadeDistance", [
|
|
3837
|
+
e.viewportEdgeFadeDistanceTop,
|
|
3838
|
+
e.viewportEdgeFadeDistanceRight,
|
|
3839
|
+
e.viewportEdgeFadeDistanceBottom,
|
|
3840
|
+
e.viewportEdgeFadeDistanceLeft
|
|
3841
|
+
]), Qa(this.markUniformInfo, {
|
|
3842
|
+
uAlign: [ll[e.align], ul[e.baseline]],
|
|
3843
|
+
uD: [e.dx, -e.dy]
|
|
3844
|
+
});
|
|
3845
|
+
}
|
|
3846
|
+
registerMarkUniformVector(e, t) {
|
|
3847
|
+
let n = this.createMarkUniformSetter(e), r = [], i = () => n(r.map((e) => e()));
|
|
3848
|
+
for (let e of t) r.push(x(e) ? this.unitView.paramRuntime.watchExpression(e.expr, i) : () => e);
|
|
3849
|
+
i();
|
|
3850
|
+
}
|
|
3851
|
+
updateGraphicsData(e) {
|
|
3852
|
+
let t = e.getData(), n = this.encoding, r = this.properties, i = x(r.logoLetters) ? this.unitView.paramRuntime.evaluateAndGet(r.logoLetters.expr) : r.logoLetters, a = this.encoders.text, o = 0, s = "format" in n.text ? f(n.text.format) : (e) => e;
|
|
3853
|
+
for (let e of t) {
|
|
3854
|
+
let t = s(a(e)), n = c(t) ? t : t === null ? "" : "" + t;
|
|
3855
|
+
o += n && n.length || 0;
|
|
3856
|
+
}
|
|
3857
|
+
let l = new hc({
|
|
3858
|
+
encoders: this.encoders,
|
|
3859
|
+
attributes: this.getAttributes(),
|
|
3860
|
+
properties: {
|
|
3861
|
+
align: r.align,
|
|
3862
|
+
baseline: r.baseline,
|
|
3863
|
+
logoLetters: i
|
|
3864
|
+
},
|
|
3865
|
+
fontMetrics: this.font.metrics,
|
|
3866
|
+
numCharacters: Math.max(o, cl)
|
|
3867
|
+
});
|
|
3868
|
+
l.addBatches(e.facetBatches);
|
|
3869
|
+
let u = l.toArrays();
|
|
3870
|
+
this.rangeMap.migrateEntries(u.rangeMap), this.updateBufferInfo(u);
|
|
3871
|
+
}
|
|
3872
|
+
prepareRender(e) {
|
|
3873
|
+
let t = super.prepareRender(e);
|
|
3874
|
+
return t.push(() => {
|
|
3875
|
+
J(this.programInfo, { uTexture: this.rendererResources.getFontTexture(this.font.bitmapUrl) });
|
|
3876
|
+
}), t.push(() => this.bindOrSetMarkUniformBlock()), t.push(() => Y(this.gl, this.programInfo, this.vertexArrayInfo)), t;
|
|
3877
|
+
}
|
|
3878
|
+
render(e) {
|
|
3879
|
+
let t = this.gl;
|
|
3880
|
+
return this.createRenderCallback((e, n) => ao(t, this.vertexArrayInfo, t.TRIANGLES, n, e), e);
|
|
3881
|
+
}
|
|
3882
|
+
}
|
|
3883
|
+
};
|
|
3884
|
+
function fl(e, t, n) {
|
|
3885
|
+
let r = dl[e.getType()];
|
|
3886
|
+
if (!r) throw Error("Unsupported WebGL mark type: " + e.getType());
|
|
3887
|
+
return new r(e, t, n);
|
|
3888
|
+
}
|
|
3889
|
+
var pl = class {
|
|
3890
|
+
#e = !1;
|
|
3891
|
+
#t = /* @__PURE__ */ new Map();
|
|
3892
|
+
#n = /* @__PURE__ */ new Map();
|
|
3893
|
+
#r = /* @__PURE__ */ new Map();
|
|
3894
|
+
constructor(e) {
|
|
3895
|
+
this.glHelper = e, e.setResourceFinalizer(() => this.dispose());
|
|
3896
|
+
}
|
|
3897
|
+
#i(e) {
|
|
3898
|
+
this.#s();
|
|
3899
|
+
let t = fl(e, this.glHelper, this), n = {
|
|
3900
|
+
mark: e,
|
|
3901
|
+
graphics: t,
|
|
3902
|
+
state: "compiling",
|
|
3903
|
+
collector: void 0,
|
|
3904
|
+
dataRevision: -1,
|
|
3905
|
+
configurationRevision: -1,
|
|
3906
|
+
encodedDataRevision: -1,
|
|
3907
|
+
scaleResolutions: /* @__PURE__ */ new Set()
|
|
3908
|
+
};
|
|
3909
|
+
this.#t.set(e, n), e.unitView.registerDisposer(() => this.releaseMark(e));
|
|
3910
|
+
try {
|
|
3911
|
+
this.#l(n), t.initializeGraphics();
|
|
3912
|
+
} catch (e) {
|
|
3913
|
+
throw n.state = "failed", this.#u(n), t.dispose(), e;
|
|
3914
|
+
}
|
|
3915
|
+
return n;
|
|
3916
|
+
}
|
|
3917
|
+
prepareMarks(e) {
|
|
3918
|
+
let t = this.#a(e);
|
|
3919
|
+
try {
|
|
3920
|
+
this.#o(t.entries);
|
|
3921
|
+
} catch (e) {
|
|
3922
|
+
t.firstError ??= e;
|
|
3923
|
+
}
|
|
3924
|
+
if (t.firstError) throw t.firstError;
|
|
3925
|
+
}
|
|
3926
|
+
#a(e) {
|
|
3927
|
+
this.#s();
|
|
3928
|
+
let t = [], n;
|
|
3929
|
+
for (let r of new Set(e)) try {
|
|
3930
|
+
let e = r.font, n = r.getType() != "text" || e?.metrics;
|
|
3931
|
+
!this.#t.has(r) && r.encoders && n && t.push(this.#i(r));
|
|
3932
|
+
} catch (e) {
|
|
3933
|
+
n ??= e;
|
|
3934
|
+
}
|
|
3935
|
+
return {
|
|
3936
|
+
entries: t,
|
|
3937
|
+
firstError: n
|
|
3938
|
+
};
|
|
3939
|
+
}
|
|
3940
|
+
#o(e) {
|
|
3941
|
+
let t;
|
|
3942
|
+
for (let n of e) try {
|
|
3943
|
+
n.graphics.finalizeGraphicsInitialization(), n.state = "ready";
|
|
3944
|
+
} catch (e) {
|
|
3945
|
+
n.state = "failed", this.#u(n), n.graphics.dispose(), t ??= e;
|
|
3946
|
+
}
|
|
3947
|
+
if (t) throw t;
|
|
3948
|
+
}
|
|
3949
|
+
releaseMark(e) {
|
|
3950
|
+
let t = this.#t.get(e);
|
|
3951
|
+
t && (this.#t.delete(e), t.state = "disposed", t.graphics.dispose(), this.#u(t));
|
|
3952
|
+
}
|
|
3953
|
+
getMarkRenderingDebugState(e) {
|
|
3954
|
+
let t = this.#t.get(e), n = t?.graphics.getDebugState();
|
|
3955
|
+
return {
|
|
3956
|
+
ready: !!(t?.state == "ready" && t.graphics.isReady()),
|
|
3957
|
+
markUniformsAltered: n?.markUniformsAltered ?? !1,
|
|
3958
|
+
vertexCount: n?.vertexCount,
|
|
3959
|
+
allocatedVertices: n?.allocatedVertices,
|
|
3960
|
+
rangeCount: n?.rangeCount ?? 0
|
|
3961
|
+
};
|
|
3962
|
+
}
|
|
3963
|
+
getMarkEntry(e) {
|
|
3964
|
+
return this.#t.get(e);
|
|
3965
|
+
}
|
|
3966
|
+
isEntryActive(e) {
|
|
3967
|
+
return e.state == "ready" && this.#t.get(e.mark) === e;
|
|
3968
|
+
}
|
|
3969
|
+
isEntryDrawable(e) {
|
|
3970
|
+
return this.isEntryActive(e) && e.graphics.isReady();
|
|
3971
|
+
}
|
|
3972
|
+
synchronize(e) {
|
|
3973
|
+
if (!this.#e) for (let t of e) {
|
|
3974
|
+
if (!this.isEntryActive(t)) continue;
|
|
3975
|
+
let e = t.mark;
|
|
3976
|
+
e.initializeRenderingRevisions([], { trackResources: !1 });
|
|
3977
|
+
let n = e.unitView.getCollector();
|
|
3978
|
+
n?.completed && (t.collector !== n || t.dataRevision != n.dataRevision || t.configurationRevision != e.getRenderingRevision("configuration") || t.encodedDataRevision != e.getEncodedDataRevision()) && (t.graphics.updateGraphicsData(n), this.#c(t));
|
|
3979
|
+
}
|
|
3980
|
+
}
|
|
3981
|
+
prepareFontBitmap(e) {
|
|
3982
|
+
this.#s();
|
|
3983
|
+
let t = this.#r.get(e);
|
|
3984
|
+
if (t) return t.ready;
|
|
3985
|
+
let n = this.glHelper.gl, r, i = new Promise((t, i) => {
|
|
3986
|
+
r = ii(n, {
|
|
3987
|
+
src: e,
|
|
3988
|
+
min: n.LINEAR
|
|
3989
|
+
}, (a) => {
|
|
3990
|
+
a ? (this.#r.delete(e), n.deleteTexture(r), i(a)) : this.#e ? i(/* @__PURE__ */ Error("WebGL renderer resources were disposed while loading a font.")) : t();
|
|
3991
|
+
});
|
|
3992
|
+
});
|
|
3993
|
+
return this.#r.set(e, {
|
|
3994
|
+
texture: r,
|
|
3995
|
+
ready: i
|
|
3996
|
+
}), i;
|
|
3997
|
+
}
|
|
3998
|
+
getFontTexture(e) {
|
|
3999
|
+
this.#s();
|
|
4000
|
+
let t = this.#r.get(e);
|
|
4001
|
+
if (!t) throw Error("Font bitmap has not been prepared: " + e);
|
|
4002
|
+
return t.texture;
|
|
4003
|
+
}
|
|
4004
|
+
dispose() {
|
|
4005
|
+
if (this.#e) return;
|
|
4006
|
+
this.#e = !0;
|
|
4007
|
+
for (let e of Array.from(this.#t.keys())) this.releaseMark(e);
|
|
4008
|
+
let e = this.glHelper.gl;
|
|
4009
|
+
for (let { texture: t } of this.#r.values()) e.deleteTexture(t);
|
|
4010
|
+
this.#r.clear();
|
|
4011
|
+
}
|
|
4012
|
+
#s() {
|
|
4013
|
+
if (this.#e) throw Error("WebGL renderer resources have been disposed.");
|
|
4014
|
+
}
|
|
4015
|
+
#c(e) {
|
|
4016
|
+
let t = e.mark;
|
|
4017
|
+
t.initializeRenderingRevisions([], { trackResources: !1 });
|
|
4018
|
+
let n = t.unitView.getCollector();
|
|
4019
|
+
e.collector = n, e.dataRevision = n?.dataRevision ?? -1, e.configurationRevision = t.getRenderingRevision("configuration") ?? -1, e.encodedDataRevision = t.getEncodedDataRevision();
|
|
4020
|
+
}
|
|
4021
|
+
#l(e) {
|
|
4022
|
+
for (let [t, n] of Object.entries(e.mark.encoders)) {
|
|
4023
|
+
if (!n.scale) continue;
|
|
4024
|
+
let i = r(n.channelDef)?.resolutionChannel ?? t;
|
|
4025
|
+
if (!m(i)) continue;
|
|
4026
|
+
let a = e.mark.unitView.getScaleResolution(i);
|
|
4027
|
+
if (!a || e.scaleResolutions.has(a)) continue;
|
|
4028
|
+
e.scaleResolutions.add(a);
|
|
4029
|
+
let o = this.#n.get(a);
|
|
4030
|
+
if (o) {
|
|
4031
|
+
o.count++;
|
|
4032
|
+
continue;
|
|
4033
|
+
}
|
|
4034
|
+
let s = () => this.glHelper.createRangeTexture(a, !0);
|
|
4035
|
+
this.glHelper.createRangeTexture(a), a.addEventListener("domain", s), a.addEventListener("range", s), this.#n.set(a, {
|
|
4036
|
+
count: 1,
|
|
4037
|
+
listener: s
|
|
4038
|
+
});
|
|
4039
|
+
}
|
|
4040
|
+
}
|
|
4041
|
+
#u(e) {
|
|
4042
|
+
for (let t of e.scaleResolutions) {
|
|
4043
|
+
let e = this.#n.get(t);
|
|
4044
|
+
e && (e.count--, e.count == 0 && (t.removeEventListener("domain", e.listener), t.removeEventListener("range", e.listener), this.#n.delete(t)));
|
|
4045
|
+
}
|
|
4046
|
+
e.scaleResolutions.clear();
|
|
4047
|
+
}
|
|
4048
|
+
};
|
|
4049
|
+
//#endregion
|
|
4050
|
+
//#region ../core/src/rendering/webgl/svgRasterizer.js
|
|
4051
|
+
function ml({ runs: e, viewRoot: t, layoutResult: n, webGLHelper: r, markAdapter: i, logicalWidth: a, logicalHeight: o, pixelRatio: s }) {
|
|
4052
|
+
let c = r.gl, l = Math.ceil(a * s), u = Math.ceil(o * s);
|
|
4053
|
+
hl(c, l, u);
|
|
4054
|
+
let d = s == 1 && n ? n : Te(t, xe.create(0, 0, a, o), {
|
|
4055
|
+
devicePixelRatio: s,
|
|
4056
|
+
renderingOptions: { firstFacet: !0 }
|
|
4057
|
+
}), f = No(c, [{
|
|
4058
|
+
format: c.RGBA,
|
|
4059
|
+
type: c.UNSIGNED_BYTE,
|
|
4060
|
+
minMag: c.LINEAR,
|
|
4061
|
+
wrap: c.CLAMP_TO_EDGE
|
|
4062
|
+
}], l, u);
|
|
4063
|
+
try {
|
|
4064
|
+
for (let t of e) {
|
|
4065
|
+
let e = new Us({ picking: !1 }, {
|
|
4066
|
+
webGLHelper: r,
|
|
4067
|
+
markAdapter: i,
|
|
4068
|
+
canvasSize: {
|
|
4069
|
+
width: a,
|
|
4070
|
+
height: o
|
|
4071
|
+
},
|
|
4072
|
+
devicePixelRatio: s,
|
|
4073
|
+
framebufferInfo: f,
|
|
4074
|
+
markPredicate: (e) => t.marks.has(e),
|
|
4075
|
+
pixelOffset: 0
|
|
4076
|
+
});
|
|
4077
|
+
d.collectRenderCommands(e), e.finish(), e.render();
|
|
4078
|
+
let n = Oe(t.bounds, s, l, u);
|
|
4079
|
+
De(t, n, s, qs(c, f, "image/png", {
|
|
4080
|
+
...n,
|
|
4081
|
+
unpremultiplyAlpha: !0
|
|
4082
|
+
}));
|
|
4083
|
+
}
|
|
4084
|
+
} finally {
|
|
4085
|
+
c.bindFramebuffer(c.FRAMEBUFFER, null), c.deleteTexture(f.attachments[0]), c.deleteFramebuffer(f.framebuffer);
|
|
4086
|
+
}
|
|
4087
|
+
}
|
|
4088
|
+
function hl(e, t, n) {
|
|
4089
|
+
let r = e.getParameter(e.MAX_RENDERBUFFER_SIZE), i = e.getParameter(e.MAX_TEXTURE_SIZE), a = Math.min(r, i);
|
|
4090
|
+
if (t <= 0 || n <= 0 || t > a || n > a) throw RangeError(`SVG raster dimensions ${t} x ${n} exceed the WebGL limit ${a}.`);
|
|
4091
|
+
}
|
|
4092
|
+
//#endregion
|
|
4093
|
+
//#region ../core/src/rendering/webgl/index.js
|
|
4094
|
+
function gl(e) {
|
|
4095
|
+
let t = new Rs(e.container, e.sizeSource, { powerPreference: e.powerPreference }, e.onCanvasResize), n = new pl(t);
|
|
4096
|
+
return {
|
|
4097
|
+
surface: t,
|
|
4098
|
+
defaultFontBitmapUrl: ke,
|
|
4099
|
+
prepareFontBitmap: (e) => n.prepareFontBitmap(e),
|
|
4100
|
+
getMarkRenderingDebugState: (e) => n.getMarkRenderingDebugState(e),
|
|
4101
|
+
createRenderCoordinator: (e) => new Gs({
|
|
4102
|
+
...e,
|
|
4103
|
+
glHelper: t,
|
|
4104
|
+
markAdapter: n
|
|
4105
|
+
}),
|
|
4106
|
+
exportCanvas: (e) => Qs({
|
|
4107
|
+
...e,
|
|
4108
|
+
glHelper: t,
|
|
4109
|
+
markAdapter: n
|
|
4110
|
+
}),
|
|
4111
|
+
exportRaster: (e) => $s({
|
|
4112
|
+
...e,
|
|
4113
|
+
glHelper: t,
|
|
4114
|
+
markAdapter: n
|
|
4115
|
+
}),
|
|
4116
|
+
rasterizeSvgRuns: (e) => ml({
|
|
4117
|
+
...e,
|
|
4118
|
+
webGLHelper: t,
|
|
4119
|
+
markAdapter: n
|
|
4120
|
+
}),
|
|
4121
|
+
readPickingId: (e, n) => {
|
|
4122
|
+
let r = t.getDevicePixelRatio(), i = Hs(t.gl, t._pickingBufferInfo, e * r, n * r);
|
|
4123
|
+
return i[0] | i[1] << 8 | i[2] << 16 | i[3] << 24;
|
|
4124
|
+
}
|
|
4125
|
+
};
|
|
4126
|
+
}
|
|
4127
|
+
//#endregion
|
|
4128
|
+
export { gl as createWebGLRenderingBackend };
|