@meimu/mutracer 0.1.4 → 0.1.5

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 (67) hide show
  1. package/dist/assets/bvh.worker.js +1 -1
  2. package/dist/mutracer.umd.js +1425 -1421
  3. package/docs/api.md +2 -1
  4. package/docs/materials.md +17 -26
  5. package/docs/threejs.md +5 -5
  6. package/docs/viewer.md +36 -3
  7. package/lib/oidn.d.ts +1 -1
  8. package/lib/oidnBundledWeights.cdn.d.ts +2 -2
  9. package/lib/renderer/WGPUFullQuadPass.js +3 -3
  10. package/lib/renderer/WGPUJNLMDenoiser.js +35 -35
  11. package/lib/renderer/WGPURayTraceOutput.js +4 -4
  12. package/lib/renderer/WGPURayTracePass.js +5 -3
  13. package/lib/renderer/WGPURayTracePass.js.map +1 -1
  14. package/lib/renderer/WGPURenderingPipeline.js +7 -7
  15. package/lib/renderer/WebGLJNLMDenoiser.js +36 -36
  16. package/lib/renderer/WebGLRayTracePass.js +1 -0
  17. package/lib/renderer/WebGLRayTracePass.js.map +1 -1
  18. package/lib/renderer/glsl/chunks/cameraRay.glsl.js +8 -8
  19. package/lib/renderer/glsl/chunks/envMap.glsl.js +26 -26
  20. package/lib/renderer/glsl/chunks/intersect.glsl.js +141 -139
  21. package/lib/renderer/glsl/chunks/intersect.glsl.js.map +1 -1
  22. package/lib/renderer/glsl/chunks/materialBuffer.glsl.js +56 -55
  23. package/lib/renderer/glsl/chunks/materialBuffer.glsl.js.map +1 -1
  24. package/lib/renderer/glsl/chunks/openPbrBsdf.glsl.js +144 -144
  25. package/lib/renderer/glsl/chunks/openPbrBsdf.glsl.js.map +1 -1
  26. package/lib/renderer/glsl/chunks/random.glsl.js +1 -1
  27. package/lib/renderer/glsl/chunks/rayTraceCore.glsl.js +14 -14
  28. package/lib/renderer/glsl/chunks/rayTraceCore.glsl.js.map +1 -1
  29. package/lib/renderer/glsl/chunks/sampleLight.glsl.js +19 -19
  30. package/lib/renderer/glsl/chunks/sampleMaterial.glsl.js +46 -46
  31. package/lib/renderer/glsl/chunks/sampleMaterial.glsl.js.map +1 -1
  32. package/lib/renderer/glsl/chunks/sampleShadowCatcher.glsl.js +6 -6
  33. package/lib/renderer/glsl/chunks/sampling.glsl.js +33 -33
  34. package/lib/renderer/glsl/chunks/sobol.glsl.js +7 -7
  35. package/lib/renderer/glsl/chunks/uvProjection.glsl.js +1 -1
  36. package/lib/renderer/glsl/depthQuery.frag.js +2 -2
  37. package/lib/renderer/glsl/rayTrace.frag.js +67 -67
  38. package/lib/renderer/glsl/shadowCatcher.frag.js +3 -3
  39. package/lib/renderer/glsl/webglPipeline.frag.js +26 -26
  40. package/lib/renderer/scratchSampling.js +16 -16
  41. package/lib/renderer/wgsl/chunks/envMap.wgsl.js +14 -14
  42. package/lib/renderer/wgsl/chunks/intersect.wgsl.js +178 -178
  43. package/lib/renderer/wgsl/chunks/intersect.wgsl.js.map +1 -1
  44. package/lib/renderer/wgsl/chunks/intersectionAlpha.wgsl.js +3 -3
  45. package/lib/renderer/wgsl/chunks/materialBuffer.wgsl.js +24 -23
  46. package/lib/renderer/wgsl/chunks/materialBuffer.wgsl.js.map +1 -1
  47. package/lib/renderer/wgsl/chunks/openPbrBsdf.wgsl.js +160 -160
  48. package/lib/renderer/wgsl/chunks/pdm_displacement.wgsl.js +12 -12
  49. package/lib/renderer/wgsl/chunks/rayTraceCore.wgsl.js +5 -5
  50. package/lib/renderer/wgsl/chunks/sampleLight.wgsl.js +44 -44
  51. package/lib/renderer/wgsl/chunks/sampleMaterial.wgsl.js +69 -69
  52. package/lib/renderer/wgsl/chunks/sampleShadowCatcher.wgsl.js +3 -3
  53. package/lib/renderer/wgsl/chunks/sampling.wgsl.js +33 -33
  54. package/lib/renderer/wgsl/chunks/sobol.wgsl.js +7 -7
  55. package/lib/renderer/wgsl/chunks/uvProjection.wgsl.js +1 -1
  56. package/lib/renderer/wgsl/compose.frag.wgsl.js +54 -54
  57. package/lib/renderer/wgsl/customDenoise.wgsl.js +6 -6
  58. package/lib/renderer/wgsl/depthQuery.wgsl.js +2 -2
  59. package/lib/renderer/wgsl/offlineAdaptive.compute.js +5 -5
  60. package/lib/renderer/wgsl/rayTrace.compute.js +103 -103
  61. package/lib/scene/OpenPBRMaterial.d.ts +1 -1
  62. package/lib/scene/OpenPBRMaterial.js +1 -1
  63. package/lib/scene/OpenPBRMaterial.js.map +1 -1
  64. package/lib/version.d.ts +1 -1
  65. package/lib/version.js +1 -1
  66. package/lib/version.js.map +1 -1
  67. package/package.json +1 -1
@@ -79,7 +79,7 @@ max(iJ + scatteringPdf, 1e-20);
79
79
  }
80
80
 
81
81
 
82
- fn fW(scatteringPdf: f32, fg: f32) -> f32 {
82
+ fn fX(scatteringPdf: f32, fg: f32) -> f32 {
83
83
  let aV = jX();
84
84
  if (aV <= 1u) {
85
85
  return aG(scatteringPdf, fg);
@@ -102,23 +102,23 @@ ${shadowCatcherAccumulationWGSL}
102
102
 
103
103
 
104
104
  fn hK(
105
- he: u32,
105
+ hg: u32,
106
106
  vy: vec3f,
107
107
  normal: vec3f
108
108
  ) {
109
109
  if (rtUniform.varianceMoments != 0) {
110
110
  let value = dot(vy, luminance);
111
- outNormal[he] += vec4f(value * value, 0.0, 0.0, 1.0);
111
+ outNormal[hg] += vec4f(value * value, 0.0, 0.0, 1.0);
112
112
  }
113
113
  else {
114
- outNormal[he] += vec4f(normal, 1.0);
114
+ outNormal[hg] += vec4f(normal, 1.0);
115
115
  }
116
116
  }
117
117
 
118
118
 
119
119
 
120
- fn iS(he: u32, value: f32) {
121
- outShadowCatcher[he].moments += vec4f(value, value * value, 0.0, 0.0);
120
+ fn iS(hg: u32, value: f32) {
121
+ outShadowCatcher[hg].moments += vec4f(value, value * value, 0.0, 0.0);
122
122
  }
123
123
 
124
124
 
@@ -131,26 +131,26 @@ isBlank: bool,
131
131
  }
132
132
 
133
133
  fn dq(sN: vec3f, height: f32, radius: f32) -> f32 {
134
- let fQ = length(sN);
135
- if (fQ < 0.00001) {
134
+ let fR = length(sN);
135
+ if (fR < 0.00001) {
136
136
  return -radius;
137
137
  }
138
138
 
139
- let iG = radius * sN.y / fQ;
139
+ let iG = radius * sN.y / fR;
140
140
  let iq = -1.5 * height;
141
141
  var ev: f32;
142
142
  if (iG >= 0.0) {
143
143
  ev = radius;
144
144
  }
145
145
  else if (iG < iq) {
146
- ev = -height * fQ / sN.y;
146
+ ev = -height * fR / sN.y;
147
147
  }
148
148
  else {
149
149
  let dW = 1.0
150
150
  - iG * iG / (3.0 * iq * iq);
151
151
  ev = radius * dW;
152
152
  }
153
- return fQ - ev;
153
+ return fR - ev;
154
154
  }
155
155
 
156
156
  fn eT(origin: vec3f, direction: vec3f) -> vec3f {
@@ -180,18 +180,18 @@ if (cC <= 0.0) {
180
180
  return direction;
181
181
  }
182
182
 
183
- let nP = bB + bY * cC;
184
- if (nP.y >= 0.0) {
185
- return normalize(nP);
183
+ let nO = bB + bY * cC;
184
+ if (nO.y >= 0.0) {
185
+ return normalize(nO);
186
186
  }
187
187
 
188
188
  if (bY.y < -0.00001 && params.y > 1.5 * params.x) {
189
189
  let hT = (-params.x - bB.y) / bY.y;
190
- let nF = bB + bY * hT;
191
- let oo = (2.0 / 3.0)
190
+ let nE = bB + bY * hT;
191
+ let om = (2.0 / 3.0)
192
192
  * sqrt(params.y * params.y - 2.25 * params.x * params.x);
193
- if (hT > 0.0 && length(nF.xz) <= oo) {
194
- return normalize(nF);
193
+ if (hT > 0.0 && length(nE.xz) <= om) {
194
+ return normalize(nE);
195
195
  }
196
196
  }
197
197
 
@@ -256,7 +256,7 @@ let bg = cW(
256
256
  (*aa).ray,
257
257
  (*si).wavelength
258
258
  );
259
- let cT = select(fW((*aa).scatteringPdf,
259
+ let cT = select(fX((*aa).scatteringPdf,
260
260
  iB(cY((*aa).ray.d)) * rtUniform.envLightPmf),
261
261
  1.0, (*aa).scatteringIsDelta);
262
262
  (*aa).li += cT * (*aa).beta * bg.rgb * bg.a;
@@ -269,7 +269,7 @@ if (SPECTRAL) {
269
269
  emission = ai(emission, (*si).wavelength);
270
270
  }
271
271
  (*aa).li += (*aa).beta * emission *
272
- fW((*aa).scatteringPdf, iB(tQ));
272
+ fX((*aa).scatteringPdf, iB(tQ));
273
273
  }
274
274
  }
275
275
  else {
@@ -301,9 +301,9 @@ if ((*aa).fromEye) {
301
301
  }
302
302
  else {
303
303
  let cam = hC(uv);
304
- let mM = dot(cam.d, (*aa).ray.d) > 0.0;
304
+ let mL = dot(cam.d, (*aa).ray.d) > 0.0;
305
305
  if (rtUniform.transmissiveOutputAlphaMin < 1.0) {
306
- if (mM) {
306
+ if (mL) {
307
307
  (*aa).alpha = max((*aa).alpha, bg.a);
308
308
  } else {
309
309
  (*aa).alpha = 1.0;
@@ -312,11 +312,11 @@ if (mM) {
312
312
  if (!USE_ENVMAP) {
313
313
 
314
314
 
315
- if (mM) {
315
+ if (mL) {
316
316
 
317
317
 
318
318
  (*aa).li += (*aa).beta *
319
- fW((*aa).scatteringPdf, 1.0) * bg.rgb;
319
+ fX((*aa).scatteringPdf, 1.0) * bg.rgb;
320
320
  }
321
321
  }
322
322
  }
@@ -343,7 +343,7 @@ let tW = max(1.0 - (*ma).transmissionWeight, 1.0 - pow(1.0 - rtUniform.transmiss
343
343
  }
344
344
  if (!cH) {
345
345
  tL = u32(max(*depth, 0));
346
- mc(si, ma, aa);
346
+ mb(si, ma, aa);
347
347
  }
348
348
  else {
349
349
 
@@ -378,10 +378,10 @@ if (*depth > 4) {
378
378
 
379
379
  if (USE_RR) {
380
380
  if (*depth >= RR_MAX && !cH) {
381
- let oI = (*aa).beta;
381
+ let oH = (*aa).beta;
382
382
 
383
- let oz = max(max(oI.x, oI.y), oI.z);
384
- let q: f32 = max(0.0, 1.0 - oz);
383
+ let oy = max(max(oH.x, oH.y), oH.z);
384
+ let q: f32 = max(0.0, 1.0 - oy);
385
385
  if (dz(cw(RUSSIAN_ROULETTE)) < q) {
386
386
 
387
387
 
@@ -422,11 +422,11 @@ let hy = eo(3u) < (*ma).alpha;
422
422
  for (var i = 0; i < rtUniform.lightsCount; i++) {
423
423
 
424
424
  let light: Light = analyticLights[i];
425
- let d = mz((*aa).ray, light, &lightSample);
425
+ let d = my((*aa).ray, light, &lightSample);
426
426
  lightSample.pdf *= light.selectionPmf;
427
- let mD = (*si).hit && d > distance((*si).position, (*aa).ray.o);
428
- if (d != INF && !(mD && hy)) {
429
- let fa = fW((*aa).scatteringPdf, lightSample.pdf);
427
+ let mC = (*si).hit && d > distance((*si).position, (*aa).ray.o);
428
+ if (d != INF && !(mC && hy)) {
429
+ let fa = fX((*aa).scatteringPdf, lightSample.pdf);
430
430
  if (SPECTRAL) {
431
431
  lightSample.emission = ai(lightSample.emission, (*si).wavelength);
432
432
  }
@@ -446,7 +446,7 @@ let bg = cW(
446
446
  (*aa).ray,
447
447
  (*si).wavelength
448
448
  );
449
- let cT = select(fW((*aa).scatteringPdf,
449
+ let cT = select(fX((*aa).scatteringPdf,
450
450
  iB(cY((*aa).ray.d)) * rtUniform.envLightPmf),
451
451
  1.0, (*aa).scatteringIsDelta);
452
452
  (*aa).li += cT * (*aa).beta * bg.rgb * bg.a;
@@ -456,7 +456,7 @@ return;
456
456
  }
457
457
  let _uv = cY((*aa).ray.d);
458
458
  var emission = textureLinear(envMap, _uv).rgb;
459
- let fa = fW(
459
+ let fa = fX(
460
460
  (*aa).scatteringPdf,
461
461
  iB(_uv) * rtUniform.envLightPmf
462
462
  );
@@ -475,9 +475,9 @@ if (!USE_BACKGROUND) {
475
475
  *depth = *depth + 1;
476
476
  }
477
477
 
478
- fn hC(fG: vec2f) -> Ray {
479
- let origin = cameraUniform.viewProjectionInv * vec4f(fG * 2.0 - 1.0, -1.0, 1.0);
480
- let center = cameraUniform.viewProjectionInv * vec4f(fG * 2.0 - 1.0, 1.0, 1.0);
478
+ fn hC(fH: vec2f) -> Ray {
479
+ let origin = cameraUniform.viewProjectionInv * vec4f(fH * 2.0 - 1.0, -1.0, 1.0);
480
+ let center = cameraUniform.viewProjectionInv * vec4f(fH * 2.0 - 1.0, 1.0, 1.0);
481
481
  var cam: Ray;
482
482
  iC(&cam, origin.xyz / origin.w, normalize(center.xyz * origin.w - origin.xyz * center.w));
483
483
 
@@ -487,28 +487,28 @@ return cam;
487
487
 
488
488
  fn kz(radius: f32, xi: f32) -> vec2f {
489
489
  var x = 0.25;
490
- for (var nH = 0; nH < 10; nH++) {
490
+ for (var nG = 0; nG < 10; nG++) {
491
491
  let x2 = x * x;
492
492
  let x3 = x2 * x;
493
493
  let kP = 1.0 - x;
494
494
  let value = 10.0 * x2 - 20.0 * x3 + 15.0 * x2 * x2 -
495
495
  4.0 * x2 * x3 - xi;
496
- let mk = 20.0 * x * kP * kP * kP;
497
- if (abs(value) < 1e-6 || mk == 0.0) { break; }
498
- x = clamp(x - value / mk, 0.0, 1.0);
496
+ let mj = 20.0 * x * kP * kP * kP;
497
+ if (abs(value) < 1e-6 || mj == 0.0) { break; }
498
+ x = clamp(x - value / mj, 0.0, 1.0);
499
499
  }
500
500
  let jo = x * radius;
501
501
  return vec2f(jo, sqrt(max(radius * radius - jo * jo, 0.0)));
502
502
  }
503
503
 
504
- fn iT(radius: f32, gw: f32) -> f32 {
505
- if (gw >= radius) { return 0.0; }
506
- let oh = radius - gw;
507
- return oh * oh * oh;
504
+ fn iT(radius: f32, gx: f32) -> f32 {
505
+ if (gx >= radius) { return 0.0; }
506
+ let og = radius - gx;
507
+ return og * og * og;
508
508
  }
509
509
 
510
510
 
511
- fn mu(source: ad, radius: f32) -> vec3f {
511
+ fn mt(source: ad, radius: f32) -> vec3f {
512
512
  var geometricNormal = source.faceNormal;
513
513
  if (dot(geometricNormal, source.vertexNormal) < 0.0) {
514
514
  geometricNormal = -geometricNormal;
@@ -519,43 +519,43 @@ aL(geometricNormal, &tangent, &bitangent);
519
519
  var iF = vec3f(0.0);
520
520
 
521
521
  for (var ig = 0; ig < BEVEL_SAMPLES; ig++) {
522
- let ph = fo(CAMERA_BEVEL_BASE + u32(ig));
522
+ let ph = fp(CAMERA_BEVEL_BASE + u32(ig));
523
523
  var cA = ph.x;
524
- let oG = ph.y;
524
+ let oF = ph.y;
525
525
  var dj = geometricNormal;
526
- var fH = tangent;
526
+ var fI = tangent;
527
527
  var ek = bitangent;
528
- var ge = 0.5;
528
+ var gf = 0.5;
529
529
  var hY = 0.25;
530
- var gG = 0.25;
530
+ var gH = 0.25;
531
531
  if (cA < 0.5) {
532
532
  cA *= 2.0;
533
533
  }
534
534
  else if (cA < 0.75) {
535
- let mK = dj;
536
- dj = fH;
537
- fH = mK;
538
- ge = 0.25;
535
+ let mJ = dj;
536
+ dj = fI;
537
+ fI = mJ;
538
+ gf = 0.25;
539
539
  hY = 0.5;
540
540
  cA = (cA - 0.5) * 4.0;
541
541
  }
542
542
  else {
543
- let mK = dj;
543
+ let mJ = dj;
544
544
  dj = ek;
545
- ek = mK;
546
- ge = 0.25;
547
- gG = 0.5;
545
+ ek = mJ;
546
+ gf = 0.25;
547
+ gH = 0.5;
548
548
  cA = (cA - 0.75) * 4.0;
549
549
  }
550
550
 
551
- let gU = kz(radius, oG);
551
+ let gV = kz(radius, oF);
552
552
  let phi = TWOPI * cA;
553
- let qv = gU.x *
554
- (cos(phi) * fH + sin(phi) * ek);
553
+ let qv = gV.x *
554
+ (cos(phi) * fI + sin(phi) * ek);
555
555
  var ray: Ray;
556
556
  iC(
557
557
  &ray,
558
- source.position + dj * gU.y + qv,
558
+ source.position + dj * gV.y + qv,
559
559
  -dj
560
560
  );
561
561
  var hit: ad;
@@ -563,20 +563,20 @@ iM(
563
563
  ray,
564
564
  &hit,
565
565
  source.instanceIndex,
566
- max(2.0 * gU.y, EPS)
566
+ max(2.0 * gV.y, EPS)
567
567
  );
568
568
  if (!hit.hit) { continue; }
569
569
 
570
- let kQ = ge * abs(dot(dj, hit.faceNormal));
571
- let mG = hY * abs(dot(fH, hit.faceNormal));
572
- let kb = gG * abs(dot(ek, hit.faceNormal));
570
+ let kQ = gf * abs(dot(dj, hit.faceNormal));
571
+ let mF = hY * abs(dot(fI, hit.faceNormal));
572
+ let kb = gH * abs(dot(ek, hit.faceNormal));
573
573
  var weight = kQ / max(
574
- kQ * kQ + mG * mG +
574
+ kQ * kQ + mF * mF +
575
575
  kb * kb,
576
576
  1e-8
577
577
  );
578
578
  weight *= iT(radius, distance(hit.position, source.position)) /
579
- max(iT(radius, gU.x), 1e-8);
579
+ max(iT(radius, gV.x), 1e-8);
580
580
  iF += weight * hit.vertexNormal;
581
581
  }
582
582
 
@@ -626,21 +626,21 @@ return bw(uv, si, ray, ma, outAux);
626
626
 
627
627
 
628
628
 
629
- var nY = ray;
630
- nY.o = (*si).position + ray.d * (EPS * 0.02);
629
+ var nX = ray;
630
+ nX.o = (*si).position + ray.d * (EPS * 0.02);
631
631
  var dE = *si;
632
632
  dE.albedoSampled = false;
633
- cZ(nY, &dE, 0, false, false);
633
+ cZ(nX, &dE, 0, false, false);
634
634
  var rr: J;
635
635
  eX(&rr, dE.materialIndex, dE.uv, dE.uv1, dE.instanceIndex, dE.vertexColor);
636
- var gm = *outAux;
636
+ var gn = *outAux;
637
637
  if (dE.hit && rr.materialType == STANDARD) {
638
- gm.albedo = select(
638
+ gn.albedo = select(
639
639
  rr.baseColor,
640
640
  vec3f(1.0),
641
641
  rr.transmissionWeight > 0.5
642
642
  );
643
- gm.normal = select(
643
+ gn.normal = select(
644
644
  dE.normal,
645
645
  -dE.normal,
646
646
  dot(
@@ -651,10 +651,10 @@ dE.position - cameraUniform.viewInv[3].xyz
651
651
  dE.albedoSampled = rr.transmissionWeight > 0.5;
652
652
  }
653
653
  let back = bw(
654
- uv, &dE, nY, &rr, &gm
654
+ uv, &dE, nX, &rr, &gn
655
655
  );
656
656
  if (coverage <= 0.0) {
657
- *outAux = gm;
657
+ *outAux = gn;
658
658
  return back;
659
659
  }
660
660
 
@@ -665,21 +665,21 @@ var iW = *outAux;
665
665
  let qY = bw(
666
666
  uv, &tu, ray, &uI, &iW
667
667
  );
668
- (*outAux).albedo = mix(gm.albedo, iW.albedo, coverage);
669
- let fV = mix(gm.normal, iW.normal, coverage);
668
+ (*outAux).albedo = mix(gn.albedo, iW.albedo, coverage);
669
+ let fW = mix(gn.normal, iW.normal, coverage);
670
670
  (*outAux).normal = select(
671
671
  vec3f(0.0),
672
- normalize(fV),
673
- dot(fV, fV) > 1e-12
672
+ normalize(fW),
673
+ dot(fW, fW) > 1e-12
674
674
  );
675
- (*outAux).isBlank = gm.isBlank && iW.isBlank;
676
- (*outAux).isShadowCatcher = gm.isShadowCatcher && iW.isShadowCatcher;
675
+ (*outAux).isBlank = gn.isBlank && iW.isBlank;
676
+ (*outAux).isShadowCatcher = gn.isShadowCatcher && iW.isShadowCatcher;
677
677
  return mix(back, qY, coverage);` : /* wgsl */ `return bw(uv, si, ray, ma, outAux);`}
678
678
  }
679
679
 
680
680
 
681
681
 
682
- fn my(uv: vec2f, ray: Ray, outAux: ptr<function, RayTraceAuxiliary>) -> vec4f {
682
+ fn mx(uv: vec2f, ray: Ray, outAux: ptr<function, RayTraceAuxiliary>) -> vec4f {
683
683
  var si: ad;
684
684
  var ma: J;
685
685
  si.albedoSampled = false;
@@ -711,7 +711,7 @@ return vec4f(vec3f(1.0), aa.alpha);
711
711
  else {
712
712
  if (HAS_BEVEL && rtUniform.bevel != 0) {
713
713
  if (ma.bevel > 0.0) {
714
- si.normal = mu(si, ma.bevel);
714
+ si.normal = mt(si, ma.bevel);
715
715
  }
716
716
  }
717
717
 
@@ -746,17 +746,17 @@ var sf = true;
746
746
  var si2 = si;
747
747
  var ma2 = ma;
748
748
  let qL = s0;
749
- let nU = em;
749
+ let nT = em;
750
750
  let eh = rtUniform.dispersionWavelengths == 1;
751
751
  let jM = si.hit &&
752
752
  ma.transmissionWeight > 0.001 &&
753
753
  ma.transmissionDispersionScale > 0.001;
754
754
  let se = select(3, 1, eh);
755
- var lP = 0;
755
+ var lO = 0;
756
756
  if (eh && jM) {
757
757
 
758
758
 
759
- lP = min(i32(floor(dz(CAMERA_WAVELENGTH) * 3.0)), 2);
759
+ lO = min(i32(floor(dz(CAMERA_WAVELENGTH) * 3.0)), 2);
760
760
  }
761
761
  for (var i = 0; i < se; i++) {
762
762
 
@@ -764,12 +764,12 @@ for (var i = 0; i < se; i++) {
764
764
 
765
765
  if (!eh) {
766
766
  s0 = qL;
767
- em = nU;
767
+ em = nT;
768
768
  cF = 0u;
769
769
  }
770
770
  si.wavelength = 0.0;
771
771
  if (!eh || jM) {
772
- si.wavelength = sQ[select(i, lP, eh)];
772
+ si.wavelength = sQ[select(i, lO, eh)];
773
773
  ma.specularIor = eN(
774
774
  si.wavelength,
775
775
  ma.specularIor,
@@ -811,7 +811,7 @@ return iD(uv, &si, ray, &ma, outAux);
811
811
  }
812
812
  }
813
813
 
814
- fn oL(ip: vec2f) -> vec2f {
814
+ fn oK(ip: vec2f) -> vec2f {
815
815
  let p = 2.0 * ip - 1.0;
816
816
  let greater = abs(p.x) > abs(p.y);
817
817
  let r = select(p.y, p.x, greater);
@@ -826,17 +826,17 @@ let outputSize = rtUniform.outputSize;
826
826
  let scaleOffset = rtUniform.scaleOffset;
827
827
  var jitter = rtUniform.jitter;
828
828
 
829
- let fG = globalId.xy * vec2u(scaleOffset.xy) + vec2u(scaleOffset.zw);
830
- if (fG.x >= u32(outputSize.x) || fG.y >= u32(outputSize.y)) {
829
+ let fH = globalId.xy * vec2u(scaleOffset.xy) + vec2u(scaleOffset.zw);
830
+ if (fH.x >= u32(outputSize.x) || fH.y >= u32(outputSize.y)) {
831
831
  return;
832
832
  }
833
- let idx = fG.x + fG.y * u32(outputSize.x);
833
+ let idx = fH.x + fH.y * u32(outputSize.x);
834
834
 
835
835
  if (
836
836
  rtUniform.adaptiveSampling != 0 &&
837
837
  outNormal[idx].a >= textureLoad(
838
838
  adaptiveSampleTargets,
839
- vec2i(fG),
839
+ vec2i(fH),
840
840
  0
841
841
  ).r
842
842
  ) {
@@ -846,23 +846,23 @@ return;
846
846
 
847
847
 
848
848
 
849
- let uv = (vec2<f32>(f32(fG.x), f32(fG.y)) + vec2f(0.5)) / outputSize;
849
+ let uv = (vec2<f32>(f32(fH.x), f32(fH.y)) + vec2f(0.5)) / outputSize;
850
850
 
851
- bc = fG;
851
+ bc = fH;
852
852
  bd = u32(outNormal[idx].a) + rtUniform.sampleSequenceOffset;
853
853
  cF = 0u; em = 0u;
854
854
  if (SAMPLING_PATTERN == 0 || SAMPLING_PATTERN == 1) {
855
- jitter = (fo(CAMERA_PIXEL) - 0.5) / outputSize;
855
+ jitter = (fp(CAMERA_PIXEL) - 0.5) / outputSize;
856
856
  }
857
- kh(fG, i32(bd ^ eg(rtUniform.sequenceSeed)));
857
+ kh(fH, i32(bd ^ eg(rtUniform.sequenceSeed)));
858
858
  var cam = hC(uv + jitter);
859
859
 
860
860
  if (cameraUniform.apertureRadius > 0.0) {
861
861
 
862
862
  let eye = cameraUniform.viewInv[3].xyz;
863
- let ol = -normalize(cameraUniform.viewInv[2].xyz);
864
- let qy = eye + cam.d * (cameraUniform.focusDistance / dot(cam.d, ol));
865
- let rK = cameraUniform.apertureRadius * oL(fo(CAMERA_LENS));
863
+ let oj = -normalize(cameraUniform.viewInv[2].xyz);
864
+ let qy = eye + cam.d * (cameraUniform.focusDistance / dot(cam.d, oj));
865
+ let rK = cameraUniform.apertureRadius * oK(fp(CAMERA_LENS));
866
866
  let origin = (cameraUniform.viewInv * vec4f(rK, 0.0, 1.0)).xyz;
867
867
  let dir = normalize(qy - origin);
868
868
  iC(&cam, origin, dir);
@@ -873,7 +873,7 @@ outAux.albedo = vec3f(0.0);
873
873
  outAux.normal = vec3f(0.0);
874
874
  outAux.isBlank = false;
875
875
  outAux.isShadowCatcher = false;
876
- var aF = my(uv + jitter, cam, &outAux);
876
+ var aF = mx(uv + jitter, cam, &outAux);
877
877
 
878
878
 
879
879
 
@@ -163,7 +163,7 @@ export default class OpenPBRMaterial {
163
163
  specularAnisotropyModel: 'openpbr' | 'gltf';
164
164
  /** Linear RG tangent direction and B strength multiplier for the base specular layer. Default `undefined`. */
165
165
  anisotropyMap?: Texture;
166
- /** Independent tangent-space coat normal in linear RGB. Without a map, coat shares the existing shading normal. Default `undefined`. */
166
+ /** Independent tangent-space coat normal in linear RGB. Without a map, coat uses the surface normal before base normal mapping. Default `undefined`. */
167
167
  coatNormalMap?: Texture;
168
168
  /** XY strength of coatNormalMap; independent of normalScale. Default `[1, 1]`. */
169
169
  coatNormalScale: Vec2;
@@ -168,7 +168,7 @@ export default class OpenPBRMaterial {
168
168
  specularAnisotropyModel = 'openpbr';
169
169
  /** Linear RG tangent direction and B strength multiplier for the base specular layer. Default `undefined`. */
170
170
  anisotropyMap;
171
- /** Independent tangent-space coat normal in linear RGB. Without a map, coat shares the existing shading normal. Default `undefined`. */
171
+ /** Independent tangent-space coat normal in linear RGB. Without a map, coat uses the surface normal before base normal mapping. Default `undefined`. */
172
172
  coatNormalMap;
173
173
  /** XY strength of coatNormalMap; independent of normalScale. Default `[1, 1]`. */
174
174
  coatNormalScale = materialDefault('coatNormalScale');
@@ -1 +1 @@
1
- {"version":3,"file":"OpenPBRMaterial.js","sourceRoot":"","sources":["../../src/scene/OpenPBRMaterial.ts"],"names":[],"mappings":"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","sourcesContent":["import type { Vec2 } from '../types.js';\nimport { ColorRGB } from '../types.js';\nimport type Texture from './Texture.js';\nimport type { ThinFilmMapChannel } from './thinFilmParameters.js';\nimport { materialDefault, applyMaterialParams } from './openPbrSchema.js';\n\nexport type UVProjection = 'none' | 'triplanar' | 'spherical' | 'cylindrical';\nexport type MaterialAlphaMode = 'auto' | 'opaque' | 'mask' | 'blend';\n\nexport type { MaterialTextureName } from './materialTextureNames.js';\n\n/**\n * OpenPBR 1.1 surface material.\n *\n * Property names are camelCase OpenPBR inputs plus documented compatibility names\n * (https://academysoftwarefoundation.github.io/OpenPBR/). Colors are linear\n * RGB. Length-valued inputs (`transmissionDepth`, `subsurfaceRadius`) use\n * scene units; `thinFilmThickness` is in micrometres as in OpenPBR.\n *\n * ```ts\n * const gold = new OpenPBRMaterial({\n * baseColor: [1.0, 0.78, 0.34], baseMetalness: 1, specularRoughness: 0.2\n * });\n * ```\n *\n * Edit parameters in place; the next `engine.update()` detects the changes.\n */\nexport default class OpenPBRMaterial {\n /** Creates a material. Omitted properties use their documented defaults. */\n constructor(params: OpenPBRMaterialParams = {}) {\n applyMaterialParams(this, params);\n }\n\n // Base\n /** Multiplier of diffuse reflection and metallic normal-incidence color; does not scale dielectric specular, transmission or subsurface. Default `1`. */\n baseWeight: number = materialDefault('baseWeight');\n /** Diffuse/metal color. Default `[0.8, 0.8, 0.8]`. */\n baseColor: ColorRGB = materialDefault('baseColor');\n /** Oren-Nayar style roughness of the diffuse lobe. Default `0`. */\n baseDiffuseRoughness: number = materialDefault('baseDiffuseRoughness');\n /** `0` dielectric, `1` metal. Default `0`. */\n baseMetalness: number = materialDefault('baseMetalness');\n\n // Specular\n /** Dielectric specular strength (via IOR) and overall metallic Fresnel multiplier. Default `1`. */\n specularWeight: number = materialDefault('specularWeight');\n /** Dielectric specular tint and metallic F82 near-grazing tint. Default `[1, 1, 1]`. */\n specularColor: ColorRGB = materialDefault('specularColor');\n /** Microfacet roughness, `0` mirror to `1` rough; retains source perceptual roughness in `gltf` anisotropy mode. Default `0.3`. */\n specularRoughness: number = materialDefault('specularRoughness');\n /** Index of refraction. Default `1.5`. */\n specularIor: number = materialDefault('specularIor');\n /**\n * GGX anisotropy strength, 0 to 1 (requires tangents); native OpenPBR or source glTF strength according to specularAnisotropyModel. Default `0`.\n * @deprecated Use specularRoughnessAnisotropy.\n */\n specularAnisotropy: number = materialDefault('specularAnisotropy');\n\n // Transmission\n /** `1` makes the dielectric base fully transmissive (glass). Default `0`. */\n transmissionWeight: number = materialDefault('transmissionWeight');\n /** Transmission tint, or the medium color at `transmissionDepth`. Default `[1, 1, 1]`. */\n transmissionColor: ColorRGB = materialDefault('transmissionColor');\n /** Depth at which `transmissionColor` is reached; `0` tints at the surface. Default `0`. */\n transmissionDepth: number = materialDefault('transmissionDepth');\n /** Volume scattering color of the transmissive medium. Default `[0, 0, 0]`. */\n transmissionScatter: ColorRGB = materialDefault('transmissionScatter');\n /** Henyey-Greenstein anisotropy of the medium, -1 to 1. Default `0`. */\n transmissionScatterAnisotropy: number = materialDefault('transmissionScatterAnisotropy');\n /** Dispersion strength; `> 0` enables spectral rendering. Default `0`. */\n transmissionDispersionScale: number = materialDefault('transmissionDispersionScale');\n /** Abbe number controlling dispersion. Default `20`. */\n transmissionDispersionAbbeNumber: number = materialDefault('transmissionDispersionAbbeNumber');\n\n // Subsurface\n /** Subsurface scattering weight. Default `0`. */\n subsurfaceWeight: number = materialDefault('subsurfaceWeight');\n /** Subsurface color. Default `[0.8, 0.8, 0.8]`. */\n subsurfaceColor: ColorRGB = materialDefault('subsurfaceColor');\n /** Mean free path in scene units. Default `1`. */\n subsurfaceRadius: number = materialDefault('subsurfaceRadius');\n /** Per-channel multiplier of `subsurfaceRadius`. Default `[1, 0.5, 0.25]`. */\n subsurfaceRadiusScale: ColorRGB = materialDefault('subsurfaceRadiusScale');\n /**\n * Scattering anisotropy, -1 to 1. Default `0`.\n * @deprecated Use subsurfaceScatterAnisotropy.\n */\n subsurfaceAnisotropy: number = materialDefault('subsurfaceAnisotropy');\n\n // Fuzz (sheen)\n /** Fuzz (sheen) layer weight. Default `0`. */\n fuzzWeight: number = materialDefault('fuzzWeight');\n /** Fuzz reflection color; substrate attenuation uses white fuzz albedo. Default `[1, 1, 1]`. */\n fuzzColor: ColorRGB = materialDefault('fuzzColor');\n /** Fuzz roughness; imported from Three.js `sheenRoughness`. Default `0.5`. */\n fuzzRoughness: number = materialDefault('fuzzRoughness');\n\n // Coat\n /** Clear coat weight. Default `0`. */\n coatWeight: number = materialDefault('coatWeight');\n /** Squared coat transmittance at normal incidence; colors the base and emission, not coat reflection. Default `[1, 1, 1]`. */\n coatColor: ColorRGB = materialDefault('coatColor');\n /** Coat roughness. Default `0`. */\n coatRoughness: number = materialDefault('coatRoughness');\n /**\n * OpenPBR GGX coat anisotropy, 0 to 1; uses the base geometry tangent. Default `0`.\n * @deprecated Use coatRoughnessAnisotropy.\n */\n coatAnisotropy: number = materialDefault('coatAnisotropy');\n /** Coat index of refraction. Default `1.6`. */\n coatIor: number = materialDefault('coatIor');\n /** Internal-reflection darkening: 0 compensates darkening, 1 is physical; absorption remains at 0. Default `1`. */\n coatDarkening: number = materialDefault('coatDarkening');\n\n // Thin film\n /** Thin-film interference weight (iridescence). Default `0`. */\n thinFilmWeight: number = materialDefault('thinFilmWeight');\n /** Film thickness in micrometres; maximum endpoint when thinFilmMap is present. Default `0.5`. */\n thinFilmThickness: number = materialDefault('thinFilmThickness');\n /** Film index of refraction. Default `1.4`. */\n thinFilmIor: number = materialDefault('thinFilmIor');\n\n /** Thickness at a thinFilmMap sample of zero, in micrometres; ignored without a map. May exceed thinFilmThickness. Default `0`. */\n thinFilmThicknessMinimum: number = materialDefault('thinFilmThicknessMinimum');\n /** Linear channel sampled by thinFilmMap. Default `r`. */\n thinFilmMapChannel: ThinFilmMapChannel = materialDefault('thinFilmMapChannel');\n\n // Emission and geometry\n /** Emission color. Default `[1, 1, 1]`. */\n emissionColor: ColorRGB = materialDefault('emissionColor');\n /** Emitted radiance scale; `0` disables emission. Default `0`. */\n emissionLuminance: number = materialDefault('emissionLuminance');\n /**\n * Coverage, `1` opaque. See `alphaMode`. Default `1`.\n * @deprecated Use geometryOpacity.\n */\n opacity: number = materialDefault('opacity');\n /**\n * Treat the surface as an infinitely thin shell (leaves, paper). Default `false`.\n * @deprecated Use geometryThinWalled.\n */\n thinWalled: boolean = materialDefault('thinWalled');\n /** Disables geometric back-face culling for this material. Default `false`. */\n doubleSided: boolean = materialDefault('doubleSided');\n\n // Textures\n /** Base color texture, multiplied with `baseColor` using Texture color encoding. Default `undefined`. */\n map?: Texture;\n /** Standalone opacity texture sampled from its green channel, matching Three.js. Default `undefined`. */\n alphaMap?: Texture;\n /**\n * Coverage for surface and shadow rays: `opaque` ignores alpha inputs,\n * `mask` uses binary alpha testing, `blend` retains fractional coverage.\n * `auto` derives the mode from the alpha inputs. Default `auto`.\n */\n alphaMode: MaterialAlphaMode = materialDefault('alphaMode');\n /** Alpha-test threshold for `mask` mode; equality is fully covered. Default `0`. */\n alphaCutoff: number = materialDefault('alphaCutoff');\n /** Emission texture multiplied with `emissionColor`. Default `undefined`. */\n emissiveMap?: Texture;\n /** Tangent-space normal map. */\n normalMap?: Texture;\n /** Normal map strength per axis. Default `[1, 1]`. */\n normalScale: Vec2 = materialDefault('normalScale');\n /** glTF-compatible B=metalness, G=specular roughness texture. Default `undefined`. */\n metallicRoughnessMap?: Texture;\n /** Standalone roughness texture sampled from its green channel. Default `undefined`. */\n roughnessMap?: Texture;\n /** Standalone metalness texture sampled from its blue channel. Default `undefined`. */\n metalnessMap?: Texture;\n /** Multiplies transmission weight using the texture's red channel. Default `undefined`. */\n transmissionMap?: Texture;\n /** Linear thickness-range texture; R and zero minimum preserve multiplication semantics. Default `undefined`. */\n thinFilmMap?: Texture;\n\n /** Multiplies coatWeight by the linear red channel. Default `undefined`. */\n coatWeightMap?: Texture;\n /** Multiplies coatRoughness by the linear green channel. Default `undefined`. */\n coatRoughnessMap?: Texture;\n /** Multiplies fuzzColor by RGB channels using Texture color encoding. Default `undefined`. */\n fuzzColorMap?: Texture;\n /** Multiplies fuzzRoughness by the linear alpha channel. Default `undefined`. */\n fuzzRoughnessMap?: Texture;\n /** Multiplies specularWeight by the linear alpha channel. Default `undefined`. */\n specularWeightMap?: Texture;\n /** Multiplies specularColor by RGB channels using Texture color encoding. Default `undefined`. */\n specularColorMap?: Texture;\n\n\n /** Source convention for base specular anisotropy. `gltf` converts textured roughness and strength before coat roughening; `openpbr` uses native parameters. Default `openpbr`. */\n specularAnisotropyModel: 'openpbr' | 'gltf' = 'openpbr';\n /** Linear RG tangent direction and B strength multiplier for the base specular layer. Default `undefined`. */\n anisotropyMap?: Texture;\n /** Independent tangent-space coat normal in linear RGB. Without a map, coat shares the existing shading normal. Default `undefined`. */\n coatNormalMap?: Texture;\n /** XY strength of coatNormalMap; independent of normalScale. Default `[1, 1]`. */\n coatNormalScale: Vec2 = materialDefault('coatNormalScale');\n /** Base direction rotation in radians, counter-clockwise in tangent/bitangent space after RG decoding. Default `0`. */\n specularAnisotropyRotation: number = 0;\n /** Coat direction rotation in radians relative to the geometry tangent. Default `0`. */\n coatAnisotropyRotation: number = 0;\n\n /** GGX roughness anisotropy in [0, 1]; native OpenPBR or source glTF strength according to specularAnisotropyModel. Requires tangents. Default `0`. */\n get specularRoughnessAnisotropy(): number { return this.specularAnisotropy; }\n set specularRoughnessAnisotropy(value: number) { this.specularAnisotropy = value; }\n\n /** OpenPBR coat GGX roughness anisotropy in [0, 1]. Default `0`. */\n get coatRoughnessAnisotropy(): number { return this.coatAnisotropy; }\n set coatRoughnessAnisotropy(value: number) { this.coatAnisotropy = value; }\n\n /** Subsurface scattering anisotropy in [-1, 1]. Default `0`. */\n get subsurfaceScatterAnisotropy(): number { return this.subsurfaceAnisotropy; }\n set subsurfaceScatterAnisotropy(value: number) { this.subsurfaceAnisotropy = value; }\n\n /** Surface coverage; alphaMode controls testing and blending. Default `1`. */\n get geometryOpacity(): number { return this.opacity; }\n set geometryOpacity(value: number) { this.opacity = value; }\n\n /** Treat the surface as an infinitely thin shell. Default `false`. */\n get geometryThinWalled(): boolean { return this.thinWalled; }\n set geometryThinWalled(value: boolean) { this.thinWalled = value; }\n\n // Renderer extensions\n /**\n * Invisible ground that only receives shadows, composited over the\n * background. Default `false`.\n */\n shadowCatcher: boolean = materialDefault('shadowCatcher');\n /** Displays emission without scattering or illuminating other surfaces. Default `false`. */\n unlit: boolean = materialDefault('unlit');\n /** Radius of rounded-edge shading (shader bevel) in scene units. `0` disables it. Default `0`. */\n bevelSize: number = materialDefault('bevelSize');\n /** How map alpha is used: ignored, opacity or transmission. Default `opaque`. */\n mapAlphaUsage: 'opaque' | 'alpha' | 'transmission' = materialDefault('mapAlphaUsage');\n /** Procedural UV projection for textures without (good) UVs. Default `none`. */\n uvProjection: UVProjection = materialDefault('uvProjection');\n /** UV scale used with `uvProjection`. Default `[1, 1]`. */\n uvProjectionScale: Vec2 = materialDefault('uvProjectionScale');\n\n // Displacement\n /** Height texture (red channel) for displacement. Default `undefined`. */\n displacementMap?: Texture;\n /** Procedural UV projection for the displacement map. Default `none`. */\n displacementUvProjection: UVProjection = materialDefault('displacementUvProjection');\n /** UV scale used with `displacementUvProjection`. Default `1`. */\n displacementUvProjectionScale: number = materialDefault('displacementUvProjectionScale');\n /** Height multiplier in mesh-local units; 0 removes height variation. Default `0.1`. */\n displacementScale: number = materialDefault('displacementScale');\n /** Offset added after scaling the height map, along the normal in mesh-local units; requires a displacement map. Default `0`. */\n displacementBias: number = materialDefault('displacementBias');\n /** Ray-marching step in mesh-local units; 0 automatically uses abs(displacementScale) / 32. Default `0`. */\n displacementStepSize: number = materialDefault('displacementStepSize');\n\n}\nexport const materialAlphaModeConstants = {\n opaque: 0,\n mask: 1,\n blend: 2\n} as const;\n\nexport type ResolvedMaterialAlphaMode = Exclude<MaterialAlphaMode, 'auto'>;\n\nexport function resolveMaterialAlphaMode(\n material: OpenPBRMaterial\n): ResolvedMaterialAlphaMode {\n if (material.alphaMode !== 'auto') return material.alphaMode;\n if (material.alphaCutoff > 0) return 'mask';\n if (\n material.opacity < 1 ||\n material.mapAlphaUsage === \"alpha\" ||\n material.alphaMap\n ) {\n return 'blend';\n }\n return 'opaque';\n}\n\nexport { materialKeys, materialTextureKeys, materialGeometryKeys, materialParamKeys, getMaterialHashKey, resetMaterialTextureId } from './openPbrSchema.js';\n\n/** Optional material properties; defaults are documented on OpenPBRMaterial. */\nexport type OpenPBRMaterialParams = Partial<OpenPBRMaterial>;\n"]}
1
+ {"version":3,"file":"OpenPBRMaterial.js","sourceRoot":"","sources":["../../src/scene/OpenPBRMaterial.ts"],"names":[],"mappings":"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","sourcesContent":["import type { Vec2 } from '../types.js';\nimport { ColorRGB } from '../types.js';\nimport type Texture from './Texture.js';\nimport type { ThinFilmMapChannel } from './thinFilmParameters.js';\nimport { materialDefault, applyMaterialParams } from './openPbrSchema.js';\n\nexport type UVProjection = 'none' | 'triplanar' | 'spherical' | 'cylindrical';\nexport type MaterialAlphaMode = 'auto' | 'opaque' | 'mask' | 'blend';\n\nexport type { MaterialTextureName } from './materialTextureNames.js';\n\n/**\n * OpenPBR 1.1 surface material.\n *\n * Property names are camelCase OpenPBR inputs plus documented compatibility names\n * (https://academysoftwarefoundation.github.io/OpenPBR/). Colors are linear\n * RGB. Length-valued inputs (`transmissionDepth`, `subsurfaceRadius`) use\n * scene units; `thinFilmThickness` is in micrometres as in OpenPBR.\n *\n * ```ts\n * const gold = new OpenPBRMaterial({\n * baseColor: [1.0, 0.78, 0.34], baseMetalness: 1, specularRoughness: 0.2\n * });\n * ```\n *\n * Edit parameters in place; the next `engine.update()` detects the changes.\n */\nexport default class OpenPBRMaterial {\n /** Creates a material. Omitted properties use their documented defaults. */\n constructor(params: OpenPBRMaterialParams = {}) {\n applyMaterialParams(this, params);\n }\n\n // Base\n /** Multiplier of diffuse reflection and metallic normal-incidence color; does not scale dielectric specular, transmission or subsurface. Default `1`. */\n baseWeight: number = materialDefault('baseWeight');\n /** Diffuse/metal color. Default `[0.8, 0.8, 0.8]`. */\n baseColor: ColorRGB = materialDefault('baseColor');\n /** Oren-Nayar style roughness of the diffuse lobe. Default `0`. */\n baseDiffuseRoughness: number = materialDefault('baseDiffuseRoughness');\n /** `0` dielectric, `1` metal. Default `0`. */\n baseMetalness: number = materialDefault('baseMetalness');\n\n // Specular\n /** Dielectric specular strength (via IOR) and overall metallic Fresnel multiplier. Default `1`. */\n specularWeight: number = materialDefault('specularWeight');\n /** Dielectric specular tint and metallic F82 near-grazing tint. Default `[1, 1, 1]`. */\n specularColor: ColorRGB = materialDefault('specularColor');\n /** Microfacet roughness, `0` mirror to `1` rough; retains source perceptual roughness in `gltf` anisotropy mode. Default `0.3`. */\n specularRoughness: number = materialDefault('specularRoughness');\n /** Index of refraction. Default `1.5`. */\n specularIor: number = materialDefault('specularIor');\n /**\n * GGX anisotropy strength, 0 to 1 (requires tangents); native OpenPBR or source glTF strength according to specularAnisotropyModel. Default `0`.\n * @deprecated Use specularRoughnessAnisotropy.\n */\n specularAnisotropy: number = materialDefault('specularAnisotropy');\n\n // Transmission\n /** `1` makes the dielectric base fully transmissive (glass). Default `0`. */\n transmissionWeight: number = materialDefault('transmissionWeight');\n /** Transmission tint, or the medium color at `transmissionDepth`. Default `[1, 1, 1]`. */\n transmissionColor: ColorRGB = materialDefault('transmissionColor');\n /** Depth at which `transmissionColor` is reached; `0` tints at the surface. Default `0`. */\n transmissionDepth: number = materialDefault('transmissionDepth');\n /** Volume scattering color of the transmissive medium. Default `[0, 0, 0]`. */\n transmissionScatter: ColorRGB = materialDefault('transmissionScatter');\n /** Henyey-Greenstein anisotropy of the medium, -1 to 1. Default `0`. */\n transmissionScatterAnisotropy: number = materialDefault('transmissionScatterAnisotropy');\n /** Dispersion strength; `> 0` enables spectral rendering. Default `0`. */\n transmissionDispersionScale: number = materialDefault('transmissionDispersionScale');\n /** Abbe number controlling dispersion. Default `20`. */\n transmissionDispersionAbbeNumber: number = materialDefault('transmissionDispersionAbbeNumber');\n\n // Subsurface\n /** Subsurface scattering weight. Default `0`. */\n subsurfaceWeight: number = materialDefault('subsurfaceWeight');\n /** Subsurface color. Default `[0.8, 0.8, 0.8]`. */\n subsurfaceColor: ColorRGB = materialDefault('subsurfaceColor');\n /** Mean free path in scene units. Default `1`. */\n subsurfaceRadius: number = materialDefault('subsurfaceRadius');\n /** Per-channel multiplier of `subsurfaceRadius`. Default `[1, 0.5, 0.25]`. */\n subsurfaceRadiusScale: ColorRGB = materialDefault('subsurfaceRadiusScale');\n /**\n * Scattering anisotropy, -1 to 1. Default `0`.\n * @deprecated Use subsurfaceScatterAnisotropy.\n */\n subsurfaceAnisotropy: number = materialDefault('subsurfaceAnisotropy');\n\n // Fuzz (sheen)\n /** Fuzz (sheen) layer weight. Default `0`. */\n fuzzWeight: number = materialDefault('fuzzWeight');\n /** Fuzz reflection color; substrate attenuation uses white fuzz albedo. Default `[1, 1, 1]`. */\n fuzzColor: ColorRGB = materialDefault('fuzzColor');\n /** Fuzz roughness; imported from Three.js `sheenRoughness`. Default `0.5`. */\n fuzzRoughness: number = materialDefault('fuzzRoughness');\n\n // Coat\n /** Clear coat weight. Default `0`. */\n coatWeight: number = materialDefault('coatWeight');\n /** Squared coat transmittance at normal incidence; colors the base and emission, not coat reflection. Default `[1, 1, 1]`. */\n coatColor: ColorRGB = materialDefault('coatColor');\n /** Coat roughness. Default `0`. */\n coatRoughness: number = materialDefault('coatRoughness');\n /**\n * OpenPBR GGX coat anisotropy, 0 to 1; uses the base geometry tangent. Default `0`.\n * @deprecated Use coatRoughnessAnisotropy.\n */\n coatAnisotropy: number = materialDefault('coatAnisotropy');\n /** Coat index of refraction. Default `1.6`. */\n coatIor: number = materialDefault('coatIor');\n /** Internal-reflection darkening: 0 compensates darkening, 1 is physical; absorption remains at 0. Default `1`. */\n coatDarkening: number = materialDefault('coatDarkening');\n\n // Thin film\n /** Thin-film interference weight (iridescence). Default `0`. */\n thinFilmWeight: number = materialDefault('thinFilmWeight');\n /** Film thickness in micrometres; maximum endpoint when thinFilmMap is present. Default `0.5`. */\n thinFilmThickness: number = materialDefault('thinFilmThickness');\n /** Film index of refraction. Default `1.4`. */\n thinFilmIor: number = materialDefault('thinFilmIor');\n\n /** Thickness at a thinFilmMap sample of zero, in micrometres; ignored without a map. May exceed thinFilmThickness. Default `0`. */\n thinFilmThicknessMinimum: number = materialDefault('thinFilmThicknessMinimum');\n /** Linear channel sampled by thinFilmMap. Default `r`. */\n thinFilmMapChannel: ThinFilmMapChannel = materialDefault('thinFilmMapChannel');\n\n // Emission and geometry\n /** Emission color. Default `[1, 1, 1]`. */\n emissionColor: ColorRGB = materialDefault('emissionColor');\n /** Emitted radiance scale; `0` disables emission. Default `0`. */\n emissionLuminance: number = materialDefault('emissionLuminance');\n /**\n * Coverage, `1` opaque. See `alphaMode`. Default `1`.\n * @deprecated Use geometryOpacity.\n */\n opacity: number = materialDefault('opacity');\n /**\n * Treat the surface as an infinitely thin shell (leaves, paper). Default `false`.\n * @deprecated Use geometryThinWalled.\n */\n thinWalled: boolean = materialDefault('thinWalled');\n /** Disables geometric back-face culling for this material. Default `false`. */\n doubleSided: boolean = materialDefault('doubleSided');\n\n // Textures\n /** Base color texture, multiplied with `baseColor` using Texture color encoding. Default `undefined`. */\n map?: Texture;\n /** Standalone opacity texture sampled from its green channel, matching Three.js. Default `undefined`. */\n alphaMap?: Texture;\n /**\n * Coverage for surface and shadow rays: `opaque` ignores alpha inputs,\n * `mask` uses binary alpha testing, `blend` retains fractional coverage.\n * `auto` derives the mode from the alpha inputs. Default `auto`.\n */\n alphaMode: MaterialAlphaMode = materialDefault('alphaMode');\n /** Alpha-test threshold for `mask` mode; equality is fully covered. Default `0`. */\n alphaCutoff: number = materialDefault('alphaCutoff');\n /** Emission texture multiplied with `emissionColor`. Default `undefined`. */\n emissiveMap?: Texture;\n /** Tangent-space normal map. */\n normalMap?: Texture;\n /** Normal map strength per axis. Default `[1, 1]`. */\n normalScale: Vec2 = materialDefault('normalScale');\n /** glTF-compatible B=metalness, G=specular roughness texture. Default `undefined`. */\n metallicRoughnessMap?: Texture;\n /** Standalone roughness texture sampled from its green channel. Default `undefined`. */\n roughnessMap?: Texture;\n /** Standalone metalness texture sampled from its blue channel. Default `undefined`. */\n metalnessMap?: Texture;\n /** Multiplies transmission weight using the texture's red channel. Default `undefined`. */\n transmissionMap?: Texture;\n /** Linear thickness-range texture; R and zero minimum preserve multiplication semantics. Default `undefined`. */\n thinFilmMap?: Texture;\n\n /** Multiplies coatWeight by the linear red channel. Default `undefined`. */\n coatWeightMap?: Texture;\n /** Multiplies coatRoughness by the linear green channel. Default `undefined`. */\n coatRoughnessMap?: Texture;\n /** Multiplies fuzzColor by RGB channels using Texture color encoding. Default `undefined`. */\n fuzzColorMap?: Texture;\n /** Multiplies fuzzRoughness by the linear alpha channel. Default `undefined`. */\n fuzzRoughnessMap?: Texture;\n /** Multiplies specularWeight by the linear alpha channel. Default `undefined`. */\n specularWeightMap?: Texture;\n /** Multiplies specularColor by RGB channels using Texture color encoding. Default `undefined`. */\n specularColorMap?: Texture;\n\n\n /** Source convention for base specular anisotropy. `gltf` converts textured roughness and strength before coat roughening; `openpbr` uses native parameters. Default `openpbr`. */\n specularAnisotropyModel: 'openpbr' | 'gltf' = 'openpbr';\n /** Linear RG tangent direction and B strength multiplier for the base specular layer. Default `undefined`. */\n anisotropyMap?: Texture;\n /** Independent tangent-space coat normal in linear RGB. Without a map, coat uses the surface normal before base normal mapping. Default `undefined`. */\n coatNormalMap?: Texture;\n /** XY strength of coatNormalMap; independent of normalScale. Default `[1, 1]`. */\n coatNormalScale: Vec2 = materialDefault('coatNormalScale');\n /** Base direction rotation in radians, counter-clockwise in tangent/bitangent space after RG decoding. Default `0`. */\n specularAnisotropyRotation: number = 0;\n /** Coat direction rotation in radians relative to the geometry tangent. Default `0`. */\n coatAnisotropyRotation: number = 0;\n\n /** GGX roughness anisotropy in [0, 1]; native OpenPBR or source glTF strength according to specularAnisotropyModel. Requires tangents. Default `0`. */\n get specularRoughnessAnisotropy(): number { return this.specularAnisotropy; }\n set specularRoughnessAnisotropy(value: number) { this.specularAnisotropy = value; }\n\n /** OpenPBR coat GGX roughness anisotropy in [0, 1]. Default `0`. */\n get coatRoughnessAnisotropy(): number { return this.coatAnisotropy; }\n set coatRoughnessAnisotropy(value: number) { this.coatAnisotropy = value; }\n\n /** Subsurface scattering anisotropy in [-1, 1]. Default `0`. */\n get subsurfaceScatterAnisotropy(): number { return this.subsurfaceAnisotropy; }\n set subsurfaceScatterAnisotropy(value: number) { this.subsurfaceAnisotropy = value; }\n\n /** Surface coverage; alphaMode controls testing and blending. Default `1`. */\n get geometryOpacity(): number { return this.opacity; }\n set geometryOpacity(value: number) { this.opacity = value; }\n\n /** Treat the surface as an infinitely thin shell. Default `false`. */\n get geometryThinWalled(): boolean { return this.thinWalled; }\n set geometryThinWalled(value: boolean) { this.thinWalled = value; }\n\n // Renderer extensions\n /**\n * Invisible ground that only receives shadows, composited over the\n * background. Default `false`.\n */\n shadowCatcher: boolean = materialDefault('shadowCatcher');\n /** Displays emission without scattering or illuminating other surfaces. Default `false`. */\n unlit: boolean = materialDefault('unlit');\n /** Radius of rounded-edge shading (shader bevel) in scene units. `0` disables it. Default `0`. */\n bevelSize: number = materialDefault('bevelSize');\n /** How map alpha is used: ignored, opacity or transmission. Default `opaque`. */\n mapAlphaUsage: 'opaque' | 'alpha' | 'transmission' = materialDefault('mapAlphaUsage');\n /** Procedural UV projection for textures without (good) UVs. Default `none`. */\n uvProjection: UVProjection = materialDefault('uvProjection');\n /** UV scale used with `uvProjection`. Default `[1, 1]`. */\n uvProjectionScale: Vec2 = materialDefault('uvProjectionScale');\n\n // Displacement\n /** Height texture (red channel) for displacement. Default `undefined`. */\n displacementMap?: Texture;\n /** Procedural UV projection for the displacement map. Default `none`. */\n displacementUvProjection: UVProjection = materialDefault('displacementUvProjection');\n /** UV scale used with `displacementUvProjection`. Default `1`. */\n displacementUvProjectionScale: number = materialDefault('displacementUvProjectionScale');\n /** Height multiplier in mesh-local units; 0 removes height variation. Default `0.1`. */\n displacementScale: number = materialDefault('displacementScale');\n /** Offset added after scaling the height map, along the normal in mesh-local units; requires a displacement map. Default `0`. */\n displacementBias: number = materialDefault('displacementBias');\n /** Ray-marching step in mesh-local units; 0 automatically uses abs(displacementScale) / 32. Default `0`. */\n displacementStepSize: number = materialDefault('displacementStepSize');\n\n}\nexport const materialAlphaModeConstants = {\n opaque: 0,\n mask: 1,\n blend: 2\n} as const;\n\nexport type ResolvedMaterialAlphaMode = Exclude<MaterialAlphaMode, 'auto'>;\n\nexport function resolveMaterialAlphaMode(\n material: OpenPBRMaterial\n): ResolvedMaterialAlphaMode {\n if (material.alphaMode !== 'auto') return material.alphaMode;\n if (material.alphaCutoff > 0) return 'mask';\n if (\n material.opacity < 1 ||\n material.mapAlphaUsage === \"alpha\" ||\n material.alphaMap\n ) {\n return 'blend';\n }\n return 'opaque';\n}\n\nexport { materialKeys, materialTextureKeys, materialGeometryKeys, materialParamKeys, getMaterialHashKey, resetMaterialTextureId } from './openPbrSchema.js';\n\n/** Optional material properties; defaults are documented on OpenPBRMaterial. */\nexport type OpenPBRMaterialParams = Partial<OpenPBRMaterial>;\n"]}
package/lib/version.d.ts CHANGED
@@ -1,2 +1,2 @@
1
1
  /** Library version. Kept in sync with package.json by a unit test. */
2
- export declare const VERSION = "0.1.4";
2
+ export declare const VERSION = "0.1.5";
package/lib/version.js CHANGED
@@ -1,3 +1,3 @@
1
1
  /** Library version. Kept in sync with package.json by a unit test. */
2
- export const VERSION = '0.1.4';
2
+ export const VERSION = '0.1.5';
3
3
  //# sourceMappingURL=version.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"version.js","sourceRoot":"","sources":["../src/version.ts"],"names":[],"mappings":"AAAA,sEAAsE;AACtE,MAAM,CAAC,MAAM,OAAO,GAAG,OAAO,CAAC","sourcesContent":["/** Library version. Kept in sync with package.json by a unit test. */\nexport const VERSION = '0.1.4';\n"]}
1
+ {"version":3,"file":"version.js","sourceRoot":"","sources":["../src/version.ts"],"names":[],"mappings":"AAAA,sEAAsE;AACtE,MAAM,CAAC,MAAM,OAAO,GAAG,OAAO,CAAC","sourcesContent":["/** Library version. Kept in sync with package.json by a unit test. */\nexport const VERSION = '0.1.5';\n"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@meimu/mutracer",
3
- "version": "0.1.4",
3
+ "version": "0.1.5",
4
4
  "description": "MuTracer: a physically based WebGPU path tracer with WebGL 2 fallback, OpenPBR materials, TinyBVH and OIDN denoising.",
5
5
  "keywords": [
6
6
  "path tracing",