@tool class_name ShadingLayer extends CanvasLayer @export_enum("vignette", "fog", "glitch", "palette", "chromatic_abberation") var mode: Array[String] = ["vignette"] as Array[String]: set(new_val): mode = new_val _setup_visibility() @export_group("Vignette", "vignette_") @export var vignette_rgb := Color8(0x3f, 0x26, 0x31): set(new_val): vignette_rgb = new_val if is_node_ready(): %Vignette.material.set("shader_parameter/vignette_rgb", new_val) @export_range(0, 5) var vignette_intensity := 0.3: set(new_val): vignette_intensity = new_val if is_node_ready(): %Vignette.material.set("shader_parameter/vignette_intensity", new_val) @export_group("Fog", "fog_") const fog_frame_count = 24 # 0-23 @export var fog_offset := FOG_OFFSET_DEFAULT: set(new_val): fog_offset = new_val if is_node_ready(): %Fog.offset = new_val @export var fog_frame := FOG_FRAME_DEFAULT: set(new_val): fog_frame = new_val if is_node_ready(): %Fog.frame = new_val @export var fog_modulate := FOG_COLOR_DEFAULT: set(new_val): fog_modulate = new_val if is_node_ready(): %Fog.self_modulate = new_val # @export var fog_offset := Vector2(0.0, 0.0): # set(new_val): # fog_offset = new_val # if not is_node_ready(): # return # %Fog.texture.noise.set("offset", new_val) # @export var fog_base_color := Color8(0xff, 0xff, 0xff, 0x3d): # set(new_val): # fog_base_color = new_val # if not is_node_ready(): # return # %Fog.material.set("shader_parameter/base_color", new_val) @export_group("Glitch", "glitch_") @export var glitch_power := 0.001: set(new_val): glitch_power = new_val if is_node_ready(): %GlitchEffect.material.set("shader_parameter/shake_power", new_val) # rate @export var glitch_rate := 0.2: set(new_val): glitch_rate = new_val if is_node_ready(): %GlitchEffect.material.set("shader_parameter/shake_rate", new_val) # speed @export var glitch_speed := 5.0: set(new_val): glitch_speed = new_val if is_node_ready(): %GlitchEffect.material.set("shader_parameter/shake_speed", new_val) # block_size @export var glitch_block_size := 30.5: set(new_val): glitch_block_size = new_val if not is_node_ready(): return %GlitchEffect.material.set("shader_parameter/shake_block_size", new_val) # color rate @export var glitch_color_rate := 0.01: set(new_val): glitch_color_rate = new_val if is_node_ready(): %GlitchEffect.material.set("shader_parameter/shake_color_rate", new_val) @export_group("Palette", "palette_") @export var palette_texture := preload("res://asset/shader/palette/bloodmoon21-1x.png"): set(new_val): palette_texture = new_val if is_node_ready(): %Palette.material.set("shader_parameter/palette", new_val) func _ready() -> void: %Sprite2D.visible = false layer = GlobalConfig.CANVAS_LAYER_SHADING # set up other properties %Vignette.material.set("shader_parameter/vignette_rgb", vignette_rgb) %Vignette.material.set("shader_parameter/vignette_intensity", vignette_intensity) %Fog.frame = fog_frame %Fog.offset = fog_offset %Fog.self_modulate = fog_modulate # %Fog.texture.noise.set("offset", fog_offset) # %Fog.material.set("shader_parameter/base_color", fog_base_color) %GlitchEffect.material.set("shader_parameter/shake_power", glitch_power) %GlitchEffect.material.set("shader_parameter/shake_rate", glitch_rate) %GlitchEffect.material.set("shader_parameter/shake_speed", glitch_speed) %GlitchEffect.material.set("shader_parameter/shake_block_size", glitch_block_size) %GlitchEffect.material.set("shader_parameter/shake_color_rate", glitch_color_rate) %Palette.material.set("shader_parameter/palette", palette_texture) # set up visibility _setup_visibility() func _setup_visibility(): if not is_node_ready(): return %Vignette.visible = mode.has("vignette") %Fog.visible = mode.has("fog") %GlitchEffect.visible = mode.has("glitch") %Palette.visible = mode.has("palette") %ChromaticAbberation.visible = mode.has("chromatic_abberation") func erase_mode(mode_name: String) -> void: if mode.has(mode_name): mode.erase(mode_name) _setup_visibility() func add_mode(mode_name: String) -> void: if not mode.has(mode_name): mode.append(mode_name) _setup_visibility() #### Tween fog #### const FOG_COLOR_DEFAULT = Color(0.8, 0.8, 0.8, 0.5) const FOG_COLOR_WHITE = Color(1, 1, 1, 1) const FOG_COLOR_BLACK = Color(0, 0, 0, 1) const FOG_COLOR_GRAY = Color(0.5, 0.5, 0.5, 1) const FOG_COLOR_DARK_GRAY = Color(0.2, 0.2, 0.2, 1) const FOG_FRAME_MIN = 0 const FOG_FRAME_DEFAULT = 23 #原15 const FOG_FRAME_MAX = 23 const FOG_OFFSET_DEFAULT = Vector2(0, 50) var _fog_tween: Tween func show_default_fog(duration := 0.8): if not mode.has("fog"): add_mode("fog") fog_modulate = Color.TRANSPARENT tween_fog(FOG_FRAME_DEFAULT, FOG_COLOR_DEFAULT, FOG_OFFSET_DEFAULT, duration) func close_fog(duration := 0.8): if mode.has("fog"): tween_fog(fog_frame, Color.TRANSPARENT, fog_offset, duration, true) func tween_fog( end_frame := fog_frame, end_modulate := fog_modulate, end_offset := fog_offset, duration := 0.8, close_at_end := false ) -> void: if not is_node_ready(): return if GlobalConfig.DEBUG: print( "Tween fog to frame: ", end_frame, " modulate: ", end_modulate, " offset: ", end_offset ) if not mode.has("fog"): # 如果没有开启 fog,先开启,并且设置为透明 add_mode("fog") fog_modulate = Color.TRANSPARENT if _fog_tween and _fog_tween.is_valid(): _fog_tween.kill() _fog_tween = create_tween() _fog_tween.tween_property(%Fog, "frame", end_frame, duration) if end_modulate != fog_modulate: _fog_tween.parallel().tween_property(%Fog, "self_modulate", end_modulate, duration) if end_offset != fog_offset: _fog_tween.parallel().tween_property(%Fog, "offset", end_offset, duration) if close_at_end: _fog_tween.tween_callback(erase_mode.bind("fog")) # vignette 闪烁 func flash_vignette(color: Color) -> void: if not is_node_ready(): return if GlobalConfig.DEBUG: print("Flash vignette with color: ", color) var original_vignette_rgb = vignette_rgb var original_vignette_intensity = vignette_intensity var v = %Vignette var display = v.visible v.visible = true var tween = create_tween() tween.tween_property(self, "vignette_rgb", color, 0.2) tween.parallel().tween_property(self, "vignette_intensity", 5.0, 0.2).from(0.0) tween.tween_interval(0.4) tween.tween_property(self, "vignette_rgb", original_vignette_rgb, 0.2) tween.parallel().tween_property(self, "vignette_intensity", original_vignette_intensity, 0.2) tween.tween_callback(v.set.bind("visible", display)) # palette 闪烁 func flash_palette(duration := 0.5) -> void: if not is_node_ready(): return add_mode("palette") get_tree().create_timer(duration).timeout.connect(erase_mode.bind("palette")) # glitch 闪烁 func flash_glitch(duration := 1.0) -> void: if not is_node_ready(): return add_mode("glitch") get_tree().create_timer(duration).timeout.connect(erase_mode.bind("glitch"))