Files
godot-4-key-rhythm-game/rhythm_game/note/visual/note_spawner.gd

92 lines
2.6 KiB
GDScript3
Raw Normal View History

2026-02-01 23:17:51 +08:00
class_name NoteSpawner extends NoteView
signal notes_spawned(beat: float)
@export var lanes: Dictionary[int, Lane]
@export var pool: NotePool
## Spawn all the notes that should exist on this beat.
func update(beat: float) -> void:
var old_begin: int = _begin
var old_end: int = _end
_update_view_relative_to_notes(notes, beat) # Updates _begin and _end.
if _previous_beat <= beat:
_set_note_visuals(old_end, _end)
_remove_note_visuals(old_begin, _begin)
else:
_remove_note_visuals(_end, old_end)
_set_note_visuals(_begin, old_begin)
_previous_beat = beat
notes_spawned.emit(beat)
# ======== IMPLEMENTATION ======== #
var _note_visuals: Dictionary[int, NoteVisual] # [Note ID, Note Visual]
var _last_lane_holds: Dictionary[int, HoldNote]
func _set_notes(p_notes: NoteArray) -> void:
super._set_notes(p_notes)
for note in _note_visuals.values():
if note == null:
continue
pool.return_note(note)
# TODO Finish implementation.
# Spawn or delete nodes in the range.
func _set_note_visuals(index_begin: int, index_end: int) -> void:
for note_id: int in range(index_begin, index_end):
match notes.type_at(note_id):
Note.TYPE.TAP:
_set_visual_for_tap_at(note_id)
Note.TYPE.HOLD_START:
_set_visual_for_hold_start_at(note_id)
Note.TYPE.HOLD_END:
_set_visual_for_hold_end_at(note_id)
func _remove_note_visuals(index_begin: int, index_end: int) -> void:
for note_id: int in range(index_begin, index_end):
match notes.type_at(note_id):
Note.TYPE.TAP:
_remove_visual_for_tap_at(note_id)
Note.TYPE.HOLD_START:
_remove_visual_for_hold_start_at(note_id)
Note.TYPE.HOLD_END:
_remove_visual_for_hold_end_at(note_id)
func _set_visual_for_tap_at(note_id: int) -> void:
var lane_id: int = notes.lane_at(note_id)
var lane: Lane = lanes[lane_id]
var note: TapNote = pool.get_tap()
lane.add_child(note)
_note_visuals[note_id] = note
func _set_visual_for_hold_start_at(note_id: int) -> void:
var lane_id: int = notes.lane_at(note_id)
var lane: Lane = lanes[lane_id]
var note: HoldNote = pool.get_hold()
lane.add_child(note)
_note_visuals[note_id] = note
_last_lane_holds[lane_id] = note
func _set_visual_for_hold_end_at(note_id: int) -> void:
var lane_id: int = notes.lane_at(note_id)
var lane: Lane = lanes[lane_id]
var note: HoldNote = _last_lane_holds[lane_id]
if note == null:
note = pool.get_hold()
lane.add_child(note)
_note_visuals[note_id] = note
_last_lane_holds[lane_id] = null
func _remove_visual_for_tap_at(note_id: int) -> void:
pass
func _remove_visual_for_hold_start_at(note_id: int) -> void:
pass
func _remove_visual_for_hold_end_at(note_id: int) -> void:
pass