Files
FNF-i486-Engine/source/CreditsState.hx
NAEL2XD 78da56a9a9 pure
2025-05-27 21:21:31 +02:00

348 lines
12 KiB
Haxe

package;
import flash.text.TextField;
import flixel.FlxG;
import flixel.FlxSprite;
import flixel.addons.display.FlxGridOverlay;
import flixel.group.FlxGroup.FlxTypedGroup;
import flixel.math.FlxMath;
import flixel.text.FlxText;
import flixel.util.FlxColor;
import flixel.tweens.FlxTween;
import flixel.tweens.FlxEase;
#if MODS_ALLOWED
import sys.FileSystem;
import sys.io.File;
#end
import lime.utils.Assets;
using StringTools;
class CreditsState extends MusicBeatState
{
var curSelected:Int = -1;
private var grpOptions:FlxTypedGroup<Alphabet>;
private var iconArray:Array<AttachedSprite> = [];
private var creditsStuff:Array<Array<String>> = [];
var bg:FlxSprite;
var descText:FlxText;
var intendedColor:Int;
var colorTween:FlxTween;
var descBox:AttachedSprite;
var offsetThing:Float = -75;
override function create()
{
Paths.clearStoredMemory();
Paths.clearUnusedMemory();
MusicBeatState.windowNameSuffix = " - Credits";
#if desktop
// Updating Discord Rich Presence
DiscordClient.changePresence("Viewing the Credits", null);
#end
persistentUpdate = true;
bg = new FlxSprite().loadGraphic(Paths.image('menuDesat'));
add(bg);
bg.screenCenter();
grpOptions = new FlxTypedGroup<Alphabet>();
add(grpOptions);
#if MODS_ALLOWED
var path:String = 'modsList.txt';
if(FileSystem.exists(path))
{
var leMods:Array<String> = CoolUtil.coolTextFile(path);
for (i in 0...leMods.length)
{
if(leMods.length > 1 && leMods[0].length > 0) {
var modSplit:Array<String> = leMods[i].split('|');
if(!Paths.ignoreModFolders.contains(modSplit[0].toLowerCase()) && !modsAdded.contains(modSplit[0]))
{
if(modSplit[1] == '1')
pushModCreditsToList(modSplit[0]);
else
modsAdded.push(modSplit[0]);
}
}
}
}
var arrayOfFolders:Array<String> = Paths.getModDirectories();
arrayOfFolders.push('');
for (folder in arrayOfFolders)
{
pushModCreditsToList(folder);
}
#end
var pisspoop:Array<Array<String>> = [ //Name - Icon name - Description - Link - BG Color
['JS Engine People'],
['Jordan Santiago', 'jor', 'Coded everything into JS Engine', 'https://twitter.com/JordansTweetsYT', 'FF9300'],
['Stinko', 'stinkern', 'Coder, a very stupid one..', 'https://stinkernn.carrd.co/', '555555'],
['MoxieCoder', 'moxie', 'Coder', 'https://github.com/moxie-coder', '000055'],
[''],
['Special Thanks'],
['Denpa Engine', 'denpeak', 'The crossfade code used for this engine\n(Currently not implemented yet!)', 'https://github.com/UmbratheUmbreon/PublicDenpaEngine', 'FF9300'],
['HRK. EXEX', 'hrk', 'Created the Old Video Rendering Mode for FNF & the Note Skipping idea,\nalong with the Rating Popup recycling idea thing', 'https://www.youtube.com/@HRK_EXEX/featured', '01F8FF'],
['cabfile', 'cabfile', 'Created the new Video Rendering Mode for FNF', 'https://github.com/cabfile', 'DDDDDD'],
['SomeGuyWhoLovesCoding', 'sgwlc', 'Rewrote the chart loading system and ported the new Rendering Mode to source', 'https://www.youtube.com/channel/UCMSusVA3DY-4EtiGP4zKAJA', 'FFBD40'],
['Betopia', 'nothing', 'Freeplay Search bar creator', 'https://www.youtube.com/channel/UCfjyz9xRhZiRbLMteQloVeg', 'FFFFFF'],
['CDEV Engine', 'cdev', 'Update Screen Creator', 'https://github.com/Core5570RYT/FNF-CDEV-Engine', '00427B'],
['NotMagniill', 'magniill', 'Code for the Sustain Note Splashes', 'https://github.com/notmagniill', 'FFBD40'],
['chromasen', 'chromasen', 'Code for the Windows Notification Event', 'https://www.youtube.com/channel/UCgGk4oZt3We-ktkEOV9HY1Q', 'FFFFFF'],
['Erizur', 'erizur', 'Cross-Platform code for the Windows Notification Event', 'https://www.youtube.com/channel/UCdCAaQzt9yOGfFM0gJDJ4bQ', 'FFFFFF'],
['Slushi (Andres)', 'slushi', 'Actual working code for the Windows Notification Event', 'https://github.com/Slushi-Github/Slushi-Engine/tree/main', '8FD9D1'],
['Nael2xd', 'nael', 'Revamped Note Multiplier, Fixed Windows Notifications, Improved Chart Editor Autosave, UI for Crash State and A nifty discord button.', 'https://www.youtube.com/@Nael2xd', '880000'],
[''],
['Psych Engine Team'],
['Shadow Mario', 'shadowmario', 'Main Programmer of Psych Engine', 'https://twitter.com/Shadow_Mario_', '444444'],
['RiverOaken', 'river', 'Main Artist/Animator of Psych Engine', 'https://twitter.com/RiverOaken', 'B42F71'],
[''],
['Former Engine Members'],
['bb-panzu', 'bb', 'Ex-Programmer of Psych Engine', 'https://twitter.com/bbsub3', '3E813A'],
[''],
['Engine Contributors'],
['iFlicky', 'flicky', 'Composer of Psync and Tea Time\nMade the Dialogue Sounds', 'https://twitter.com/flicky_i', '9E29CF'],
['SqirraRNG', 'sqirra', 'Crash Handler and Base code for\nChart Editor\'s Waveform', 'https://twitter.com/gedehari', 'E1843A'],
['EliteMasterEric', 'mastereric', 'Runtime Shaders support', 'https://twitter.com/EliteMasterEric', 'FFBD40'],
['PolybiusProxy', 'proxy', '.MP4 Video Loader Library (hxCodec)', 'https://twitter.com/polybiusproxy', 'DCD294'],
['KadeDev', 'kade', 'Fixed some cool stuff on Chart Editor\nand other PRs', 'https://twitter.com/kade0912', '64A250'],
['Keoiki', 'keoiki', 'Note Splash Animations', 'https://twitter.com/Keoiki_', 'D2D2D2'],
['Nebula the Zorua', 'nebula', 'LUA JIT Fork and some Lua reworks', 'https://twitter.com/Nebula_Zorua', '7D40B2'],
['Smokey', 'smokey', 'Sprite Atlas Support', 'https://twitter.com/Smokey_5_', '483D92'],
[''],
["Funkin' Crew"],
['ninjamuffin99', 'ninjamuffin99', "Programmer of Friday Night Funkin'", 'https://twitter.com/ninja_muffin99', 'CF2D2D'],
['PhantomArcade', 'phantomarcade', "Animator of Friday Night Funkin'", 'https://twitter.com/PhantomArcade3K', 'FADC45'],
['evilsk8r', 'evilsk8r', "Artist of Friday Night Funkin'", 'https://twitter.com/evilsk8r', '5ABD4B'],
['kawaisprite', 'kawaisprite', "Composer of Friday Night Funkin'", 'https://twitter.com/kawaisprite', '378FC7']
];
for(i in pisspoop){
creditsStuff.push(i);
}
for (i in 0...creditsStuff.length)
{
var isSelectable:Bool = !unselectableCheck(i);
var optionText:Alphabet = new Alphabet(FlxG.width / 2, 300, creditsStuff[i][0], !isSelectable);
optionText.isMenuItem = true;
optionText.targetY = i;
optionText.changeX = false;
optionText.snapToPosition();
grpOptions.add(optionText);
if(isSelectable) {
if(creditsStuff[i][5] != null)
{
Paths.currentModDirectory = creditsStuff[i][5];
}
var icon:AttachedSprite = new AttachedSprite('credits/' + creditsStuff[i][1]);
icon.xAdd = optionText.width + 10;
icon.sprTracker = optionText;
// using a FlxGroup is too much fuss!
iconArray.push(icon);
add(icon);
Paths.currentModDirectory = '';
if(curSelected == -1) curSelected = i;
}
else optionText.alignment = CENTERED;
}
descBox = new AttachedSprite();
descBox.makeGraphic(1, 1, FlxColor.BLACK);
descBox.xAdd = -10;
descBox.yAdd = -10;
descBox.alphaMult = 0.6;
descBox.alpha = 0.6;
add(descBox);
descText = new FlxText(50, FlxG.height + offsetThing - 25, 1180, "", 32);
descText.setFormat(Paths.font("vcr.ttf"), 32, FlxColor.WHITE, CENTER/*, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK*/);
descText.scrollFactor.set();
//descText.borderSize = 2.4;
descBox.sprTracker = descText;
add(descText);
bg.color = getCurrentBGColor();
intendedColor = bg.color;
changeSelection();
super.create();
}
var quitting:Bool = false;
var holdTime:Float = 0;
override function update(elapsed:Float)
{
if (FlxG.sound.music.volume < 0.7)
{
FlxG.sound.music.volume += 0.5 * FlxG.elapsed;
}
if(!quitting)
{
if(creditsStuff.length > 1)
{
var shiftMult:Int = 1;
if(FlxG.keys.pressed.SHIFT) shiftMult = 3;
var upP = controls.UI_UP_P;
var downP = controls.UI_DOWN_P;
if (upP)
{
changeSelection(-shiftMult);
holdTime = 0;
}
if (downP)
{
changeSelection(shiftMult);
holdTime = 0;
}
if(controls.UI_DOWN || controls.UI_UP)
{
var checkLastHold:Int = Math.floor((holdTime - 0.5) * 10);
holdTime += elapsed;
var checkNewHold:Int = Math.floor((holdTime - 0.5) * 10);
if(holdTime > 0.5 && checkNewHold - checkLastHold > 0)
{
changeSelection((checkNewHold - checkLastHold) * (controls.UI_UP ? -shiftMult : shiftMult));
}
}
}
if(controls.ACCEPT && (creditsStuff[curSelected][3] == null || creditsStuff[curSelected][3].length > 4)) {
CoolUtil.browserLoad(creditsStuff[curSelected][3]);
}
if (controls.BACK)
{
if(colorTween != null) {
colorTween.cancel();
}
FlxG.sound.play(Paths.sound('cancelMenu'));
FlxG.switchState(MainMenuState.new);
quitting = true;
}
}
for (item in grpOptions.members)
{
if(!item.bold)
{
var lerpVal:Float = CoolUtil.boundTo(elapsed * 12, 0, 1);
if(item.targetY == 0)
{
var lastX:Float = item.x;
item.screenCenter(X);
item.x = FlxMath.lerp(lastX, item.x - 70, lerpVal);
}
else
{
item.x = FlxMath.lerp(item.x, 200 + -40 * Math.abs(item.targetY), lerpVal);
}
}
}
super.update(elapsed);
}
var moveTween:FlxTween = null;
function changeSelection(change:Int = 0)
{
FlxG.sound.play(Paths.sound('scrollMenu'), 0.4);
do {
curSelected += change;
if (curSelected < 0)
curSelected = creditsStuff.length - 1;
if (curSelected >= creditsStuff.length)
curSelected = 0;
} while(unselectableCheck(curSelected));
var newColor:Int = getCurrentBGColor();
if(newColor != intendedColor) {
if(colorTween != null) {
colorTween.cancel();
}
intendedColor = newColor;
colorTween = FlxTween.color(bg, 1, bg.color, intendedColor, {
onComplete: function(twn:FlxTween) {
colorTween = null;
}
});
}
var bullShit:Int = 0;
for (item in grpOptions.members)
{
item.targetY = bullShit - curSelected;
bullShit++;
if(!unselectableCheck(bullShit-1)) {
item.alpha = 0.6;
if (item.targetY == 0) {
item.alpha = 1;
}
}
}
descText.text = creditsStuff[curSelected][2];
descText.y = FlxG.height - descText.height + offsetThing - 60;
if(moveTween != null) moveTween.cancel();
moveTween = FlxTween.tween(descText, {y : descText.y + 75}, 0.25, {ease: FlxEase.sineOut});
descBox.setGraphicSize(Std.int(descText.width + 20), Std.int(descText.height + 25));
descBox.updateHitbox();
}
#if MODS_ALLOWED
private var modsAdded:Array<String> = [];
function pushModCreditsToList(folder:String)
{
if(modsAdded.contains(folder)) return;
var creditsFile:String = null;
if(folder != null && folder.trim().length > 0) creditsFile = Paths.mods(folder + '/data/credits.txt');
else creditsFile = Paths.mods('data/credits.txt');
if (FileSystem.exists(creditsFile))
{
var firstarray:Array<String> = File.getContent(creditsFile).split('\n');
for(i in firstarray)
{
var arr:Array<String> = i.replace('\\n', '\n').split("::");
if(arr.length >= 5) arr.push(folder);
creditsStuff.push(arr);
}
creditsStuff.push(['']);
}
modsAdded.push(folder);
}
#end
function getCurrentBGColor() {
var bgColor:String = creditsStuff[curSelected][4];
if(!bgColor.startsWith('0x')) {
bgColor = '0xFF' + bgColor;
}
return Std.parseInt(bgColor);
}
private function unselectableCheck(num:Int):Bool {
return creditsStuff[num].length <= 1;
}
}