itowns 2.44.3-next.37 → 2.44.3-next.39
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/dist/debug.js +1 -1
- package/dist/debug.js.map +1 -1
- package/dist/itowns.js +1 -1
- package/dist/itowns.js.map +1 -1
- package/examples/3dtiles_loader.html +14 -3
- package/examples/effects_stereo.html +2 -2
- package/examples/misc_collada.html +2 -2
- package/examples/view_3d_map_webxr.html +3 -1
- package/examples/view_multi_25d.html +2 -2
- package/lib/Layer/OGC3DTilesLayer.js +4 -1
- package/lib/ThreeExtended/libs/ktx-parse.module.js +310 -274
- package/lib/ThreeExtended/loaders/DRACOLoader.js +3 -2
- package/lib/ThreeExtended/loaders/GLTFLoader.js +6 -3
- package/lib/ThreeExtended/loaders/KTX2Loader.js +144 -60
- package/lib/ThreeExtended/math/ColorSpaces.js +59 -0
- package/package.json +5 -5
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { BufferAttribute, BufferGeometry, Color, FileLoader, Loader, LinearSRGBColorSpace, SRGBColorSpace } from 'three';
|
|
1
|
+
import { BufferAttribute, BufferGeometry, Color, ColorManagement, FileLoader, Loader, LinearSRGBColorSpace, SRGBColorSpace } from 'three';
|
|
2
2
|
const _taskCache = new WeakMap();
|
|
3
3
|
class DRACOLoader extends Loader {
|
|
4
4
|
constructor(manager) {
|
|
@@ -150,7 +150,8 @@ class DRACOLoader extends Loader {
|
|
|
150
150
|
if (inputColorSpace !== SRGBColorSpace) return;
|
|
151
151
|
const _color = new Color();
|
|
152
152
|
for (let i = 0, il = attribute.count; i < il; i++) {
|
|
153
|
-
_color.fromBufferAttribute(attribute, i)
|
|
153
|
+
_color.fromBufferAttribute(attribute, i);
|
|
154
|
+
ColorManagement.toWorkingColorSpace(_color, SRGBColorSpace);
|
|
154
155
|
attribute.setXYZ(i, _color.r, _color.g, _color.b);
|
|
155
156
|
}
|
|
156
157
|
}
|
|
@@ -109,9 +109,6 @@ class GLTFLoader extends Loader {
|
|
|
109
109
|
this.dracoLoader = dracoLoader;
|
|
110
110
|
return this;
|
|
111
111
|
}
|
|
112
|
-
setDDSLoader() {
|
|
113
|
-
throw new Error('THREE.GLTFLoader: "MSFT_texture_dds" no longer supported. Please update to "KHR_texture_basisu".');
|
|
114
|
-
}
|
|
115
112
|
setKTX2Loader(ktx2Loader) {
|
|
116
113
|
this.ktx2Loader = ktx2Loader;
|
|
117
114
|
return this;
|
|
@@ -1514,6 +1511,7 @@ function getNormalizedComponentScale(constructor) {
|
|
|
1514
1511
|
function getImageURIMimeType(uri) {
|
|
1515
1512
|
if (uri.search(/\.jpe?g($|\?)/i) > 0 || uri.search(/^data\:image\/jpeg/) === 0) return 'image/jpeg';
|
|
1516
1513
|
if (uri.search(/\.webp($|\?)/i) > 0 || uri.search(/^data\:image\/webp/) === 0) return 'image/webp';
|
|
1514
|
+
if (uri.search(/\.ktx2($|\?)/i) > 0 || uri.search(/^data\:image\/ktx2/) === 0) return 'image/ktx2';
|
|
1517
1515
|
return 'image/png';
|
|
1518
1516
|
}
|
|
1519
1517
|
const _identityMatrix = new Matrix4();
|
|
@@ -1928,6 +1926,9 @@ class GLTFParser {
|
|
|
1928
1926
|
// Avoid modifying the original ArrayBuffer, if the bufferView wasn't initialized with zeroes.
|
|
1929
1927
|
bufferAttribute = new BufferAttribute(bufferAttribute.array.slice(), bufferAttribute.itemSize, bufferAttribute.normalized);
|
|
1930
1928
|
}
|
|
1929
|
+
|
|
1930
|
+
// Ignore normalized since we copy from sparse
|
|
1931
|
+
bufferAttribute.normalized = false;
|
|
1931
1932
|
for (let i = 0, il = sparseIndices.length; i < il; i++) {
|
|
1932
1933
|
const index = sparseIndices[i];
|
|
1933
1934
|
bufferAttribute.setX(index, sparseValues[i * itemSize]);
|
|
@@ -1936,6 +1937,7 @@ class GLTFParser {
|
|
|
1936
1937
|
if (itemSize >= 4) bufferAttribute.setW(index, sparseValues[i * itemSize + 3]);
|
|
1937
1938
|
if (itemSize >= 5) throw new Error('THREE.GLTFLoader: Unsupported itemSize in sparse BufferAttribute.');
|
|
1938
1939
|
}
|
|
1940
|
+
bufferAttribute.normalized = normalized;
|
|
1939
1941
|
}
|
|
1940
1942
|
return bufferAttribute;
|
|
1941
1943
|
});
|
|
@@ -1981,6 +1983,7 @@ class GLTFParser {
|
|
|
1981
1983
|
texture.minFilter = WEBGL_FILTERS[sampler.minFilter] || LinearMipmapLinearFilter;
|
|
1982
1984
|
texture.wrapS = WEBGL_WRAPPINGS[sampler.wrapS] || RepeatWrapping;
|
|
1983
1985
|
texture.wrapT = WEBGL_WRAPPINGS[sampler.wrapT] || RepeatWrapping;
|
|
1986
|
+
texture.generateMipmaps = !texture.isCompressedTexture && texture.minFilter !== NearestFilter && texture.minFilter !== LinearFilter;
|
|
1984
1987
|
parser.associations.set(texture, {
|
|
1985
1988
|
textures: textureIndex
|
|
1986
1989
|
});
|
|
@@ -9,12 +9,14 @@
|
|
|
9
9
|
* References:
|
|
10
10
|
* - KTX: http://github.khronos.org/KTX-Specification/
|
|
11
11
|
* - DFD: https://www.khronos.org/registry/DataFormat/specs/1.3/dataformat.1.3.html#basicdescriptor
|
|
12
|
+
* - BasisU HDR: https://github.com/BinomialLLC/basis_universal/wiki/UASTC-HDR-Texture-Specification-v1.0
|
|
12
13
|
*/
|
|
13
14
|
|
|
14
|
-
import { CompressedTexture, CompressedArrayTexture, CompressedCubeTexture, Data3DTexture, DataTexture,
|
|
15
|
+
import { CompressedTexture, CompressedArrayTexture, CompressedCubeTexture, Data3DTexture, DataTexture, FileLoader, FloatType, HalfFloatType, NoColorSpace, LinearFilter, LinearMipmapLinearFilter, LinearSRGBColorSpace, Loader, RedFormat, RGB_BPTC_UNSIGNED_Format, RGB_ETC1_Format, RGB_ETC2_Format, RGB_PVRTC_4BPPV1_Format, RGBA_ASTC_4x4_Format, RGBA_ASTC_6x6_Format, RGBA_BPTC_Format, RGBA_ETC2_EAC_Format, RGBA_PVRTC_4BPPV1_Format, RGBA_S3TC_DXT5_Format, RGBA_S3TC_DXT1_Format, RGBAFormat, RGFormat, SRGBColorSpace, UnsignedByteType } from 'three';
|
|
15
16
|
import { WorkerPool } from "../utils/WorkerPool.js";
|
|
16
|
-
import { read, KHR_DF_FLAG_ALPHA_PREMULTIPLIED, KHR_DF_TRANSFER_SRGB, KHR_SUPERCOMPRESSION_NONE, KHR_SUPERCOMPRESSION_ZSTD, VK_FORMAT_UNDEFINED, VK_FORMAT_R16_SFLOAT, VK_FORMAT_R16G16_SFLOAT, VK_FORMAT_R16G16B16A16_SFLOAT, VK_FORMAT_R32_SFLOAT, VK_FORMAT_R32G32_SFLOAT, VK_FORMAT_R32G32B32A32_SFLOAT, VK_FORMAT_R8_SRGB, VK_FORMAT_R8_UNORM, VK_FORMAT_R8G8_SRGB, VK_FORMAT_R8G8_UNORM, VK_FORMAT_R8G8B8A8_SRGB, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_ASTC_6x6_SRGB_BLOCK, VK_FORMAT_ASTC_6x6_UNORM_BLOCK, KHR_DF_PRIMARIES_UNSPECIFIED, KHR_DF_PRIMARIES_BT709, KHR_DF_PRIMARIES_DISPLAYP3 } from "../libs/ktx-parse.module.js";
|
|
17
|
+
import { read, KHR_DF_FLAG_ALPHA_PREMULTIPLIED, KHR_DF_TRANSFER_SRGB, KHR_SUPERCOMPRESSION_NONE, KHR_SUPERCOMPRESSION_ZSTD, VK_FORMAT_UNDEFINED, VK_FORMAT_R16_SFLOAT, VK_FORMAT_R16G16_SFLOAT, VK_FORMAT_R16G16B16A16_SFLOAT, VK_FORMAT_R32_SFLOAT, VK_FORMAT_R32G32_SFLOAT, VK_FORMAT_R32G32B32A32_SFLOAT, VK_FORMAT_R8_SRGB, VK_FORMAT_R8_UNORM, VK_FORMAT_R8G8_SRGB, VK_FORMAT_R8G8_UNORM, VK_FORMAT_R8G8B8A8_SRGB, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_ASTC_4x4_SFLOAT_BLOCK_EXT, VK_FORMAT_ASTC_6x6_SRGB_BLOCK, VK_FORMAT_ASTC_6x6_UNORM_BLOCK, KHR_DF_PRIMARIES_UNSPECIFIED, KHR_DF_PRIMARIES_BT709, KHR_DF_PRIMARIES_DISPLAYP3 } from "../libs/ktx-parse.module.js";
|
|
17
18
|
import { ZSTDDecoder } from "../libs/zstddec.module.js";
|
|
19
|
+
import { DisplayP3ColorSpace, LinearDisplayP3ColorSpace } from "../math/ColorSpaces.js";
|
|
18
20
|
const _taskCache = new WeakMap();
|
|
19
21
|
let _activeLoaders = 0;
|
|
20
22
|
let _zstd;
|
|
@@ -42,6 +44,8 @@ class KTX2Loader extends Loader {
|
|
|
42
44
|
async detectSupportAsync(renderer) {
|
|
43
45
|
this.workerConfig = {
|
|
44
46
|
astcSupported: await renderer.hasFeatureAsync('texture-compression-astc'),
|
|
47
|
+
astcHDRSupported: false,
|
|
48
|
+
// https://github.com/gpuweb/gpuweb/issues/3856
|
|
45
49
|
etc1Supported: await renderer.hasFeatureAsync('texture-compression-etc1'),
|
|
46
50
|
etc2Supported: await renderer.hasFeatureAsync('texture-compression-etc2'),
|
|
47
51
|
dxtSupported: await renderer.hasFeatureAsync('texture-compression-bc'),
|
|
@@ -54,6 +58,8 @@ class KTX2Loader extends Loader {
|
|
|
54
58
|
if (renderer.isWebGPURenderer === true) {
|
|
55
59
|
this.workerConfig = {
|
|
56
60
|
astcSupported: renderer.hasFeature('texture-compression-astc'),
|
|
61
|
+
astcHDRSupported: false,
|
|
62
|
+
// https://github.com/gpuweb/gpuweb/issues/3856
|
|
57
63
|
etc1Supported: renderer.hasFeature('texture-compression-etc1'),
|
|
58
64
|
etc2Supported: renderer.hasFeature('texture-compression-etc2'),
|
|
59
65
|
dxtSupported: renderer.hasFeature('texture-compression-bc'),
|
|
@@ -63,6 +69,7 @@ class KTX2Loader extends Loader {
|
|
|
63
69
|
} else {
|
|
64
70
|
this.workerConfig = {
|
|
65
71
|
astcSupported: renderer.extensions.has('WEBGL_compressed_texture_astc'),
|
|
72
|
+
astcHDRSupported: renderer.extensions.has('WEBGL_compressed_texture_astc') && renderer.extensions.get('WEBGL_compressed_texture_astc').getSupportedProfiles().includes('hdr'),
|
|
66
73
|
etc1Supported: renderer.extensions.has('WEBGL_compressed_texture_etc1'),
|
|
67
74
|
etc2Supported: renderer.extensions.has('WEBGL_compressed_texture_etc'),
|
|
68
75
|
dxtSupported: renderer.extensions.has('WEBGL_compressed_texture_s3tc'),
|
|
@@ -89,7 +96,7 @@ class KTX2Loader extends Loader {
|
|
|
89
96
|
this.transcoderPending = Promise.all([jsContent, binaryContent]).then(_ref => {
|
|
90
97
|
let [jsContent, binaryContent] = _ref;
|
|
91
98
|
const fn = KTX2Loader.BasisWorker.toString();
|
|
92
|
-
const body = ['/* constants */', 'let _EngineFormat = ' + JSON.stringify(KTX2Loader.EngineFormat), 'let _TranscoderFormat = ' + JSON.stringify(KTX2Loader.TranscoderFormat), 'let _BasisFormat = ' + JSON.stringify(KTX2Loader.BasisFormat), '/* basis_transcoder.js */', jsContent, '/* worker */', fn.substring(fn.indexOf('{') + 1, fn.lastIndexOf('}'))].join('\n');
|
|
99
|
+
const body = ['/* constants */', 'let _EngineFormat = ' + JSON.stringify(KTX2Loader.EngineFormat), 'let _EngineType = ' + JSON.stringify(KTX2Loader.EngineType), 'let _TranscoderFormat = ' + JSON.stringify(KTX2Loader.TranscoderFormat), 'let _BasisFormat = ' + JSON.stringify(KTX2Loader.BasisFormat), '/* basis_transcoder.js */', jsContent, '/* worker */', fn.substring(fn.indexOf('{') + 1, fn.lastIndexOf('}'))].join('\n');
|
|
93
100
|
this.workerSourceURL = URL.createObjectURL(new Blob([body]));
|
|
94
101
|
this.transcoderBinary = binaryContent;
|
|
95
102
|
this.workerPool.setWorkerCreator(() => {
|
|
@@ -138,21 +145,24 @@ class KTX2Loader extends Loader {
|
|
|
138
145
|
}
|
|
139
146
|
_createTextureFrom(transcodeResult, container) {
|
|
140
147
|
const {
|
|
141
|
-
|
|
142
|
-
width,
|
|
143
|
-
height,
|
|
144
|
-
format,
|
|
145
|
-
type,
|
|
148
|
+
type: messageType,
|
|
146
149
|
error,
|
|
147
|
-
|
|
150
|
+
data: {
|
|
151
|
+
faces,
|
|
152
|
+
width,
|
|
153
|
+
height,
|
|
154
|
+
format,
|
|
155
|
+
type,
|
|
156
|
+
dfdFlags
|
|
157
|
+
}
|
|
148
158
|
} = transcodeResult;
|
|
149
|
-
if (
|
|
159
|
+
if (messageType === 'error') return Promise.reject(error);
|
|
150
160
|
let texture;
|
|
151
161
|
if (container.faceCount === 6) {
|
|
152
|
-
texture = new CompressedCubeTexture(faces, format,
|
|
162
|
+
texture = new CompressedCubeTexture(faces, format, type);
|
|
153
163
|
} else {
|
|
154
164
|
const mipmaps = faces[0].mipmaps;
|
|
155
|
-
texture = container.layerCount > 1 ? new CompressedArrayTexture(mipmaps, width, height, container.layerCount, format,
|
|
165
|
+
texture = container.layerCount > 1 ? new CompressedArrayTexture(mipmaps, width, height, container.layerCount, format, type) : new CompressedTexture(mipmaps, width, height, format, type);
|
|
156
166
|
}
|
|
157
167
|
texture.minFilter = faces[0].mipmaps.length === 1 ? LinearFilter : LinearMipmapLinearFilter;
|
|
158
168
|
texture.magFilter = LinearFilter;
|
|
@@ -171,7 +181,17 @@ class KTX2Loader extends Loader {
|
|
|
171
181
|
async _createTexture(buffer) {
|
|
172
182
|
let config = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
173
183
|
const container = read(new Uint8Array(buffer));
|
|
174
|
-
|
|
184
|
+
|
|
185
|
+
// Basis UASTC HDR is a subset of ASTC, which can be transcoded efficiently
|
|
186
|
+
// to BC6H. To detect whether a KTX2 file uses Basis UASTC HDR, or default
|
|
187
|
+
// ASTC, inspect the DFD color model.
|
|
188
|
+
//
|
|
189
|
+
// Source: https://github.com/BinomialLLC/basis_universal/issues/381
|
|
190
|
+
const isBasisHDR = container.vkFormat === VK_FORMAT_ASTC_4x4_SFLOAT_BLOCK_EXT && container.dataFormatDescriptor[0].colorModel === 0xA7;
|
|
191
|
+
|
|
192
|
+
// If the device supports ASTC, Basis UASTC HDR requires no transcoder.
|
|
193
|
+
const needsTranscoder = container.vkFormat === VK_FORMAT_UNDEFINED || isBasisHDR && !this.workerConfig.astcHDRSupported;
|
|
194
|
+
if (!needsTranscoder) {
|
|
175
195
|
return createRawTexture(container);
|
|
176
196
|
}
|
|
177
197
|
|
|
@@ -203,8 +223,11 @@ class KTX2Loader extends Loader {
|
|
|
203
223
|
|
|
204
224
|
KTX2Loader.BasisFormat = {
|
|
205
225
|
ETC1S: 0,
|
|
206
|
-
|
|
226
|
+
UASTC: 1,
|
|
227
|
+
UASTC_HDR: 2
|
|
207
228
|
};
|
|
229
|
+
|
|
230
|
+
// Source: https://github.com/BinomialLLC/basis_universal/blob/master/webgl/texture_test/index.html
|
|
208
231
|
KTX2Loader.TranscoderFormat = {
|
|
209
232
|
ETC1: 0,
|
|
210
233
|
ETC2: 1,
|
|
@@ -222,11 +245,15 @@ KTX2Loader.TranscoderFormat = {
|
|
|
222
245
|
RGBA32: 13,
|
|
223
246
|
RGB565: 14,
|
|
224
247
|
BGR565: 15,
|
|
225
|
-
RGBA4444: 16
|
|
248
|
+
RGBA4444: 16,
|
|
249
|
+
BC6H: 22,
|
|
250
|
+
RGB_HALF: 24,
|
|
251
|
+
RGBA_HALF: 25
|
|
226
252
|
};
|
|
227
253
|
KTX2Loader.EngineFormat = {
|
|
228
254
|
RGBAFormat: RGBAFormat,
|
|
229
255
|
RGBA_ASTC_4x4_Format: RGBA_ASTC_4x4_Format,
|
|
256
|
+
RGB_BPTC_UNSIGNED_Format: RGB_BPTC_UNSIGNED_Format,
|
|
230
257
|
RGBA_BPTC_Format: RGBA_BPTC_Format,
|
|
231
258
|
RGBA_ETC2_EAC_Format: RGBA_ETC2_EAC_Format,
|
|
232
259
|
RGBA_PVRTC_4BPPV1_Format: RGBA_PVRTC_4BPPV1_Format,
|
|
@@ -236,6 +263,11 @@ KTX2Loader.EngineFormat = {
|
|
|
236
263
|
RGB_PVRTC_4BPPV1_Format: RGB_PVRTC_4BPPV1_Format,
|
|
237
264
|
RGBA_S3TC_DXT1_Format: RGBA_S3TC_DXT1_Format
|
|
238
265
|
};
|
|
266
|
+
KTX2Loader.EngineType = {
|
|
267
|
+
UnsignedByteType: UnsignedByteType,
|
|
268
|
+
HalfFloatType: HalfFloatType,
|
|
269
|
+
FloatType: FloatType
|
|
270
|
+
};
|
|
239
271
|
|
|
240
272
|
/* WEB WORKER */
|
|
241
273
|
|
|
@@ -244,6 +276,7 @@ KTX2Loader.BasisWorker = function () {
|
|
|
244
276
|
let transcoderPending;
|
|
245
277
|
let BasisModule;
|
|
246
278
|
const EngineFormat = _EngineFormat; // eslint-disable-line no-undef
|
|
279
|
+
const EngineType = _EngineType; // eslint-disable-line no-undef
|
|
247
280
|
const TranscoderFormat = _TranscoderFormat; // eslint-disable-line no-undef
|
|
248
281
|
const BasisFormat = _BasisFormat; // eslint-disable-line no-undef
|
|
249
282
|
|
|
@@ -264,17 +297,21 @@ KTX2Loader.BasisWorker = function () {
|
|
|
264
297
|
height,
|
|
265
298
|
hasAlpha,
|
|
266
299
|
format,
|
|
300
|
+
type,
|
|
267
301
|
dfdFlags
|
|
268
302
|
} = transcode(message.buffer);
|
|
269
303
|
self.postMessage({
|
|
270
304
|
type: 'transcode',
|
|
271
305
|
id: message.id,
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
306
|
+
data: {
|
|
307
|
+
faces,
|
|
308
|
+
width,
|
|
309
|
+
height,
|
|
310
|
+
hasAlpha,
|
|
311
|
+
format,
|
|
312
|
+
type,
|
|
313
|
+
dfdFlags
|
|
314
|
+
}
|
|
278
315
|
}, buffers);
|
|
279
316
|
} catch (error) {
|
|
280
317
|
console.error(error);
|
|
@@ -312,7 +349,16 @@ KTX2Loader.BasisWorker = function () {
|
|
|
312
349
|
cleanup();
|
|
313
350
|
throw new Error('THREE.KTX2Loader: Invalid or unsupported .ktx2 file');
|
|
314
351
|
}
|
|
315
|
-
|
|
352
|
+
let basisFormat;
|
|
353
|
+
if (ktx2File.isUASTC()) {
|
|
354
|
+
basisFormat = BasisFormat.UASTC;
|
|
355
|
+
} else if (ktx2File.isETC1S()) {
|
|
356
|
+
basisFormat = BasisFormat.ETC1S;
|
|
357
|
+
} else if (ktx2File.isHDR()) {
|
|
358
|
+
basisFormat = BasisFormat.UASTC_HDR;
|
|
359
|
+
} else {
|
|
360
|
+
throw new Error('THREE.KTX2Loader: Unknown Basis encoding');
|
|
361
|
+
}
|
|
316
362
|
const width = ktx2File.getWidth();
|
|
317
363
|
const height = ktx2File.getHeight();
|
|
318
364
|
const layerCount = ktx2File.getLayers() || 1;
|
|
@@ -322,7 +368,8 @@ KTX2Loader.BasisWorker = function () {
|
|
|
322
368
|
const dfdFlags = ktx2File.getDFDFlags();
|
|
323
369
|
const {
|
|
324
370
|
transcoderFormat,
|
|
325
|
-
engineFormat
|
|
371
|
+
engineFormat,
|
|
372
|
+
engineType
|
|
326
373
|
} = getTranscoderFormat(basisFormat, width, height, hasAlpha);
|
|
327
374
|
if (!width || !height || !levelCount) {
|
|
328
375
|
cleanup();
|
|
@@ -354,8 +401,11 @@ KTX2Loader.BasisWorker = function () {
|
|
|
354
401
|
mipWidth = levelInfo.width;
|
|
355
402
|
mipHeight = levelInfo.height;
|
|
356
403
|
}
|
|
357
|
-
|
|
404
|
+
let dst = new Uint8Array(ktx2File.getImageTranscodedSizeInBytes(mip, layer, 0, transcoderFormat));
|
|
358
405
|
const status = ktx2File.transcodeImage(dst, mip, layer, face, transcoderFormat, 0, -1, -1);
|
|
406
|
+
if (engineType === EngineType.HalfFloatType) {
|
|
407
|
+
dst = new Uint16Array(dst.buffer, dst.byteOffset, dst.byteLength / Uint16Array.BYTES_PER_ELEMENT);
|
|
408
|
+
}
|
|
359
409
|
if (!status) {
|
|
360
410
|
cleanup();
|
|
361
411
|
throw new Error('THREE.KTX2Loader: .transcodeImage failed.');
|
|
@@ -374,7 +424,8 @@ KTX2Loader.BasisWorker = function () {
|
|
|
374
424
|
mipmaps,
|
|
375
425
|
width,
|
|
376
426
|
height,
|
|
377
|
-
format: engineFormat
|
|
427
|
+
format: engineFormat,
|
|
428
|
+
type: engineType
|
|
378
429
|
});
|
|
379
430
|
}
|
|
380
431
|
cleanup();
|
|
@@ -384,99 +435,131 @@ KTX2Loader.BasisWorker = function () {
|
|
|
384
435
|
width,
|
|
385
436
|
height,
|
|
386
437
|
hasAlpha,
|
|
438
|
+
dfdFlags,
|
|
387
439
|
format: engineFormat,
|
|
388
|
-
|
|
440
|
+
type: engineType
|
|
389
441
|
};
|
|
390
442
|
}
|
|
391
443
|
|
|
392
444
|
//
|
|
393
445
|
|
|
394
|
-
// Optimal choice of a transcoder target format depends on the Basis format (ETC1S
|
|
395
|
-
// device capabilities, and texture dimensions. The list below ranks the formats
|
|
396
|
-
// for
|
|
446
|
+
// Optimal choice of a transcoder target format depends on the Basis format (ETC1S, UASTC, or
|
|
447
|
+
// UASTC HDR), device capabilities, and texture dimensions. The list below ranks the formats
|
|
448
|
+
// separately for each format. Currently, priority is assigned based on:
|
|
449
|
+
//
|
|
450
|
+
// high quality > low quality > uncompressed
|
|
451
|
+
//
|
|
452
|
+
// Prioritization may be revisited, or exposed for configuration, in the future.
|
|
397
453
|
//
|
|
398
|
-
//
|
|
399
|
-
// significant memory cost) compared to ETC1/2, BC1/3, and PVRTC. The transcoder currently
|
|
400
|
-
// chooses RGBA32 only as a last resort and does not expose that option to the caller.
|
|
454
|
+
// Reference: https://github.com/KhronosGroup/3D-Formats-Guidelines/blob/main/KTXDeveloperGuide.md
|
|
401
455
|
const FORMAT_OPTIONS = [{
|
|
402
456
|
if: 'astcSupported',
|
|
403
|
-
basisFormat: [BasisFormat.
|
|
457
|
+
basisFormat: [BasisFormat.UASTC],
|
|
404
458
|
transcoderFormat: [TranscoderFormat.ASTC_4x4, TranscoderFormat.ASTC_4x4],
|
|
405
459
|
engineFormat: [EngineFormat.RGBA_ASTC_4x4_Format, EngineFormat.RGBA_ASTC_4x4_Format],
|
|
460
|
+
engineType: [EngineType.UnsignedByteType],
|
|
406
461
|
priorityETC1S: Infinity,
|
|
407
462
|
priorityUASTC: 1,
|
|
408
463
|
needsPowerOfTwo: false
|
|
409
464
|
}, {
|
|
410
465
|
if: 'bptcSupported',
|
|
411
|
-
basisFormat: [BasisFormat.ETC1S, BasisFormat.
|
|
466
|
+
basisFormat: [BasisFormat.ETC1S, BasisFormat.UASTC],
|
|
412
467
|
transcoderFormat: [TranscoderFormat.BC7_M5, TranscoderFormat.BC7_M5],
|
|
413
468
|
engineFormat: [EngineFormat.RGBA_BPTC_Format, EngineFormat.RGBA_BPTC_Format],
|
|
469
|
+
engineType: [EngineType.UnsignedByteType],
|
|
414
470
|
priorityETC1S: 3,
|
|
415
471
|
priorityUASTC: 2,
|
|
416
472
|
needsPowerOfTwo: false
|
|
417
473
|
}, {
|
|
418
474
|
if: 'dxtSupported',
|
|
419
|
-
basisFormat: [BasisFormat.ETC1S, BasisFormat.
|
|
475
|
+
basisFormat: [BasisFormat.ETC1S, BasisFormat.UASTC],
|
|
420
476
|
transcoderFormat: [TranscoderFormat.BC1, TranscoderFormat.BC3],
|
|
421
477
|
engineFormat: [EngineFormat.RGBA_S3TC_DXT1_Format, EngineFormat.RGBA_S3TC_DXT5_Format],
|
|
478
|
+
engineType: [EngineType.UnsignedByteType],
|
|
422
479
|
priorityETC1S: 4,
|
|
423
480
|
priorityUASTC: 5,
|
|
424
481
|
needsPowerOfTwo: false
|
|
425
482
|
}, {
|
|
426
483
|
if: 'etc2Supported',
|
|
427
|
-
basisFormat: [BasisFormat.ETC1S, BasisFormat.
|
|
484
|
+
basisFormat: [BasisFormat.ETC1S, BasisFormat.UASTC],
|
|
428
485
|
transcoderFormat: [TranscoderFormat.ETC1, TranscoderFormat.ETC2],
|
|
429
486
|
engineFormat: [EngineFormat.RGB_ETC2_Format, EngineFormat.RGBA_ETC2_EAC_Format],
|
|
487
|
+
engineType: [EngineType.UnsignedByteType],
|
|
430
488
|
priorityETC1S: 1,
|
|
431
489
|
priorityUASTC: 3,
|
|
432
490
|
needsPowerOfTwo: false
|
|
433
491
|
}, {
|
|
434
492
|
if: 'etc1Supported',
|
|
435
|
-
basisFormat: [BasisFormat.ETC1S, BasisFormat.
|
|
493
|
+
basisFormat: [BasisFormat.ETC1S, BasisFormat.UASTC],
|
|
436
494
|
transcoderFormat: [TranscoderFormat.ETC1],
|
|
437
495
|
engineFormat: [EngineFormat.RGB_ETC1_Format],
|
|
496
|
+
engineType: [EngineType.UnsignedByteType],
|
|
438
497
|
priorityETC1S: 2,
|
|
439
498
|
priorityUASTC: 4,
|
|
440
499
|
needsPowerOfTwo: false
|
|
441
500
|
}, {
|
|
442
501
|
if: 'pvrtcSupported',
|
|
443
|
-
basisFormat: [BasisFormat.ETC1S, BasisFormat.
|
|
502
|
+
basisFormat: [BasisFormat.ETC1S, BasisFormat.UASTC],
|
|
444
503
|
transcoderFormat: [TranscoderFormat.PVRTC1_4_RGB, TranscoderFormat.PVRTC1_4_RGBA],
|
|
445
504
|
engineFormat: [EngineFormat.RGB_PVRTC_4BPPV1_Format, EngineFormat.RGBA_PVRTC_4BPPV1_Format],
|
|
505
|
+
engineType: [EngineType.UnsignedByteType],
|
|
446
506
|
priorityETC1S: 5,
|
|
447
507
|
priorityUASTC: 6,
|
|
448
508
|
needsPowerOfTwo: true
|
|
509
|
+
}, {
|
|
510
|
+
if: 'bptcSupported',
|
|
511
|
+
basisFormat: [BasisFormat.UASTC_HDR],
|
|
512
|
+
transcoderFormat: [TranscoderFormat.BC6H],
|
|
513
|
+
engineFormat: [EngineFormat.RGB_BPTC_UNSIGNED_Format],
|
|
514
|
+
engineType: [EngineType.HalfFloatType],
|
|
515
|
+
priorityHDR: 1,
|
|
516
|
+
needsPowerOfTwo: false
|
|
517
|
+
},
|
|
518
|
+
// Uncompressed fallbacks.
|
|
519
|
+
|
|
520
|
+
{
|
|
521
|
+
basisFormat: [BasisFormat.ETC1S, BasisFormat.UASTC],
|
|
522
|
+
transcoderFormat: [TranscoderFormat.RGBA32, TranscoderFormat.RGBA32],
|
|
523
|
+
engineFormat: [EngineFormat.RGBAFormat, EngineFormat.RGBAFormat],
|
|
524
|
+
engineType: [EngineType.UnsignedByteType, EngineType.UnsignedByteType],
|
|
525
|
+
priorityETC1S: 100,
|
|
526
|
+
priorityUASTC: 100,
|
|
527
|
+
needsPowerOfTwo: false
|
|
528
|
+
}, {
|
|
529
|
+
basisFormat: [BasisFormat.UASTC_HDR],
|
|
530
|
+
transcoderFormat: [TranscoderFormat.RGBA_HALF],
|
|
531
|
+
engineFormat: [EngineFormat.RGBAFormat],
|
|
532
|
+
engineType: [EngineType.HalfFloatType],
|
|
533
|
+
priorityHDR: 100,
|
|
534
|
+
needsPowerOfTwo: false
|
|
449
535
|
}];
|
|
450
|
-
const
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
|
|
536
|
+
const OPTIONS = {
|
|
537
|
+
// TODO: For ETC1S we intentionally sort by _UASTC_ priority, preserving
|
|
538
|
+
// a historical accident shown to avoid performance pitfalls for Linux with
|
|
539
|
+
// Firefox & AMD GPU (RadeonSI). Further work needed.
|
|
540
|
+
// See https://github.com/mrdoob/three.js/pull/29730.
|
|
541
|
+
[BasisFormat.ETC1S]: FORMAT_OPTIONS.filter(opt => opt.basisFormat.includes(BasisFormat.ETC1S)).sort((a, b) => a.priorityUASTC - b.priorityUASTC),
|
|
542
|
+
[BasisFormat.UASTC]: FORMAT_OPTIONS.filter(opt => opt.basisFormat.includes(BasisFormat.UASTC)).sort((a, b) => a.priorityUASTC - b.priorityUASTC),
|
|
543
|
+
[BasisFormat.UASTC_HDR]: FORMAT_OPTIONS.filter(opt => opt.basisFormat.includes(BasisFormat.UASTC_HDR)).sort((a, b) => a.priorityHDR - b.priorityHDR)
|
|
544
|
+
};
|
|
456
545
|
function getTranscoderFormat(basisFormat, width, height, hasAlpha) {
|
|
457
|
-
|
|
458
|
-
let engineFormat;
|
|
459
|
-
const options = basisFormat === BasisFormat.ETC1S ? ETC1S_OPTIONS : UASTC_OPTIONS;
|
|
546
|
+
const options = OPTIONS[basisFormat];
|
|
460
547
|
for (let i = 0; i < options.length; i++) {
|
|
461
548
|
const opt = options[i];
|
|
462
|
-
if (!config[opt.if]) continue;
|
|
549
|
+
if (opt.if && !config[opt.if]) continue;
|
|
463
550
|
if (!opt.basisFormat.includes(basisFormat)) continue;
|
|
464
551
|
if (hasAlpha && opt.transcoderFormat.length < 2) continue;
|
|
465
552
|
if (opt.needsPowerOfTwo && !(isPowerOfTwo(width) && isPowerOfTwo(height))) continue;
|
|
466
|
-
transcoderFormat = opt.transcoderFormat[hasAlpha ? 1 : 0];
|
|
467
|
-
engineFormat = opt.engineFormat[hasAlpha ? 1 : 0];
|
|
553
|
+
const transcoderFormat = opt.transcoderFormat[hasAlpha ? 1 : 0];
|
|
554
|
+
const engineFormat = opt.engineFormat[hasAlpha ? 1 : 0];
|
|
555
|
+
const engineType = opt.engineType[0];
|
|
468
556
|
return {
|
|
469
557
|
transcoderFormat,
|
|
470
|
-
engineFormat
|
|
558
|
+
engineFormat,
|
|
559
|
+
engineType
|
|
471
560
|
};
|
|
472
561
|
}
|
|
473
|
-
|
|
474
|
-
transcoderFormat = TranscoderFormat.RGBA32;
|
|
475
|
-
engineFormat = EngineFormat.RGBAFormat;
|
|
476
|
-
return {
|
|
477
|
-
transcoderFormat,
|
|
478
|
-
engineFormat
|
|
479
|
-
};
|
|
562
|
+
throw new Error('THREE.KTX2Loader: Failed to identify transcoding target.');
|
|
480
563
|
}
|
|
481
564
|
function isPowerOfTwo(value) {
|
|
482
565
|
if (value <= 2) return true;
|
|
@@ -502,8 +585,7 @@ KTX2Loader.BasisWorker = function () {
|
|
|
502
585
|
}
|
|
503
586
|
};
|
|
504
587
|
|
|
505
|
-
//
|
|
506
|
-
// Parsing for non-Basis textures. These textures are may have supercompression
|
|
588
|
+
// Parsing for non-Basis textures. These textures may have supercompression
|
|
507
589
|
// like Zstd, but they do not require transcoding.
|
|
508
590
|
|
|
509
591
|
const UNCOMPRESSED_FORMATS = new Set([RGBAFormat, RGFormat, RedFormat]);
|
|
@@ -520,6 +602,7 @@ const FORMAT_MAP = {
|
|
|
520
602
|
[VK_FORMAT_R16_SFLOAT]: RedFormat,
|
|
521
603
|
[VK_FORMAT_R8_SRGB]: RedFormat,
|
|
522
604
|
[VK_FORMAT_R8_UNORM]: RedFormat,
|
|
605
|
+
[VK_FORMAT_ASTC_4x4_SFLOAT_BLOCK_EXT]: RGBA_ASTC_4x4_Format,
|
|
523
606
|
[VK_FORMAT_ASTC_6x6_SRGB_BLOCK]: RGBA_ASTC_6x6_Format,
|
|
524
607
|
[VK_FORMAT_ASTC_6x6_UNORM_BLOCK]: RGBA_ASTC_6x6_Format
|
|
525
608
|
};
|
|
@@ -536,6 +619,7 @@ const TYPE_MAP = {
|
|
|
536
619
|
[VK_FORMAT_R16_SFLOAT]: HalfFloatType,
|
|
537
620
|
[VK_FORMAT_R8_SRGB]: UnsignedByteType,
|
|
538
621
|
[VK_FORMAT_R8_UNORM]: UnsignedByteType,
|
|
622
|
+
[VK_FORMAT_ASTC_4x4_SFLOAT_BLOCK_EXT]: HalfFloatType,
|
|
539
623
|
[VK_FORMAT_ASTC_6x6_SRGB_BLOCK]: UnsignedByteType,
|
|
540
624
|
[VK_FORMAT_ASTC_6x6_UNORM_BLOCK]: UnsignedByteType
|
|
541
625
|
};
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
import { LinearTransfer, Matrix3, SRGBTransfer } from 'three';
|
|
2
|
+
|
|
3
|
+
// Reference: http://www.russellcottrell.com/photo/matrixCalculator.htm
|
|
4
|
+
|
|
5
|
+
const P3_PRIMARIES = [0.680, 0.320, 0.265, 0.690, 0.150, 0.060];
|
|
6
|
+
const P3_LUMINANCE_COEFFICIENTS = [0.2289, 0.6917, 0.0793];
|
|
7
|
+
const REC2020_PRIMARIES = [0.708, 0.292, 0.170, 0.797, 0.131, 0.046];
|
|
8
|
+
const REC2020_LUMINANCE_COEFFICIENTS = [0.2627, 0.6780, 0.0593];
|
|
9
|
+
const D65 = [0.3127, 0.3290];
|
|
10
|
+
|
|
11
|
+
/******************************************************************************
|
|
12
|
+
* Display P3 definitions
|
|
13
|
+
*/
|
|
14
|
+
|
|
15
|
+
const LINEAR_DISPLAY_P3_TO_XYZ = /*@__PURE__*/new Matrix3().set(0.4865709, 0.2656677, 0.1982173, 0.2289746, 0.6917385, 0.0792869, 0.0000000, 0.0451134, 1.0439444);
|
|
16
|
+
const XYZ_TO_LINEAR_DISPLAY_P3 = /*@__PURE__*/new Matrix3().set(2.4934969, -0.9313836, -0.4027108, -0.8294890, 1.7626641, 0.0236247, 0.0358458, -0.0761724, 0.9568845);
|
|
17
|
+
export const DisplayP3ColorSpace = 'display-p3';
|
|
18
|
+
export const LinearDisplayP3ColorSpace = 'display-p3-linear';
|
|
19
|
+
export const DisplayP3ColorSpaceImpl = {
|
|
20
|
+
primaries: P3_PRIMARIES,
|
|
21
|
+
whitePoint: D65,
|
|
22
|
+
transfer: SRGBTransfer,
|
|
23
|
+
toXYZ: LINEAR_DISPLAY_P3_TO_XYZ,
|
|
24
|
+
fromXYZ: XYZ_TO_LINEAR_DISPLAY_P3,
|
|
25
|
+
luminanceCoefficients: P3_LUMINANCE_COEFFICIENTS,
|
|
26
|
+
outputColorSpaceConfig: {
|
|
27
|
+
drawingBufferColorSpace: DisplayP3ColorSpace
|
|
28
|
+
}
|
|
29
|
+
};
|
|
30
|
+
export const LinearDisplayP3ColorSpaceImpl = {
|
|
31
|
+
primaries: P3_PRIMARIES,
|
|
32
|
+
whitePoint: D65,
|
|
33
|
+
transfer: LinearTransfer,
|
|
34
|
+
toXYZ: LINEAR_DISPLAY_P3_TO_XYZ,
|
|
35
|
+
fromXYZ: XYZ_TO_LINEAR_DISPLAY_P3,
|
|
36
|
+
luminanceCoefficients: P3_LUMINANCE_COEFFICIENTS,
|
|
37
|
+
workingColorSpaceConfig: {
|
|
38
|
+
unpackColorSpace: DisplayP3ColorSpace
|
|
39
|
+
},
|
|
40
|
+
outputColorSpaceConfig: {
|
|
41
|
+
drawingBufferColorSpace: DisplayP3ColorSpace
|
|
42
|
+
}
|
|
43
|
+
};
|
|
44
|
+
|
|
45
|
+
/******************************************************************************
|
|
46
|
+
* Rec. 2020 definitions
|
|
47
|
+
*/
|
|
48
|
+
|
|
49
|
+
const LINEAR_REC2020_TO_XYZ = /*@__PURE__*/new Matrix3().set(0.6369580, 0.1446169, 0.1688810, 0.2627002, 0.6779981, 0.0593017, 0.0000000, 0.0280727, 1.0609851);
|
|
50
|
+
const XYZ_TO_LINEAR_REC2020 = /*@__PURE__*/new Matrix3().set(1.7166512, -0.3556708, -0.2533663, -0.6666844, 1.6164812, 0.0157685, 0.0176399, -0.0427706, 0.9421031);
|
|
51
|
+
export const LinearRec2020ColorSpace = 'rec2020-linear';
|
|
52
|
+
export const LinearRec2020ColorSpaceImpl = {
|
|
53
|
+
primaries: REC2020_PRIMARIES,
|
|
54
|
+
whitePoint: D65,
|
|
55
|
+
transfer: LinearTransfer,
|
|
56
|
+
toXYZ: LINEAR_REC2020_TO_XYZ,
|
|
57
|
+
fromXYZ: XYZ_TO_LINEAR_REC2020,
|
|
58
|
+
luminanceCoefficients: REC2020_LUMINANCE_COEFFICIENTS
|
|
59
|
+
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "itowns",
|
|
3
|
-
"version": "2.44.3-next.
|
|
3
|
+
"version": "2.44.3-next.39",
|
|
4
4
|
"description": "A JS/WebGL framework for 3D geospatial data visualization",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "lib/Main.js",
|
|
@@ -61,7 +61,7 @@
|
|
|
61
61
|
"@maplibre/maplibre-gl-style-spec": "^22.0.0",
|
|
62
62
|
"@tmcw/togeojson": "^5.8.1",
|
|
63
63
|
"@tweenjs/tween.js": "^25.0.0",
|
|
64
|
-
"3d-tiles-renderer": "^0.
|
|
64
|
+
"3d-tiles-renderer": "^0.4.4",
|
|
65
65
|
"brotli-compress": "^1.3.3",
|
|
66
66
|
"copc": "^0.0.6",
|
|
67
67
|
"earcut": "^3.0.0",
|
|
@@ -73,7 +73,7 @@
|
|
|
73
73
|
},
|
|
74
74
|
"peerDependencies": {
|
|
75
75
|
"proj4": "^2.12.1",
|
|
76
|
-
"three": "^0.
|
|
76
|
+
"three": "^0.170.0"
|
|
77
77
|
},
|
|
78
78
|
"devDependencies": {
|
|
79
79
|
"@babel/cli": "^7.25.6",
|
|
@@ -84,7 +84,7 @@
|
|
|
84
84
|
"@babel/register": "^7.24.6",
|
|
85
85
|
"@stylistic/eslint-plugin": "^2.8.0",
|
|
86
86
|
"@types/proj4": "^2.5.5",
|
|
87
|
-
"@types/three": "^0.
|
|
87
|
+
"@types/three": "^0.170.0",
|
|
88
88
|
"@typescript-eslint/eslint-plugin": "^8.5.0",
|
|
89
89
|
"@typescript-eslint/parser": "^8.5.0",
|
|
90
90
|
"@xmldom/xmldom": "^0.9.2",
|
|
@@ -120,7 +120,7 @@
|
|
|
120
120
|
"q": "^1.5.1",
|
|
121
121
|
"replace-in-file": "^8.1.0",
|
|
122
122
|
"sinon": "^19.0.2",
|
|
123
|
-
"three": "^0.
|
|
123
|
+
"three": "^0.170.0",
|
|
124
124
|
"typescript": "^5.6.2",
|
|
125
125
|
"undici": "^7.2.0",
|
|
126
126
|
"webgl-mock": "^0.1.7",
|