Unveränderter Ausgangsstand inklusive Masterprompt und Konzeptbildern unter assets/. .godot/ und docs/screenshots/ bleiben laut .gitignore unversioniert; letztere sind unter ../backups gesichert. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
58 lines
2.2 KiB
Text
58 lines
2.2 KiB
Text
shader_type spatial;
|
|
// The imported AB/BB/QG surfaces are double-sided, including thin foliage.
|
|
render_mode diffuse_burley, specular_schlick_ggx, cull_disabled;
|
|
uniform float roughness_value : hint_range(0, 1) = 0.75;
|
|
uniform float metallic_value : hint_range(0, 1) = 0.0;
|
|
uniform float grain_amount = 0.08;
|
|
uniform float grain_scale = 90.0;
|
|
uniform float relief_depth = 0.00045;
|
|
// 0 mineral, 1 leather, 2 fabric, 3 bark, 4 leaf, 5 metal.
|
|
uniform int surface_kind = 0;
|
|
|
|
float hash21(vec2 p) {
|
|
p = fract(p * vec2(123.34, 456.21));
|
|
p += dot(p, p + 45.32);
|
|
return fract(p.x * p.y);
|
|
}
|
|
|
|
float grain_noise(vec2 p) {
|
|
vec2 cell = floor(p);
|
|
vec2 f = fract(p);
|
|
vec2 blend = f * f * (3.0 - 2.0 * f);
|
|
return mix(mix(hash21(cell), hash21(cell + vec2(1.0, 0.0)), blend.x),
|
|
mix(hash21(cell + vec2(0.0, 1.0)), hash21(cell + vec2(1.0)), blend.x), blend.y);
|
|
}
|
|
|
|
void fragment() {
|
|
if (!FRONT_FACING) { NORMAL = -NORMAL; }
|
|
vec2 p = UV * grain_scale;
|
|
float footprint = max(length(dFdx(p)), length(dFdy(p)));
|
|
float detail = 1.0 - smoothstep(0.5, 2.0, footprint);
|
|
float coarse = grain_noise(p * 0.37);
|
|
float fine = grain_noise(p) * 0.65 + grain_noise(p * 2.03 + 19.7) * 0.35;
|
|
float grain = mix(0.0, fine - 0.5, detail);
|
|
float relief = grain;
|
|
if (surface_kind == 2) {
|
|
// Subpixel weave fades out instead of producing a moving checkerboard.
|
|
float weave = sin(p.x * 6.28318) * sin(p.y * 6.28318);
|
|
relief += weave * detail * 0.1;
|
|
} else if (surface_kind == 3) {
|
|
relief = (grain_noise(vec2(p.x, p.y * 0.12)) - 0.5) * detail;
|
|
} else if (surface_kind == 4) {
|
|
relief *= 0.2;
|
|
BACKLIGHT = COLOR.rgb * 0.12;
|
|
} else if (surface_kind == 5) {
|
|
relief = (grain_noise(vec2(p.x * 0.1, p.y)) - 0.5) * detail * 0.2;
|
|
}
|
|
ALBEDO = COLOR.rgb * (1.0 + grain * grain_amount + (coarse - 0.5) * grain_amount * 0.35);
|
|
ROUGHNESS = clamp(roughness_value + grain * 0.07, 0.08, 1.0);
|
|
METALLIC = metallic_value;
|
|
// Surface gradient in view space; preserves authored UVs while joints deform.
|
|
vec3 dx = dFdx(VERTEX), dy = dFdy(VERTEX);
|
|
vec3 rx = cross(dy, NORMAL), ry = cross(NORMAL, dx);
|
|
float determinant = dot(dx, rx);
|
|
if (abs(determinant) > 0.00000001) {
|
|
NORMAL = normalize(abs(determinant) * NORMAL - sign(determinant) *
|
|
(dFdx(relief) * rx + dFdy(relief) * ry) * relief_depth);
|
|
}
|
|
}
|