Files
2025-06-22 12:00:12 -04:00

122 lines
3.3 KiB
Plaintext
Executable File

import funkin.audio.FunkinSound;
import flixel.FlxG;
import funkin.graphics.FunkinSprite;
import flixel.FlxSprite;
import funkin.play.song.Song;
import funkin.play.PlayState;
import funkin.util.Constants;
import funkin.play.PlayStatePlaylist;
import funkin.Paths;
import flixel.util.FlxTimer;
class ThornsSong extends Song {
var hasPlayedCutscene:Bool;
public function new() {
super('thorns');
}
public override function onCountdownStart(event:CountdownScriptEvent):Void {
super.onCountdownStart(event);
if (!PlayStatePlaylist.isStoryMode) hasPlayedCutscene = true;
if (!hasPlayedCutscene) {
trace('Pausing countdown to play cutscene.');
hasPlayedCutscene = true;
startCutscene();
event.cancel(); // CANCEL THE COUNTDOWN!
}
}
function startCutscene() {
trace('Hit start of song! Starting cutscene.');
PlayState.instance.camHUD.visible = false;
PlayState.instance.camCutscene.visible = true;
var red = new FunkinSprite(-20, -20).makeSolidColor(FlxG.width * 1.5, FlxG.height * 1.5, 0xFFFF1B31);
red.cameras = [PlayState.instance.camCutscene];
red.alpha = 1.0;
PlayState.instance.add(red);
var senpaiCrazy = FunkinSprite.createSparrow(0, 0, 'weeb/senpaiCrazy');
senpaiCrazy.cameras = [PlayState.instance.camCutscene];
senpaiCrazy.animation.addByPrefix('idle', 'Senpai Pre Explosion instance 1', 24, false);
senpaiCrazy.setGraphicSize(Std.int(senpaiCrazy.width * Constants.PIXEL_ART_SCALE));
senpaiCrazy.antialiasing = false;
senpaiCrazy.scrollFactor.set();
senpaiCrazy.updateHitbox();
senpaiCrazy.screenCenter();
senpaiCrazy.x += senpaiCrazy.width / 5;
senpaiCrazy.alpha = 0;
PlayState.instance.add(senpaiCrazy);
// Senpai fades in stepwise rather than linear.
new FlxTimer().start(0.3, function(timer:FlxTimer) {
senpaiCrazy.alpha += 0.15;
if (senpaiCrazy.alpha < 1) {
timer.reset();
} else {
senpaiCrazy.alpha = 1;
// Play the actual animation.
senpaiCrazy.animation.play('idle');
// Play the SFX alongside it.
trace('Playing senpai death SFX.');
FunkinSound.playOnce(Paths.sound('Senpai_Dies'), 1.0, function () {
trace('Senpai death SFX done.');
// Called when the sound completes. Clean up the cutscene here.
// Hard cut to the cutscene.
PlayState.instance.remove(senpaiCrazy);
PlayState.instance.remove(red);
PlayState.instance.camCutscene.fade(0xFFEEEEEE, 0.8, true);
startDialogue();
});
// Fade to white 3.2 seconds into the cutscene.
new FlxTimer().start(3.2, function(deadTime:FlxTimer)
{
PlayState.instance.camCutscene.fade(0xFFEEEEEE, 1.6, false);
});
}
});
}
function startDialogue() {
PlayState.instance.startConversation('thorns');
}
/**
* Don't replay the cutscene between restarts.
*/
function onSongRetry(event:ScriptEvent)
{
super.onSongRetry(event);
hasPlayedCutscene = true;
}
/**
* Replay the cutscene after leaving the song.
*/
function onCreate(event:ScriptEvent):Void
{
super.onCreate(event);
hasPlayedCutscene = false;
}
public override function onDialogueEnd() {
// We may need to wait for the outro to play.
Countdown.performCountdown();
}
}