90 lines
2.5 KiB
GDScript
90 lines
2.5 KiB
GDScript
class_name StrongBuffVisual
|
||
extends Node2D
|
||
|
||
const DEFAULT_FRAME_DIRECTORY := "res://assets/ui/strong_buff"
|
||
|
||
@export var frame_directory := DEFAULT_FRAME_DIRECTORY
|
||
@export var frames_per_second := 20.0
|
||
@export var center_offset := Vector2(0.0, -38.0)
|
||
@export var effect_scale := 0.18
|
||
|
||
var _active := false
|
||
var _frame_index := 0
|
||
var _frame_elapsed := 0.0
|
||
var _frames: Array[Texture2D] = []
|
||
var _sprite: Sprite2D
|
||
|
||
|
||
func _ready() -> void:
|
||
z_index = 1
|
||
_sprite = Sprite2D.new()
|
||
_sprite.name = "StrongBuffEffect"
|
||
_sprite.centered = true
|
||
_sprite.position = center_offset
|
||
_sprite.texture_filter = CanvasItem.TEXTURE_FILTER_NEAREST
|
||
_sprite.visible = false
|
||
add_child(_sprite)
|
||
_load_frames()
|
||
set_active(false)
|
||
|
||
|
||
func _process(delta: float) -> void:
|
||
if not _active or _frames.is_empty():
|
||
return
|
||
_frame_elapsed += delta
|
||
var frame_duration := 1.0 / maxf(1.0, frames_per_second)
|
||
while _frame_elapsed >= frame_duration:
|
||
_frame_elapsed -= frame_duration
|
||
_frame_index = (_frame_index + 1) % _frames.size()
|
||
_sprite.texture = _frames[_frame_index]
|
||
|
||
|
||
func set_active(active: bool) -> void:
|
||
_active = active and not _frames.is_empty()
|
||
visible = _active
|
||
set_process(_active)
|
||
if _sprite != null:
|
||
_sprite.visible = _active
|
||
_sprite.position = center_offset
|
||
_sprite.scale = Vector2.ONE * effect_scale
|
||
if _active and _sprite.texture == null and not _frames.is_empty():
|
||
_sprite.texture = _frames[_frame_index]
|
||
|
||
|
||
func is_active() -> bool:
|
||
return _active
|
||
|
||
|
||
func frame_count() -> int:
|
||
return _frames.size()
|
||
|
||
|
||
func current_effect_scale() -> float:
|
||
return effect_scale
|
||
|
||
|
||
func _load_frames() -> void:
|
||
_frames.clear()
|
||
var dir := DirAccess.open(frame_directory)
|
||
if dir == null:
|
||
return
|
||
# 导出包内贴图在目录列表里显示为 xxx.png.import / xxx.png.remap;
|
||
# 还原原名后 load() 才能命中。编辑器里原图与 .import 同时在列,需去重。
|
||
var files := PackedStringArray()
|
||
dir.list_dir_begin()
|
||
var file_name := dir.get_next()
|
||
while not file_name.is_empty():
|
||
if not dir.current_is_dir():
|
||
var resource_name := file_name.trim_suffix(".import").trim_suffix(".remap")
|
||
if resource_name.ends_with(".png") and not files.has(resource_name):
|
||
files.append(resource_name)
|
||
file_name = dir.get_next()
|
||
dir.list_dir_end()
|
||
files.sort()
|
||
for path_name: String in files:
|
||
var texture := load("%s/%s" % [frame_directory, path_name]) as Texture2D
|
||
if texture != null:
|
||
_frames.append(texture)
|
||
if not _frames.is_empty() and _sprite != null:
|
||
_sprite.texture = _frames[0]
|