增加 shader 素材;优化飘动纸片的效果;部署 c01 书店内外的场景

This commit is contained in:
cakipaul 2025-02-06 20:19:45 +08:00
parent 6983b8a398
commit d879e9d3fa
38 changed files with 735 additions and 50 deletions

Binary file not shown.

After

Width:  |  Height:  |  Size: 86 KiB

View File

@ -0,0 +1,34 @@
[remap]
importer="texture"
type="CompressedTexture2D"
uid="uid://wvnpr0w3srtr"
path="res://.godot/imported/ghost-sheet.png-b0ae6f2c371a730d2abf0df2867d0094.ctex"
metadata={
"vram_texture": false
}
[deps]
source_file="res://asset/art/临时草稿/ghost-sheet.png"
dest_files=["res://.godot/imported/ghost-sheet.png-b0ae6f2c371a730d2abf0df2867d0094.ctex"]
[params]
compress/mode=0
compress/high_quality=false
compress/lossy_quality=0.7
compress/hdr_compression=1
compress/normal_map=0
compress/channel_pack=0
mipmaps/generate=false
mipmaps/limit=-1
roughness/mode=0
roughness/src_normal=""
process/fix_alpha_border=true
process/premult_alpha=false
process/normal_map_invert_y=false
process/hdr_as_srgb=false
process/hdr_clamp_exposure=false
process/size_limit=0
detect_3d/compress_to=1

Binary file not shown.

After

Width:  |  Height:  |  Size: 35 KiB

View File

@ -0,0 +1,34 @@
[remap]
importer="texture"
type="CompressedTexture2D"
uid="uid://dryx1iyict3gd"
path="res://.godot/imported/ghost.png-be8d53dbf62bca42bbf3c61f27140309.ctex"
metadata={
"vram_texture": false
}
[deps]
source_file="res://asset/art/临时草稿/ghost.png"
dest_files=["res://.godot/imported/ghost.png-be8d53dbf62bca42bbf3c61f27140309.ctex"]
[params]
compress/mode=0
compress/high_quality=false
compress/lossy_quality=0.7
compress/hdr_compression=1
compress/normal_map=0
compress/channel_pack=0
mipmaps/generate=false
mipmaps/limit=-1
roughness/mode=0
roughness/src_normal=""
process/fix_alpha_border=true
process/premult_alpha=false
process/normal_map_invert_y=false
process/hdr_as_srgb=false
process/hdr_clamp_exposure=false
process/size_limit=0
detect_3d/compress_to=1

Binary file not shown.

After

Width:  |  Height:  |  Size: 955 B

View File

@ -0,0 +1,34 @@
[remap]
importer="texture"
type="CompressedTexture2D"
uid="uid://c6vi6umco6o0a"
path="res://.godot/imported/纸片_正面.png-42b654938cd8738cd210ea618ad1b29d.ctex"
metadata={
"vram_texture": false
}
[deps]
source_file="res://asset/art/临时草稿/纸片_正面.png"
dest_files=["res://.godot/imported/纸片_正面.png-42b654938cd8738cd210ea618ad1b29d.ctex"]
[params]
compress/mode=0
compress/high_quality=false
compress/lossy_quality=0.7
compress/hdr_compression=1
compress/normal_map=0
compress/channel_pack=0
mipmaps/generate=false
mipmaps/limit=-1
roughness/mode=0
roughness/src_normal=""
process/fix_alpha_border=true
process/premult_alpha=false
process/normal_map_invert_y=false
process/hdr_as_srgb=false
process/hdr_clamp_exposure=false
process/size_limit=0
detect_3d/compress_to=1

View File

@ -40,7 +40,7 @@ ui_auto_saved,自动保存成功,,,,
ui_press_e,按 E 与场景互动,,,,
ui_press_b,按 B 打开背包,,,,
ui_press_shift,按住 Shift 奔跑,,,,
input_拼凑信件,按 E 旋转,方向键移动,,,,
input_拼凑信件,点击选择信件碎片,方向键移动,按 E 旋转,,,,
ui_获得,获得,,,,
ui_退出,退出,Exit,,,
ui_阅读,阅读,Read,,,

1 keys zh_CN en _character _notes _tags
40 ui_press_b 按 B 打开背包
41 ui_press_shift 按住 Shift 奔跑
42 input_拼凑信件 按 E 旋转,方向键移动 点击选择信件碎片,方向键移动,按 E 旋转
43 ui_获得 获得
44 ui_退出 退出 Exit
45 ui_阅读 阅读 Read
46 ui_检阅 检阅

View File

@ -22,7 +22,7 @@
按 E 与场景互动 [ID:ui_press_e]
按 B 打开背包 [ID:ui_press_b]
按住 Shift 奔跑 [ID:ui_press_shift]
按 E 旋转,方向键移动 [ID:input_拼凑信件]
点击选择信件碎片,方向键移动,按 E 旋转 [ID:input_拼凑信件]
获得 [ID:ui_获得]
退出 [ID:ui_退出]

View File

@ -1,6 +1,7 @@
/*
Glitch Effect Shader by Yui Kinomoto @arlez80
https://godotshaders.com/shader/glitch-effect-shader-for-godot-engine-4/
Glitch Effect Shader by Yui Kinomoto @arlez80
MIT License
*/

View File

@ -0,0 +1,23 @@
// https://godotshaders.com/shader/rotation-displacement-vertex-shader/
shader_type canvas_item;
// Set this to your polygon's center in local space.
uniform vec2 center = vec2(25., 25.);
uniform float amplitude : hint_range(0.0, 1.0) = 0.15;
uniform float frequency = 1.5;
void vertex() {
// Translate vertex position so the center is at (0, 0).
vec2 pos = VERTEX - center;
// Compute the angle of the vertex relative to the center.
// This angle will be used to offset the sine wave phase.
float angle = atan(pos.y, pos.x);
// Create a sine wave where each vertex is offset by its angle.
// You can adjust the formula as desired.
float wave = sin(TIME * frequency - angle);
// Use the wave value to scale the vertex's distance from the center.
pos *= 1.0 + amplitude * wave;
// Move the vertex back to the original coordinate space.
VERTEX = pos + center;
}

View File

@ -0,0 +1,30 @@
// https://godotshaders.com/shader/wobbly-grid/
shader_type canvas_item;
uniform float lineWidth : hint_range(0.0, 3.0, 0.1);
uniform vec2 size;
uniform sampler2D noise: filter_nearest;
uniform sampler2D noise2: filter_nearest;
uniform float edge_fade : hint_range(0.0, 1.0, 0.1);
uniform float wave_speed: hint_range(0.0, 10.0, 0.1);
void fragment() {
float n = texture(noise,mod(UV+-TIME*wave_speed/21.2,1.0)).r;
float n2 = texture(noise2,mod(UV+14.7+TIME*wave_speed/40.3,1.0)).r;;
float n3 = clamp(0.0,0.3+pow(n+(n2*0.4),3.0)*1.5,1.0);
//COLOR.rgb *= vec3(n3);
vec2 m = 1.0-(edge_fade*abs(UV-0.5)*2.0*size-size+1.0+lineWidth/50.0);
float ma = min(m.x,m.y);
float uvx = mod(UV.x-((n3-0.5)/100.0)-(mod(size.x,2)/2.0+0.5),1.0/size.x)*size.x;
float uvy = mod(UV.y-((n3-0.5)/100.0)-(mod(size.y,2)/2.0+0.5),1.0/size.y)*size.y;
vec2 uv = vec2(uvx,uvy);
vec2 w = size * max(n3,0.5) * lineWidth/10.0;
if(((uv.x>=w.x)&&(uv.x<=1.0-w.x))&&((uv.y>=w.y)&&(uv.y<=1.0-w.y))){
discard;
}
COLOR.a = ma * n3;
}

View File

@ -0,0 +1,22 @@
[gd_resource type="ShaderMaterial" load_steps=6 format=3 uid="uid://dwf85pmqefh3v"]
[ext_resource type="Shader" path="res://asset/shader/wobbly_grid.gdshader" id="1_dm0mo"]
[sub_resource type="FastNoiseLite" id="FastNoiseLite_i7qxy"]
[sub_resource type="NoiseTexture2D" id="NoiseTexture2D_hol54"]
noise = SubResource("FastNoiseLite_i7qxy")
[sub_resource type="FastNoiseLite" id="FastNoiseLite_5dvys"]
[sub_resource type="NoiseTexture2D" id="NoiseTexture2D_8s07y"]
noise = SubResource("FastNoiseLite_5dvys")
[resource]
shader = ExtResource("1_dm0mo")
shader_parameter/lineWidth = 0.1
shader_parameter/size = Vector2(8, 8)
shader_parameter/edge_fade = 1.0
shader_parameter/wave_speed = 1.0
shader_parameter/noise = SubResource("NoiseTexture2D_hol54")
shader_parameter/noise2 = SubResource("NoiseTexture2D_8s07y")

View File

@ -0,0 +1,53 @@
// https://godotshaders.com/shader/2d-aurora-borealis/
shader_type canvas_item;
group_uniforms Frag_unis;
uniform float aurora_scroll_speed: hint_range(0.0, 1.0, 0.1) = .2;
uniform float color_scroll_speed: hint_range(0.0, 5.0, 0.1) = 1.2;
uniform sampler2D lower_transparency_mask :repeat_enable;
uniform float curve_horizontal_repition: hint_range(1.0, 10.0, 0.0001);
uniform float glow_strength: hint_range(0.0, 10.0, 0.01) = 3.;
uniform float base_white_size: hint_range(0.0, 10.0, 0.01) = 1.5;
uniform sampler2D gradient_base :repeat_enable;
uniform vec4 tint: source_color = vec4(0.3, 0.8, 0.5,0.0);
group_uniforms Vertex_unis;
uniform float sway_strength = 1.2;
uniform float sway_phase_len = 1.2;
uniform float sway_speed = 1.2;
void vertex() {
float strength = COLOR.r * sway_strength;
VERTEX.x += sin(VERTEX.x * sway_phase_len * 1.123 + TIME * sway_speed) * strength;
VERTEX.y += cos(VERTEX.y * sway_phase_len + TIME * sway_speed * 1.12412) * strength;
}
void fragment() {
vec2 scroll_uv = vec2(UV.x + TIME * aurora_scroll_speed, UV.y);
vec4 result = texture(TEXTURE, scroll_uv);
//the sin is optional causes there to be more "play" of the colors
vec4 base_color = texture(gradient_base, vec2(scroll_uv.x + sin(TIME * color_scroll_speed)+.2, scroll_uv.y));
//we subtract TIME to make the transparency mask move in the opposite direction of the aurora, looks more funky imo :3
//also we do UV.y -.01 to get rid of a ugly 1 px wide line that would appear else wise OTL
vec4 curve = texture(lower_transparency_mask, vec2(UV.x * curve_horizontal_repition - TIME * .3, UV.y -.01 ));
//applies the transparency of our mask texture to avoid a hard lower cutoff
result.a *= mix(result.a, 0., curve.a);
//add stronger luminance to the base of the aurora
result.rgb *= mix(result.rgb, result.rgb*base_white_size, curve.a);
//more transparency mixing to create a more "organic" looking result
result.a *= mix(0., 1., result.r);
result.a *= mix(0,1, UV.y);
//more funky color magic, remove/edit as needed
result.rgb *= mix(result.rgb, base_color.rgb, UV.y );
result.rgb *= mix(result.rgb, result.rgb*glow_strength,UV.y);
result.rgb *= mix(result.rgb, result.rgb*glow_strength, curve.a);
//gives it an overall richer color
result.rgb *= tint.rgb;
COLOR = result;
}

View File

@ -0,0 +1,62 @@
// https://godotshaders.com/shader/balatro-background-shader/
shader_type canvas_item;
//took it directly from balatro source code
//buy balatro now: https://www.playbalatro.com
uniform highp float spin_rotation_speed = 2.0;
uniform highp float move_speed = 7.0;
uniform highp vec2 offset = vec2(0., 0.);
uniform highp vec4 colour_1 : source_color = vec4(0.871, 0.267, 0.231, 1.0);
uniform highp vec4 colour_2 : source_color = vec4(0.0, 0.42, 0.706, 1.0);
uniform highp vec4 colour_3 : source_color = vec4(0.086, 0.137, 0.145, 1.0);
uniform highp float contrast = 3.5;
uniform highp float lighting = 0.4;
uniform highp float spin_amount = 0.25;
uniform highp float pixel_filter = 740.;
uniform bool is_rotating = false;
#define SPIN_EASE 1.0
vec4 effect(vec2 screenSize, vec2 screen_coords){
highp float pixel_size = length(screenSize.xy) / pixel_filter;
highp vec2 uv = (floor(screen_coords.xy*(1./pixel_size))*pixel_size - 0.5*screenSize.xy)/length(screenSize.xy) - offset;
highp float uv_len = length(uv);
highp float speed = (spin_rotation_speed*SPIN_EASE*0.2);
if(is_rotating){
speed = TIME * speed;
}
speed += 302.2;
highp float new_pixel_angle = (atan(uv.y, uv.x)) + speed - SPIN_EASE*20.*(1.*spin_amount*uv_len + (1. - 1.*spin_amount));
highp vec2 mid = (screenSize.xy/length(screenSize.xy))/2.;
uv = (vec2((uv_len * cos(new_pixel_angle) + mid.x), (uv_len * sin(new_pixel_angle) + mid.y)) - mid);
uv *= 30.;
speed = TIME*(move_speed);
highp vec2 uv2 = vec2(uv.x+uv.y);
for(int i=0; i < 5; i++) {
uv2 += sin(max(uv.x, uv.y)) + uv;
uv += 0.5*vec2(cos(5.1123314 + 0.353*uv2.y + speed*0.131121),sin(uv2.x - 0.113*speed));
uv -= 1.0*cos(uv.x + uv.y) - 1.0*sin(uv.x*0.711 - uv.y);
}
highp float contrast_mod = (0.25*contrast + 0.5*spin_amount + 1.2);
highp float paint_res = min(2., max(0.,length(uv)*(0.035)*contrast_mod));
highp float c1p = max(0.,1. - contrast_mod*abs(1.-paint_res));
highp float c2p = max(0.,1. - contrast_mod*abs(paint_res));
highp float c3p = 1. - min(1., c1p + c2p);
highp float ligth = (lighting - 0.2) * max(c1p*5. - 4., 0.) + lighting * max(c2p*5. - 4., 0.);
highp vec4 ret_col = (0.3/contrast)*colour_1 + (1. - 0.3/contrast)*(colour_1*c1p + colour_2*c2p + vec4(c3p*colour_3.rgb, c3p*colour_1.a)) + ligth;
return ret_col;
}
void fragment() {
vec2 uv = UV;
COLOR *= effect(TEXTURE_PIXEL_SIZE, uv);
}

View File

@ -0,0 +1,52 @@
// https://godotshaders.com/shader/balatro-fire-shader/
shader_type canvas_item;
uniform sampler2D noise_tex : hint_default_white;
uniform vec4 bottom_color : source_color = vec4(0.0, 0.7, 1.0, 1.0);
uniform vec4 middle_color : source_color = vec4(1.0, 0.5, 0.0, 1.0);
uniform vec4 top_color : source_color = vec4(1.0, 0.03, 0.001, 1.0);
uniform float fire_alpha : hint_range(0.0, 1.0) = 1.0;
uniform vec2 fire_speed = vec2(0.0, 2.0);
uniform float fire_aperture : hint_range(0.0, 3.0) = 0.22;
vec4 tri_color_mix(vec4 color1, vec4 color2, vec4 color3, float pos) {
pos = clamp(pos, 0.0, 1.0);
if (pos < 0.5) {
return mix(color1, color2, pos * 2.0);
} else {
return mix(color2, color3, (pos - 0.5) * 2.0);
}
}
void fragment() {
// Scale UVs to make the noise more visible
vec2 base_uv = UV * 1.0;
// Create two layers of noise with different speeds
vec2 shifted_uv1 = base_uv + TIME * fire_speed;
vec2 shifted_uv2 = base_uv + TIME * fire_speed * 1.5;
// Sample noise texture twice
float fire_noise1 = texture(noise_tex, fract(shifted_uv1)).r;
float fire_noise2 = texture(noise_tex, fract(shifted_uv2)).r;
// Combine the noise samples
float combined_noise = (fire_noise1 + fire_noise2) * 0.5;
// Calculate fire shape
float noise = UV.y * (((UV.y + fire_aperture) * combined_noise - fire_aperture) * 75.0);
// Add horizontal movement
noise += sin(UV.y * 10.0 + TIME * 2.0) * 0.1;
// Calculate gradient position and mix three colors
float gradient_pos = clamp(noise * 0.08, 0.3, 2.0);
//vec4 smoth_mid_color = smoothstep(top_color, middle_color, vec4(1));
vec4 fire_color = tri_color_mix(bottom_color, middle_color, top_color, gradient_pos);
// Set final color and alpha
COLOR = fire_color;
COLOR.a = clamp(noise, 0.0, 1.0) * fire_alpha;
}

View File

@ -0,0 +1,29 @@
//https://godotshaders.com/shader/electric-ball-canvas-item/
shader_type canvas_item;
render_mode blend_add;
uniform sampler2D noise : repeat_enable;
uniform sampler2D noise2 : repeat_enable;
uniform float brightness = 2.5;
uniform float time_scale = 1.0;
void fragment() {
vec2 cc_uv = UV - vec2(.5);
float angle = atan(cc_uv.y, cc_uv.x) / PI + 1.;
float p = sqrt(dot(cc_uv, cc_uv));
vec2 puv = vec2(p, angle * .5);
vec2 uv = puv * 2.;
float time = TIME * time_scale;
vec4 old_colo = COLOR;
COLOR = vec4(.0);
for(int i = 1; i <= 5; i++){
float intensive = .1 + .07 * float(i);
vec2 offset = (texture(noise, vec2(time*.35*(.5+fract(sin(float(i)*55.))), angle)).rg - vec2(.5)) * intensive;
vec2 uuv = uv + offset;
float dist = abs(uuv.x - .5);
float rand_speed = .2 + .05 * fract(cos(float(i)*1144.));
float gone = smoothstep(.1 + 0.05 * (float(i) - .5), 1.0, texture(noise2, uv + vec2(time*rand_speed)).s);
COLOR += gone * old_colo / dist * .01 * texture(noise2, uuv + vec2(time)).s;
}
vec4 light = old_colo * smoothstep(1.0, -2.0, abs(uv.x - .5) * 2.0) * texture(noise2, uv).a;
COLOR += light * brightness;
}

View File

@ -0,0 +1,49 @@
//https://godotshaders.com/shader/fireball-fire-ball-with-light/
shader_type canvas_item;
render_mode blend_add;
uniform float s_scale_y = 1.0;
uniform float l_s_scale_y = 1.0;
uniform float lness = 1.0;
uniform float lness2 = .0;
uniform sampler2D noise : repeat_enable, filter_nearest_mipmap_anisotropic;
uniform sampler2D noise2 : repeat_enable, filter_nearest_mipmap_anisotropic;
uniform sampler2D colo_curve;
vec4 f1(vec2 uv, float time){
vec4 nv2 = texture(noise, uv + vec2(time, 0.0));
vec4 n2v2 = texture(noise2, uv + vec2(time*.8, 0.0));
nv2.a = max(0., nv2.a + uv.x - 1.0);
n2v2.a = max(0., n2v2.a + uv.x - 1.0);
return nv2 * n2v2;
}
void fragment()
{
vec2 mUV = UV * 4. - 1.5;
vec2 uv = mUV * vec2(1., s_scale_y);
float time = TIME;
vec2 cuv = mUV - vec2(.5);
float d2c = length(cuv);
vec4 color = COLOR;
//
color *= (f1(uv, time) + f1(uv + vec2(.1,0.), time+11.514) + f1(uv+vec2(.05,0.), time+14.14));
color.a -= 1.0;
color.a = - pow(color.a, 2.0) + 1.0;
//
color.rgb = texture(colo_curve, vec2(color.a,0.)).rgb;
float randmoo = texture(noise2, mUV + vec2(time, -time)).a;
randmoo = mix(randmoo, 0., mUV.x);
color.a *= smoothstep(.5, .48 - (.2 - min(mUV.x, 1.0)*.2), d2c + randmoo * 0.4);
COLOR = color;
COLOR.rgb = mix(COLOR.rgb, vec3(.0), smoothstep(0.00001, 0.0, color.a));
// light
float d2c_l = length(UV * vec2(1., l_s_scale_y) - vec2(.58, .5*l_s_scale_y));
float l = - log(d2c_l + lness2) * lness;
float randmoo2 = texture(noise2, vec2(time, -time)).a;
COLOR += texture(colo_curve, vec2(1.0-d2c_l - .1*randmoo2, 0.0)) * l;
//COLOR += vec4(.8, .8, .6, 1.0) * l;
//
COLOR.a *= smoothstep(0.5, 0.1, length(UV - vec2(.5)));
}

View File

@ -0,0 +1,51 @@
//https://godotshaders.com/shader/ball-of-fire/
shader_type canvas_item;
uniform float time : hint_range(0.0, 10.0);
float snoise(vec3 uv, float res)
{
const vec3 s = vec3(1e0, 1e2, 1e3);
uv *= res;
vec3 uv0 = floor(mod(uv, res)) * s;
vec3 uv1 = floor(mod(uv + vec3(1.0), res)) * s;
vec3 f = fract(uv);
f = f * f * (3.0 - 2.0 * f);
vec4 v = vec4(uv0.x + uv0.y + uv0.z, uv1.x + uv0.y + uv0.z,
uv0.x + uv1.y + uv0.z, uv1.x + uv1.y + uv0.z);
vec4 r = fract(sin(v * 1e-1) * 1e3);
float r0 = mix(mix(r.x, r.y, f.x), mix(r.z, r.w, f.x), f.y);
r = fract(sin((v + uv1.z - uv0.z) * 1e-1) * 1e3);
float r1 = mix(mix(r.x, r.y, f.x), mix(r.z, r.w, f.x), f.y);
return mix(r0, r1, f.z) * 2.0 - 1.0;
}
void fragment()
{
// Calcular las coordenadas de la pantalla usando SCREEN_PIXEL_SIZE
vec2 screen_size = vec2(1.0 / SCREEN_PIXEL_SIZE.x, 1.0 / SCREEN_PIXEL_SIZE.y);
vec2 fragCoord = FRAGCOORD.xy;
vec2 p = -0.5 + fragCoord.xy / screen_size;
p.x *= screen_size.x / screen_size.y;
float color = 3.0 - (3.0 * length(2.0 * p));
vec3 coord = vec3(atan(p.x, p.y) / 6.2832 + 0.5, length(p) * 0.4, 0.5);
// if you dont want use gdscript to animate you can replace the 'time' to 'TIME'
for (int i = 1; i <= 7; i++)
{
float power = pow(2.0, float(i));
color += (1.5 / power) * snoise(coord + vec3(0.0, -time * 0.05, time * 0.01), power * 16.0);
}
COLOR = vec4(color, pow(max(color, 0.0), 2.0) * 0.4, pow(max(color, 0.0), 3.0) * 0.15, 1.0);
}

View File

@ -0,0 +1,83 @@
// https://godotshaders.com/shader/highlight-canvasitem/
shader_type canvas_item;
//Color is controlled by the object itself, change the color property of the ColorRect to change the highlight
// if the shader is applyed to the texture element, then the texture will be clipped by the highlight
render_mode blend_premul_alpha;
// makes the highlight edges softer, 0 = hard edges;
uniform float Line_Smoothness : hint_range(0, 0.1) = 0.045;
// makes line thiner/wider, 0 = thin line;
uniform float Line_Width : hint_range(0, 0.2) = 0.09;
//multiplicative parameter, that makes the line more visible,
// diffirent combinations of Line Smoothness, Line Width and Brightness produces various results;
uniform float Brightness = 3.0;
// rotates the highlight, incrementing the value rotates the highlight clockwise;
uniform float Rotation_deg : hint_range(-90, 90) = 30;
// merges line with the edges of the ColorRect (see ColorRect in How to use section);
uniform float Distortion : hint_range(1, 2) = 1.8;
// dictates how fast the effect is moving from one side to the opposite;
uniform float Speed = 0.7;
// manual placement of the highlight line, 0 = Position Min, 1 = Position Max;
uniform float Position : hint_range(0, 1) = 0;
// starting point of the highlight line;
uniform float Position_Min = 0.25;
// end point of the highlight line;
uniform float Position_Max = 0.5;
// controls the overall visibility of the highlight;
uniform float Alpha : hint_range(0, 1) = 1;
vec2 rotate_uv(vec2 uv, vec2 center, float rotation, bool use_degrees){
float _angle = rotation;
if(use_degrees){
_angle = rotation * (3.1415926/180.0);
}
mat2 _rotation = mat2(
vec2(cos(_angle), -sin(_angle)),
vec2(sin(_angle), cos(_angle))
);
vec2 _delta = uv - center;
_delta = _rotation * _delta;
return _delta + center;
}
void fragment() {
vec2 center_uv = UV - vec2(0.5, 0.5);
float gradient_to_edge = max(abs(center_uv.x), abs(center_uv.y));
gradient_to_edge = gradient_to_edge * Distortion;
gradient_to_edge = 1.0 - gradient_to_edge;
vec2 rotaded_uv = rotate_uv(UV, vec2(0.5, 0.5), Rotation_deg, true);
float remapped_position;
{
float output_range = Position_Max - Position_Min;
remapped_position = Position_Min + output_range * Position;
}
float remapped_time = TIME * Speed + remapped_position;
remapped_time = fract(remapped_time);
{
float output_range = 2.0 - (-2.0);
remapped_time = -2.0 + output_range * remapped_time;
}
vec2 offset_uv = vec2(rotaded_uv.xy) + vec2(remapped_time, 0.0);
float line = vec3(offset_uv, 0.0).x;
line = abs(line);
line = gradient_to_edge * line;
line = sqrt(line);
float line_smoothness = clamp(Line_Smoothness, 0.001, 1.0);
float offset_plus = Line_Width + line_smoothness;
float offset_minus = Line_Width - line_smoothness;
float remapped_line;
{
float input_range = offset_minus - offset_plus;
remapped_line = (line - offset_plus) / input_range;
}
remapped_line = remapped_line * Brightness;
remapped_line = min(remapped_line, Alpha);
COLOR.rgb = vec3(COLOR.xyz) * vec3(remapped_line);
COLOR.a = remapped_line;
}

View File

@ -0,0 +1,43 @@
//https://godotshaders.com/shader/transparent-ripples/
// Attach to a ColorRect in front of texture/background
shader_type canvas_item;
// Handles the concentric ripples
uniform float frequency: hint_range(0, 15, 0.01) = 4.0;
uniform float amplitude: hint_range(0, 3, 0.1) = 2.0;
uniform float ripple_rate : hint_range(0, 20.0, 1) = 5;
// Handles the waves themselves
uniform float wave_amplitude: hint_range(0.001, 0.1, 0.001) = 0.05;
uniform float wave_frequency: hint_range(0, 15, 0.01) = 4.0;
uniform sampler2D noise;
uniform sampler2D SCREEN_TEXTURE: hint_screen_texture, filter_linear_mipmap;
vec2 wave(vec2 uv, float time) {
return vec2(
uv.x + sin(uv.y * wave_frequency + time) * wave_amplitude,
uv.y + sin(uv.x * wave_frequency + time) * wave_amplitude
);
}
void fragment() {
vec2 center_position = -1.0 + 2.0 * UV / (1.0 / TEXTURE_PIXEL_SIZE);
float center_distance = length(center_position);
float ripple = sin(center_distance * -frequency * PI + ripple_rate * TIME) * amplitude / (center_distance + 1.0);
vec2 uv = FRAGCOORD.xy / (1.0 / SCREEN_PIXEL_SIZE).xy + (center_position/center_distance) * ripple * wave_amplitude;
vec2 background_wave = wave(uv, TIME);
vec4 background_texture = texture(SCREEN_TEXTURE,background_wave) * sqrt(amplitude);
float alpha_scalar = (1.0 - min(center_distance, 1.0)) * background_texture.x * 2.5;
background_texture.a *= 1.0 * alpha_scalar * (ripple + background_texture.x * background_texture.y);
background_texture.a = max(background_texture.a - (background_texture.y * 0.45), 0.0);
COLOR = vec4(background_texture.xyz, background_texture.a);
}

View File

@ -0,0 +1,31 @@
//https://godotshaders.com/shader/weird-tube-with-balls/
shader_type canvas_item;
uniform float whiteness = 0.0;
uniform float l = 100.0;
uniform float balls[16];
uniform float basic_wid_s = .1;
float my_smooth(float a, float b, float v) {
return smoothstep(a, b, v) * .2 + smoothstep(a * 2., b, v)*.2 + smoothstep(a * 5., b, v)*.3;
}
void fragment() {
COLOR = vec4(vec3(1.), smoothstep(basic_wid_s, basic_wid_s-.01, 2. * abs(UV.y - .5)));
float closeness = 0.0;
for(int i = 0; i < balls.length(); i++) {
float offset = balls[i];
float edge_shrink = smoothstep(0.0, .01, offset) * smoothstep(1.0, 0.99, offset);
closeness += my_smooth(.1 / l * 255.0 * edge_shrink, .0, abs(UV.x - offset))
/ (float(balls.length()) + float(i)) * edge_shrink;
//COLOR += vec4(vec3(1.), closeness * smoothstep(.4, .0, 2. * abs(UV.y - .5)));
}
closeness = smoothstep(0.0, 1.0, .7 + closeness * .4) - smoothstep(0.0, 1.0, .7);
closeness *= 2.2;
float edge_shrink_t = smoothstep(- 0.02, .035, UV.x) * smoothstep(1.02, 0.965, UV.x);
closeness *= edge_shrink_t;
float a = smoothstep(closeness, -0.0001, 2. * abs(UV.y - .5));
a = smoothstep(.0, .2, a);
COLOR += vec4(vec3(1.), a);
}

View File

@ -6,7 +6,7 @@ class_name Portal2D extends Sprite2D
set(val):
enabled = val
_check_sign_mark_and_texture()
@export var immediately := true
@export var immediately := false
@export_enum("left", "right", "1", "2", "3", "4", "5", "6", "7", "8", "9") var portal_name := "left":
set(value):
#if portal_name:

View File

@ -138,7 +138,8 @@ func play_footstep_sound() -> void:
func move_player_to_portal(portal_name: String) -> void:
var portal_node = get_node_or_null("DeployLayer/portal_" + portal_name) as Node2D
var node_path = NodePath("DeployLayer/portal_" + portal_name)
var portal_node = get_node_or_null(node_path) as Portal2D
if portal_node and player:
player.global_position.x = portal_node.global_position.x
if portal_name == "left":
@ -148,7 +149,9 @@ func move_player_to_portal(portal_name: String) -> void:
_reset_player_y()
if GlobalConfig.DEBUG:
print("move player to portal:", portal_name, portal_node.global_position)
elif player:
printerr(scene_name, " portal not found: ", node_path)
else:
printerr(scene_name + " portal not found: " + portal_name)
printerr("move_player_to_portal player not ready")
# 传送后,重置 camera 位置
camera_focus_marker.reset_position_immediately()

View File

@ -66,6 +66,7 @@ portal_name = "1"
[node name="portal_2" parent="Ground/DeployLayer" index="3" instance=ExtResource("4_ulvsd")]
position = Vector2(995, 28)
debug_note = "c01_s07 的 2 号门通往书店"
immediately = false
portal_name = "2"
target_scene = "c01_s08"
target_portal = "left"

View File

@ -22,11 +22,10 @@ func _on_ground_ready() -> void:
mask = $"../DeployLayer/Mask"
var shelf_game_success = ArchiveManager.archive.get_global_value("shelf_game_success")
if shelf_game_success:
# 书架游戏成功后,展示诡异的街道
_set_portal_target_to_wierd_street()
_on_game_success()
var game_secne = preload("res://scene/little_game/书架.tscn")
var game_secne = preload("res://scene/little_game/书架/书架.tscn")
var game_node = game_secne.instantiate()
@ -52,11 +51,12 @@ func _on_game_exiting() -> void:
func _on_game_success() -> void:
ArchiveManager.archive.set_global_entry("shelf_game_success", true)
_set_portal_target_to_wierd_street()
#TODO: 书架游戏成功后的处理
# 书架游戏成功后,展示老鼠
$"../DeployLayer/自动跟随的老鼠".visible = true
func _set_portal_target_to_wierd_street() -> void:
# 设置传送门目标为诡异的街道
var portal = $"../DeployLayer/portal_left" as Portal2D
portal.target_scene = "c01_s07"
portal.target_portal = "portal_2"
portal.target_scene = "c01_s12"
portal.target_portal = "2"

View File

@ -1,10 +1,11 @@
[gd_scene load_steps=7 format=3 uid="uid://cwu4dhayra8pg"]
[gd_scene load_steps=8 format=3 uid="uid://cwu4dhayra8pg"]
[ext_resource type="PackedScene" uid="uid://dayyx4jerj7io" path="res://scene/ground/ground.tscn" id="1_b3cca"]
[ext_resource type="Script" path="res://scene/ground/scene/c01/s08_animation.gd" id="2_0lque"]
[ext_resource type="Texture2D" uid="uid://coo8sw8yigii6" path="res://asset/art/scene/c01/s08_书店/bg_书店.png" id="3_322m4"]
[ext_resource type="PackedScene" uid="uid://bnf3lkcbpx1ar" path="res://scene/entity/ambush.tscn" id="4_c4lg5"]
[ext_resource type="Texture2D" uid="uid://cqy0qfmko00rx" path="res://asset/art/scene/c01/s08_书店/e_梯子.png" id="5_tnrke"]
[ext_resource type="PackedScene" uid="uid://nwpbl5yuh280" path="res://scene/ground/script/c01/s00_自动跟随的老鼠.tscn" id="6_05do1"]
[ext_resource type="Texture2D" uid="uid://c3ii6vsja0645" path="res://asset/art/scene/c01/s08_书店/书店参考.png" id="6_l2q02"]
[node name="S08" type="Node2D"]
@ -29,7 +30,6 @@ target_scene = "c01_s07"
target_portal = "2"
[node name="portal_right" parent="Ground/DeployLayer" index="1"]
immediately = false
target_scene = "c02_s08"
[node name="Ambush梯子" parent="Ground/DeployLayer" index="2" instance=ExtResource("4_c4lg5")]
@ -55,6 +55,10 @@ grow_vertical = 2
mouse_filter = 2
color = Color(0, 0, 0, 0)
[node name="自动跟随的老鼠" parent="Ground/DeployLayer" index="4" instance=ExtResource("6_05do1")]
position = Vector2(-8, 88)
action_area = Vector2(600, 32)
[node name="MainPlayer" parent="Ground" index="5"]
position = Vector2(41, 98)
character = "小小蝶"

View File

@ -19,9 +19,11 @@ var ghost
func _on_ground_ready() -> void:
ghost = $"../DeployLayer/Ghost"
# test
call_deferred("_ghost_move")
# call_deferred("_ghost_move")
func _ghost_move() -> void:
ghost.visible = true
ghost.play()
var tween = create_tween()
tween.tween_property(ghost, "global_position", Vector2(1500, 0), 20.0).as_relative()

View File

@ -1,4 +1,4 @@
[gd_scene load_steps=12 format=3 uid="uid://bol5hl68pbpgq"]
[gd_scene load_steps=13 format=3 uid="uid://bol5hl68pbpgq"]
[ext_resource type="PackedScene" uid="uid://dayyx4jerj7io" path="res://scene/ground/ground.tscn" id="1_llw14"]
[ext_resource type="Script" path="res://scene/ground/scene/c01/s12_animation.gd" id="2_krdvw"]
@ -11,6 +11,7 @@
[ext_resource type="PackedScene" uid="uid://ci34db7xool2n" path="res://scene/ground/script/c01/s01_自动枯萎的花朵.tscn" id="7_aq8vg"]
[ext_resource type="PackedScene" uid="uid://h0s5ms7r7d8g" path="res://scene/shading/ghost.tscn" id="8_gk0gq"]
[ext_resource type="PackedScene" uid="uid://bnf3lkcbpx1ar" path="res://scene/entity/ambush.tscn" id="9_nqlku"]
[ext_resource type="PackedScene" uid="uid://nwpbl5yuh280" path="res://scene/ground/script/c01/s00_自动跟随的老鼠.tscn" id="12_qpv8m"]
[node name="S12" type="Node2D"]
@ -31,7 +32,6 @@ texture = ExtResource("3_npdxo")
offset = Vector2(0, -158)
[node name="portal_right" parent="Ground/DeployLayer" index="1"]
immediately = false
target_scene = "c02_s08"
[node name="portal_2" parent="Ground/DeployLayer" index="2" instance=ExtResource("4_o7hfk")]
@ -53,12 +53,18 @@ position = Vector2(36, 81)
focus_node = NodePath("../Ghost")
[node name="Ghost" parent="Ground/DeployLayer" index="5" instance=ExtResource("8_gk0gq")]
visible = false
z_index = 10
position = Vector2(-159, 23)
position = Vector2(-158, 23)
autoplay = ""
[node name="Ambush玩家被抓" parent="Ground/DeployLayer/Ghost" instance=ExtResource("9_nqlku")]
freeze_time = 0.1
[node name="自动跟随的老鼠" parent="Ground/DeployLayer" index="6" instance=ExtResource("12_qpv8m")]
position = Vector2(-7, 80)
action_area = Vector2(1550, 40)
[node name="Light" parent="Ground/AmbientLayer" index="0" instance=ExtResource("5_kywnm")]
position = Vector2(999, -5)
texture = null

View File

@ -24,11 +24,13 @@ texture = ExtResource("2_ni1a4")
[node name="portal_left" parent="Ground/DeployLayer" index="0"]
position = Vector2(78, 27)
immediately = true
[node name="portal_right" parent="Ground/DeployLayer" index="1"]
position = Vector2(392, 2)
target_scene = "c02_s02"
target_portal = "left"
status = "opened"
[node name="Note寻人启事" parent="Ground/DeployLayer" index="2" instance=ExtResource("3_6lnxd")]
position = Vector2(250, -22)

View File

@ -51,6 +51,7 @@ position = Vector2(2286, 16)
[node name="portal_1" parent="Ground/DeployLayer" index="2" instance=ExtResource("5_00b7a")]
position = Vector2(193, 14)
debug_note = "1012保卫科"
immediately = false
portal_name = "1"
target_scene = "c02_s05"
target_portal = "left"

View File

@ -75,7 +75,7 @@ func _init_mice(scatter := scatter_on_start) -> void:
func _physics_process(delta: float) -> void:
if Engine.is_editor_hint() or not enabled:
if Engine.is_editor_hint() or not enabled or not visible:
return
if not player:
player = SceneManager.get_player()

View File

@ -2,15 +2,7 @@
extends Node2D
@export var velocity := 0.1
@export var remote_node: Node2D:
set(val):
remote_node = val
if is_node_ready():
if remote_node:
remote_transform.remote_path = remote_node.get_path()
else:
remote_transform.remote_path = ""
@export var remote_node: Node2D
@export var area_size := Vector2(400, 50):
set(val):
area_size = val
@ -20,11 +12,10 @@ extends Node2D
gizmo_outline_color = val
queue_redraw()
@onready var remote_transform := $RemoteTransform2D as RemoteTransform2D
@onready var sprite_frames := $Sprite2D as Sprite2D
func _draw() -> void:
remote_transform.remote_path = remote_node.get_path()
if Engine.is_editor_hint():
# draw gizmo
var area_rect = Rect2(Vector2.ZERO, area_size)
@ -100,7 +91,7 @@ func _rand_point() -> Vector2:
# 设置到 remote_transform 的 position 与 rotation
# 速度为 velocity权重为 weight
func _process(delta: float) -> void:
if Engine.is_editor_hint():
if Engine.is_editor_hint() or not remote_node:
return
weight += velocity * delta
if weight >= 1.0:
@ -114,6 +105,7 @@ func _process(delta: float) -> void:
var p = p1.cubic_interpolate(p2, p0, p3, weight)
# var p = p1.bezier_interpolate(p0, p3, p2, weight)
remote_transform.position = p
remote_node.position = p
# bezier 插值获得角度
remote_transform.rotation = lerp_angle(remote_transform.rotation, p1.angle_to(p2), delta)
remote_node.rotation = lerp_angle(remote_node.rotation, p1.angle_to(p2), delta)
remote_node.skew = -remote_node.rotation * 0.5

View File

@ -1,7 +1,14 @@
[gd_scene load_steps=3 format=3 uid="uid://cn1ypquvs07wx"]
[gd_scene load_steps=5 format=3 uid="uid://cn1ypquvs07wx"]
[ext_resource type="Script" path="res://scene/ground/script/c01/s12_飘动的寻人启事.gd" id="1_like6"]
[ext_resource type="Texture2D" uid="uid://cx8ny1barwdwy" path="res://asset/art/临时草稿/纸片.png" id="2_46pmx"]
[ext_resource type="Shader" path="res://asset/shader/rotation_displacement_vertex.gdshader" id="2_2w1m2"]
[ext_resource type="Texture2D" uid="uid://c6vi6umco6o0a" path="res://asset/art/临时草稿/纸片_正面.png" id="3_dl751"]
[sub_resource type="ShaderMaterial" id="ShaderMaterial_q4vn8"]
shader = ExtResource("2_2w1m2")
shader_parameter/center = Vector2(25, 25)
shader_parameter/amplitude = 0.15
shader_parameter/frequency = 1.5
[node name="S12" type="Node2D" node_paths=PackedStringArray("remote_node")]
position = Vector2(43, 96)
@ -10,9 +17,6 @@ velocity = 0.4
remote_node = NodePath("Sprite2D")
area_size = Vector2(500, 150)
[node name="RemoteTransform2D" type="RemoteTransform2D" parent="."]
remote_path = NodePath("/root/@EditorNode@16896/@Panel@13/@VBoxContainer@14/DockHSplitLeftL/DockHSplitLeftR/DockHSplitMain/@VBoxContainer@25/DockVSplitCenter/@VSplitContainer@52/@VBoxContainer@53/@PanelContainer@98/MainScreen/@CanvasItemEditor@9280/@VSplitContainer@9102/@HSplitContainer@9104/@HSplitContainer@9106/@Control@9107/@SubViewportContainer@9108/@SubViewport@9109/S12/Sprite2D")
update_scale = false
[node name="Sprite2D" type="Sprite2D" parent="."]
texture = ExtResource("2_46pmx")
material = SubResource("ShaderMaterial_q4vn8")
texture = ExtResource("3_dl751")

View File

@ -1,6 +1,6 @@
[gd_scene load_steps=54 format=3 uid="uid://fwfr0b2sylwx"]
[ext_resource type="Script" path="res://scene/little_game/书架.gd" id="1_8af23"]
[ext_resource type="Script" path="res://scene/little_game/书架/书架.gd" id="1_8af23"]
[ext_resource type="PackedScene" uid="uid://c85t6stvytvjn" path="res://scene/entity/general/sfx.tscn" id="3_03tyv"]
[ext_resource type="AudioStream" uid="uid://bi4hcr04231qr" path="res://asset/audio/sfx/ui/挂画查看.mp3" id="3_elhhm"]
[ext_resource type="AudioStream" uid="uid://dky3j8lwcy5sk" path="res://asset/audio/sfx/ui/物品查看.mp3" id="4_0ihy7"]

View File

@ -0,0 +1,7 @@
[gd_scene format=3 uid="uid://bl5pohc77hi43"]
[node name="生死簿" type="Node2D"]
[node name="p1" type="Sprite2D" parent="."]
[node name="p2" type="Sprite2D" parent="."]

View File

@ -4,6 +4,7 @@ extends CanvasLayer
@onready var whole = %Whole as Sprite2D
# from part 0 to 3, rotated by 0, 90, 180, 270 degrees
var rotations = [0, 0, 0, 0]
var images = []
var selected := 0:
set(value):
@ -16,6 +17,7 @@ func _ready() -> void:
for i in range(4):
var part = container.get_child(i)
part.pressed.connect(_select_part.bind(part))
images.append(part.texture_normal.get_image())
_shuffle()
_display_selected()
whole.visible = false
@ -40,9 +42,8 @@ func _rotate_part(direction := 1) -> void:
var part = container.get_child(selected) as TextureButton
var id = int(str(part.name))
rotations[id] = wrapi(rotations[id] + direction, 0, 4)
var image = part.texture_normal.get_image()
image.rotate_90(direction)
part.texture_normal = ImageTexture.create_from_image(image)
images[id].rotate_90(direction)
part.texture_normal = ImageTexture.create_from_image(images[id])
func _shuffle() -> void:
@ -55,7 +56,7 @@ func _shuffle() -> void:
for i in range(4):
selected = i
for j in range(randi() % 4):
_rotate_part(1)
_rotate_part()
selected = 0

View File

@ -1,7 +1,7 @@
[gd_scene load_steps=5 format=3 uid="uid://h0s5ms7r7d8g"]
[gd_scene load_steps=9 format=3 uid="uid://h0s5ms7r7d8g"]
[ext_resource type="Shader" path="res://scene/shading/ghost.gdshader" id="1_n4q4i"]
[ext_resource type="Texture2D" uid="uid://b7gyapghy3tsy" path="res://asset/art/neutral_point_light.png" id="2_y00i5"]
[ext_resource type="Texture2D" uid="uid://wvnpr0w3srtr" path="res://asset/art/临时草稿/ghost-sheet.png" id="2_vp102"]
[ext_resource type="Texture2D" uid="uid://bc64s5xfysrc3" path="res://asset/art/scene/c01/s07_书店外/bg_书店外_夜晚.png" id="4_lap87"]
[sub_resource type="ShaderMaterial" id="ShaderMaterial_fv2fx"]
@ -12,10 +12,41 @@ shader_parameter/shake_speed = 6.0
shader_parameter/shake_block_size = 5.0
shader_parameter/shake_color_rate = 0.005
[node name="Ghost" type="Sprite2D"]
[sub_resource type="AtlasTexture" id="AtlasTexture_vaq88"]
atlas = ExtResource("2_vp102")
region = Rect2(0, 0, 256, 256)
[sub_resource type="AtlasTexture" id="AtlasTexture_mh23v"]
atlas = ExtResource("2_vp102")
region = Rect2(256, 0, 256, 256)
[sub_resource type="AtlasTexture" id="AtlasTexture_5x2re"]
atlas = ExtResource("2_vp102")
region = Rect2(512, 0, 256, 256)
[sub_resource type="SpriteFrames" id="SpriteFrames_fqswq"]
animations = [{
"frames": [{
"duration": 3.0,
"texture": SubResource("AtlasTexture_vaq88")
}, {
"duration": 1.0,
"texture": SubResource("AtlasTexture_mh23v")
}, {
"duration": 2.0,
"texture": SubResource("AtlasTexture_5x2re")
}],
"loop": true,
"name": &"default",
"speed": 5.0
}]
[node name="Ghost" type="AnimatedSprite2D"]
material = SubResource("ShaderMaterial_fv2fx")
position = Vector2(135, 130)
texture = ExtResource("2_y00i5")
position = Vector2(135, 129)
sprite_frames = SubResource("SpriteFrames_fqswq")
autoplay = "default"
frame_progress = 0.983059
[node name="BackBufferCopy" type="BackBufferCopy" parent="."]
copy_mode = 2