diff options
| author | Akshay Nair <phenax5@gmail.com> | 2026-09-24 11:53:12 +0530 |
|---|---|---|
| committer | Akshay Nair <phenax5@gmail.com> | 2026-09-24 11:53:12 +0530 |
| commit | dc29499b23a90fac438cf74eb4865c15afecbdbd (patch) | |
| tree | 4ef563c2611074ba58d59a54c4af231ec32512bb /src/main/resources | |
| parent | 7bdd84e8ecade87ececdefe3cee614df8438e0a1 (diff) | |
| download | art-playground-openrndr-dc29499b23a90fac438cf74eb4865c15afecbdbd.tar.gz art-playground-openrndr-dc29499b23a90fac438cf74eb4865c15afecbdbd.zip | |
Door thingy
Diffstat (limited to 'src/main/resources')
| -rw-r--r-- | src/main/resources/shaders/modules/utils.glsl | 6 | ||||
| -rw-r--r-- | src/main/resources/shaders/mrdoor.glsl | 169 |
2 files changed, 175 insertions, 0 deletions
diff --git a/src/main/resources/shaders/modules/utils.glsl b/src/main/resources/shaders/modules/utils.glsl index 6908f3b..3520df1 100644 --- a/src/main/resources/shaders/modules/utils.glsl +++ b/src/main/resources/shaders/modules/utils.glsl @@ -7,3 +7,9 @@ float ssubtract(float a, float b, float k) { return -smin(-a, b, k); } +vec3 srgb(float r, float g, float b) { + return vec3(pow(r, 2.2), pow(g, 2.2), pow(b, 2.2)); +} +vec3 srgb(vec3 c) { + return srgb(c.r, c.g, c.b); +} diff --git a/src/main/resources/shaders/mrdoor.glsl b/src/main/resources/shaders/mrdoor.glsl new file mode 100644 index 0000000..06733c6 --- /dev/null +++ b/src/main/resources/shaders/mrdoor.glsl @@ -0,0 +1,169 @@ +#version 430 +layout(local_size_x = 1, local_size_y = 1) in; + +#include <sdf> +#include <utils> +#include <noise> + +uniform float seconds = 0; +uniform vec3 camera_position = vec3(0, 1, 0); +uniform mat3 camera_transformation; +uniform vec3 key_light_position; +layout(rgba8) uniform writeonly image2D output_image; + +const vec3 door1_light_position = vec3(0.8, 4, 0.4); +const vec3 sunlight_color = vec3(1, 0.99, 0.99); + +#define PI 3.14159265358979323 + +struct Obj { + int objid; + float dist; + vec3 material; + bool lighting; + float shine; +}; + +Obj null_object = Obj(-1, -1.0, vec3(0.01), false, 0.0); // 0.35, 0.6, 0.9 +Obj create_obj(in int objid, in float dist) { + return Obj(objid, dist, vec3(1), true, 0.0); +} + +Obj scene(in vec3 p) { + vec3 doorpos = p - vec3(-0.5, 1.4, 5); + vec3 doorsize = vec3(1., 2., 0.1); + + float doorbody = sdf_box(doorpos, doorsize, 0.04); + doorbody = ssubtract(doorbody, sdf_box(doorpos - vec3(0, 1.1, -0.2), vec3(0.65, 0.5, 0.1), 0), 0.1); + doorbody = ssubtract(doorbody, sdf_box(doorpos - vec3(0, -0.75, -0.2), vec3(0.65, 0.85, 0.1), 0), 0.1); + Obj doorhandle = create_obj(2, sdf_circle(doorpos - vec3(0.75, 0.34, -0.3), 0.1)); + doorhandle.material = vec3(0.4, 0.4, 0.4); + doorhandle.shine = 22.0; + Obj door = create_obj(2, doorbody); + door.material = vec3(0.68, 0.17, 0.20); + door.shine = 2.0; + + float doorframe = ssubtract( + sdf_box(doorpos - vec3(0, 0.5, 0), vec3(2., 2.6, 0.1), 0), + sdf_box(doorpos, doorsize + vec3(0.01, 0.01, 0.04), 0), 0.0); + vec3 wallpos = doorpos; + wallpos.xz *= mat2x2(cos(PI / 2.), -sin(PI / 2.), sin(PI / 2.), cos(PI / 2.)); + float wallsides = min( + sdf_box(wallpos - vec3(0, 0.5, -2), vec3(2., 2.6, 0.08), 0), + sdf_box(wallpos - vec3(0, 0.5, 2), vec3(2., 2.6, 0.08), 0)); + float roof = sdf_box(doorpos - vec3(0, 3.3, -2), vec3(2., 0.08, 2.6), 0); + Obj walls = create_obj(2, min(min(doorframe, wallsides), roof)); + walls.material = vec3(0.15, 0.28, 0.42); + + Obj debugdot = create_obj(-1, sdf_circle(p - door1_light_position, 0.1)); + debugdot.lighting = false; + debugdot.material = vec3(0, 1, 0); + + Obj floor = create_obj(0, sdf_plane(p - vec3(0, -0.6, 0), vec3(0, 1, 0), 0.0)); + floor.material = vec3(0.4); + float dist = floor.dist; + dist = min(door.dist, dist); + dist = min(doorhandle.dist, dist); + dist = min(walls.dist, dist); + dist = min(debugdot.dist, dist); + if (dist == door.dist) return door; + if (dist == doorhandle.dist) return doorhandle; + if (dist == floor.dist) return floor; + if (dist == walls.dist) return walls; + if (dist == debugdot.dist) return debugdot; + return null_object; +} + +#define RM_SHADOW_MAX_ITERATIONS 100 +#define RM_MAX_ITERATIONS 300 +#define RM_MAX_DISTANCE 80 + +Obj ray_march_scene(in vec3 ray_origin, in vec3 ray_direction) { + float dist = 0; + for (int i = 0; i < RM_MAX_ITERATIONS && dist < RM_MAX_DISTANCE; i++) { + vec3 p = ray_origin + ray_direction * dist; + Obj o = scene(p); + dist += o.dist; + if (o.dist <= 0.01) { + o.dist = dist; + return o; + } + } + return null_object; +} + +vec3 surface_normal_scene(in vec3 p) { + vec2 e = vec2(0.01, 0); + return normalize(vec3( + scene(p + e.xyy).dist - scene(p - e.xyy).dist, + scene(p + e.yxy).dist - scene(p - e.yxy).dist, + scene(p + e.yyx).dist - scene(p - e.yyx).dist)); +} + +float shadow_scene(in vec3 ray_origin, in vec3 ray_direction, in float light_intensity) { + float dist = 0.015; + float res = 1.; + float prev_gap = 1e10; + for (int i = 0; i < RM_SHADOW_MAX_ITERATIONS && dist < RM_MAX_DISTANCE; i++) { + vec3 p = ray_origin + dist * ray_direction; + Obj obj = scene(p); + float gap = obj.dist; + if (!obj.lighting) + continue; + float y = gap * gap / (10000.0 * prev_gap); + float d = sqrt(abs(gap * gap - y * y)); + res = min(res, light_intensity * d / max(0, dist - y)); + prev_gap = gap; + dist += gap; + + if (res < 0.0001) + break; + } + + res = clamp(res * 1.1, 0.18, 1.0); + return res * res * (3.0 - 2.0 * res); +} + +void main() { + vec2 resolution = vec2(imageSize(output_image).xy); + float aspect_ratio = resolution.y / resolution.x; + vec2 uv = (gl_GlobalInvocationID.xy - resolution / 2) * vec2(1.0, aspect_ratio) / resolution; + + vec3 origin = vec3(0); + vec3 uv_direction = normalize((vec3(uv.x, uv.y, 1) - origin) * camera_transformation + origin); + + Obj obj = ray_march_scene(camera_position, uv_direction); + vec3 p = camera_position + uv_direction * obj.dist; + vec3 normal = surface_normal_scene(p); + + vec3 color = srgb(obj.material); + + if (obj.lighting) { + float ambient = 0.03; + + vec3 keyl_dir = normalize(key_light_position - p); + float key_contrast = 1.; + key_contrast *= clamp(dot(normal, keyl_dir), 0, 1); + key_contrast *= shadow_scene(p, keyl_dir, 8.); + key_contrast = clamp(key_contrast, 0, 1); + + vec3 door1_ldir = normalize(door1_light_position - p); + float door1_contrast = 1.; + door1_contrast *= clamp(dot(normal, door1_ldir), 0, 1); + door1_contrast *= shadow_scene(p, door1_ldir, 128.); + door1_contrast = clamp(door1_contrast, 0, 1); + + float contrast = max(key_contrast, door1_contrast); + color *= clamp(ambient + contrast * (1.0 - ambient), 0, 1); + + vec3 hal_door1 = normalize(door1_ldir - uv_direction); + float spec_door1 = + pow(clamp(dot(normal, hal_door1), 0.0, 1.0), 16.0) * contrast * + (0.04 + + 0.96 * pow(clamp(1.0 + dot(hal_door1, uv_direction), 0.0, 1.0), 5.0)); + color += obj.shine * spec_door1 * vec3(1.00, 0.70, 0.5); + } + + color = clamp(color, 0, 1); + imageStore(output_image, ivec2(gl_GlobalInvocationID.xy), vec4(color, 1)); +} |
