three-gpu-pathtracer 0.0.23 → 0.0.25

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.
Files changed (83) hide show
  1. package/README.md +53 -528
  2. package/build/index.module.js +319 -66
  3. package/build/index.module.js.map +1 -1
  4. package/build/index.umd.cjs +318 -64
  5. package/build/index.umd.cjs.map +1 -1
  6. package/package.json +35 -18
  7. package/src/core/PathTracingSceneGenerator.js +21 -2
  8. package/src/core/WebGLPathTracer.js +16 -7
  9. package/src/core/utils/mergeGeometries.js +14 -1
  10. package/src/core/utils/sceneUpdateUtils.js +8 -12
  11. package/src/detectors/PrecisionMaterial.js +9 -9
  12. package/src/index.d.ts +2 -1
  13. package/src/index.js +1 -0
  14. package/src/materials/pathtracing/PhysicalPathTracingMaterial.js +2 -1
  15. package/src/materials/pathtracing/glsl/attenuate_hit_function.glsl.js +2 -1
  16. package/src/materials/pathtracing/glsl/camera_util_functions.glsl.js +1 -1
  17. package/src/materials/pathtracing/glsl/get_surface_record_function.glsl.js +2 -1
  18. package/src/materials/surface/AmbientOcclusionMaterial.js +2 -0
  19. package/src/objects/PhysicalSpotLight.js +2 -0
  20. package/src/shader/bsdf/bsdf_functions.glsl.js +0 -1
  21. package/src/shader/bvh/inside_fog_volume_function.glsl.js +1 -1
  22. package/src/shader/structs/material_struct.glsl.js +3 -1
  23. package/src/textures/BlueNoiseTexture.js +6 -6
  24. package/src/textures/ProceduralEquirectTexture.js +8 -7
  25. package/src/textures/turquinMetal.png +0 -0
  26. package/src/uniforms/EquirectHdrInfoUniform.js +9 -4
  27. package/src/uniforms/FloatAttributeTextureArray.js +11 -11
  28. package/src/uniforms/MaterialsTexture.js +13 -10
  29. package/src/webgpu/API.md +762 -0
  30. package/src/webgpu/AtlasTexture.js +471 -0
  31. package/src/webgpu/BlurredEnvMapGenerator.js +129 -0
  32. package/src/webgpu/EquirectBackgroundInfo.js +97 -0
  33. package/src/webgpu/EquirectHdrInfoNode.js +151 -0
  34. package/src/webgpu/LightsInfoNode.js +224 -0
  35. package/src/webgpu/MegaKernelPathTracer.js +277 -0
  36. package/src/webgpu/PathTracerBackend.js +216 -0
  37. package/src/webgpu/TurquinTexture.js +169 -0
  38. package/src/webgpu/WaveFrontPathTracer.js +586 -0
  39. package/src/webgpu/WebGPUPathTracer.js +1302 -0
  40. package/src/webgpu/compute/ComputeKernel.js +92 -0
  41. package/src/webgpu/compute/CopyBufferKernel.js +40 -0
  42. package/src/webgpu/compute/PathTracerMegaKernel.js +470 -0
  43. package/src/webgpu/compute/SampleDebugKernel.js +51 -0
  44. package/src/webgpu/compute/TallySampleCountsKernel.js +111 -0
  45. package/src/webgpu/compute/ZeroOutBufferKernel.js +35 -0
  46. package/src/webgpu/compute/ZeroOutKernel.js +31 -0
  47. package/src/webgpu/compute/wavefront/LogicKernel.js +349 -0
  48. package/src/webgpu/compute/wavefront/MaterialKernel.js +371 -0
  49. package/src/webgpu/compute/wavefront/PopulatePixelIndicesKernel.js +72 -0
  50. package/src/webgpu/compute/wavefront/QueueLengthToDispatchKernel.js +38 -0
  51. package/src/webgpu/compute/wavefront/ResetSlotsKernel.js +66 -0
  52. package/src/webgpu/compute/wavefront/TraceRayKernel.js +71 -0
  53. package/src/webgpu/compute/wavefront/TraceShadowRayKernel.js +67 -0
  54. package/src/webgpu/compute/wavefront/structs.js +155 -0
  55. package/src/webgpu/constants.js +62 -0
  56. package/src/webgpu/denoise/OIDNDenoiser.js +431 -0
  57. package/src/webgpu/index.d.ts +176 -0
  58. package/src/webgpu/index.js +11 -0
  59. package/src/webgpu/materials/GltfCompliantMaterial.js +608 -0
  60. package/src/webgpu/materials/GraphMaterial.js +331 -0
  61. package/src/webgpu/materials/PathtracingMaterial.js +89 -0
  62. package/src/webgpu/materials/RenderToScreenMaterial.js +150 -0
  63. package/src/webgpu/materials/debug/AtlasDebugMaterial.js +41 -0
  64. package/src/webgpu/materials/debug/SampleDensityMaterial.js +61 -0
  65. package/src/webgpu/nodes/PathtracerBVHComputeData.js +1037 -0
  66. package/src/webgpu/nodes/debugBounds.wgsl.js +228 -0
  67. package/src/webgpu/nodes/eon.wgsl.js +262 -0
  68. package/src/webgpu/nodes/ggx.wgsl.js +190 -0
  69. package/src/webgpu/nodes/lights.wgsl.js +203 -0
  70. package/src/webgpu/nodes/material.wgsl.js +990 -0
  71. package/src/webgpu/nodes/rand/bluedither.wgsl.js +92 -0
  72. package/src/webgpu/nodes/rand/pcg.wgsl.js +81 -0
  73. package/src/webgpu/nodes/rand/sobol.wgsl.js +287 -0
  74. package/src/webgpu/nodes/random.wgsl.js +20 -0
  75. package/src/webgpu/nodes/reset.wgsl.js +21 -0
  76. package/src/webgpu/nodes/sampling.wgsl.js +193 -0
  77. package/src/webgpu/nodes/sheen.wgsl.js +148 -0
  78. package/src/webgpu/nodes/structs.wgsl.js +272 -0
  79. package/src/webgpu/nodes/utils.wgsl.js +366 -0
  80. package/src/webgpu/shims/ArrayCameraShim.js +74 -0
  81. package/src/webgpu/shims/EquirectCameraShim.js +37 -0
  82. package/src/webgpu/shims/PhysicalCameraShim.js +151 -0
  83. package/src/webgpu/upscale/FSRUpscaler.js +108 -0
package/package.json CHANGED
@@ -1,18 +1,29 @@
1
1
  {
2
2
  "name": "three-gpu-pathtracer",
3
- "version": "0.0.23",
3
+ "version": "0.0.25",
4
4
  "description": "Path tracing renderer and utilities for three.js built on top of three-mesh-bvh.",
5
5
  "module": "src/index.js",
6
6
  "main": "build/index.umd.cjs",
7
+ "exports": {
8
+ ".": {
9
+ "import": "./src/index.js",
10
+ "require": "./build/index.umd.cjs"
11
+ },
12
+ "./webgpu": "./src/webgpu/index.js",
13
+ "./src/*": "./src/*"
14
+ },
7
15
  "type": "module",
8
16
  "types": "src/index.d.ts",
9
- "sideEffects": false,
17
+ "sideEffects": [
18
+ "./src/webgpu/index.js",
19
+ "./src/webgpu/shims/*.js"
20
+ ],
10
21
  "files": [
11
22
  "src/*",
12
23
  "build/*"
13
24
  ],
14
25
  "keywords": [
15
- "webgl",
26
+ "webgpu",
16
27
  "threejs",
17
28
  "performance",
18
29
  "geometry",
@@ -30,35 +41,41 @@
30
41
  "tracer"
31
42
  ],
32
43
  "devDependencies": {
33
- "@lookingglass/webxr": "^0.3.1",
44
+ "@lookingglass/webxr": "^0.6.0",
34
45
  "@monogrid/gainmap-js": "^3.0.5",
35
- "@types/node": "^20.12.7",
36
- "@types/three": "^0.163.0",
37
- "@typescript-eslint/parser": "^6.21.0",
38
- "canvas-capture": "^2.0.5",
39
- "eslint": "^7.32.0",
46
+ "@pmndrs/upscaler": "^0.2.0",
47
+ "@types/node": "^24.3.1",
48
+ "@types/three": "^0.185.1",
49
+ "@typescript-eslint/eslint-plugin": "^8.40.0",
50
+ "@vitejs/plugin-basic-ssl": "^2.3.0",
51
+ "@webgpu/types": "^0.1.72",
52
+ "eslint": "^8.56.0",
40
53
  "eslint-config-mdcs": "^5.0.0",
54
+ "eslint-plugin-jsdoc": "^50.8.0",
55
+ "jsdoc": "^4.0.5",
56
+ "mediabunny": "^1.50.9",
41
57
  "node-fetch": "^3.2.9",
42
- "parcel": "^2.12.0",
58
+ "oidn-web": "^0.4.0",
43
59
  "pixelmatch": "^5.3.0",
44
60
  "pngjs": "^6.0.0",
45
61
  "process": "^0.11.10",
46
- "puppeteer": "^15.4.0",
62
+ "puppeteer": "^24.42.0",
47
63
  "rollup": "^2.70.0",
48
64
  "simple-git": "^3.10.0",
49
- "three": "^0.163.0",
50
- "three-mesh-bvh": "^0.7.4",
51
- "typescript": "5.3.3",
65
+ "three": "^0.185.1",
66
+ "three-mesh-bvh": "^0.9.15",
67
+ "typescript": "^5.9.2",
68
+ "vite": "^8.2.2",
52
69
  "yargs": "^17.5.1"
53
70
  },
54
71
  "peerDependencies": {
55
- "three": ">=0.151.0",
56
- "three-mesh-bvh": ">=0.7.4",
72
+ "three": ">=0.185.0",
73
+ "three-mesh-bvh": ">=0.9.15",
57
74
  "xatlas-web": "^0.1.0"
58
75
  },
59
76
  "scripts": {
60
- "start": "cd example && parcel serve ./*.html --dist-dir ./dev-bundle/ --no-cache --no-hmr",
61
- "build-examples": "cd example && parcel build ./*.html --dist-dir ./bundle/ --public-url . --no-cache --no-content-hash",
77
+ "start": "vite --config ./vite.config.js",
78
+ "build-examples": "vite build --config ./vite.config.js",
62
79
  "update-screenshots": "node ./scripts/push-screenshots.js",
63
80
  "screenshot-diff": "node ./scripts/regression-test.js",
64
81
  "build": "rollup -c",
@@ -95,6 +95,7 @@ export class PathTracingSceneGenerator {
95
95
  this._bvhWorker = null;
96
96
  this._pendingGenerate = null;
97
97
  this._buildAsync = false;
98
+ this._materialUuids = null;
98
99
 
99
100
  }
100
101
 
@@ -176,12 +177,29 @@ export class PathTracingSceneGenerator {
176
177
  // generate the geometry
177
178
  const result = staticGeometryGenerator.generate( geometry );
178
179
  const materials = result.materials;
180
+ let needsMaterialIndexUpdate = result.changeType !== NO_CHANGE || this._materialUuids === null || this._materialUuids.length !== length;
181
+ if ( ! needsMaterialIndexUpdate ) {
182
+
183
+ for ( let i = 0, length = materials.length; i < length; i ++ ) {
184
+
185
+ const material = materials[ i ];
186
+ if ( material.uuid !== this._materialUuids[ i ] ) {
187
+
188
+ needsMaterialIndexUpdate = true;
189
+ break;
190
+
191
+ }
192
+
193
+ }
194
+
195
+ }
196
+
179
197
  const textures = getTextures( materials );
180
198
  const { lights, iesTextures } = getLights( objects );
181
-
182
- if ( result.changeType !== NO_CHANGE ) {
199
+ if ( needsMaterialIndexUpdate ) {
183
200
 
184
201
  updateMaterialIndexAttribute( geometry, materials, materials );
202
+ this._materialUuids = materials.map( material => material.uuid );
185
203
 
186
204
  }
187
205
 
@@ -225,6 +243,7 @@ export class PathTracingSceneGenerator {
225
243
  return {
226
244
  bvhChanged: result.changeType !== NO_CHANGE,
227
245
  bvh: this.bvh,
246
+ needsMaterialIndexUpdate,
228
247
  lights,
229
248
  iesTextures,
230
249
  geometry,
@@ -102,6 +102,8 @@ export class WebGLPathTracer {
102
102
 
103
103
  constructor( renderer ) {
104
104
 
105
+ console.warn( 'WebGLPathTracer: This class has been deprecated and will be removed in a future release. Use "WebGPUPathTracer" instead.' );
106
+
105
107
  // members
106
108
  this._renderer = renderer;
107
109
  this._generator = new PathTracingSceneGenerator();
@@ -306,7 +308,7 @@ export class WebGLPathTracer {
306
308
  }
307
309
 
308
310
  // update scene environment
309
- material.environmentIntensity = scene.environmentIntensity ?? 1;
311
+ material.environmentIntensity = scene.environment !== null ? ( scene.environmentIntensity ?? 1 ) : 0;
310
312
  material.environmentRotation.makeRotationFromEuler( scene.environmentRotation ).invert();
311
313
  if ( this._previousEnvironment !== scene.environment ) {
312
314
 
@@ -326,10 +328,6 @@ export class WebGLPathTracer {
326
328
 
327
329
  }
328
330
 
329
- } else {
330
-
331
- material.environmentIntensity = 0;
332
-
333
331
  }
334
332
 
335
333
  }
@@ -347,6 +345,7 @@ export class WebGLPathTracer {
347
345
  geometry,
348
346
  bvh,
349
347
  bvhChanged,
348
+ needsMaterialIndexUpdate,
350
349
  } = results;
351
350
 
352
351
  this._materials = materials;
@@ -364,6 +363,10 @@ export class WebGLPathTracer {
364
363
  geometry.attributes.color,
365
364
  );
366
365
 
366
+ }
367
+
368
+ if ( needsMaterialIndexUpdate ) {
369
+
367
370
  material.materialIndexAttribute.updateFrom( geometry.attributes.materialIndex );
368
371
 
369
372
  }
@@ -494,8 +497,8 @@ export class WebGLPathTracer {
494
497
 
495
498
  dispose() {
496
499
 
497
- this._renderQuad.dispose();
498
- this._renderQuad.material.dispose();
500
+ this._quad.dispose();
501
+ this._quad.material.dispose();
499
502
  this._pathTracer.dispose();
500
503
 
501
504
  }
@@ -523,4 +526,10 @@ export class WebGLPathTracer {
523
526
 
524
527
  }
525
528
 
529
+ getRenderTime() {
530
+
531
+ return this._clock.getElapsedTime() * 1e3;
532
+
533
+ }
534
+
526
535
  }
@@ -205,7 +205,20 @@ export function mergeGeometries( geometries, options = {}, targetGeometry = new
205
205
  const attr = geometry.getAttribute( key );
206
206
  if ( ! skip ) {
207
207
 
208
- copyAttributeContents( attr, targetAttribute, offset );
208
+ if ( key === 'color' && targetAttribute.itemSize !== attr.itemSize ) {
209
+
210
+ // make sure the color attribute is aligned with itemSize 3 to 4
211
+ for ( let index = offset, l = attr.count; index < l; index ++ ) {
212
+
213
+ attr.setXYZW( index, targetAttribute.getX( index ), targetAttribute.getY( index ), targetAttribute.getZ( index ), 1.0 );
214
+
215
+ }
216
+
217
+ } else {
218
+
219
+ copyAttributeContents( attr, targetAttribute, offset );
220
+
221
+ }
209
222
 
210
223
  }
211
224
 
@@ -72,20 +72,16 @@ export function getTextures( materials ) {
72
72
  export function getLights( scene ) {
73
73
 
74
74
  const lights = [];
75
- scene.traverse( c => {
75
+ scene.traverseVisible( c => {
76
76
 
77
- if ( c.visible ) {
77
+ if (
78
+ c.isRectAreaLight ||
79
+ c.isSpotLight ||
80
+ c.isPointLight ||
81
+ c.isDirectionalLight
82
+ ) {
78
83
 
79
- if (
80
- c.isRectAreaLight ||
81
- c.isSpotLight ||
82
- c.isPointLight ||
83
- c.isDirectionalLight
84
- ) {
85
-
86
- lights.push( c );
87
-
88
- }
84
+ lights.push( c );
89
85
 
90
86
  }
91
87
 
@@ -104,15 +104,15 @@ export class PrecisionMaterial extends MaterialBase {
104
104
 
105
105
  switch ( v.toLowerCase() ) {
106
106
 
107
- case 'float':
108
- this.setDefine( 'MODE', 0 );
109
- break;
110
- case 'int':
111
- this.setDefine( 'MODE', 1 );
112
- break;
113
- case 'uint':
114
- this.setDefine( 'MODE', 2 );
115
- break;
107
+ case 'float':
108
+ this.setDefine( 'MODE', 0 );
109
+ break;
110
+ case 'int':
111
+ this.setDefine( 'MODE', 1 );
112
+ break;
113
+ case 'uint':
114
+ this.setDefine( 'MODE', 2 );
115
+ break;
116
116
 
117
117
  }
118
118
 
package/src/index.d.ts CHANGED
@@ -21,7 +21,7 @@ import {
21
21
  Scene,
22
22
  PMREMGenerator
23
23
  } from 'three';
24
- import { FullScreenQuad } from 'three/examples/jsm/postprocessing/Pass';
24
+ import { FullScreenQuad } from 'three/examples/jsm/postprocessing/Pass.js';
25
25
  import { MeshBVH, MeshBVHOptions } from 'three-mesh-bvh';
26
26
 
27
27
  // three.js type augmentation
@@ -57,6 +57,7 @@ export interface PathTracingSceneGeneratorResult {
57
57
  lights: Array<Light>;
58
58
  iesTextures: Array<DataTexture>;
59
59
  geometry: BufferGeometry;
60
+ needsMaterialIndexUpdate: boolean;
60
61
  materials: Array<Material>;
61
62
  textures: Array<Texture>;
62
63
  objects: Array<Object3D>;
package/src/index.js CHANGED
@@ -18,6 +18,7 @@ export * from './utils/BlurredEnvMapGenerator.js';
18
18
  // materials
19
19
  export * from './materials/fullscreen/DenoiseMaterial.js';
20
20
  export * from './materials/surface/FogVolumeMaterial.js';
21
+ export * from './materials/surface/AmbientOcclusionMaterial.js';
21
22
 
22
23
  // deprecated
23
24
  export * from './materials/pathtracing/PhysicalPathTracingMaterial.js';
@@ -10,7 +10,7 @@ import { PhysicalCameraUniform } from '../../uniforms/PhysicalCameraUniform.js';
10
10
  import { EquirectHdrInfoUniform } from '../../uniforms/EquirectHdrInfoUniform.js';
11
11
  import { LightsInfoUniformStruct } from '../../uniforms/LightsInfoUniformStruct.js';
12
12
  import { AttributesTextureArray } from '../../uniforms/AttributesTextureArray.js';
13
- import { MaterialsTexture } from '../../uniforms/MaterialsTexture.js';
13
+ import { MaterialsTexture, MATERIAL_PIXELS } from '../../uniforms/MaterialsTexture.js';
14
14
  import { RenderTarget2DArray } from '../../uniforms/RenderTarget2DArray.js';
15
15
  import { StratifiedSamplesTexture } from '../../uniforms/StratifiedSamplesTexture.js';
16
16
  import { BlueNoiseTexture } from '../../textures/BlueNoiseTexture.js';
@@ -66,6 +66,7 @@ export class PhysicalPathTracingMaterial extends MaterialBase {
66
66
  ATTR_TANGENT: 1,
67
67
  ATTR_UV: 2,
68
68
  ATTR_COLOR: 3,
69
+ MATERIAL_PIXELS: MATERIAL_PIXELS,
69
70
  },
70
71
 
71
72
  uniforms: {
@@ -97,7 +97,8 @@ export const attenuate_hit_function = /* glsl */`
97
97
  // alphaMap
98
98
  if ( material.alphaMap != - 1 ) {
99
99
 
100
- albedo.a *= texture2D( textures, vec3( uv, material.alphaMap ) ).x;
100
+ vec3 uvPrime = material.alphaMapTransform * vec3( uv, 1 );
101
+ albedo.a *= texture2D( textures, vec3( uvPrime.xy, material.alphaMap ) ).x;
101
102
 
102
103
  }
103
104
 
@@ -60,7 +60,7 @@ export const camera_util_functions = /* glsl */`
60
60
  vec3 shapeUVW= rand3( 1 );
61
61
  int blades = physicalCamera.apertureBlades;
62
62
  float anamorphicRatio = physicalCamera.anamorphicRatio;
63
- vec2 apertureSample = blades == 0 ? sampleCircle( shapeUVW.xy ) : sampleRegularPolygon( blades, shapeUVW );
63
+ vec2 apertureSample = sampleAperture( blades, shapeUVW );
64
64
  apertureSample *= physicalCamera.bokehSize * 0.5 * 1e-3;
65
65
 
66
66
  // rotate the aperture shape
@@ -48,7 +48,8 @@ export const get_surface_record_function = /* glsl */`
48
48
  // alphaMap
49
49
  if ( material.alphaMap != - 1 ) {
50
50
 
51
- albedo.a *= texture2D( textures, vec3( uv, material.alphaMap ) ).x;
51
+ vec3 uvPrime = material.alphaMapTransform * vec3( uv, 1 );
52
+ albedo.a *= texture2D( textures, vec3( uvPrime.xy, material.alphaMap ) ).x;
52
53
 
53
54
  }
54
55
 
@@ -1,6 +1,7 @@
1
1
  import { TangentSpaceNormalMap, Vector2 } from 'three';
2
2
  import { MaterialBase } from '../MaterialBase.js';
3
3
  import { MeshBVHUniformStruct, BVHShaderGLSL } from 'three-mesh-bvh';
4
+ import { MATERIAL_PIXELS } from '../../uniforms/MaterialsTexture.js';
4
5
 
5
6
  import * as StructsGLSL from '../../shader/structs/index.js';
6
7
  import * as SamplingGLSL from '../../shader/sampling/index.js';
@@ -43,6 +44,7 @@ export class AmbientOcclusionMaterial extends MaterialBase {
43
44
 
44
45
  defines: {
45
46
  SAMPLES: 10,
47
+ MATERIAL_PIXELS: MATERIAL_PIXELS,
46
48
  },
47
49
 
48
50
  uniforms: {
@@ -1,5 +1,7 @@
1
1
  import { SpotLight } from 'three';
2
2
 
3
+ // TODO: this should extend IESSpotLight, but the class is only exported from "three/webgpu" and
4
+ // the node library resolves light nodes by exact constructor so a subclass would not rasterize
3
5
  export class PhysicalSpotLight extends SpotLight {
4
6
 
5
7
  constructor( ...args ) {
@@ -233,7 +233,6 @@ export const bsdf_functions = /* glsl */`
233
233
  // See equation (1) in http://www.aconty.com/pdf/s2017_pbs_imageworks_sheen.pdf
234
234
  vec3 color = surf.sheenColor;
235
235
  color *= D * G / ( 4.0 * abs( cosThetaO * cosThetaI ) );
236
- color *= wi.z;
237
236
 
238
237
  return color;
239
238
 
@@ -7,7 +7,7 @@ export const inside_fog_volume_function = /* glsl */`
7
7
  // returns whether the given material is a fog material or not
8
8
  bool isMaterialFogVolume( sampler2D materials, uint materialIndex ) {
9
9
 
10
- uint i = materialIndex * 45u;
10
+ uint i = materialIndex * uint( MATERIAL_PIXELS );
11
11
  vec4 s14 = texelFetch1D( materials, i + 14u );
12
12
  return bool( int( s14.b ) & 4 );
13
13
 
@@ -81,6 +81,7 @@ export const material_struct = /* glsl */ `
81
81
  mat3 iridescenceThicknessMapTransform;
82
82
  mat3 specularColorMapTransform;
83
83
  mat3 specularIntensityMapTransform;
84
+ mat3 alphaMapTransform;
84
85
 
85
86
  };
86
87
 
@@ -101,7 +102,7 @@ export const material_struct = /* glsl */ `
101
102
 
102
103
  Material readMaterialInfo( sampler2D tex, uint index ) {
103
104
 
104
- uint i = index * 45u;
105
+ uint i = index * uint( MATERIAL_PIXELS );
105
106
 
106
107
  vec4 s0 = texelFetch1D( tex, i + 0u );
107
108
  vec4 s1 = texelFetch1D( tex, i + 1u );
@@ -200,6 +201,7 @@ export const material_struct = /* glsl */ `
200
201
  m.iridescenceThicknessMapTransform = m.iridescenceThicknessMap == - 1 ? mat3( 1.0 ) : readTextureTransform( tex, firstTextureTransformIdx + 24u );
201
202
  m.specularColorMapTransform = m.specularColorMap == - 1 ? mat3( 1.0 ) : readTextureTransform( tex, firstTextureTransformIdx + 26u );
202
203
  m.specularIntensityMapTransform = m.specularIntensityMap == - 1 ? mat3( 1.0 ) : readTextureTransform( tex, firstTextureTransformIdx + 28u );
204
+ m.alphaMapTransform = m.alphaMap == - 1 ? mat3( 1.0 ) : readTextureTransform( tex, firstTextureTransformIdx + 30u );
203
205
 
204
206
  return m;
205
207
 
@@ -19,12 +19,12 @@ function getFormat( channels ) {
19
19
 
20
20
  switch ( channels ) {
21
21
 
22
- case 1:
23
- return RedFormat;
24
- case 2:
25
- return RGFormat;
26
- default:
27
- return RGBAFormat;
22
+ case 1:
23
+ return RedFormat;
24
+ case 2:
25
+ return RGFormat;
26
+ default:
27
+ return RGBAFormat;
28
28
 
29
29
  }
30
30
 
@@ -2,13 +2,14 @@ import {
2
2
  ClampToEdgeWrapping,
3
3
  Color,
4
4
  DataTexture,
5
+ DataUtils,
5
6
  EquirectangularReflectionMapping,
7
+ HalfFloatType,
6
8
  LinearFilter,
7
9
  RepeatWrapping,
8
10
  RGBAFormat,
9
11
  Spherical,
10
12
  Vector2,
11
- FloatType
12
13
  } from 'three';
13
14
 
14
15
  const _uv = new Vector2();
@@ -20,8 +21,8 @@ export class ProceduralEquirectTexture extends DataTexture {
20
21
  constructor( width = 512, height = 512 ) {
21
22
 
22
23
  super(
23
- new Float32Array( width * height * 4 ),
24
- width, height, RGBAFormat, FloatType, EquirectangularReflectionMapping,
24
+ new Uint16Array( width * height * 4 ),
25
+ width, height, RGBAFormat, HalfFloatType, EquirectangularReflectionMapping,
25
26
  RepeatWrapping, ClampToEdgeWrapping, LinearFilter, LinearFilter,
26
27
  );
27
28
 
@@ -53,10 +54,10 @@ export class ProceduralEquirectTexture extends DataTexture {
53
54
 
54
55
  const i = y * width + x;
55
56
  const i4 = 4 * i;
56
- data[ i4 + 0 ] = ( _color.r );
57
- data[ i4 + 1 ] = ( _color.g );
58
- data[ i4 + 2 ] = ( _color.b );
59
- data[ i4 + 3 ] = ( 1.0 );
57
+ data[ i4 + 0 ] = DataUtils.toHalfFloat( _color.r );
58
+ data[ i4 + 1 ] = DataUtils.toHalfFloat( _color.g );
59
+ data[ i4 + 2 ] = DataUtils.toHalfFloat( _color.b );
60
+ data[ i4 + 3 ] = DataUtils.toHalfFloat( 1.0 );
60
61
 
61
62
  }
62
63
 
Binary file
@@ -178,6 +178,12 @@ export class EquirectHdrInfoUniform {
178
178
 
179
179
  }
180
180
 
181
+ getPixelWeight( r, g, b ) {
182
+
183
+ return colorToLuminance( r, g, b );
184
+
185
+ }
186
+
181
187
  dispose() {
182
188
 
183
189
  this.marginalWeights.dispose();
@@ -218,10 +224,9 @@ export class EquirectHdrInfoUniform {
218
224
  const g = DataUtils.fromHalfFloat( data[ 4 * i + 1 ] );
219
225
  const b = DataUtils.fromHalfFloat( data[ 4 * i + 2 ] );
220
226
 
221
- // the probability of the pixel being selected in this row is the
222
- // scale of the luminance relative to the rest of the pixels.
223
- // TODO: this should also account for the solid angle of the pixel when sampling
224
- const weight = colorToLuminance( r, g, b );
227
+ // the probability of the pixel being selected in its row is proportional
228
+ // to its luminance relative to the other pixels.
229
+ const weight = this.getPixelWeight( r, g, b, y, height );
225
230
  cumulativeRowWeight += weight;
226
231
  totalSumValue += weight;
227
232
 
@@ -15,17 +15,17 @@ function copyArrayToArray( fromArray, fromStride, toArray, toStride, offset ) {
15
15
  let maxValue = 1.0;
16
16
  switch ( fromArray.constructor ) {
17
17
 
18
- case Uint8Array:
19
- case Uint16Array:
20
- case Uint32Array:
21
- maxValue = 2 ** bpe - 1;
22
- break;
23
-
24
- case Int8Array:
25
- case Int16Array:
26
- case Int32Array:
27
- maxValue = 2 ** ( bpe - 1 ) - 1;
28
- break;
18
+ case Uint8Array:
19
+ case Uint16Array:
20
+ case Uint32Array:
21
+ maxValue = 2 ** bpe - 1;
22
+ break;
23
+
24
+ case Int8Array:
25
+ case Int16Array:
26
+ case Int32Array:
27
+ maxValue = 2 ** ( bpe - 1 ) - 1;
28
+ break;
29
29
 
30
30
  }
31
31
 
@@ -2,7 +2,7 @@ import { DataTexture, RGBAFormat, ClampToEdgeWrapping, FloatType, FrontSide, Bac
2
2
  import { getTextureHash } from '../core/utils/sceneUpdateUtils.js';
3
3
  import { bufferToHash } from '../utils/bufferToHash.js';
4
4
 
5
- const MATERIAL_PIXELS = 45;
5
+ export const MATERIAL_PIXELS = 47;
6
6
  const MATERIAL_STRIDE = MATERIAL_PIXELS * 4;
7
7
 
8
8
  class MaterialFeatures {
@@ -362,15 +362,15 @@ export class MaterialsTexture extends DataTexture {
362
362
 
363
363
  switch ( m.side ) {
364
364
 
365
- case FrontSide:
366
- floatArray[ index ++ ] = 1;
367
- break;
368
- case BackSide:
369
- floatArray[ index ++ ] = - 1;
370
- break;
371
- case DoubleSide:
372
- floatArray[ index ++ ] = 0;
373
- break;
365
+ case FrontSide:
366
+ floatArray[ index ++ ] = 1;
367
+ break;
368
+ case BackSide:
369
+ floatArray[ index ++ ] = - 1;
370
+ break;
371
+ case DoubleSide:
372
+ floatArray[ index ++ ] = 0;
373
+ break;
374
374
 
375
375
  }
376
376
 
@@ -427,6 +427,9 @@ export class MaterialsTexture extends DataTexture {
427
427
  // specularIntensityMap transform 43
428
428
  index += writeTextureMatrixToArray( m, 'specularIntensityMap', floatArray, index );
429
429
 
430
+ // alphaMap transform 45
431
+ index += writeTextureMatrixToArray( m, 'alphaMap', floatArray, index );
432
+
430
433
  }
431
434
 
432
435
  // check if the contents have changed