From 8560d4ac4dc75b3d5a741f06f4f96ec83a957882 Mon Sep 17 00:00:00 2001 From: Spencer Killen Date: Sat, 19 Aug 2023 10:45:09 -0600 Subject: [PATCH] Add screen shader --- godot/Level/World/screen_shader.gdshader | 165 +++++++++++++++++++++++ godot/Level/World/screen_shader.tscn | 21 +++ godot/Level/World/world_environment.tscn | 11 ++ godot/Models/grape_man.tscn | 3 + godot/Models/slime.tscn | 24 ++-- godot/tests/test_scale_and_look.tscn | 27 ++++ 6 files changed, 239 insertions(+), 12 deletions(-) create mode 100644 godot/Level/World/screen_shader.gdshader create mode 100644 godot/Level/World/screen_shader.tscn create mode 100644 godot/Level/World/world_environment.tscn create mode 100644 godot/tests/test_scale_and_look.tscn diff --git a/godot/Level/World/screen_shader.gdshader b/godot/Level/World/screen_shader.gdshader new file mode 100644 index 0000000..c78698d --- /dev/null +++ b/godot/Level/World/screen_shader.gdshader @@ -0,0 +1,165 @@ +shader_type canvas_item; + +// Color space code from +// HSV: https://godotshaders.com/shader/hsv-adjustment/ +// LAB/XYZ: https://gist.github.com/msbarry/cd98f928542f5152111a +// Note: don't use the XYZ space, but sources use it to convert to LAB + + + +uniform sampler2D screen_texture : hint_screen_texture; + + +uniform float param : hint_range(0.0, 255.0, 1.0); +uniform float param2 : hint_range(0.0, 255.0, 1.0); + +vec3 rgb2hsv(vec3 c) { + vec4 K = vec4(0.0, -1.0 / 3.0, 2.0 / 3.0, -1.0); + vec4 p = mix(vec4(c.bg, K.wz), vec4(c.gb, K.xy), step(c.b, c.g)); + vec4 q = mix(vec4(p.xyw, c.r), vec4(c.r, p.yzx), step(p.x, c.r)); + + float d = q.x - min(q.w, q.y); + float e = 1.0e-10; + return vec3(abs(q.z + (q.w - q.y) / (6.0 * d + e)), d / (q.x + e), q.x); +} + +vec3 hsv2rgb(vec3 c) { + vec4 K = vec4(1.0, 2.0 / 3.0, 1.0 / 3.0, 3.0); + vec3 p = abs(fract(c.xxx + K.xyz) * 6.0 - K.www); + return c.z * mix(K.xxx, clamp(p - K.xxx, 0.0, 1.0), c.y); +} + +vec3 rgb2xyz(vec3 c) { + float R = ((c.r > 0.04045) ? pow((( c.r + 0.055 ) / 1.055), 2.4) : (c.r / 12.92)) * 100.0; + float G = ((c.g > 0.04045) ? pow((( c.g + 0.055 ) / 1.055), 2.4) : (c.g / 12.92)) * 100.0; + float B = ((c.b > 0.04045) ? pow((( c.b + 0.055 ) / 1.055), 2.4) : (c.b / 12.92)) * 100.0; + + float X = R * 0.4124 + G * 0.3576 + B * 0.1805; + float Y = R * 0.2126 + G * 0.7152 + B * 0.0722; + float Z = R * 0.0193 + G * 0.1192 + B * 0.9505; + + return vec3(X, Y, Z); +} + +vec3 xyz2rgb(vec3 c) { + float X = c.x / 100.0; + float Y = c.y / 100.0; + float Z = c.z / 100.0; + + float R = X * 3.2406 + Y * -1.5372 + Z * -0.4986; + float G = X * -0.9689 + Y * 1.8758 + Z * 0.0415; + float B = X * 0.0557 + Y * -0.2040 + Z * 1.0570; + + R = ((R > 0.0031308) ? (1.055 * ( pow( R, 1./2.4 ) ) - 0.055) : (12.92 * R)); + G = ((G > 0.0031308) ? (1.055 * ( pow( G, 1./2.4 ) ) - 0.055) : (12.92 * G)); + B = ((B > 0.0031308) ? (1.055 * ( pow( B, 1./2.4 ) ) - 0.055) : (12.92 * B)); + + return vec3(R, G, B); +} + +vec3 xyz2lab(vec3 c) { + float X = c.x / 95.047; + float Y = c.y / 100.0; + float Z = c.z / 108.883; + + X = ((X > 0.008856) ? (pow( X, 1./3.)) : (( 7.787 * X ) + ( 16./116.))); + Y = ((Y > 0.008856) ? (pow( Y, 1./3.)) : (( 7.787 * Y ) + ( 16./116.))); + Z = ((Z > 0.008856) ? (pow( Z, 1./3.)) : (( 7.787 * Z ) + ( 16./116.))); + + float L = ( 116. * Y ) - 16.; + float a = 500. * ( X - Y ); + float b = 200. * ( Y - Z ); + + return vec3(L, a, b); +} + +vec3 lab2xyz(vec3 c) { + float L = c.x; + float a = c.y; + float b = c.z; + + float Y = ( L + 16. ) / 116.; + float X = a / 500. + Y; + float Z = Y - b / 200.; + + Y = ((pow(Y,3.) > 0.008856) ? (pow(Y,3.)) : ((Y - 16. / 116.) / 7.787)); + X = ((pow(X,3.) > 0.008856) ? (pow(X,3.)) : ((X - 16. / 116.) / 7.787)); + Z = ((pow(Z,3.) > 0.008856) ? (pow(Z,3.)) : ((Z - 16. / 116.) / 7.787)); + + float ref_X = 95.047; + float ref_Y = 100.0; + float ref_Z = 108.883; + + return vec3(ref_X * X, ref_Y * Y, ref_Z * Z); +} + + +vec3 band_colors(vec3 rgb) +{ + return round(rgb * param) / param; +} + +vec3 band_colors_preserve_hue_lum(vec3 rgb, float ncolors) +{ + vec3 hsv = rgb2hsv(rgb); + hsv.r = round(hsv.r * ncolors) / ncolors; + vec3 lab = xyz2lab(rgb2xyz(rgb)); + lab.r = round(lab.r * (ncolors / 100.0)) / (ncolors / 100.0); + + // Into HSV + vec2 sv = rgb2hsv(xyz2rgb(lab2xyz(lab))).gb; + hsv.gb = sv; + return hsv2rgb(hsv); +} + +uniform float scale = 2.0; +uniform int grid = 5; + +vec3 band_dither(vec3 rgb, vec2 uv) +{ + + uv *= (1.0 / scale); + int x = int(mod(uv.x, float(grid))) + 1; + int y = int(mod(uv.y, float(grid))) + 1; + + vec3 hsv = rgb2hsv(rgb); + + int g = int(round(mix(float(grid), float(2), fract(hsv.r * param)))); + + + if (x % g == 0 && y % g == 0) { + hsv.r = ceil(hsv.r * param) / param; + } else { + hsv.r = floor(hsv.r * param) / param; + } + vec3 lab = xyz2lab(rgb2xyz(rgb)); + if (x % g == 0 && y % g == 0) { + lab.r = ceil(lab.r * (param / 100.0)) / (param / 100.0); + } else { + lab.r = floor(lab.r * (param / 100.0)) / (param / 100.0); + } + + // Into HSV + vec2 sv = rgb2hsv(xyz2rgb(lab2xyz(lab))).gb; + hsv.gb = sv; + + + return hsv2rgb(hsv); + +} + +uniform float anim_period : hint_range(0.1, 5, 0.01); +void fragment() +{ + vec3 rgb = texture(screen_texture, SCREEN_UV).rgb; + vec3 band1 = band_colors_preserve_hue_lum(rgb, param); + vec3 band2 = band_colors_preserve_hue_lum(rgb, param2); + float weight = mod(TIME, anim_period) / anim_period; + float double_weight = mod(TIME, anim_period*2.0) / (anim_period*2.0); + weight = double_weight > 0.5 ? (1.-weight) : weight; + vec3 mixed = mix(band1, band2, weight); + COLOR.rgb = mixed; + + + //COLOR.rgb = banded_nostalgia; +} \ No newline at end of file diff --git a/godot/Level/World/screen_shader.tscn b/godot/Level/World/screen_shader.tscn new file mode 100644 index 0000000..07cc1d6 --- /dev/null +++ b/godot/Level/World/screen_shader.tscn @@ -0,0 +1,21 @@ +[gd_scene load_steps=3 format=3 uid="uid://d2d4uv7o5gx5p"] + +[ext_resource type="Shader" path="res://Level/World/screen_shader.gdshader" id="1_ldrc3"] + +[sub_resource type="ShaderMaterial" id="ShaderMaterial_yagpk"] +shader = ExtResource("1_ldrc3") +shader_parameter/param = 40.0 +shader_parameter/param2 = 20.0 +shader_parameter/scale = 4.0 +shader_parameter/grid = 5 +shader_parameter/anim_period = 3.0 + +[node name="ScreenShader" type="CanvasLayer"] + +[node name="ColorRect" type="ColorRect" parent="."] +material = SubResource("ShaderMaterial_yagpk") +anchors_preset = 15 +anchor_right = 1.0 +anchor_bottom = 1.0 +grow_horizontal = 2 +grow_vertical = 2 diff --git a/godot/Level/World/world_environment.tscn b/godot/Level/World/world_environment.tscn new file mode 100644 index 0000000..14b4c2e --- /dev/null +++ b/godot/Level/World/world_environment.tscn @@ -0,0 +1,11 @@ +[gd_scene load_steps=2 format=3 uid="uid://b35w4hlh4n1jt"] + +[sub_resource type="Environment" id="Environment_cxd2l"] +background_mode = 1 +background_color = Color(0.733333, 0.317647, 0, 1) +ambient_light_source = 2 +ambient_light_color = Color(1, 1, 1, 1) +ambient_light_energy = 0.1 + +[node name="WorldEnvironment" type="WorldEnvironment"] +environment = SubResource("Environment_cxd2l") diff --git a/godot/Models/grape_man.tscn b/godot/Models/grape_man.tscn index 9f367a7..86858fe 100644 --- a/godot/Models/grape_man.tscn +++ b/godot/Models/grape_man.tscn @@ -22,3 +22,6 @@ bones/15/rotation = Quaternion(0.105246, -0.0039338, 0.0113526, 0.994374) [node name="GrabPointLocation" type="Node3D" parent="." index="2"] transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1.29365) + +[node name="OmniLight3D" type="OmniLight3D" parent="." index="3"] +transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0.289473, 8.26292, 4.26359) diff --git a/godot/Models/slime.tscn b/godot/Models/slime.tscn index 86c0aa6..26165cf 100644 --- a/godot/Models/slime.tscn +++ b/godot/Models/slime.tscn @@ -9,34 +9,34 @@ animation = &"Slime_Idle" [sub_resource type="AnimationNodeAnimation" id="AnimationNodeAnimation_avpkh"] animation = &"Slime_Walk" -[sub_resource type="AnimationNodeStateMachineTransition" id="AnimationNodeStateMachineTransition_y7liq"] -advance_mode = 2 - [sub_resource type="AnimationNodeStateMachineTransition" id="AnimationNodeStateMachineTransition_n3s05"] xfade_time = 0.3 [sub_resource type="AnimationNodeStateMachineTransition" id="AnimationNodeStateMachineTransition_fbi2x"] xfade_time = 0.3 +[sub_resource type="AnimationNodeStateMachineTransition" id="AnimationNodeStateMachineTransition_srcja"] +advance_mode = 2 + [sub_resource type="AnimationNodeStateMachine" id="AnimationNodeStateMachine_prt7l"] states/Idle/node = SubResource("AnimationNodeAnimation_nwfvl") states/Idle/position = Vector2(570, 145) states/Walk/node = SubResource("AnimationNodeAnimation_avpkh") states/Walk/position = Vector2(329, 155) -transitions = ["Start", "Walk", SubResource("AnimationNodeStateMachineTransition_y7liq"), "Walk", "Idle", SubResource("AnimationNodeStateMachineTransition_n3s05"), "Idle", "Walk", SubResource("AnimationNodeStateMachineTransition_fbi2x")] +transitions = ["Walk", "Idle", SubResource("AnimationNodeStateMachineTransition_n3s05"), "Idle", "Walk", SubResource("AnimationNodeStateMachineTransition_fbi2x"), "Start", "Idle", SubResource("AnimationNodeStateMachineTransition_srcja")] [node name="slime" instance=ExtResource("1_jttw0")] script = ExtResource("2_xo27e") [node name="Skeleton3D" parent="Armature" index="0"] -bones/1/position = Vector3(0, 0.410324, 0) -bones/2/position = Vector3(0.00236768, 0.44386, 0.00104018) -bones/2/rotation = Quaternion(-0.0371253, -0.00167519, -0.213342, 0.976271) -bones/3/rotation = Quaternion(0.104013, -0.697591, 0.00939198, 0.708844) -bones/7/rotation = Quaternion(-0.301863, 2.16678e-09, 2.86589e-09, 0.953351) -bones/8/rotation = Quaternion(0.186806, -9.15072e-10, -4.81489e-10, 0.982397) -bones/10/rotation = Quaternion(0.183918, -5.22532e-08, 1.09779e-08, 0.982942) -bones/11/rotation = Quaternion(0.0467994, 9.84262e-08, 4.31854e-08, 0.998904) +bones/1/position = Vector3(0, 0.264857, 0) +bones/2/position = Vector3(0.028393, 0.513056, 0.0124737) +bones/2/rotation = Quaternion(-0.178538, 0.0193832, -0.211014, 0.960844) +bones/3/rotation = Quaternion(0.109512, -0.695192, 0.00400734, 0.710422) +bones/7/rotation = Quaternion(-0.347763, 2.02718e-09, 2.9685e-09, 0.937583) +bones/8/rotation = Quaternion(-0.091967, -7.45328e-10, -7.10578e-10, 0.995762) +bones/10/rotation = Quaternion(0.0144373, -4.10082e-08, -1.82391e-09, 0.999896) +bones/11/rotation = Quaternion(-0.373719, 8.36829e-08, 6.89615e-08, 0.927542) [node name="AnimationTree" type="AnimationTree" parent="." index="2"] tree_root = SubResource("AnimationNodeStateMachine_prt7l") diff --git a/godot/tests/test_scale_and_look.tscn b/godot/tests/test_scale_and_look.tscn new file mode 100644 index 0000000..19295fd --- /dev/null +++ b/godot/tests/test_scale_and_look.tscn @@ -0,0 +1,27 @@ +[gd_scene load_steps=7 format=3 uid="uid://da6lgcbp5slpk"] + +[ext_resource type="PackedScene" uid="uid://difi2tur2j4dg" path="res://Models/island.tscn" id="1_noj3j"] +[ext_resource type="PackedScene" uid="uid://bgoo1lbt28na" path="res://Models/grape_man.tscn" id="2_wgkew"] +[ext_resource type="PackedScene" uid="uid://c3q6fva1c1baa" path="res://Models/slime.tscn" id="3_fy5yt"] +[ext_resource type="PackedScene" uid="uid://ctbyl0qbks4k6" path="res://Models/ocean.tscn" id="4_3bnpu"] +[ext_resource type="PackedScene" uid="uid://d2d4uv7o5gx5p" path="res://Level/World/screen_shader.tscn" id="5_ea8s5"] +[ext_resource type="PackedScene" uid="uid://b35w4hlh4n1jt" path="res://Level/World/world_environment.tscn" id="6_61q30"] + +[node name="test_scale" type="Node3D"] + +[node name="island" parent="." instance=ExtResource("1_noj3j")] + +[node name="grape_man" parent="." instance=ExtResource("2_wgkew")] +transform = Transform3D(0.065, 0, 0, 0, 0.065, 0, 0, 0, 0.065, -0.218604, 1.55987, 0) + +[node name="slime" parent="." instance=ExtResource("3_fy5yt")] +transform = Transform3D(0.035, 0, 0, 0, 0.035, 0, 0, 0, 0.035, -0.0855325, 1.58964, 0) + +[node name="Camera3D" type="Camera3D" parent="."] +transform = Transform3D(1, 0, 0, 0, 0.906308, 0.422618, 0, -0.422618, 0.906308, -0.086, 2.5, 1.04) + +[node name="ocean" parent="." instance=ExtResource("4_3bnpu")] + +[node name="ScreenShader" parent="." instance=ExtResource("5_ea8s5")] + +[node name="WorldEnvironment" parent="." instance=ExtResource("6_61q30")]