Skip to content

Instantly share code, notes, and snippets.

@HungryProton
Last active July 31, 2024 16:12
Show Gist options
  • Save HungryProton/2459d9c4ba4a3e710d9435e24d39b6f2 to your computer and use it in GitHub Desktop.
Save HungryProton/2459d9c4ba4a3e710d9435e24d39b6f2 to your computer and use it in GitHub Desktop.
Random experiments for POM from the "Godot Effects and Shaders" discord group, based on Tentabrobpy's shader.
shader_type spatial;
render_mode skip_vertex_transform;
uniform vec4 albedo : source_color = vec4(1.0);
uniform sampler2D texture_albedo : source_color,filter_linear_mipmap,repeat_enable;
uniform sampler2D texture_normal : hint_roughness_normal,filter_linear_mipmap,repeat_enable;
uniform float normal_scale : hint_range(-16,16) = 1.0;
uniform sampler2D texture_heightmap : hint_default_black,filter_linear_mipmap,repeat_enable;
uniform float heightmap_scale = 1.0;
uniform int heightmap_min_layers: hint_range(0, 128, 1) = 8;
uniform int heightmap_max_layers : hint_range(0, 128, 1) = 32;
uniform vec3 uv1_scale = vec3(1.0);
uniform vec3 uv1_offset;
void vertex() {
VERTEX = (MODELVIEW_MATRIX * vec4(VERTEX, 1.0)).xyz;
TANGENT = normalize(MODELVIEW_NORMAL_MATRIX * TANGENT);
BINORMAL = normalize(MODELVIEW_NORMAL_MATRIX * BINORMAL);
NORMAL =normalize( MODELVIEW_NORMAL_MATRIX * NORMAL);
mat3 view_tangent_matrix = transpose(mat3(TANGENT, -BINORMAL, NORMAL));
UV = (view_tangent_matrix * (VERTEX - NODE_POSITION_VIEW)).xy;
UV = UV * uv1_scale.xy + uv1_offset.xy;
}
void fragment() {
vec2 base_uv = UV;
mat3 tangent_view_matrix = mat3(TANGENT, -BINORMAL, NORMAL);
vec3 view_dir = normalize(transpose(tangent_view_matrix) * VIEW) * uv1_scale;
float num_layers = mix(float(heightmap_max_layers),float(heightmap_min_layers), abs(dot(vec3(0.0, 0.0, 1.0), view_dir)));
float layer_depth = 1.0 / num_layers;
vec2 P = view_dir.xy / view_dir.z * heightmap_scale * 0.01;
vec2 delta = P / num_layers;
vec2 ofs = base_uv;
float depth = 1.0 - texture(texture_heightmap, ofs).r;
float current_depth = 0.0;
while(current_depth < depth) {
ofs -= delta;
depth = 1.0 - texture(texture_heightmap, ofs).r;
current_depth += layer_depth;
}
vec2 prev_ofs = ofs + delta;
float after_depth = depth - current_depth;
float before_depth = ( 1.0 - texture(texture_heightmap, prev_ofs).r ) - current_depth + layer_depth;
float weight = after_depth / (after_depth - before_depth);
ofs = ofs + delta * weight;
vec2 uv_diff = base_uv - ofs;
base_uv = ofs;
vec3 surface_vector = (tangent_view_matrix * vec3(uv_diff / uv1_scale.xy, 0.0));
float sampled_depth = 1.0 - texture(texture_heightmap, base_uv).r;
vec3 depth_vector = NORMAL * sampled_depth * heightmap_scale * 0.01;
vec3 offset_vector = depth_vector + surface_vector;
vec3 offset_vertex = VERTEX - offset_vector;
offset_vertex.z = min(VERTEX.z, offset_vertex.z);
vec4 vertex_ndc = PROJECTION_MATRIX * vec4(offset_vertex, 1.0);
float offset_depth = vertex_ndc.z / vertex_ndc.w;
DEPTH = offset_depth;
vec4 albedo_tex = texture(texture_albedo,base_uv);
ALBEDO = albedo.rgb * albedo_tex.rgb;
NORMAL_MAP = texture(texture_normal,base_uv).rgb;
NORMAL_MAP_DEPTH = normal_scale;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment