@meimu/mutracer 0.1.3 → 0.1.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/assets/bvh.worker.js +1 -1
- package/dist/mutracer.umd.js +4114 -4015
- package/docs/api.md +11 -9
- package/docs/threejs.md +30 -4
- package/lib/Engine.js +18 -1
- package/lib/Engine.js.map +1 -1
- package/lib/main.d.ts +1 -1
- package/lib/main.js.map +1 -1
- package/lib/oidn.d.ts +1 -1
- package/lib/oidnBundledWeights.cdn.d.ts +2 -2
- package/lib/renderer/MaterialTable.d.ts +1 -0
- package/lib/renderer/MaterialTable.js +10 -4
- package/lib/renderer/MaterialTable.js.map +1 -1
- package/lib/renderer/WGPUBloomPass.js +18 -18
- package/lib/renderer/WGPUFullQuadPass.js +6 -6
- package/lib/renderer/WGPUJNLMDenoiser.js +69 -69
- package/lib/renderer/WGPURayTraceOutput.js +14 -14
- package/lib/renderer/WGPURayTracePass.d.ts +2 -0
- package/lib/renderer/WGPURayTracePass.js +12 -6
- package/lib/renderer/WGPURayTracePass.js.map +1 -1
- package/lib/renderer/WGPURenderingPipeline.js +15 -15
- package/lib/renderer/WebGLJNLMDenoiser.js +69 -69
- package/lib/renderer/WebGLRayTraceOutputPass.js +4 -4
- package/lib/renderer/WebGLRayTracePass.d.ts +1 -0
- package/lib/renderer/WebGLRayTracePass.js +7 -1
- package/lib/renderer/WebGLRayTracePass.js.map +1 -1
- package/lib/renderer/envMapCreation.d.ts +5 -1
- package/lib/renderer/envMapCreation.js +42 -5
- package/lib/renderer/envMapCreation.js.map +1 -1
- package/lib/renderer/geometryUpdates.js +1 -1
- package/lib/renderer/geometryUpdates.js.map +1 -1
- package/lib/renderer/glsl/chunks/cameraRay.glsl.js +12 -12
- package/lib/renderer/glsl/chunks/envMap.glsl.js +66 -54
- package/lib/renderer/glsl/chunks/envMap.glsl.js.map +1 -1
- package/lib/renderer/glsl/chunks/intersect.glsl.js +316 -310
- package/lib/renderer/glsl/chunks/intersect.glsl.js.map +1 -1
- package/lib/renderer/glsl/chunks/materialBuffer.glsl.js +151 -119
- package/lib/renderer/glsl/chunks/materialBuffer.glsl.js.map +1 -1
- package/lib/renderer/glsl/chunks/openPbrBsdf.glsl.js +414 -414
- package/lib/renderer/glsl/chunks/rand.glsl.js +3 -3
- package/lib/renderer/glsl/chunks/random.glsl.js +3 -3
- package/lib/renderer/glsl/chunks/rayTraceCore.glsl.js +40 -39
- package/lib/renderer/glsl/chunks/rayTraceCore.glsl.js.map +1 -1
- package/lib/renderer/glsl/chunks/sampleLight.glsl.js +69 -69
- package/lib/renderer/glsl/chunks/sampleMaterial.glsl.js +78 -78
- package/lib/renderer/glsl/chunks/sampleShadowCatcher.glsl.js +12 -12
- package/lib/renderer/glsl/chunks/sampling.glsl.js +75 -75
- package/lib/renderer/glsl/chunks/sobol.glsl.js +61 -61
- package/lib/renderer/glsl/chunks/textureLinear.glsl.js +5 -5
- package/lib/renderer/glsl/chunks/uvProjection.glsl.js +11 -11
- package/lib/renderer/glsl/depthQuery.frag.js +5 -5
- package/lib/renderer/glsl/depthQuery.frag.js.map +1 -1
- package/lib/renderer/glsl/normalizeRayTraceOutput.frag.js +8 -8
- package/lib/renderer/glsl/rayTrace.frag.js +133 -133
- package/lib/renderer/glsl/rayTrace.frag.js.map +1 -1
- package/lib/renderer/glsl/shadowCatcher.frag.js +9 -9
- package/lib/renderer/glsl/shadowCatcher.frag.js.map +1 -1
- package/lib/renderer/glsl/webglPipeline.frag.js +52 -52
- package/lib/renderer/lightsUtil.js +6 -4
- package/lib/renderer/lightsUtil.js.map +1 -1
- package/lib/renderer/materialChanges.js +1 -1
- package/lib/renderer/materialChanges.js.map +1 -1
- package/lib/renderer/materialComparison.generated.js +36 -18
- package/lib/renderer/materialComparison.generated.js.map +1 -1
- package/lib/renderer/prepareMeshBVH.js +2 -2
- package/lib/renderer/prepareMeshBVH.js.map +1 -1
- package/lib/renderer/sceneChangeDetector.js +4 -1
- package/lib/renderer/sceneChangeDetector.js.map +1 -1
- package/lib/renderer/sceneLightChanges.js +3 -2
- package/lib/renderer/sceneLightChanges.js.map +1 -1
- package/lib/renderer/scratchSampling.js +18 -18
- package/lib/renderer/wgsl/chunks/common.wgsl.js +4 -4
- package/lib/renderer/wgsl/chunks/envMap.wgsl.d.ts +1 -1
- package/lib/renderer/wgsl/chunks/envMap.wgsl.js +39 -31
- package/lib/renderer/wgsl/chunks/envMap.wgsl.js.map +1 -1
- package/lib/renderer/wgsl/chunks/intersect.wgsl.js +475 -469
- package/lib/renderer/wgsl/chunks/intersect.wgsl.js.map +1 -1
- package/lib/renderer/wgsl/chunks/intersectionAlpha.wgsl.js +8 -8
- package/lib/renderer/wgsl/chunks/materialBuffer.wgsl.js +93 -59
- package/lib/renderer/wgsl/chunks/materialBuffer.wgsl.js.map +1 -1
- package/lib/renderer/wgsl/chunks/openPbrBsdf.wgsl.js +469 -469
- package/lib/renderer/wgsl/chunks/pdm_displacement.wgsl.d.ts +1 -1
- package/lib/renderer/wgsl/chunks/pdm_displacement.wgsl.js +117 -120
- package/lib/renderer/wgsl/chunks/pdm_displacement.wgsl.js.map +1 -1
- package/lib/renderer/wgsl/chunks/rand.wgsl.js +3 -3
- package/lib/renderer/wgsl/chunks/rayTraceCore.wgsl.js +25 -22
- package/lib/renderer/wgsl/chunks/rayTraceCore.wgsl.js.map +1 -1
- package/lib/renderer/wgsl/chunks/sampleLight.wgsl.js +127 -127
- package/lib/renderer/wgsl/chunks/sampleMaterial.wgsl.js +136 -136
- package/lib/renderer/wgsl/chunks/sampleShadowCatcher.wgsl.js +6 -6
- package/lib/renderer/wgsl/chunks/sampling.wgsl.js +73 -73
- package/lib/renderer/wgsl/chunks/sobol.wgsl.js +62 -62
- package/lib/renderer/wgsl/chunks/uvProjection.wgsl.js +11 -11
- package/lib/renderer/wgsl/compose.frag.wgsl.js +105 -105
- package/lib/renderer/wgsl/customDenoise.wgsl.js +10 -10
- package/lib/renderer/wgsl/depthQuery.wgsl.d.ts +1 -1
- package/lib/renderer/wgsl/depthQuery.wgsl.js +5 -5
- package/lib/renderer/wgsl/depthQuery.wgsl.js.map +1 -1
- package/lib/renderer/wgsl/offlineAdaptive.compute.js +28 -28
- package/lib/renderer/wgsl/rayTrace.compute.js +251 -248
- package/lib/renderer/wgsl/rayTrace.compute.js.map +1 -1
- package/lib/scene/EnvironmentLight.d.ts +9 -3
- package/lib/scene/EnvironmentLight.js +9 -2
- package/lib/scene/EnvironmentLight.js.map +1 -1
- package/lib/scene/Scene.d.ts +4 -0
- package/lib/scene/Scene.js.map +1 -1
- package/lib/scene/SpotLight.d.ts +2 -2
- package/lib/scene/SpotLight.js +1 -1
- package/lib/scene/SpotLight.js.map +1 -1
- package/lib/scene/Texture.d.ts +17 -6
- package/lib/scene/Texture.js +13 -4
- package/lib/scene/Texture.js.map +1 -1
- package/lib/util/fromTHREE.js +151 -29
- package/lib/util/fromTHREE.js.map +1 -1
- package/lib/version.d.ts +1 -1
- package/lib/version.js +1 -1
- package/lib/version.js.map +1 -1
- package/package.json +1 -1
|
@@ -15,6 +15,7 @@ export default createShaderMixin({
|
|
|
15
15
|
mapTransform: Shader.arrayUniform('vec4', 'NUM_MAPS'),
|
|
16
16
|
mapUvChannel: Shader.arrayUniform('float', 'NUM_MAPS'),
|
|
17
17
|
mapColorLinear: Shader.arrayUniform('float', 'NUM_MAPS'),
|
|
18
|
+
mapWrap: Shader.arrayUniform('vec2', 'NUM_MAPS'),
|
|
18
19
|
map: Shader.uniform('sampler2DArray')
|
|
19
20
|
},
|
|
20
21
|
defines: {
|
|
@@ -23,7 +24,7 @@ export default createShaderMixin({
|
|
|
23
24
|
main: glsl `
|
|
24
25
|
${materialRowsGlsl()}
|
|
25
26
|
#ifdef HAS_GLTF_ANISOTROPY
|
|
26
|
-
vec2
|
|
27
|
+
vec2 fe(float roughness, float strength) {
|
|
27
28
|
if (strength == 0.0) { return vec2(roughness, 0.0); }
|
|
28
29
|
float u = roughness * roughness;
|
|
29
30
|
float a = u + (1.0 - u) * strength * strength;
|
|
@@ -33,15 +34,15 @@ return vec2(pow((a*a + u*u) * 0.5, 0.25), clamp(1.0 - u/a, 0.0, 1.0));
|
|
|
33
34
|
|
|
34
35
|
#endif
|
|
35
36
|
|
|
36
|
-
vec3
|
|
37
|
+
vec3 oK(vec3 c) {
|
|
37
38
|
return mix(pow(c * 0.9478672986 + 0.0521327014, vec3(2.4)), c * 0.0773993808, vec3(lessThan(c, vec3(0.04045))));
|
|
38
39
|
}
|
|
39
40
|
vec4 fetchMatData(int i) {
|
|
40
|
-
return
|
|
41
|
+
return kG(materialBuffer, i, materialBufferColumns);
|
|
41
42
|
}
|
|
42
43
|
|
|
43
44
|
|
|
44
|
-
float
|
|
45
|
+
float lr(float alpha, int alphaMode, float alphaCutoff) {
|
|
45
46
|
if (alphaMode == ${materialAlphaModeConstants.opaque}) {
|
|
46
47
|
return 1.0;
|
|
47
48
|
}
|
|
@@ -51,7 +52,7 @@ return alpha >= alphaCutoff ? 1.0 : 0.0;
|
|
|
51
52
|
return alpha;
|
|
52
53
|
}
|
|
53
54
|
|
|
54
|
-
float
|
|
55
|
+
float wb(int idx) {
|
|
55
56
|
return fetchMatData(idx * MAT_DATA_SIZE + MAT_ROW_COLOR).w;
|
|
56
57
|
}
|
|
57
58
|
|
|
@@ -62,33 +63,44 @@ return vec2(float(val >> 8), float(val & 0xff) / 255.0);
|
|
|
62
63
|
#ifdef NUM_MAPS
|
|
63
64
|
vec3 decodeMapColor(int index, vec3 c) {
|
|
64
65
|
if (mapColorLinear[index] > 0.5) { return c; }
|
|
65
|
-
return
|
|
66
|
+
return oK(c);
|
|
66
67
|
}
|
|
67
68
|
|
|
68
|
-
vec2
|
|
69
|
+
vec2 kJ(int index) {
|
|
69
70
|
return mapInfo[index].xy;
|
|
70
71
|
}
|
|
71
72
|
|
|
72
|
-
float
|
|
73
|
+
float lk(int index) {
|
|
73
74
|
return floor(mapInfo[index].z);
|
|
74
75
|
}
|
|
75
76
|
|
|
76
|
-
vec2
|
|
77
|
+
vec2 jP(int index) {
|
|
77
78
|
return vec2(fract(mapInfo[index].z), mapInfo[index].w);
|
|
78
79
|
}
|
|
79
80
|
|
|
80
|
-
|
|
81
|
+
float fS(float value, float mode) {
|
|
82
|
+
if (mode < 0.5) return fract(value);
|
|
83
|
+
if (mode < 1.5) return clamp(value, 0.0, 1.0);
|
|
84
|
+
return 1.0 - abs(1.0 - (value - 2.0 * floor(value * 0.5)));
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
vec2 kv(int index, vec2 uv) {
|
|
81
88
|
vec4 transform = mapTransform[index];
|
|
82
|
-
vec2
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
vec2
|
|
87
|
-
vec2
|
|
89
|
+
vec2 value = uv * transform.xy + transform.zw;
|
|
90
|
+
return vec2(fS(value.x, mapWrap[index].x), fS(value.y, mapWrap[index].y));
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
vec2 sq(int index, vec2 uv) {
|
|
94
|
+
vec2 qH = kv(index, uv);
|
|
95
|
+
vec2 jk = 1.0 / vec2(textureSize(map, 0).xy);
|
|
96
|
+
vec2 dZ = jP(index);
|
|
97
|
+
vec2 kn = kJ(index) + jk;
|
|
98
|
+
vec2 oN = dZ - 0.5 * jk;
|
|
99
|
+
vec2 lE = dZ + kn - jk;
|
|
88
100
|
return clamp(
|
|
89
|
-
|
|
101
|
+
oN + qH * kn,
|
|
90
102
|
dZ,
|
|
91
|
-
|
|
103
|
+
lE
|
|
92
104
|
);
|
|
93
105
|
}
|
|
94
106
|
|
|
@@ -96,91 +108,111 @@ vec2 getMapUvSet(int index, vec2 uv, vec2 uv1) {
|
|
|
96
108
|
return mapUvChannel[index] > 0.5 ? uv1 : uv;
|
|
97
109
|
}
|
|
98
110
|
|
|
111
|
+
vec4 eU(int index, ivec2 jm, ivec2 size, ivec2 origin, vec2 iK) {
|
|
112
|
+
ivec2 p = clamp(jm, ivec2(0), size - 1);
|
|
113
|
+
if (iK.x < 0.5) p.x = ((jm.x % size.x) + size.x) % size.x;
|
|
114
|
+
if (iK.y < 0.5) p.y = ((jm.y % size.y) + size.y) % size.y;
|
|
115
|
+
return texelFetch(map, ivec3(origin + p, int(lk(index))), 0);
|
|
116
|
+
}
|
|
117
|
+
|
|
99
118
|
vec4 sampleMap(int index, vec2 uv) {
|
|
100
|
-
|
|
119
|
+
ivec2 size = ivec2(round(kJ(index) * vec2(textureSize(map, 0).xy) + 1.0));
|
|
120
|
+
vec2 eA = kv(index, uv) * vec2(size) - 0.5;
|
|
121
|
+
vec2 iK = mapWrap[index];
|
|
122
|
+
if ((size.x > 1 && iK.x < 0.5 && (eA.x < 0.0 || eA.x > float(size.x - 1))) ||
|
|
123
|
+
(size.y > 1 && iK.y < 0.5 && (eA.y < 0.0 || eA.y > float(size.y - 1)))) {
|
|
124
|
+
ivec2 base = ivec2(floor(eA));
|
|
125
|
+
vec2 weight = fract(eA);
|
|
126
|
+
ivec2 origin = ivec2(round(jP(index) * vec2(textureSize(map, 0).xy) - 0.5));
|
|
127
|
+
return mix(
|
|
128
|
+
mix(eU(index, base, size, origin, iK), eU(index, base + ivec2(1, 0), size, origin, iK), weight.x),
|
|
129
|
+
mix(eU(index, base + ivec2(0, 1), size, origin, iK), eU(index, base + ivec2(1, 1), size, origin, iK), weight.x), weight.y);
|
|
130
|
+
}
|
|
131
|
+
return texture(map, vec3(sq(index, uv), lk(index)));
|
|
101
132
|
}
|
|
102
133
|
#endif
|
|
103
134
|
|
|
104
135
|
|
|
105
136
|
vec2 aK(float roughness, float anisotropy) {
|
|
106
137
|
float alpha = roughness * roughness;
|
|
107
|
-
float
|
|
108
|
-
if (anisotropy == 0.0) { return vec2(max(
|
|
109
|
-
float
|
|
110
|
-
float
|
|
111
|
-
return max(vec2(
|
|
138
|
+
float pg = ROUGHNESS_MIN * ROUGHNESS_MIN;
|
|
139
|
+
if (anisotropy == 0.0) { return vec2(max(pg, alpha)); }
|
|
140
|
+
float di = 1.0 - anisotropy;
|
|
141
|
+
float sh = alpha * sqrt(2.0 / (1.0 + di * di));
|
|
142
|
+
return max(vec2(pg), vec2(sh, di * sh));
|
|
112
143
|
}
|
|
113
144
|
|
|
114
145
|
vec4 bv(int i);
|
|
115
|
-
vec3
|
|
146
|
+
vec3 kI(int instanceIndex) {
|
|
116
147
|
if (instanceIndex < 0) return vec3(1.0);
|
|
117
148
|
return bv(instanceIndex * ${INSTANCE_VEC4_STRIDE + ''} + 9).rgb;
|
|
118
149
|
}
|
|
119
150
|
|
|
120
|
-
void
|
|
151
|
+
void eX(
|
|
121
152
|
inout J mat,
|
|
122
153
|
int materialIndex,
|
|
123
154
|
vec2 uv,
|
|
124
155
|
vec2 uv1,
|
|
125
|
-
int instanceIndex
|
|
156
|
+
int instanceIndex,
|
|
157
|
+
vec3 vertexColor
|
|
126
158
|
) {
|
|
127
159
|
int i = materialIndex * MAT_DATA_SIZE;
|
|
128
|
-
vec4
|
|
129
|
-
vec4
|
|
130
|
-
vec4
|
|
131
|
-
vec4
|
|
132
|
-
vec4
|
|
160
|
+
vec4 oV = fetchMatData(i + MAT_ROW_COLOR);
|
|
161
|
+
vec4 hh = fetchMatData(i + MAT_ROW_ROUGHNESS_NORMAL);
|
|
162
|
+
vec4 gn = fetchMatData(i + MAT_ROW_METALLIC_MAPS);
|
|
163
|
+
vec4 hI = fetchMatData(i + MAT_ROW_EMISSION);
|
|
164
|
+
vec4 gY = fetchMatData(i + MAT_ROW_IOR_TRANSMISSION);
|
|
133
165
|
vec4 misc = fetchMatData(i + MAT_ROW_MISC);
|
|
134
|
-
vec4
|
|
135
|
-
vec4
|
|
136
|
-
vec4
|
|
166
|
+
vec4 nC = fetchMatData(i + MAT_ROW_ALPHA_FILM);
|
|
167
|
+
vec4 lS = fetchMatData(i + MAT_ROW_BASE_CONTROLS);
|
|
168
|
+
vec4 oZ = fetchMatData(i + MAT_ROW_SPECULAR_FUZZ);
|
|
137
169
|
vec4 subsurface = fetchMatData(i + MAT_ROW_SUBSURFACE);
|
|
138
|
-
vec4
|
|
139
|
-
vec4
|
|
140
|
-
vec4
|
|
141
|
-
vec4
|
|
142
|
-
vec4
|
|
170
|
+
vec4 wq = fetchMatData(i + MAT_ROW_FUZZ);
|
|
171
|
+
vec4 vL = fetchMatData(i + MAT_ROW_COAT);
|
|
172
|
+
vec4 lT = fetchMatData(i + MAT_ROW_COAT_CONTROLS);
|
|
173
|
+
vec4 mY = fetchMatData(i + MAT_ROW_FILM_DISPERSION);
|
|
174
|
+
vec4 nB = fetchMatData(i + MAT_ROW_STANDALONE_MAPS);
|
|
143
175
|
int mapAlphaUsage = int(misc.a);
|
|
144
176
|
|
|
145
|
-
mat.baseColor =
|
|
146
|
-
mat.materialType = int(
|
|
147
|
-
mat.specularRoughness =
|
|
148
|
-
mat.baseMetalness =
|
|
149
|
-
mat.specularAnisotropy = clamp(
|
|
150
|
-
mat.emission =
|
|
177
|
+
mat.baseColor = oV.rgb;
|
|
178
|
+
mat.materialType = int(oV.w);
|
|
179
|
+
mat.specularRoughness = hh.x;
|
|
180
|
+
mat.baseMetalness = gn.x;
|
|
181
|
+
mat.specularAnisotropy = clamp(gn.y, 0.0, 1.0);
|
|
182
|
+
mat.emission = hI.rgb;
|
|
151
183
|
mat.inside = false;
|
|
152
|
-
mat.specularIor =
|
|
153
|
-
mat.transmissionWeight =
|
|
184
|
+
mat.specularIor = gY.x;
|
|
185
|
+
mat.transmissionWeight = gY.y;
|
|
154
186
|
#ifdef HAS_MEDIUM
|
|
155
|
-
mat.mediumType = int(
|
|
187
|
+
mat.mediumType = int(gY.z);
|
|
156
188
|
#else
|
|
157
189
|
mat.mediumType = 0;
|
|
158
190
|
#endif
|
|
159
|
-
mat.thinWalled =
|
|
191
|
+
mat.thinWalled = gY.w > 0.5;
|
|
160
192
|
mat.bevel = misc.r;
|
|
161
193
|
mat.transmissionDispersionScale = misc.g;
|
|
162
|
-
mat.dispersionAbbeNumber = max(
|
|
194
|
+
mat.dispersionAbbeNumber = max(mY.y, 1e-6);
|
|
163
195
|
mat.thinFilmThickness = misc.b;
|
|
164
|
-
mat.thinFilmIor =
|
|
165
|
-
mat.thinFilmWeight = clamp(
|
|
196
|
+
mat.thinFilmIor = nC.b;
|
|
197
|
+
mat.thinFilmWeight = clamp(mY.x, 0.0, 1.0);
|
|
166
198
|
|
|
167
199
|
mat.thinFilmThickness *= 1000.0;
|
|
168
|
-
mat.baseWeight = clamp(
|
|
169
|
-
mat.diffuseRoughness = clamp(
|
|
170
|
-
mat.specularWeight = max(0.0,
|
|
171
|
-
mat.subsurfaceWeight = clamp(
|
|
172
|
-
mat.specularColor = max(
|
|
173
|
-
mat.fuzzWeight = clamp(
|
|
200
|
+
mat.baseWeight = clamp(lS.x, 0.0, 1.0);
|
|
201
|
+
mat.diffuseRoughness = clamp(lS.y, 0.0, 1.0);
|
|
202
|
+
mat.specularWeight = max(0.0, lS.z);
|
|
203
|
+
mat.subsurfaceWeight = clamp(lS.w, 0.0, 1.0);
|
|
204
|
+
mat.specularColor = max(oZ.rgb, vec3(0.0));
|
|
205
|
+
mat.fuzzWeight = clamp(oZ.w, 0.0, 1.0);
|
|
174
206
|
mat.subsurfaceColor = max(subsurface.rgb, vec3(0.0));
|
|
175
207
|
mat.transmissionColor = max(fetchMatData(i + MAT_ROW_TRANSMISSION_COLOR).rgb, vec3(0.0));
|
|
176
|
-
mat.fuzzColor = max(
|
|
177
|
-
mat.fuzzRoughness = clamp(
|
|
178
|
-
mat.coatColor = max(
|
|
179
|
-
mat.coatWeight = clamp(
|
|
180
|
-
mat.coatRoughness = clamp(
|
|
181
|
-
mat.coatAnisotropy = clamp(
|
|
182
|
-
mat.coatIor = max(
|
|
183
|
-
mat.coatDarkening = clamp(
|
|
208
|
+
mat.fuzzColor = max(wq.rgb, vec3(0.0));
|
|
209
|
+
mat.fuzzRoughness = clamp(wq.w, 0.0, 1.0);
|
|
210
|
+
mat.coatColor = max(vL.rgb, vec3(0.0));
|
|
211
|
+
mat.coatWeight = clamp(vL.w, 0.0, 1.0);
|
|
212
|
+
mat.coatRoughness = clamp(lT.x, ROUGHNESS_MIN, 1.0);
|
|
213
|
+
mat.coatAnisotropy = clamp(lT.y, 0.0, 1.0);
|
|
214
|
+
mat.coatIor = max(lT.z, 1.0);
|
|
215
|
+
mat.coatDarkening = clamp(lT.w, 0.0, 1.0);
|
|
184
216
|
|
|
185
217
|
#ifdef HAS_MEDIUM
|
|
186
218
|
mat.mediumExtinction = max(fetchMatData(i + MAT_ROW_MEDIUM_EXTINCTION).rgb, vec3(0.0));
|
|
@@ -191,48 +223,48 @@ mat.mediumType = max(max(mat.mediumExtinction.x, mat.mediumExtinction.y), mat.me
|
|
|
191
223
|
|
|
192
224
|
|
|
193
225
|
#ifdef HAS_ALPHA
|
|
194
|
-
mat.alpha =
|
|
226
|
+
mat.alpha = nC.r;
|
|
195
227
|
#else
|
|
196
228
|
mat.alpha = 1.0;
|
|
197
229
|
#endif
|
|
198
230
|
|
|
199
231
|
#ifdef NUM_DIFFUSE_MAPS
|
|
200
|
-
int diffuseMapIndex = int(
|
|
232
|
+
int diffuseMapIndex = int(gn.z);
|
|
201
233
|
if (diffuseMapIndex >= 0) {
|
|
202
|
-
vec4
|
|
234
|
+
vec4 ob = sampleMap(
|
|
203
235
|
diffuseMapIndex, getMapUvSet(diffuseMapIndex, uv, uv1)
|
|
204
236
|
);
|
|
205
237
|
|
|
206
238
|
|
|
207
|
-
mat.baseColor *= decodeMapColor(diffuseMapIndex,
|
|
239
|
+
mat.baseColor *= decodeMapColor(diffuseMapIndex, ob.rgb);
|
|
208
240
|
|
|
209
241
|
|
|
210
242
|
if (mapAlphaUsage == ${mapAlphaUsageConstants.transmission + ''}) {
|
|
211
|
-
mat.transmissionWeight = 1.0 -
|
|
243
|
+
mat.transmissionWeight = 1.0 - ob.a;
|
|
212
244
|
}
|
|
213
245
|
else if (mapAlphaUsage == ${mapAlphaUsageConstants.alpha + ''}) {
|
|
214
|
-
mat.alpha *=
|
|
246
|
+
mat.alpha *= ob.a;
|
|
215
247
|
}
|
|
216
248
|
}
|
|
217
249
|
#endif
|
|
218
250
|
|
|
219
251
|
${simpleTextureSample('alphaMap', 'glsl')}
|
|
220
252
|
|
|
221
|
-
mat.alpha =
|
|
222
|
-
mat.alpha, int(fetchMatData(i + MAT_ROW_ALPHA).w),
|
|
253
|
+
mat.alpha = lr(
|
|
254
|
+
mat.alpha, int(fetchMatData(i + MAT_ROW_ALPHA).w), nB.w
|
|
223
255
|
);
|
|
224
256
|
|
|
225
257
|
${simpleTextureSample('transmissionMap', 'glsl')}
|
|
226
258
|
|
|
227
259
|
#ifdef NUM_METALLIC_ROUGHNESS_MAPS
|
|
228
|
-
int metallicRoughnessMapIndex = int(
|
|
260
|
+
int metallicRoughnessMapIndex = int(gn.w);
|
|
229
261
|
if (metallicRoughnessMapIndex >= 0) {
|
|
230
|
-
vec4
|
|
262
|
+
vec4 fN = sampleMap(
|
|
231
263
|
metallicRoughnessMapIndex,
|
|
232
264
|
getMapUvSet(metallicRoughnessMapIndex, uv, uv1)
|
|
233
265
|
);
|
|
234
|
-
mat.baseMetalness *=
|
|
235
|
-
mat.specularRoughness *=
|
|
266
|
+
mat.baseMetalness *= fN.b;
|
|
267
|
+
mat.specularRoughness *= fN.g;
|
|
236
268
|
}
|
|
237
269
|
#endif
|
|
238
270
|
|
|
@@ -241,7 +273,7 @@ ${simpleTextureSample('roughnessMap', 'glsl')}
|
|
|
241
273
|
${simpleTextureSample('metalnessMap', 'glsl')}
|
|
242
274
|
|
|
243
275
|
#ifdef NUM_EMISSIVE_MAPS
|
|
244
|
-
int emissiveMapIndex = int(
|
|
276
|
+
int emissiveMapIndex = int(hI.w);
|
|
245
277
|
if (emissiveMapIndex >= 0) {
|
|
246
278
|
vec3 emissive = sampleMap(
|
|
247
279
|
emissiveMapIndex, getMapUvSet(emissiveMapIndex, uv, uv1)
|
|
@@ -251,12 +283,12 @@ mat.emission *= decodeMapColor(emissiveMapIndex, emissive);
|
|
|
251
283
|
#endif
|
|
252
284
|
|
|
253
285
|
#ifdef NUM_COAT_WEIGHT_MAPS
|
|
254
|
-
int
|
|
255
|
-
if (
|
|
256
|
-
float
|
|
257
|
-
|
|
286
|
+
int hQ = int(fetchMatData(i + MAT_ROW_LAYER_MAPS).x);
|
|
287
|
+
if (hQ >= 0 && mat.materialType == 0) {
|
|
288
|
+
float qw = clamp(vL.w, 0.0, 1.0) * sampleMap(
|
|
289
|
+
hQ, getMapUvSet(hQ, uv, uv1)
|
|
258
290
|
).r;
|
|
259
|
-
mat.emission *= mix(vec3(1.0), sqrt(max(
|
|
291
|
+
mat.emission *= mix(vec3(1.0), sqrt(max(vL.rgb, vec3(0.0))), qw);
|
|
260
292
|
}
|
|
261
293
|
#endif
|
|
262
294
|
|
|
@@ -277,29 +309,29 @@ ${simpleTextureSample('specularWeightMap', 'glsl')}
|
|
|
277
309
|
|
|
278
310
|
${simpleTextureSample('specularColorMap', 'glsl')}
|
|
279
311
|
|
|
280
|
-
vec4
|
|
312
|
+
vec4 kW = fetchMatData(i + MAT_ROW_DIRECTION_NORMAL);
|
|
281
313
|
mat.anisotropyDirection = vec2(1.0, 0.0);
|
|
282
|
-
mat.anisotropyDirectionEnabled =
|
|
314
|
+
mat.anisotropyDirectionEnabled = kW.y != 0.0;
|
|
283
315
|
mat.coatAnisotropyRotation = fetchMatData(i + MAT_ROW_FILM_TEXTURE).x;
|
|
284
316
|
#ifdef NUM_ANISOTROPY_MAPS
|
|
285
|
-
if (
|
|
286
|
-
int index = int(
|
|
287
|
-
vec4
|
|
288
|
-
mat.specularAnisotropy *=
|
|
289
|
-
vec2 direction =
|
|
317
|
+
if (kW.x >= 0.0) {
|
|
318
|
+
int index = int(kW.x);
|
|
319
|
+
vec4 eA = sampleMap(index, getMapUvSet(index, uv, uv1));
|
|
320
|
+
mat.specularAnisotropy *= eA.b;
|
|
321
|
+
vec2 direction = eA.rg * 2.0 - 1.0;
|
|
290
322
|
if (dot(direction, direction) > 1e-4) mat.anisotropyDirection = normalize(direction);
|
|
291
323
|
mat.anisotropyDirectionEnabled = true;
|
|
292
324
|
}
|
|
293
325
|
#endif
|
|
294
326
|
#ifdef HAS_GLTF_ANISOTROPY
|
|
295
327
|
if (fetchMatData(i + MAT_ROW_FILM_TEXTURE).y > 0.5 && mat.specularAnisotropy > 0.0) {
|
|
296
|
-
vec2
|
|
297
|
-
mat.specularRoughness =
|
|
298
|
-
mat.specularAnisotropy =
|
|
328
|
+
vec2 sF = fe(clamp(mat.specularRoughness, 0.0, 1.0), mat.specularAnisotropy);
|
|
329
|
+
mat.specularRoughness = sF.x;
|
|
330
|
+
mat.specularAnisotropy = sF.y;
|
|
299
331
|
}
|
|
300
332
|
#endif
|
|
301
333
|
if (mat.anisotropyDirectionEnabled) {
|
|
302
|
-
float theta =
|
|
334
|
+
float theta = kW.y;
|
|
303
335
|
vec2 d = mat.anisotropyDirection;
|
|
304
336
|
mat.anisotropyDirection = vec2(cos(theta)*d.x - sin(theta)*d.y, sin(theta)*d.x + cos(theta)*d.y);
|
|
305
337
|
}
|
|
@@ -307,14 +339,14 @@ mat.anisotropyDirection = vec2(cos(theta)*d.x - sin(theta)*d.y, sin(theta)*d.x +
|
|
|
307
339
|
|
|
308
340
|
|
|
309
341
|
if (mat.coatWeight > 0.0 && mat.coatRoughness > 0.0) {
|
|
310
|
-
float
|
|
311
|
-
float
|
|
342
|
+
float hM = mat.specularRoughness * mat.specularRoughness;
|
|
343
|
+
float hN = mat.coatRoughness * mat.coatRoughness;
|
|
312
344
|
mat.specularRoughness = mix(mat.specularRoughness,
|
|
313
|
-
pow(min(1.0,
|
|
345
|
+
pow(min(1.0, hM * hM + 2.0 * hN * hN), 0.25), mat.coatWeight);
|
|
314
346
|
}
|
|
315
|
-
vec3
|
|
316
|
-
mat.baseColor *=
|
|
317
|
-
if (mat.materialType == UNLIT) mat.emission *=
|
|
347
|
+
vec3 color = kI(instanceIndex) * vertexColor;
|
|
348
|
+
mat.baseColor *= color;
|
|
349
|
+
if (mat.materialType == UNLIT) mat.emission *= color;
|
|
318
350
|
|
|
319
351
|
mat.specularRoughness = clamp(mat.specularRoughness, ROUGHNESS_MIN, 1.0);
|
|
320
352
|
mat.baseMetalness = clamp(mat.baseMetalness, 0.0, 1.0);
|
|
@@ -324,40 +356,40 @@ mat.alphaY = specularAlpha.y;
|
|
|
324
356
|
}
|
|
325
357
|
|
|
326
358
|
#if defined(NUM_NORMAL_MAPS)
|
|
327
|
-
vec3
|
|
359
|
+
vec3 om(int materialIndex, vec2 uv, vec3 normal, vec3 dp1, vec3 dp2, vec2 od, vec2 oe) {
|
|
328
360
|
int i = materialIndex * MAT_DATA_SIZE;
|
|
329
|
-
vec4
|
|
330
|
-
int normalMapIndex = int(
|
|
361
|
+
vec4 hh = fetchMatData(i + MAT_ROW_ROUGHNESS_NORMAL);
|
|
362
|
+
int normalMapIndex = int(hh.y);
|
|
331
363
|
if (normalMapIndex >= 0) {
|
|
332
364
|
|
|
333
365
|
|
|
334
366
|
|
|
335
|
-
vec3
|
|
336
|
-
vec3
|
|
337
|
-
vec3 dpdu =
|
|
338
|
-
vec3
|
|
339
|
-
float
|
|
340
|
-
if (
|
|
341
|
-
float
|
|
342
|
-
dpdu *=
|
|
343
|
-
|
|
367
|
+
vec3 qW = cross(dp2, normal);
|
|
368
|
+
vec3 qV = cross(normal, dp1);
|
|
369
|
+
vec3 dpdu = qW * od.x + qV * oe.x;
|
|
370
|
+
vec3 sn = qW * od.y + qV * oe.y;
|
|
371
|
+
float dT = max(dot(dpdu, dpdu), dot(sn, sn));
|
|
372
|
+
if (dT > 1e-12) {
|
|
373
|
+
float sz = inversesqrt(dT);
|
|
374
|
+
dpdu *= sz;
|
|
375
|
+
sn *= sz;
|
|
344
376
|
}
|
|
345
377
|
else {
|
|
346
378
|
|
|
347
379
|
|
|
348
380
|
|
|
349
|
-
vec3
|
|
381
|
+
vec3 nt = abs(normal.z) < 0.999
|
|
350
382
|
? vec3(0.0, 0.0, 1.0)
|
|
351
383
|
: vec3(0.0, 1.0, 0.0);
|
|
352
|
-
dpdu = normalize(cross(
|
|
353
|
-
|
|
384
|
+
dpdu = normalize(cross(nt, normal));
|
|
385
|
+
sn = cross(normal, dpdu);
|
|
354
386
|
}
|
|
355
387
|
|
|
356
388
|
vec3 n = 2.0 * sampleMap(normalMapIndex, uv).rgb - 1.0;
|
|
357
|
-
n.xy *=
|
|
389
|
+
n.xy *= hh.zw;
|
|
358
390
|
n = normalize(n);
|
|
359
391
|
|
|
360
|
-
mat3 tbn = mat3(dpdu,
|
|
392
|
+
mat3 tbn = mat3(dpdu, sn, normal);
|
|
361
393
|
|
|
362
394
|
return normalize(tbn * n);
|
|
363
395
|
} else {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"materialBuffer.glsl.js","sourceRoot":"","sources":["../../../../src/renderer/glsl/chunks/materialBuffer.glsl.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,mBAAmB,EAAE,qBAAqB,EAAE,MAAM,+BAA+B,CAAC;AAC3F,OAAO,EAAE,gBAAgB,EAAE,MAAM,yBAAyB,CAAC;AAC3D,OAAO,EAAE,0BAA0B,EAAE,MAAM,mCAAmC,CAAC;AAC/E,OAAO,EAAE,oBAAoB,EAAE,MAAM,mBAAmB,CAAC;AACzD,OAAO,EAAE,sBAAsB,EAAE,MAAM,4BAA4B,CAAC;AACpE,qDAAqD;AACrD,sDAAsD;AACtD,kFAAkF;AAElF,OAAO,EAAE,iBAAiB,EAAE,IAAI,EAAE,MAAM,EAAE,MAAM,iBAAiB,CAAC;AAElE,eAAe,iBAAiB,CAAC;IAC/B,QAAQ,EAAE;QACR,cAAc,EAAE,MAAM,CAAC,OAAO,CAAC,WAAW,CAAC;QAC3C,qBAAqB,EAAE,MAAM,CAAC,OAAO,CAAC,KAAK,EAAE,CAAC,CAAC;QAC/C,OAAO,EAAE,MAAM,CAAC,YAAY,CAAC,MAAM,EAAE,UAAU,CAAC;QAChD,YAAY,EAAE,MAAM,CAAC,YAAY,CAAC,MAAM,EAAE,UAAU,CAAC;QACrD,YAAY,EAAE,MAAM,CAAC,YAAY,CAAC,OAAO,EAAE,UAAU,CAAC;QACtD,cAAc,EAAE,MAAM,CAAC,YAAY,CAAC,OAAO,EAAE,UAAU,CAAC;QACxD,GAAG,EAAE,MAAM,CAAC,OAAO,CAAC,gBAAgB,CAAC;KACtC;IACD,OAAO,EAAE;QACP,aAAa,EAAE,CAAC;KACjB;IACD,IAAI,EAAE,IAAI,CAAA;EACV,gBAAgB,EAAE;;;;;;;;;;;;;;;;;;;;;mBAqBC,0BAA0B,CAAC,MAAM;;;mBAGjC,0BAA0B,CAAC,IAAI;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;4BAqEhB,oBAAoB,GAAG,EAAE;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;uBA6FhC,sBAAsB,CAAC,YAAY,GAAG,EAAE;;;4BAGnC,sBAAsB,CAAC,KAAK,GAAG,EAAE;;;;;;EAM/D,mBAAmB,CAAC,UAAU,EAAE,MAAM,CAAC;;;;;;EAMvC,mBAAmB,CAAC,iBAAiB,EAAE,MAAM,CAAC;;;;;;;;;;;;;;EAc9C,mBAAmB,CAAC,cAAc,EAAE,MAAM,CAAC;;EAE3C,mBAAmB,CAAC,cAAc,EAAE,MAAM,CAAC;;;;;;;;;;;;;;;;;;;;;;EAsB3C,qBAAqB,CAAC,MAAM,CAAC;;EAE7B,mBAAmB,CAAC,eAAe,EAAE,MAAM,CAAC;;;;;EAK5C,mBAAmB,CAAC,kBAAkB,EAAE,MAAM,CAAC;;EAE/C,mBAAmB,CAAC,cAAc,EAAE,MAAM,CAAC;;EAE3C,mBAAmB,CAAC,kBAAkB,EAAE,MAAM,CAAC;;EAE/C,mBAAmB,CAAC,mBAAmB,EAAE,MAAM,CAAC;;EAEhD,mBAAmB,CAAC,kBAAkB,EAAE,MAAM,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CA2FlD;CACA,CAAC,CAAC","sourcesContent":["import { simpleTextureSample, thinFilmTextureSample } from '../../materialTextureSlots.js';\nimport { materialRowsGlsl } from '../../materialLayout.js';\nimport { materialAlphaModeConstants } from '../../../scene/OpenPBRMaterial.js';\nimport { INSTANCE_VEC4_STRIDE } from '../../bvhAccel.js';\nimport { mapAlphaUsageConstants } from '../../materialConstants.js';\n// Portions adapted from ray-tracing-renderer@0.10.15\n// (https://github.com/hoverinc/ray-tracing-renderer).\n// Copyright (c) 2019 HOVER, MIT license; see LICENSES/RayTracingRenderer-MIT.txt.\n\nimport { createShaderMixin, glsl, Shader } from '../../shader.js';\n\nexport default createShaderMixin({\n uniforms: {\n materialBuffer: Shader.uniform('sampler2D'),\n materialBufferColumns: Shader.uniform('int', 1),\n mapInfo: Shader.arrayUniform('vec4', 'NUM_MAPS'),\n mapTransform: Shader.arrayUniform('vec4', 'NUM_MAPS'),\n mapUvChannel: Shader.arrayUniform('float', 'NUM_MAPS'),\n mapColorLinear: Shader.arrayUniform('float', 'NUM_MAPS'),\n map: Shader.uniform('sampler2DArray')\n },\n defines: {\n NUM_MATERIALS: 1\n },\n main: glsl`\n${materialRowsGlsl()}\n#ifdef HAS_GLTF_ANISOTROPY\nvec2 gltf_anisotropy_to_openpbr(float roughness, float strength) {\n if (strength == 0.0) { return vec2(roughness, 0.0); }\n float u = roughness * roughness;\n float a = u + (1.0 - u) * strength * strength;\n if (a == 0.0) { return vec2(0.0); }\n return vec2(pow((a*a + u*u) * 0.5, 0.25), clamp(1.0 - u/a, 0.0, 1.0));\n}\n\n#endif\n\nvec3 sRGBToLinear(vec3 c) {\n return mix(pow(c * 0.9478672986 + 0.0521327014, vec3(2.4)), c * 0.0773993808, vec3(lessThan(c, vec3(0.04045))));\n}\nvec4 fetchMatData(int i) {\n return fetchData(materialBuffer, i, materialBufferColumns);\n}\n\n// Shared by surface evaluation and shadow occlusion, after texture factors.\nfloat resolveMaterialAlpha(float alpha, int alphaMode, float alphaCutoff) {\n if (alphaMode == ${materialAlphaModeConstants.opaque}) {\n return 1.0;\n }\n if (alphaMode == ${materialAlphaModeConstants.mask}) {\n return alpha >= alphaCutoff ? 1.0 : 0.0;\n }\n return alpha;\n}\n\nfloat getMatType(int idx) {\n return fetchMatData(idx * MAT_DATA_SIZE + MAT_ROW_COLOR).w;\n}\n\nvec2 unpackMaterialIndex(int val) {\n return vec2(float(val >> 8), float(val & 0xff) / 255.0);\n}\n\n#ifdef NUM_MAPS\nvec3 decodeMapColor(int index, vec3 c) {\n if (mapColorLinear[index] > 0.5) { return c; }\n return sRGBToLinear(c);\n}\n\nvec2 getMapSize(int index) {\n return mapInfo[index].xy;\n}\n\nfloat getMapLayer(int index) {\n return floor(mapInfo[index].z);\n}\n\nvec2 getMapOffset(int index) {\n return vec2(fract(mapInfo[index].z), mapInfo[index].w);\n}\n\nvec2 getMapUV(int index, vec2 uv) {\n vec4 transform = mapTransform[index];\n vec2 repeatedUv = fract(uv * transform.xy + transform.zw);\n vec2 atlasTexel = 1.0 / vec2(textureSize(map, 0).xy);\n vec2 firstTexelCenter = getMapOffset(index);\n vec2 sourceExtent = getMapSize(index) + atlasTexel;\n vec2 sourceOrigin = firstTexelCenter - 0.5 * atlasTexel;\n vec2 lastTexelCenter = firstTexelCenter + sourceExtent - atlasTexel;\n return clamp(\n sourceOrigin + repeatedUv * sourceExtent,\n firstTexelCenter,\n lastTexelCenter\n );\n}\n\nvec2 getMapUvSet(int index, vec2 uv, vec2 uv1) {\n return mapUvChannel[index] > 0.5 ? uv1 : uv;\n}\n\nvec4 sampleMap(int index, vec2 uv) {\n return texture(map, vec3(getMapUV(index, uv), getMapLayer(index)));\n}\n#endif\n\n// OpenPBR 1.1.1: RMS-preserving GGX anisotropy, shared by base and coat.\nvec2 openpbr_roughness_to_alpha(float roughness, float anisotropy) {\n float alpha = roughness * roughness;\n float alphaMin = ROUGHNESS_MIN * ROUGHNESS_MIN;\n if (anisotropy == 0.0) { return vec2(max(alphaMin, alpha)); }\n float complement = 1.0 - anisotropy;\n float alphaT = alpha * sqrt(2.0 / (1.0 + complement * complement));\n return max(vec2(alphaMin), vec2(alphaT, complement * alphaT));\n}\n\nvec4 fetchIns(int i);\nvec3 getInstanceColor(int instanceIndex) {\n if (instanceIndex < 0) return vec3(1.0);\n return fetchIns(instanceIndex * ${INSTANCE_VEC4_STRIDE + ''} + 9).rgb;\n}\n\nvoid getMaterial(\n inout OpenPbrResolvedMaterial mat,\n int materialIndex,\n vec2 uv,\n vec2 uv1,\n int instanceIndex\n) {\n int i = materialIndex * MAT_DATA_SIZE;\n vec4 colorAndMatType = fetchMatData(i + MAT_ROW_COLOR);\n vec4 roughnessAndNormal = fetchMatData(i + MAT_ROW_ROUGHNESS_NORMAL);\n vec4 metallicAndMapIndex = fetchMatData(i + MAT_ROW_METALLIC_MAPS);\n vec4 emissionAndEmissiveMapIndex = fetchMatData(i + MAT_ROW_EMISSION);\n vec4 iorAndTransmission = fetchMatData(i + MAT_ROW_IOR_TRANSMISSION);\n vec4 misc = fetchMatData(i + MAT_ROW_MISC);\n vec4 alphaAndThinFilm = fetchMatData(i + MAT_ROW_ALPHA_FILM);\n vec4 baseControls = fetchMatData(i + MAT_ROW_BASE_CONTROLS);\n vec4 specularAndFuzz = fetchMatData(i + MAT_ROW_SPECULAR_FUZZ);\n vec4 subsurface = fetchMatData(i + MAT_ROW_SUBSURFACE);\n vec4 fuzz = fetchMatData(i + MAT_ROW_FUZZ);\n vec4 coat = fetchMatData(i + MAT_ROW_COAT);\n vec4 coatControls = fetchMatData(i + MAT_ROW_COAT_CONTROLS);\n vec4 filmAndDispersion = fetchMatData(i + MAT_ROW_FILM_DISPERSION);\n vec4 standaloneMetalRoughMaps = fetchMatData(i + MAT_ROW_STANDALONE_MAPS);\n int mapAlphaUsage = int(misc.a);\n\n mat.baseColor = colorAndMatType.rgb;\n mat.materialType = int(colorAndMatType.w);\n mat.specularRoughness = roughnessAndNormal.x;\n mat.baseMetalness = metallicAndMapIndex.x;\n mat.specularAnisotropy = clamp(metallicAndMapIndex.y, 0.0, 1.0);\n mat.emission = emissionAndEmissiveMapIndex.rgb;\n mat.inside = false;\n mat.specularIor = iorAndTransmission.x;\n mat.transmissionWeight = iorAndTransmission.y;\n#ifdef HAS_MEDIUM\n mat.mediumType = int(iorAndTransmission.z);\n#else\n mat.mediumType = 0;\n#endif\n mat.thinWalled = iorAndTransmission.w > 0.5;\n mat.bevel = misc.r;\n mat.transmissionDispersionScale = misc.g;\n mat.dispersionAbbeNumber = max(filmAndDispersion.y, 1e-6);\n mat.thinFilmThickness = misc.b;\n mat.thinFilmIor = alphaAndThinFilm.b;\n mat.thinFilmWeight = clamp(filmAndDispersion.x, 0.0, 1.0);\n // OpenPBR specifies micrometres; the interference routine uses nanometres.\n mat.thinFilmThickness *= 1000.0;\n mat.baseWeight = clamp(baseControls.x, 0.0, 1.0);\n mat.diffuseRoughness = clamp(baseControls.y, 0.0, 1.0);\n mat.specularWeight = max(0.0, baseControls.z);\n mat.subsurfaceWeight = clamp(baseControls.w, 0.0, 1.0);\n mat.specularColor = max(specularAndFuzz.rgb, vec3(0.0));\n mat.fuzzWeight = clamp(specularAndFuzz.w, 0.0, 1.0);\n mat.subsurfaceColor = max(subsurface.rgb, vec3(0.0));\n mat.transmissionColor = max(fetchMatData(i + MAT_ROW_TRANSMISSION_COLOR).rgb, vec3(0.0));\n mat.fuzzColor = max(fuzz.rgb, vec3(0.0));\n mat.fuzzRoughness = clamp(fuzz.w, 0.0, 1.0);\n mat.coatColor = max(coat.rgb, vec3(0.0));\n mat.coatWeight = clamp(coat.w, 0.0, 1.0);\n mat.coatRoughness = clamp(coatControls.x, ROUGHNESS_MIN, 1.0);\n mat.coatAnisotropy = clamp(coatControls.y, 0.0, 1.0);\n mat.coatIor = max(coatControls.z, 1.0);\n mat.coatDarkening = clamp(coatControls.w, 0.0, 1.0);\n\n#ifdef HAS_MEDIUM\n mat.mediumExtinction = max(fetchMatData(i + MAT_ROW_MEDIUM_EXTINCTION).rgb, vec3(0.0));\n mat.mediumAnisotropy = clamp(fetchMatData(i + MAT_ROW_MEDIUM_EXTINCTION).a, -1.0, 1.0);\n mat.mediumScattering = max(fetchMatData(i + MAT_ROW_MEDIUM_SCATTERING).rgb, vec3(0.0));\n mat.mediumType = max(max(mat.mediumExtinction.x, mat.mediumExtinction.y), mat.mediumExtinction.z) > 0.0 ? 1 : 0;\n#endif\n\n\n#ifdef HAS_ALPHA\n mat.alpha = alphaAndThinFilm.r;\n#else\n mat.alpha = 1.0;\n#endif\n\n #ifdef NUM_DIFFUSE_MAPS\n int diffuseMapIndex = int(metallicAndMapIndex.z);\n if (diffuseMapIndex >= 0) {\n vec4 diffuse = sampleMap(\n diffuseMapIndex, getMapUvSet(diffuseMapIndex, uv, uv1)\n );\n // Material factors from THREE / glTF are already linear. Only color\n // textures need decoding from their stored sRGB values.\n mat.baseColor *= decodeMapColor(diffuseMapIndex, diffuse.rgb);\n\n // Map alpha to transmission\n if (mapAlphaUsage == ${mapAlphaUsageConstants.transmission + ''}) {\n mat.transmissionWeight = 1.0 - diffuse.a;\n }\n else if (mapAlphaUsage == ${mapAlphaUsageConstants.alpha + ''}) {\n mat.alpha *= diffuse.a;\n }\n }\n #endif\n\n ${simpleTextureSample('alphaMap', 'glsl')}\n\n mat.alpha = resolveMaterialAlpha(\n mat.alpha, int(fetchMatData(i + MAT_ROW_ALPHA).w), standaloneMetalRoughMaps.w\n );\n\n ${simpleTextureSample('transmissionMap', 'glsl')}\n\n #ifdef NUM_METALLIC_ROUGHNESS_MAPS\n int metallicRoughnessMapIndex = int(metallicAndMapIndex.w);\n if (metallicRoughnessMapIndex >= 0) {\n vec4 metallicRoughness = sampleMap(\n metallicRoughnessMapIndex,\n getMapUvSet(metallicRoughnessMapIndex, uv, uv1)\n );\n mat.baseMetalness *= metallicRoughness.b;\n mat.specularRoughness *= metallicRoughness.g;\n }\n #endif\n\n ${simpleTextureSample('roughnessMap', 'glsl')}\n\n ${simpleTextureSample('metalnessMap', 'glsl')}\n\n #ifdef NUM_EMISSIVE_MAPS\n int emissiveMapIndex = int(emissionAndEmissiveMapIndex.w);\n if (emissiveMapIndex >= 0) {\n vec3 emissive = sampleMap(\n emissiveMapIndex, getMapUvSet(emissiveMapIndex, uv, uv1)\n ).rgb;\n mat.emission *= decodeMapColor(emissiveMapIndex, emissive);\n }\n #endif\n\n #ifdef NUM_COAT_WEIGHT_MAPS\n int emissionCoatMapIndex = int(fetchMatData(i + MAT_ROW_LAYER_MAPS).x);\n if (emissionCoatMapIndex >= 0 && mat.materialType == 0) {\n float emissionCoatWeight = clamp(coat.w, 0.0, 1.0) * sampleMap(\n emissionCoatMapIndex, getMapUvSet(emissionCoatMapIndex, uv, uv1)\n ).r;\n mat.emission *= mix(vec3(1.0), sqrt(max(coat.rgb, vec3(0.0))), emissionCoatWeight);\n }\n #endif\n\n ${thinFilmTextureSample('glsl')}\n\n ${simpleTextureSample('coatWeightMap', 'glsl')}\n#ifdef NUM_COAT_NORMAL_MAPS\n mat.coatNormalEnabled = fetchMatData(i + MAT_ROW_LAYER_MAPS).z >= 0.0 && mat.coatWeight > 0.0;\n#endif\n\n ${simpleTextureSample('coatRoughnessMap', 'glsl')}\n\n ${simpleTextureSample('fuzzColorMap', 'glsl')}\n\n ${simpleTextureSample('fuzzRoughnessMap', 'glsl')}\n\n ${simpleTextureSample('specularWeightMap', 'glsl')}\n\n ${simpleTextureSample('specularColorMap', 'glsl')}\n\n vec4 directionInfo = fetchMatData(i + MAT_ROW_DIRECTION_NORMAL);\n mat.anisotropyDirection = vec2(1.0, 0.0);\n mat.anisotropyDirectionEnabled = directionInfo.y != 0.0;\n mat.coatAnisotropyRotation = fetchMatData(i + MAT_ROW_FILM_TEXTURE).x;\n#ifdef NUM_ANISOTROPY_MAPS\n if (directionInfo.x >= 0.0) {\n int index = int(directionInfo.x);\n vec4 texel = sampleMap(index, getMapUvSet(index, uv, uv1));\n mat.specularAnisotropy *= texel.b;\n vec2 direction = texel.rg * 2.0 - 1.0;\n if (dot(direction, direction) > 1e-4) mat.anisotropyDirection = normalize(direction);\n mat.anisotropyDirectionEnabled = true;\n }\n#endif\n#ifdef HAS_GLTF_ANISOTROPY\n if (fetchMatData(i + MAT_ROW_FILM_TEXTURE).y > 0.5 && mat.specularAnisotropy > 0.0) {\n vec2 native = gltf_anisotropy_to_openpbr(clamp(mat.specularRoughness, 0.0, 1.0), mat.specularAnisotropy);\n mat.specularRoughness = native.x;\n mat.specularAnisotropy = native.y;\n }\n#endif\n if (mat.anisotropyDirectionEnabled) {\n float theta = directionInfo.y;\n vec2 d = mat.anisotropyDirection;\n mat.anisotropyDirection = vec2(cos(theta)*d.x - sin(theta)*d.y, sin(theta)*d.x + cos(theta)*d.y);\n }\n\n // OpenPBR 1.1.1: coat refraction broadens all base microfacet lobes.\n // Keep the zero-coat / smooth-coat paths byte-identical.\n if (mat.coatWeight > 0.0 && mat.coatRoughness > 0.0) {\n float baseRoughness2 = mat.specularRoughness * mat.specularRoughness;\n float coatRoughness2 = mat.coatRoughness * mat.coatRoughness;\n mat.specularRoughness = mix(mat.specularRoughness,\n pow(min(1.0, baseRoughness2 * baseRoughness2 + 2.0 * coatRoughness2 * coatRoughness2), 0.25), mat.coatWeight);\n }\n vec3 instanceColor = getInstanceColor(instanceIndex);\n mat.baseColor *= instanceColor;\n if (mat.materialType == UNLIT) mat.emission *= instanceColor;\n\n mat.specularRoughness = clamp(mat.specularRoughness, ROUGHNESS_MIN, 1.0);\n mat.baseMetalness = clamp(mat.baseMetalness, 0.0, 1.0);\n vec2 specularAlpha = openpbr_roughness_to_alpha(mat.specularRoughness, mat.specularAnisotropy);\n mat.alphaX = specularAlpha.x;\n mat.alphaY = specularAlpha.y;\n}\n\n#if defined(NUM_NORMAL_MAPS)\nvec3 getMatNormal(int materialIndex, vec2 uv, vec3 normal, vec3 dp1, vec3 dp2, vec2 duv1, vec2 duv2) {\n int i = materialIndex * MAT_DATA_SIZE;\n vec4 roughnessAndNormal = fetchMatData(i + MAT_ROW_ROUGHNESS_NORMAL);\n int normalMapIndex = int(roughnessAndNormal.y);\n if (normalMapIndex >= 0) {\n // http://www.thetenthplanet.de/archives/1180\n // TODO use tangent attribute\n // Compute co-tangent and co-bitangent vectors\n vec3 dp2perp = cross(dp2, normal);\n vec3 dp1perp = cross(normal, dp1);\n vec3 dpdu = dp2perp * duv1.x + dp1perp * duv2.x;\n vec3 dpdv = dp2perp * duv1.y + dp1perp * duv2.y;\n float gradientLengthSquared = max(dot(dpdu, dpdu), dot(dpdv, dpdv));\n if (gradientLengthSquared > 1e-12) {\n float invmax = inversesqrt(gradientLengthSquared);\n dpdu *= invmax;\n dpdv *= invmax;\n }\n else {\n // Imported meshes can legitimately omit UVs and use generated or\n // triplanar projection. Their zero UV derivatives must not turn the TBN\n // basis (and then every lighting result) into NaN.\n vec3 referenceAxis = abs(normal.z) < 0.999\n ? vec3(0.0, 0.0, 1.0)\n : vec3(0.0, 1.0, 0.0);\n dpdu = normalize(cross(referenceAxis, normal));\n dpdv = cross(normal, dpdu);\n }\n\n vec3 n = 2.0 * sampleMap(normalMapIndex, uv).rgb - 1.0;\n n.xy *= roughnessAndNormal.zw;\n n = normalize(n);\n\n mat3 tbn = mat3(dpdu, dpdv, normal);\n\n return normalize(tbn * n);\n } else {\n return normal;\n }\n}\n#endif\n\n`\n});\n"]}
|
|
1
|
+
{"version":3,"file":"materialBuffer.glsl.js","sourceRoot":"","sources":["../../../../src/renderer/glsl/chunks/materialBuffer.glsl.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,mBAAmB,EAAE,qBAAqB,EAAE,MAAM,+BAA+B,CAAC;AAC3F,OAAO,EAAE,gBAAgB,EAAE,MAAM,yBAAyB,CAAC;AAC3D,OAAO,EAAE,0BAA0B,EAAE,MAAM,mCAAmC,CAAC;AAC/E,OAAO,EAAE,oBAAoB,EAAE,MAAM,mBAAmB,CAAC;AACzD,OAAO,EAAE,sBAAsB,EAAE,MAAM,4BAA4B,CAAC;AACpE,qDAAqD;AACrD,sDAAsD;AACtD,kFAAkF;AAElF,OAAO,EAAE,iBAAiB,EAAE,IAAI,EAAE,MAAM,EAAE,MAAM,iBAAiB,CAAC;AAElE,eAAe,iBAAiB,CAAC;IAC/B,QAAQ,EAAE;QACR,cAAc,EAAE,MAAM,CAAC,OAAO,CAAC,WAAW,CAAC;QAC3C,qBAAqB,EAAE,MAAM,CAAC,OAAO,CAAC,KAAK,EAAE,CAAC,CAAC;QAC/C,OAAO,EAAE,MAAM,CAAC,YAAY,CAAC,MAAM,EAAE,UAAU,CAAC;QAChD,YAAY,EAAE,MAAM,CAAC,YAAY,CAAC,MAAM,EAAE,UAAU,CAAC;QACrD,YAAY,EAAE,MAAM,CAAC,YAAY,CAAC,OAAO,EAAE,UAAU,CAAC;QACtD,cAAc,EAAE,MAAM,CAAC,YAAY,CAAC,OAAO,EAAE,UAAU,CAAC;QACxD,OAAO,EAAE,MAAM,CAAC,YAAY,CAAC,MAAM,EAAE,UAAU,CAAC;QAChD,GAAG,EAAE,MAAM,CAAC,OAAO,CAAC,gBAAgB,CAAC;KACtC;IACD,OAAO,EAAE;QACP,aAAa,EAAE,CAAC;KACjB;IACD,IAAI,EAAE,IAAI,CAAA;EACV,gBAAgB,EAAE;;;;;;;;;;;;;;;;;;;;;mBAqBC,0BAA0B,CAAC,MAAM;;;mBAGjC,0BAA0B,CAAC,IAAI;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;4BAmGhB,oBAAoB,GAAG,EAAE;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;uBA8FhC,sBAAsB,CAAC,YAAY,GAAG,EAAE;;;4BAGnC,sBAAsB,CAAC,KAAK,GAAG,EAAE;;;;;;EAM/D,mBAAmB,CAAC,UAAU,EAAE,MAAM,CAAC;;;;;;EAMvC,mBAAmB,CAAC,iBAAiB,EAAE,MAAM,CAAC;;;;;;;;;;;;;;EAc9C,mBAAmB,CAAC,cAAc,EAAE,MAAM,CAAC;;EAE3C,mBAAmB,CAAC,cAAc,EAAE,MAAM,CAAC;;;;;;;;;;;;;;;;;;;;;;EAsB3C,qBAAqB,CAAC,MAAM,CAAC;;EAE7B,mBAAmB,CAAC,eAAe,EAAE,MAAM,CAAC;;;;;EAK5C,mBAAmB,CAAC,kBAAkB,EAAE,MAAM,CAAC;;EAE/C,mBAAmB,CAAC,cAAc,EAAE,MAAM,CAAC;;EAE3C,mBAAmB,CAAC,kBAAkB,EAAE,MAAM,CAAC;;EAE/C,mBAAmB,CAAC,mBAAmB,EAAE,MAAM,CAAC;;EAEhD,mBAAmB,CAAC,kBAAkB,EAAE,MAAM,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CA2FlD;CACA,CAAC,CAAC","sourcesContent":["import { simpleTextureSample, thinFilmTextureSample } from '../../materialTextureSlots.js';\nimport { materialRowsGlsl } from '../../materialLayout.js';\nimport { materialAlphaModeConstants } from '../../../scene/OpenPBRMaterial.js';\nimport { INSTANCE_VEC4_STRIDE } from '../../bvhAccel.js';\nimport { mapAlphaUsageConstants } from '../../materialConstants.js';\n// Portions adapted from ray-tracing-renderer@0.10.15\n// (https://github.com/hoverinc/ray-tracing-renderer).\n// Copyright (c) 2019 HOVER, MIT license; see LICENSES/RayTracingRenderer-MIT.txt.\n\nimport { createShaderMixin, glsl, Shader } from '../../shader.js';\n\nexport default createShaderMixin({\n uniforms: {\n materialBuffer: Shader.uniform('sampler2D'),\n materialBufferColumns: Shader.uniform('int', 1),\n mapInfo: Shader.arrayUniform('vec4', 'NUM_MAPS'),\n mapTransform: Shader.arrayUniform('vec4', 'NUM_MAPS'),\n mapUvChannel: Shader.arrayUniform('float', 'NUM_MAPS'),\n mapColorLinear: Shader.arrayUniform('float', 'NUM_MAPS'),\n mapWrap: Shader.arrayUniform('vec2', 'NUM_MAPS'),\n map: Shader.uniform('sampler2DArray')\n },\n defines: {\n NUM_MATERIALS: 1\n },\n main: glsl`\n${materialRowsGlsl()}\n#ifdef HAS_GLTF_ANISOTROPY\nvec2 gltf_anisotropy_to_openpbr(float roughness, float strength) {\n if (strength == 0.0) { return vec2(roughness, 0.0); }\n float u = roughness * roughness;\n float a = u + (1.0 - u) * strength * strength;\n if (a == 0.0) { return vec2(0.0); }\n return vec2(pow((a*a + u*u) * 0.5, 0.25), clamp(1.0 - u/a, 0.0, 1.0));\n}\n\n#endif\n\nvec3 sRGBToLinear(vec3 c) {\n return mix(pow(c * 0.9478672986 + 0.0521327014, vec3(2.4)), c * 0.0773993808, vec3(lessThan(c, vec3(0.04045))));\n}\nvec4 fetchMatData(int i) {\n return fetchData(materialBuffer, i, materialBufferColumns);\n}\n\n// Shared by surface evaluation and shadow occlusion, after texture factors.\nfloat resolveMaterialAlpha(float alpha, int alphaMode, float alphaCutoff) {\n if (alphaMode == ${materialAlphaModeConstants.opaque}) {\n return 1.0;\n }\n if (alphaMode == ${materialAlphaModeConstants.mask}) {\n return alpha >= alphaCutoff ? 1.0 : 0.0;\n }\n return alpha;\n}\n\nfloat getMatType(int idx) {\n return fetchMatData(idx * MAT_DATA_SIZE + MAT_ROW_COLOR).w;\n}\n\nvec2 unpackMaterialIndex(int val) {\n return vec2(float(val >> 8), float(val & 0xff) / 255.0);\n}\n\n#ifdef NUM_MAPS\nvec3 decodeMapColor(int index, vec3 c) {\n if (mapColorLinear[index] > 0.5) { return c; }\n return sRGBToLinear(c);\n}\n\nvec2 getMapSize(int index) {\n return mapInfo[index].xy;\n}\n\nfloat getMapLayer(int index) {\n return floor(mapInfo[index].z);\n}\n\nvec2 getMapOffset(int index) {\n return vec2(fract(mapInfo[index].z), mapInfo[index].w);\n}\n\nfloat wrapMapCoordinate(float value, float mode) {\n if (mode < 0.5) return fract(value);\n if (mode < 1.5) return clamp(value, 0.0, 1.0);\n return 1.0 - abs(1.0 - (value - 2.0 * floor(value * 0.5)));\n}\n\nvec2 wrappedMapUv(int index, vec2 uv) {\n vec4 transform = mapTransform[index];\n vec2 value = uv * transform.xy + transform.zw;\n return vec2(wrapMapCoordinate(value.x, mapWrap[index].x), wrapMapCoordinate(value.y, mapWrap[index].y));\n}\n\nvec2 getMapUV(int index, vec2 uv) {\n vec2 repeatedUv = wrappedMapUv(index, uv);\n vec2 atlasTexel = 1.0 / vec2(textureSize(map, 0).xy);\n vec2 firstTexelCenter = getMapOffset(index);\n vec2 sourceExtent = getMapSize(index) + atlasTexel;\n vec2 sourceOrigin = firstTexelCenter - 0.5 * atlasTexel;\n vec2 lastTexelCenter = firstTexelCenter + sourceExtent - atlasTexel;\n return clamp(\n sourceOrigin + repeatedUv * sourceExtent,\n firstTexelCenter,\n lastTexelCenter\n );\n}\n\nvec2 getMapUvSet(int index, vec2 uv, vec2 uv1) {\n return mapUvChannel[index] > 0.5 ? uv1 : uv;\n}\n\nvec4 loadMapTexel(int index, ivec2 coordinate, ivec2 size, ivec2 origin, vec2 modes) {\n ivec2 p = clamp(coordinate, ivec2(0), size - 1);\n if (modes.x < 0.5) p.x = ((coordinate.x % size.x) + size.x) % size.x;\n if (modes.y < 0.5) p.y = ((coordinate.y % size.y) + size.y) % size.y;\n return texelFetch(map, ivec3(origin + p, int(getMapLayer(index))), 0);\n}\n\nvec4 sampleMap(int index, vec2 uv) {\n ivec2 size = ivec2(round(getMapSize(index) * vec2(textureSize(map, 0).xy) + 1.0));\n vec2 texel = wrappedMapUv(index, uv) * vec2(size) - 0.5;\n vec2 modes = mapWrap[index];\n if ((size.x > 1 && modes.x < 0.5 && (texel.x < 0.0 || texel.x > float(size.x - 1))) ||\n (size.y > 1 && modes.y < 0.5 && (texel.y < 0.0 || texel.y > float(size.y - 1)))) {\n ivec2 base = ivec2(floor(texel));\n vec2 weight = fract(texel);\n ivec2 origin = ivec2(round(getMapOffset(index) * vec2(textureSize(map, 0).xy) - 0.5));\n return mix(\n mix(loadMapTexel(index, base, size, origin, modes), loadMapTexel(index, base + ivec2(1, 0), size, origin, modes), weight.x),\n mix(loadMapTexel(index, base + ivec2(0, 1), size, origin, modes), loadMapTexel(index, base + ivec2(1, 1), size, origin, modes), weight.x), weight.y);\n }\n return texture(map, vec3(getMapUV(index, uv), getMapLayer(index)));\n}\n#endif\n\n// OpenPBR 1.1.1: RMS-preserving GGX anisotropy, shared by base and coat.\nvec2 openpbr_roughness_to_alpha(float roughness, float anisotropy) {\n float alpha = roughness * roughness;\n float alphaMin = ROUGHNESS_MIN * ROUGHNESS_MIN;\n if (anisotropy == 0.0) { return vec2(max(alphaMin, alpha)); }\n float complement = 1.0 - anisotropy;\n float alphaT = alpha * sqrt(2.0 / (1.0 + complement * complement));\n return max(vec2(alphaMin), vec2(alphaT, complement * alphaT));\n}\n\nvec4 fetchIns(int i);\nvec3 getInstanceColor(int instanceIndex) {\n if (instanceIndex < 0) return vec3(1.0);\n return fetchIns(instanceIndex * ${INSTANCE_VEC4_STRIDE + ''} + 9).rgb;\n}\n\nvoid getMaterial(\n inout OpenPbrResolvedMaterial mat,\n int materialIndex,\n vec2 uv,\n vec2 uv1,\n int instanceIndex,\n vec3 vertexColor\n) {\n int i = materialIndex * MAT_DATA_SIZE;\n vec4 colorAndMatType = fetchMatData(i + MAT_ROW_COLOR);\n vec4 roughnessAndNormal = fetchMatData(i + MAT_ROW_ROUGHNESS_NORMAL);\n vec4 metallicAndMapIndex = fetchMatData(i + MAT_ROW_METALLIC_MAPS);\n vec4 emissionAndEmissiveMapIndex = fetchMatData(i + MAT_ROW_EMISSION);\n vec4 iorAndTransmission = fetchMatData(i + MAT_ROW_IOR_TRANSMISSION);\n vec4 misc = fetchMatData(i + MAT_ROW_MISC);\n vec4 alphaAndThinFilm = fetchMatData(i + MAT_ROW_ALPHA_FILM);\n vec4 baseControls = fetchMatData(i + MAT_ROW_BASE_CONTROLS);\n vec4 specularAndFuzz = fetchMatData(i + MAT_ROW_SPECULAR_FUZZ);\n vec4 subsurface = fetchMatData(i + MAT_ROW_SUBSURFACE);\n vec4 fuzz = fetchMatData(i + MAT_ROW_FUZZ);\n vec4 coat = fetchMatData(i + MAT_ROW_COAT);\n vec4 coatControls = fetchMatData(i + MAT_ROW_COAT_CONTROLS);\n vec4 filmAndDispersion = fetchMatData(i + MAT_ROW_FILM_DISPERSION);\n vec4 standaloneMetalRoughMaps = fetchMatData(i + MAT_ROW_STANDALONE_MAPS);\n int mapAlphaUsage = int(misc.a);\n\n mat.baseColor = colorAndMatType.rgb;\n mat.materialType = int(colorAndMatType.w);\n mat.specularRoughness = roughnessAndNormal.x;\n mat.baseMetalness = metallicAndMapIndex.x;\n mat.specularAnisotropy = clamp(metallicAndMapIndex.y, 0.0, 1.0);\n mat.emission = emissionAndEmissiveMapIndex.rgb;\n mat.inside = false;\n mat.specularIor = iorAndTransmission.x;\n mat.transmissionWeight = iorAndTransmission.y;\n#ifdef HAS_MEDIUM\n mat.mediumType = int(iorAndTransmission.z);\n#else\n mat.mediumType = 0;\n#endif\n mat.thinWalled = iorAndTransmission.w > 0.5;\n mat.bevel = misc.r;\n mat.transmissionDispersionScale = misc.g;\n mat.dispersionAbbeNumber = max(filmAndDispersion.y, 1e-6);\n mat.thinFilmThickness = misc.b;\n mat.thinFilmIor = alphaAndThinFilm.b;\n mat.thinFilmWeight = clamp(filmAndDispersion.x, 0.0, 1.0);\n // OpenPBR specifies micrometres; the interference routine uses nanometres.\n mat.thinFilmThickness *= 1000.0;\n mat.baseWeight = clamp(baseControls.x, 0.0, 1.0);\n mat.diffuseRoughness = clamp(baseControls.y, 0.0, 1.0);\n mat.specularWeight = max(0.0, baseControls.z);\n mat.subsurfaceWeight = clamp(baseControls.w, 0.0, 1.0);\n mat.specularColor = max(specularAndFuzz.rgb, vec3(0.0));\n mat.fuzzWeight = clamp(specularAndFuzz.w, 0.0, 1.0);\n mat.subsurfaceColor = max(subsurface.rgb, vec3(0.0));\n mat.transmissionColor = max(fetchMatData(i + MAT_ROW_TRANSMISSION_COLOR).rgb, vec3(0.0));\n mat.fuzzColor = max(fuzz.rgb, vec3(0.0));\n mat.fuzzRoughness = clamp(fuzz.w, 0.0, 1.0);\n mat.coatColor = max(coat.rgb, vec3(0.0));\n mat.coatWeight = clamp(coat.w, 0.0, 1.0);\n mat.coatRoughness = clamp(coatControls.x, ROUGHNESS_MIN, 1.0);\n mat.coatAnisotropy = clamp(coatControls.y, 0.0, 1.0);\n mat.coatIor = max(coatControls.z, 1.0);\n mat.coatDarkening = clamp(coatControls.w, 0.0, 1.0);\n\n#ifdef HAS_MEDIUM\n mat.mediumExtinction = max(fetchMatData(i + MAT_ROW_MEDIUM_EXTINCTION).rgb, vec3(0.0));\n mat.mediumAnisotropy = clamp(fetchMatData(i + MAT_ROW_MEDIUM_EXTINCTION).a, -1.0, 1.0);\n mat.mediumScattering = max(fetchMatData(i + MAT_ROW_MEDIUM_SCATTERING).rgb, vec3(0.0));\n mat.mediumType = max(max(mat.mediumExtinction.x, mat.mediumExtinction.y), mat.mediumExtinction.z) > 0.0 ? 1 : 0;\n#endif\n\n\n#ifdef HAS_ALPHA\n mat.alpha = alphaAndThinFilm.r;\n#else\n mat.alpha = 1.0;\n#endif\n\n #ifdef NUM_DIFFUSE_MAPS\n int diffuseMapIndex = int(metallicAndMapIndex.z);\n if (diffuseMapIndex >= 0) {\n vec4 diffuse = sampleMap(\n diffuseMapIndex, getMapUvSet(diffuseMapIndex, uv, uv1)\n );\n // Material factors from THREE / glTF are already linear. Only color\n // textures need decoding from their stored sRGB values.\n mat.baseColor *= decodeMapColor(diffuseMapIndex, diffuse.rgb);\n\n // Map alpha to transmission\n if (mapAlphaUsage == ${mapAlphaUsageConstants.transmission + ''}) {\n mat.transmissionWeight = 1.0 - diffuse.a;\n }\n else if (mapAlphaUsage == ${mapAlphaUsageConstants.alpha + ''}) {\n mat.alpha *= diffuse.a;\n }\n }\n #endif\n\n ${simpleTextureSample('alphaMap', 'glsl')}\n\n mat.alpha = resolveMaterialAlpha(\n mat.alpha, int(fetchMatData(i + MAT_ROW_ALPHA).w), standaloneMetalRoughMaps.w\n );\n\n ${simpleTextureSample('transmissionMap', 'glsl')}\n\n #ifdef NUM_METALLIC_ROUGHNESS_MAPS\n int metallicRoughnessMapIndex = int(metallicAndMapIndex.w);\n if (metallicRoughnessMapIndex >= 0) {\n vec4 metallicRoughness = sampleMap(\n metallicRoughnessMapIndex,\n getMapUvSet(metallicRoughnessMapIndex, uv, uv1)\n );\n mat.baseMetalness *= metallicRoughness.b;\n mat.specularRoughness *= metallicRoughness.g;\n }\n #endif\n\n ${simpleTextureSample('roughnessMap', 'glsl')}\n\n ${simpleTextureSample('metalnessMap', 'glsl')}\n\n #ifdef NUM_EMISSIVE_MAPS\n int emissiveMapIndex = int(emissionAndEmissiveMapIndex.w);\n if (emissiveMapIndex >= 0) {\n vec3 emissive = sampleMap(\n emissiveMapIndex, getMapUvSet(emissiveMapIndex, uv, uv1)\n ).rgb;\n mat.emission *= decodeMapColor(emissiveMapIndex, emissive);\n }\n #endif\n\n #ifdef NUM_COAT_WEIGHT_MAPS\n int emissionCoatMapIndex = int(fetchMatData(i + MAT_ROW_LAYER_MAPS).x);\n if (emissionCoatMapIndex >= 0 && mat.materialType == 0) {\n float emissionCoatWeight = clamp(coat.w, 0.0, 1.0) * sampleMap(\n emissionCoatMapIndex, getMapUvSet(emissionCoatMapIndex, uv, uv1)\n ).r;\n mat.emission *= mix(vec3(1.0), sqrt(max(coat.rgb, vec3(0.0))), emissionCoatWeight);\n }\n #endif\n\n ${thinFilmTextureSample('glsl')}\n\n ${simpleTextureSample('coatWeightMap', 'glsl')}\n#ifdef NUM_COAT_NORMAL_MAPS\n mat.coatNormalEnabled = fetchMatData(i + MAT_ROW_LAYER_MAPS).z >= 0.0 && mat.coatWeight > 0.0;\n#endif\n\n ${simpleTextureSample('coatRoughnessMap', 'glsl')}\n\n ${simpleTextureSample('fuzzColorMap', 'glsl')}\n\n ${simpleTextureSample('fuzzRoughnessMap', 'glsl')}\n\n ${simpleTextureSample('specularWeightMap', 'glsl')}\n\n ${simpleTextureSample('specularColorMap', 'glsl')}\n\n vec4 directionInfo = fetchMatData(i + MAT_ROW_DIRECTION_NORMAL);\n mat.anisotropyDirection = vec2(1.0, 0.0);\n mat.anisotropyDirectionEnabled = directionInfo.y != 0.0;\n mat.coatAnisotropyRotation = fetchMatData(i + MAT_ROW_FILM_TEXTURE).x;\n#ifdef NUM_ANISOTROPY_MAPS\n if (directionInfo.x >= 0.0) {\n int index = int(directionInfo.x);\n vec4 texel = sampleMap(index, getMapUvSet(index, uv, uv1));\n mat.specularAnisotropy *= texel.b;\n vec2 direction = texel.rg * 2.0 - 1.0;\n if (dot(direction, direction) > 1e-4) mat.anisotropyDirection = normalize(direction);\n mat.anisotropyDirectionEnabled = true;\n }\n#endif\n#ifdef HAS_GLTF_ANISOTROPY\n if (fetchMatData(i + MAT_ROW_FILM_TEXTURE).y > 0.5 && mat.specularAnisotropy > 0.0) {\n vec2 native = gltf_anisotropy_to_openpbr(clamp(mat.specularRoughness, 0.0, 1.0), mat.specularAnisotropy);\n mat.specularRoughness = native.x;\n mat.specularAnisotropy = native.y;\n }\n#endif\n if (mat.anisotropyDirectionEnabled) {\n float theta = directionInfo.y;\n vec2 d = mat.anisotropyDirection;\n mat.anisotropyDirection = vec2(cos(theta)*d.x - sin(theta)*d.y, sin(theta)*d.x + cos(theta)*d.y);\n }\n\n // OpenPBR 1.1.1: coat refraction broadens all base microfacet lobes.\n // Keep the zero-coat / smooth-coat paths byte-identical.\n if (mat.coatWeight > 0.0 && mat.coatRoughness > 0.0) {\n float baseRoughness2 = mat.specularRoughness * mat.specularRoughness;\n float coatRoughness2 = mat.coatRoughness * mat.coatRoughness;\n mat.specularRoughness = mix(mat.specularRoughness,\n pow(min(1.0, baseRoughness2 * baseRoughness2 + 2.0 * coatRoughness2 * coatRoughness2), 0.25), mat.coatWeight);\n }\n vec3 color = getInstanceColor(instanceIndex) * vertexColor;\n mat.baseColor *= color;\n if (mat.materialType == UNLIT) mat.emission *= color;\n\n mat.specularRoughness = clamp(mat.specularRoughness, ROUGHNESS_MIN, 1.0);\n mat.baseMetalness = clamp(mat.baseMetalness, 0.0, 1.0);\n vec2 specularAlpha = openpbr_roughness_to_alpha(mat.specularRoughness, mat.specularAnisotropy);\n mat.alphaX = specularAlpha.x;\n mat.alphaY = specularAlpha.y;\n}\n\n#if defined(NUM_NORMAL_MAPS)\nvec3 getMatNormal(int materialIndex, vec2 uv, vec3 normal, vec3 dp1, vec3 dp2, vec2 duv1, vec2 duv2) {\n int i = materialIndex * MAT_DATA_SIZE;\n vec4 roughnessAndNormal = fetchMatData(i + MAT_ROW_ROUGHNESS_NORMAL);\n int normalMapIndex = int(roughnessAndNormal.y);\n if (normalMapIndex >= 0) {\n // http://www.thetenthplanet.de/archives/1180\n // TODO use tangent attribute\n // Compute co-tangent and co-bitangent vectors\n vec3 dp2perp = cross(dp2, normal);\n vec3 dp1perp = cross(normal, dp1);\n vec3 dpdu = dp2perp * duv1.x + dp1perp * duv2.x;\n vec3 dpdv = dp2perp * duv1.y + dp1perp * duv2.y;\n float gradientLengthSquared = max(dot(dpdu, dpdu), dot(dpdv, dpdv));\n if (gradientLengthSquared > 1e-12) {\n float invmax = inversesqrt(gradientLengthSquared);\n dpdu *= invmax;\n dpdv *= invmax;\n }\n else {\n // Imported meshes can legitimately omit UVs and use generated or\n // triplanar projection. Their zero UV derivatives must not turn the TBN\n // basis (and then every lighting result) into NaN.\n vec3 referenceAxis = abs(normal.z) < 0.999\n ? vec3(0.0, 0.0, 1.0)\n : vec3(0.0, 1.0, 0.0);\n dpdu = normalize(cross(referenceAxis, normal));\n dpdv = cross(normal, dpdu);\n }\n\n vec3 n = 2.0 * sampleMap(normalMapIndex, uv).rgb - 1.0;\n n.xy *= roughnessAndNormal.zw;\n n = normalize(n);\n\n mat3 tbn = mat3(dpdu, dpdv, normal);\n\n return normalize(tbn * n);\n } else {\n return normal;\n }\n}\n#endif\n\n`\n});\n"]}
|