three-gpu-pathtracer 0.0.12 → 0.0.14

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 (58) hide show
  1. package/README.md +102 -7
  2. package/build/index.module.js +2891 -2065
  3. package/build/index.module.js.map +1 -1
  4. package/build/index.umd.cjs +2886 -2062
  5. package/build/index.umd.cjs.map +1 -1
  6. package/package.json +2 -1
  7. package/src/core/PathTracingRenderer.js +87 -16
  8. package/src/core/PathTracingSceneGenerator.js +1 -1
  9. package/src/core/QuiltPathTracingRenderer.js +223 -0
  10. package/src/index.js +5 -8
  11. package/src/materials/{GraphMaterial.js → debug/GraphMaterial.js} +1 -1
  12. package/src/materials/{AlphaDisplayMaterial.js → fullscreen/AlphaDisplayMaterial.js} +1 -1
  13. package/src/materials/{BlendMaterial.js → fullscreen/BlendMaterial.js} +1 -1
  14. package/src/materials/{DenoiseMaterial.js → fullscreen/DenoiseMaterial.js} +1 -1
  15. package/src/materials/{LambertPathTracingMaterial.js → pathtracing/LambertPathTracingMaterial.js} +18 -7
  16. package/src/materials/pathtracing/PhysicalPathTracingMaterial.js +635 -0
  17. package/src/materials/pathtracing/glsl/attenuateHit.glsl.js +179 -0
  18. package/src/materials/pathtracing/glsl/cameraUtils.glsl.js +81 -0
  19. package/src/materials/pathtracing/glsl/getSurfaceRecord.glsl.js +317 -0
  20. package/src/materials/pathtracing/glsl/traceScene.glsl.js +54 -0
  21. package/src/materials/{AmbientOcclusionMaterial.js → surface/AmbientOcclusionMaterial.js} +16 -8
  22. package/src/materials/surface/FogVolumeMaterial.js +23 -0
  23. package/src/shader/bsdf/bsdfSampling.glsl.js +490 -0
  24. package/src/shader/bsdf/fog.glsl.js +23 -0
  25. package/src/shader/bsdf/ggx.glsl.js +102 -0
  26. package/src/shader/bsdf/iridescence.glsl.js +135 -0
  27. package/src/shader/bsdf/sheen.glsl.js +98 -0
  28. package/src/shader/{shaderLayerTexelFetchFunctions.js → common/arraySamplerTexelFetch.glsl.js} +1 -1
  29. package/src/shader/common/bvhAnyHit.glsl.js +76 -0
  30. package/src/shader/common/fresnel.glsl.js +98 -0
  31. package/src/shader/common/intersectShapes.glsl.js +62 -0
  32. package/src/shader/common/math.glsl.js +81 -0
  33. package/src/shader/common/utils.glsl.js +116 -0
  34. package/src/shader/{shaderRandFunctions.js → rand/pcg.glsl.js} +1 -1
  35. package/src/shader/{shaderSobolSampling.js → rand/sobol.glsl.js} +3 -3
  36. package/src/shader/sampling/equirectSampling.glsl.js +62 -0
  37. package/src/shader/sampling/lightSampling.glsl.js +223 -0
  38. package/src/shader/sampling/shapeSampling.glsl.js +86 -0
  39. package/src/shader/structs/cameraStruct.glsl.js +13 -0
  40. package/src/shader/structs/equirectStruct.glsl.js +14 -0
  41. package/src/shader/structs/fogMaterialBvh.glsl.js +62 -0
  42. package/src/shader/structs/lightsStruct.glsl.js +78 -0
  43. package/src/shader/{shaderStructs.js → structs/materialStruct.glsl.js} +5 -123
  44. package/src/uniforms/EquirectHdrInfoUniform.js +29 -11
  45. package/src/uniforms/LightsInfoUniformStruct.js +9 -4
  46. package/src/uniforms/MaterialsTexture.js +80 -3
  47. package/src/utils/BlurredEnvMapGenerator.js +2 -2
  48. package/src/utils/SobolNumberMapGenerator.js +3 -3
  49. package/src/utils/macroify.js +9 -0
  50. package/src/materials/PhysicalPathTracingMaterial.js +0 -982
  51. package/src/shader/shaderBvhAnyHit.js +0 -76
  52. package/src/shader/shaderEnvMapSampling.js +0 -58
  53. package/src/shader/shaderGGXFunctions.js +0 -100
  54. package/src/shader/shaderIridescenceFunctions.js +0 -130
  55. package/src/shader/shaderLightSampling.js +0 -229
  56. package/src/shader/shaderMaterialSampling.js +0 -506
  57. package/src/shader/shaderSheenFunctions.js +0 -98
  58. package/src/shader/shaderUtils.js +0 -361
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "three-gpu-pathtracer",
3
- "version": "0.0.12",
3
+ "version": "0.0.14",
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",
@@ -32,6 +32,7 @@
32
32
  "three-mesh-bvh": "^0.5.19"
33
33
  },
34
34
  "devDependencies": {
35
+ "@lookingglass/webxr": "^0.3.1",
35
36
  "canvas-capture": "^2.0.5",
36
37
  "eslint": "^7.32.0",
37
38
  "eslint-config-mdcs": "^5.0.0",
@@ -1,8 +1,11 @@
1
- import { RGBAFormat, FloatType, Color, Vector2, WebGLRenderTarget, NoBlending, NormalBlending } from 'three';
1
+ import { RGBAFormat, FloatType, Color, Vector2, WebGLRenderTarget, NoBlending, NormalBlending, Vector4 } from 'three';
2
2
  import { FullScreenQuad } from 'three/examples/jsm/postprocessing/Pass.js';
3
- import { BlendMaterial } from '../materials/BlendMaterial.js';
3
+ import { BlendMaterial } from '../materials/fullscreen/BlendMaterial.js';
4
4
  import { SobolNumberMapGenerator } from '../utils/SobolNumberMapGenerator.js';
5
5
 
6
+ const _scissor = new Vector4();
7
+ const _viewport = new Vector4();
8
+
6
9
  function* renderTask() {
7
10
 
8
11
  const {
@@ -12,10 +15,13 @@ function* renderTask() {
12
15
  _primaryTarget,
13
16
  _blendTargets,
14
17
  _sobolTarget,
18
+ _subframe,
15
19
  alpha,
16
20
  camera,
17
21
  material,
18
22
  } = this;
23
+ const _ogScissor = new Vector4();
24
+ const _ogViewport = new Vector4();
19
25
 
20
26
  const blendMaterial = _blendQuad.material;
21
27
  let [ blendTarget1, blendTarget2 ] = _blendTargets;
@@ -24,20 +30,22 @@ function* renderTask() {
24
30
 
25
31
  if ( alpha ) {
26
32
 
27
- blendMaterial.opacity = 1 / ( this.samples + 1 );
33
+ blendMaterial.opacity = this._opacityFactor / ( this._samples + 1 );
28
34
  material.blending = NoBlending;
29
35
  material.opacity = 1;
30
36
 
31
37
  } else {
32
38
 
33
- material.opacity = 1 / ( this.samples + 1 );
39
+ material.opacity = this._opacityFactor / ( this._samples + 1 );
34
40
  material.blending = NormalBlending;
35
41
 
36
42
  }
37
43
 
44
+ const [ subX, subY, subW, subH ] = _subframe;
45
+
38
46
  const w = _primaryTarget.width;
39
47
  const h = _primaryTarget.height;
40
- material.resolution.set( w, h );
48
+ material.resolution.set( w * subW, h * subH );
41
49
  material.sobolTexture = _sobolTarget.texture;
42
50
  material.seed ++;
43
51
 
@@ -45,6 +53,7 @@ function* renderTask() {
45
53
  const tilesY = this.tiles.y || 1;
46
54
  const totalTiles = tilesX * tilesY;
47
55
  const dprInv = ( 1 / _renderer.getPixelRatio() );
56
+
48
57
  for ( let y = 0; y < tilesY; y ++ ) {
49
58
 
50
59
  for ( let x = 0; x < tilesX; x ++ ) {
@@ -73,8 +82,12 @@ function* renderTask() {
73
82
 
74
83
  material.setDefine( 'CAMERA_TYPE', cameraType );
75
84
 
85
+ // store og state
76
86
  const ogRenderTarget = _renderer.getRenderTarget();
77
87
  const ogAutoClear = _renderer.autoClear;
88
+ const ogScissorTest = _renderer.getScissorTest();
89
+ _renderer.getScissor( _ogScissor );
90
+ _renderer.getViewport( _ogViewport );
78
91
 
79
92
  let tx = x;
80
93
  let ty = y;
@@ -91,18 +104,48 @@ function* renderTask() {
91
104
  // three.js renderer takes values relative to the current pixel ratio
92
105
  _renderer.setRenderTarget( _primaryTarget );
93
106
  _renderer.setScissorTest( true );
94
- _renderer.setScissor(
95
- dprInv * Math.ceil( tx * w / tilesX ),
96
- dprInv * Math.ceil( ( tilesY - ty - 1 ) * h / tilesY ),
97
- dprInv * Math.ceil( w / tilesX ),
98
- dprInv * Math.ceil( h / tilesY ) );
107
+
108
+ // set the scissor window for a subtile
109
+ _scissor.x = tx * w / tilesX;
110
+ _scissor.y = ( tilesY - ty - 1 ) * h / tilesY;
111
+ _scissor.z = w / tilesX;
112
+ _scissor.w = h / tilesY;
113
+
114
+ // adjust for the subframe
115
+ _scissor.x = subX * w + subW * _scissor.x;
116
+ _scissor.y = subY * h + subH * _scissor.y;
117
+ _scissor.z = subW * _scissor.z;
118
+ _scissor.w = subH * _scissor.w;
119
+
120
+ // round for floating point cases
121
+ _scissor.x = _scissor.x;
122
+ _scissor.y = _scissor.y;
123
+ _scissor.z = _scissor.z;
124
+ _scissor.w = _scissor.w;
125
+
126
+ // multiply inverse of DPR in because threes multiplies it in
127
+ _scissor.multiplyScalar( dprInv ).ceil();
128
+
129
+ _viewport.x = subX * w;
130
+ _viewport.y = subY * h;
131
+ _viewport.z = subW * w;
132
+ _viewport.w = subH * h;
133
+ _viewport.multiplyScalar( dprInv ).ceil();
134
+
135
+ _renderer.setScissor( _scissor );
136
+ _renderer.setViewport( _viewport );
137
+
99
138
  _renderer.autoClear = false;
100
139
  _fsQuad.render( _renderer );
101
140
 
102
- _renderer.setScissorTest( false );
141
+ // reset original renderer state
142
+ _renderer.setViewport( _ogViewport );
143
+ _renderer.setScissor( _ogScissor );
144
+ _renderer.setScissorTest( ogScissorTest );
103
145
  _renderer.setRenderTarget( ogRenderTarget );
104
146
  _renderer.autoClear = ogAutoClear;
105
147
 
148
+ // swap and blend alpha targets
106
149
  if ( alpha ) {
107
150
 
108
151
  blendMaterial.target1 = blendTarget1.texture;
@@ -114,7 +157,14 @@ function* renderTask() {
114
157
 
115
158
  }
116
159
 
117
- this.samples += ( 1 / totalTiles );
160
+ this._samples += ( 1 / totalTiles );
161
+
162
+ // round the samples value if we've finished the tiles
163
+ if ( x === tilesX - 1 && y === tilesY - 1 ) {
164
+
165
+ this._samples = Math.round( this._samples );
166
+
167
+ }
118
168
 
119
169
  yield;
120
170
 
@@ -124,8 +174,6 @@ function* renderTask() {
124
174
 
125
175
  [ blendTarget1, blendTarget2 ] = [ blendTarget2, blendTarget1 ];
126
176
 
127
- this.samples = Math.round( this.samples );
128
-
129
177
  }
130
178
 
131
179
  }
@@ -153,6 +201,12 @@ export class PathTracingRenderer {
153
201
 
154
202
  set alpha( v ) {
155
203
 
204
+ if ( this._alpha === v ) {
205
+
206
+ return;
207
+
208
+ }
209
+
156
210
  if ( ! v ) {
157
211
 
158
212
  this._blendTargets[ 0 ].dispose();
@@ -171,15 +225,23 @@ export class PathTracingRenderer {
171
225
 
172
226
  }
173
227
 
228
+ get samples() {
229
+
230
+ return this._samples;
231
+
232
+ }
233
+
174
234
  constructor( renderer ) {
175
235
 
176
236
  this.camera = null;
177
237
  this.tiles = new Vector2( 1, 1 );
178
238
 
179
- this.samples = 0;
180
239
  this.stableNoise = false;
181
240
  this.stableTiles = true;
182
241
 
242
+ this._samples = 0;
243
+ this._subframe = new Vector4( 0, 0, 1, 1 );
244
+ this._opacityFactor = 1.0;
183
245
  this._renderer = renderer;
184
246
  this._alpha = false;
185
247
  this._fsQuad = new FullScreenQuad( null );
@@ -207,6 +269,15 @@ export class PathTracingRenderer {
207
269
 
208
270
  setSize( w, h ) {
209
271
 
272
+ w = Math.ceil( w );
273
+ h = Math.ceil( h );
274
+
275
+ if ( this._primaryTarget.width === w && this._primaryTarget.height === h ) {
276
+
277
+ return;
278
+
279
+ }
280
+
210
281
  this._primaryTarget.setSize( w, h );
211
282
  this._blendTargets[ 0 ].setSize( w, h );
212
283
  this._blendTargets[ 1 ].setSize( w, h );
@@ -249,7 +320,7 @@ export class PathTracingRenderer {
249
320
  _renderer.setClearColor( ogClearColor, ogClearAlpha );
250
321
  _renderer.setRenderTarget( ogRenderTarget );
251
322
 
252
- this.samples = 0;
323
+ this._samples = 0;
253
324
  this._task = null;
254
325
 
255
326
  if ( this.stableNoise ) {
@@ -33,7 +33,7 @@ export class PathTracingSceneGenerator {
33
33
 
34
34
  meshes.push( c );
35
35
 
36
- } else if ( c.isRectAreaLight || c.isSpotLight ) {
36
+ } else if ( c.isRectAreaLight || c.isSpotLight || c.isDirectionalLight || c.isPointLight ) {
37
37
 
38
38
  lights.push( c );
39
39
 
@@ -0,0 +1,223 @@
1
+ import { PerspectiveCamera, Vector3, MathUtils, Vector2, Matrix4, Vector4 } from 'three';
2
+ import { PathTracingRenderer } from './PathTracingRenderer.js';
3
+
4
+ function* _task( cb ) {
5
+
6
+ const {
7
+ viewCount,
8
+ _camera,
9
+ _quiltUtility,
10
+ _subframe,
11
+ } = this;
12
+
13
+ const quiltViewInfo = {
14
+ subframe: _subframe,
15
+ projectionMatrix: _camera.projectionMatrix,
16
+ offsetDirection: new Vector3(),
17
+ };
18
+
19
+ while ( true ) {
20
+
21
+ for ( let i = 0; i < viewCount; i ++ ) {
22
+
23
+ // get the camera info for the current view index
24
+ _quiltUtility.near = this.camera.near;
25
+ _quiltUtility.far = this.camera.far;
26
+ _quiltUtility.getCameraViewInfo( i, quiltViewInfo );
27
+
28
+ // transform offset into world frame from camera frame
29
+ quiltViewInfo.offsetDirection.transformDirection( this.camera.matrixWorld );
30
+
31
+ // adjust the render camera with the view offset
32
+ this.camera.matrixWorld.decompose(
33
+ _camera.position,
34
+ _camera.quaternion,
35
+ _camera.scale,
36
+ );
37
+ _camera.position.addScaledVector( quiltViewInfo.offsetDirection, quiltViewInfo.offset );
38
+ _camera.updateMatrixWorld();
39
+
40
+ // get the inverse projection
41
+ _camera.projectionMatrixInverse
42
+ .copy( _camera.projectionMatrix )
43
+ .invert();
44
+
45
+ this._opacityFactor = Math.floor( this._samples + 1 ) / Math.floor( this._quiltSamples + 1 );
46
+
47
+ do {
48
+
49
+ const ogCamera = this.camera;
50
+ this.camera = _camera;
51
+ cb();
52
+ this.camera = ogCamera;
53
+ yield;
54
+
55
+ } while ( this._samples % 1 !== 0 );
56
+
57
+ this._quiltSamples += 1 / viewCount;
58
+
59
+ }
60
+
61
+ this._quiltSamples = Math.round( this._quiltSamples );
62
+
63
+ }
64
+
65
+ }
66
+
67
+ // Helper for extracting the camera projection, offset, and quilt subframe needed
68
+ // for rendering a quilt with the provided parameters.
69
+ class QuiltViewUtility {
70
+
71
+ constructor() {
72
+
73
+ this.viewCount = 48;
74
+ this.quiltDimensions = new Vector2( 8, 6 );
75
+ this.viewCone = 35 * MathUtils.DEG2RAD;
76
+ this.viewFoV = 14 * MathUtils.DEG2RAD;
77
+ this.displayDistance = 1;
78
+ this.displayAspect = 0.75;
79
+ this.near = 0.01;
80
+ this.far = 10;
81
+
82
+ }
83
+
84
+ getCameraViewInfo( i, target = {} ) {
85
+
86
+ const {
87
+ quiltDimensions,
88
+ viewCone,
89
+ displayDistance,
90
+ viewCount,
91
+ viewFoV,
92
+ displayAspect,
93
+ near,
94
+ far,
95
+ } = this;
96
+
97
+ // initialize defaults
98
+ target.subframe = target.subframe || new Vector4();
99
+ target.offsetDirection = target.offsetDirection || new Vector3();
100
+ target.projectionMatrix = target.projectionMatrix || new Matrix4();
101
+
102
+ // set camera offset
103
+ const halfWidth = Math.tan( 0.5 * viewCone ) * displayDistance;
104
+ const totalWidth = halfWidth * 2.0;
105
+ const stride = totalWidth / ( viewCount - 1 );
106
+ const offset = viewCount === 1 ? 0 : - halfWidth + stride * i;
107
+ target.offsetDirection.set( 1.0, 0, 0 );
108
+ target.offset = offset;
109
+
110
+ // set the projection matrix
111
+ const displayHalfHeight = Math.tan( viewFoV * 0.5 ) * displayDistance;
112
+ const displayHalfWidth = displayAspect * displayHalfHeight;
113
+ const nearScale = near / displayDistance;
114
+
115
+ target.projectionMatrix.makePerspective(
116
+ nearScale * ( - displayHalfWidth - offset ), nearScale * ( displayHalfWidth - offset ),
117
+ nearScale * displayHalfHeight, nearScale * - displayHalfHeight,
118
+ near, far,
119
+ );
120
+
121
+ // set the quilt subframe
122
+ const x = i % quiltDimensions.x;
123
+ const y = Math.floor( i / quiltDimensions.x );
124
+
125
+ const qw = 1 / quiltDimensions.x;
126
+ const qh = 1 / quiltDimensions.y;
127
+ target.subframe.set( x * qw, y * qh, qw, qh );
128
+
129
+ return target;
130
+
131
+ }
132
+
133
+ setFromDisplayView( viewerDistance, displayWidth, displayHeight ) {
134
+
135
+ this.displayAspect = displayWidth / displayHeight;
136
+ this.displayDistance = viewerDistance;
137
+ this.viewFoV = 2.0 * Math.atan( 0.5 * displayHeight / viewerDistance );
138
+
139
+ }
140
+
141
+ }
142
+
143
+ export class QuiltPathTracingRenderer extends PathTracingRenderer {
144
+
145
+ get samples() {
146
+
147
+ return this._samples / this.viewCount;
148
+
149
+ }
150
+
151
+ constructor( ...args ) {
152
+
153
+ super( ...args );
154
+
155
+ [
156
+ 'quiltDimensions',
157
+ 'viewCount',
158
+ 'viewCone',
159
+ 'viewFoV',
160
+ 'displayDistance',
161
+ 'displayAspect',
162
+ ].forEach( member => {
163
+
164
+ Object.defineProperty( this, member, {
165
+
166
+ enumerable: true,
167
+
168
+ set: v => {
169
+
170
+ this._quiltUtility[ member ] = v;
171
+
172
+ },
173
+
174
+ get: () => {
175
+
176
+ return this._quiltUtility[ member ];
177
+
178
+ }
179
+
180
+ } );
181
+
182
+ } );
183
+
184
+
185
+ this._quiltUtility = new QuiltViewUtility();
186
+ this._quiltSamples = 0;
187
+ this._camera = new PerspectiveCamera();
188
+ this._quiltTask = null;
189
+
190
+ }
191
+
192
+ setFromDisplayView( ...args ) {
193
+
194
+ this._quiltUtility.setFromDisplayView( ...args );
195
+
196
+ }
197
+
198
+ update() {
199
+
200
+ this.alpha = false;
201
+ if ( ! this._quiltTask ) {
202
+
203
+ this._quiltTask = _task.call( this, () => {
204
+
205
+ super.update();
206
+
207
+ } );
208
+
209
+ }
210
+
211
+ this._quiltTask.next();
212
+
213
+ }
214
+
215
+ reset() {
216
+
217
+ super.reset();
218
+ this._quiltTask = null;
219
+ this._quiltSamples = 0;
220
+
221
+ }
222
+
223
+ }
package/src/index.js CHANGED
@@ -1,5 +1,6 @@
1
1
  // core
2
2
  export * from './core/PathTracingRenderer.js';
3
+ export * from './core/QuiltPathTracingRenderer.js';
3
4
  export * from './core/PathTracingSceneGenerator.js';
4
5
  export * from './core/DynamicPathTracingSceneGenerator.js';
5
6
  export * from './core/MaterialReducer.js';
@@ -28,12 +29,8 @@ export * from './utils/BlurredEnvMapGenerator.js';
28
29
  export * from './utils/IESLoader.js';
29
30
 
30
31
  // materials
31
- export * from './materials/DenoiseMaterial.js';
32
- export * from './materials/GraphMaterial.js';
32
+ export * from './materials/fullscreen/DenoiseMaterial.js';
33
+ export * from './materials/debug/GraphMaterial.js';
33
34
  export * from './materials/MaterialBase.js';
34
- export * from './materials/PhysicalPathTracingMaterial.js';
35
-
36
- // shaders
37
- export * from './shader/shaderMaterialSampling.js';
38
- export * from './shader/shaderUtils.js';
39
- export * from './shader/shaderStructs.js';
35
+ export * from './materials/pathtracing/PhysicalPathTracingMaterial.js';
36
+ export * from './materials/surface/FogVolumeMaterial.js';
@@ -1,5 +1,5 @@
1
1
  import { NoBlending, Color, Vector2, Vector4 } from 'three';
2
- import { MaterialBase } from './MaterialBase.js';
2
+ import { MaterialBase } from '../MaterialBase.js';
3
3
 
4
4
  export class GraphMaterial extends MaterialBase {
5
5
 
@@ -1,5 +1,5 @@
1
1
  import { NoBlending } from 'three';
2
- import { MaterialBase } from './MaterialBase.js';
2
+ import { MaterialBase } from '../MaterialBase.js';
3
3
 
4
4
  export class AlphaDisplayMaterial extends MaterialBase {
5
5
 
@@ -1,5 +1,5 @@
1
1
  import { NoBlending } from 'three';
2
- import { MaterialBase } from './MaterialBase.js';
2
+ import { MaterialBase } from '../MaterialBase.js';
3
3
 
4
4
  export class BlendMaterial extends MaterialBase {
5
5
 
@@ -1,5 +1,5 @@
1
1
  import { NoBlending } from 'three';
2
- import { MaterialBase } from './MaterialBase.js';
2
+ import { MaterialBase } from '../MaterialBase.js';
3
3
 
4
4
  export class DenoiseMaterial extends MaterialBase {
5
5
 
@@ -1,13 +1,17 @@
1
1
  import { Matrix4, Color } from 'three';
2
- import { MaterialBase } from './MaterialBase.js';
2
+ import { MaterialBase } from '../MaterialBase.js';
3
3
  import {
4
4
  MeshBVHUniformStruct, FloatVertexAttributeTexture, UIntVertexAttributeTexture,
5
5
  shaderStructs, shaderIntersectFunction,
6
6
  } from 'three-mesh-bvh';
7
- import { shaderMaterialStructs } from '../shader/shaderStructs.js';
8
- import { shaderUtils } from '../shader/shaderUtils.js';
7
+
8
+ // uniforms
9
9
  import { MaterialStructArrayUniform } from '../uniforms/MaterialStructArrayUniform.js';
10
- import { RenderTarget2DArray } from '../uniforms/RenderTarget2DArray.js';
10
+ import { RenderTarget2DArray } from '../../uniforms/RenderTarget2DArray.js';
11
+
12
+ import { materialStructGLSL } from '../../shader/structs/materialStruct.glsl.js';
13
+ import { shapeSamplingGLSL } from '../../shader/sampling/shapeSampling.glsl.js';
14
+ import { pcgGLSL } from '../../shader/rand/pcg.glsl.js';
11
15
 
12
16
  export class LambertPathTracingMaterial extends MaterialBase {
13
17
 
@@ -83,8 +87,15 @@ export class LambertPathTracingMaterial extends MaterialBase {
83
87
 
84
88
  ${ shaderStructs }
85
89
  ${ shaderIntersectFunction }
86
- ${ shaderMaterialStructs }
87
- ${ shaderUtils }
90
+
91
+ // uniform structs
92
+ ${ materialStructGLSL }
93
+
94
+ // rand
95
+ ${ pcgGLSL }
96
+
97
+ // common
98
+ ${ shapeSamplingGLSL }
88
99
 
89
100
  #ifdef USE_ENVMAP
90
101
 
@@ -258,7 +269,7 @@ export class LambertPathTracingMaterial extends MaterialBase {
258
269
  vec3 absPoint = abs( point );
259
270
  float maxPoint = max( absPoint.x, max( absPoint.y, absPoint.z ) );
260
271
  rayOrigin = point + faceNormal * ( maxPoint + 1.0 ) * RAY_OFFSET;
261
- rayDirection = getHemisphereSample( normal, rand2() );
272
+ rayDirection = sampleHemisphere( normal, rand2() );
262
273
 
263
274
  // if the surface normal is skewed such that the outgoing vector can wind up underneath
264
275
  // the triangle surface then just consider it absorbed.