immersive-home/app/assets/materials/glass.gdshader

81 lines
2.6 KiB
Plaintext
Raw Normal View History

2024-04-21 19:25:57 +03:00
shader_type spatial;
2024-04-23 23:11:18 +03:00
render_mode diffuse_burley, specular_schlick_ggx, blend_mix, cull_disabled, shadows_disabled;
2024-04-22 00:45:09 +03:00
2024-04-23 15:26:20 +03:00
group_uniforms Color;
uniform vec4 color : source_color = vec4(1.0, 1.0, 1.0, 0.3);
2024-04-22 00:45:09 +03:00
uniform vec4 border_color : source_color = vec4(1.0, 1.0, 1.0, 1.0);
2024-04-23 00:47:56 +03:00
uniform vec4 edge_color : source_color = vec4(0.0, 0.0, 0.0, 1.0);
2024-04-23 15:26:20 +03:00
group_uniforms Size;
uniform vec2 size = vec2(1.0, 1.0);
uniform float border_size: hint_range(0.0, 0.5) = 0.001;
uniform float border_fade_in: hint_range(0.0, 0.5) = 0.005;
uniform float border_fade_out: hint_range(0.0, 0.5) = 0.0;
2024-04-23 23:11:18 +03:00
uniform float corner_radius = 0.04;
2024-04-23 15:26:20 +03:00
group_uniforms Roughness;
uniform float roughness : hint_range(0.0, 1.0) = 0.3;
uniform float grain_amount : hint_range(0.0, 1.0) = 0.02;
2024-04-22 00:45:09 +03:00
2024-04-21 19:25:57 +03:00
float rectangle(vec2 position) {
vec2 component_wise_edge_distance = abs(position) - (vec2(0.5, 0.5) * size + corner_radius * (size - 1.0));
float outsideDistance = length(max(component_wise_edge_distance, 0));
float insideDistance = min(max(component_wise_edge_distance.x, component_wise_edge_distance.y), 0);
return outsideDistance + insideDistance;
}
2024-04-23 00:47:56 +03:00
float SchlickFresnel(float u) {
float m = 1.0 - u;
float m2 = m * m;
return m2 * m2 * m;
}
2024-04-21 19:25:57 +03:00
void fragment() {
2024-04-23 00:47:56 +03:00
float VdotN = dot(VIEW, NORMAL);
float fresnel = clamp(SchlickFresnel(VdotN), 0.0, 1.0);
2024-04-22 00:45:09 +03:00
ALBEDO = border_color.xyz;
ALPHA = 0.0;
2024-04-21 19:25:57 +03:00
float border_scale = 1.0 + 2.0 * corner_radius;
float d = rectangle((UV - 0.5) * size * border_scale);
float border_width = (border_size + border_fade_in + border_fade_out) * border_scale;
2024-04-23 15:26:20 +03:00
bool inside = false;
2024-04-21 19:25:57 +03:00
if (d >= corner_radius - border_width && d <= corner_radius) {
2024-04-23 15:26:20 +03:00
// Border
2024-04-21 19:25:57 +03:00
float rel_d = (d - corner_radius + border_width) / border_width;
2024-04-22 00:45:09 +03:00
float alpha = min((rel_d / (border_fade_in * border_scale / border_width)), (1.0 - (rel_d)) / (border_fade_out * border_scale / border_width));
if (d < corner_radius - (border_size + border_fade_out) * border_scale) {
2024-04-23 15:26:20 +03:00
// Inner Fade
2024-04-22 00:45:09 +03:00
ALBEDO = mix(color, border_color, alpha).xyz;
ALPHA = mix(color.w, border_color.w, alpha);
2024-04-23 15:26:20 +03:00
inside = true;
2024-04-22 00:45:09 +03:00
} else {
2024-04-23 15:26:20 +03:00
// Outer Fade
2024-04-22 00:45:09 +03:00
ALBEDO = border_color.xyz;
ALPHA = mix(0.0, border_color.w, alpha);
}
} else if (d < corner_radius - border_width ) {
2024-04-23 15:26:20 +03:00
// Inside
2024-04-22 00:45:09 +03:00
ALBEDO = color.xyz;
ALPHA = color.w;
2024-04-23 15:26:20 +03:00
inside = true;
2024-04-21 19:25:57 +03:00
}
2024-04-23 15:26:20 +03:00
if (inside) {
float a = mix(0.001, 1.0, ALPHA);
ALPHA = mix(fresnel * edge_color.a, 1.0, a);
ALBEDO = mix(edge_color.rgb * edge_color.a, ALBEDO.rgb, a);
ROUGHNESS = roughness;
SPECULAR = 0.5 * inversesqrt(ALPHA);
float noise = (fract(sin(dot(UV, vec2(12.9898, 78.233))) * 43758.5453) - 0.5) * 2.0;
2024-04-22 00:45:09 +03:00
2024-04-23 15:26:20 +03:00
ALBEDO += noise * grain_amount;
}
2024-04-21 19:25:57 +03:00
}