diff --git a/Project.xml b/Project.xml index ffb6961..2d23bb6 100644 --- a/Project.xml +++ b/Project.xml @@ -3,7 +3,7 @@ xsi:schemaLocation="http://lime.openfl.org/project/1.0.4 http://lime.openfl.org/xsd/project-1.0.4.xsd"> - + @@ -52,7 +52,7 @@ xsi:schemaLocation="http://lime.openfl.org/project/1.0.4 http://lime.openfl.org/ - + @@ -62,10 +62,10 @@ xsi:schemaLocation="http://lime.openfl.org/project/1.0.4 http://lime.openfl.org/ - + - + diff --git a/README.md b/README.md index 8c3dd58..e176b51 100644 --- a/README.md +++ b/README.md @@ -17,7 +17,7 @@ ![GitHub repo size](https://img.shields.io/github/repo-size/Slushi-Github/Slushi-Engine) -[Gamejolt](https://gamejolt.com/games/SlushiEngine/884361) - [GameBanana](https://gamebanana.com/tools/17953) +[GameBanana](https://gamebanana.com/tools/17953) - [Gamejolt](https://gamejolt.com/games/SlushiEngine/884361) Slushi Engine is an FNF' engine that allows you to make modcharts with [Modcharting Tools](https://github.com/EdwhakKB/FNF-Modcharting-Tools) and other [SC Engine](https://github.com/EdwhakKB/SC-SP-ENGINE) utilities, while also being able to make a unique kind of modchart that uses Windows functions! diff --git a/README_ES.md b/README_ES.md index 0d1e158..ae30e5b 100644 --- a/README_ES.md +++ b/README_ES.md @@ -17,7 +17,7 @@ ![GitHub repo size](https://img.shields.io/github/repo-size/Slushi-Github/Slushi-Engine) -[Gamejolt](https://gamejolt.com/games/SlushiEngine/884361) - [GameBanana](https://gamebanana.com/tools/17953) +[GameBanana](https://gamebanana.com/tools/17953) - [Gamejolt](https://gamejolt.com/games/SlushiEngine/884361) Slushi Engine es un motor de FNF' que te permite hacer modcharts con [Modcharting Tools](https://github.com/EdwhakKB/FNF-Modcharting-Tools) y otras utilidades del [SC Engine](https://github.com/EdwhakKB/SC-SP-ENGINE), ¡mientras que también te permite hacer un tipo único de modchart que utiliza funciones de Windows! diff --git a/assets/shared/data/characters/bf.json b/assets/shared/data/characters/bf.json index 81833b7..11b1124 100644 --- a/assets/shared/data/characters/bf.json +++ b/assets/shared/data/characters/bf.json @@ -141,7 +141,7 @@ "flip_x": true, "healthbar_colors": [49, 176, 209], "camera_position": [0, 0], - "noteSkin": "noteSkins/NOTE_assets", + "noteSkin": "", "sing_duration": 4, "scale": 1, "_editor_isPlayer": true diff --git a/assets/shared/data/fonts/wendy.ttf b/assets/shared/data/fonts/wendy.ttf new file mode 100644 index 0000000..bba4525 Binary files /dev/null and b/assets/shared/data/fonts/wendy.ttf differ diff --git a/assets/shared/images/noteSkins/NOTE_assets-notitg.png b/assets/shared/images/noteSkins/NOTE_assets-notitg.png new file mode 100644 index 0000000..d2aacfb Binary files /dev/null and b/assets/shared/images/noteSkins/NOTE_assets-notitg.png differ diff --git a/assets/shared/images/noteSkins/NOTE_assets-notitg.xml b/assets/shared/images/noteSkins/NOTE_assets-notitg.xml new file mode 100644 index 0000000..2b8655b --- /dev/null +++ b/assets/shared/images/noteSkins/NOTE_assets-notitg.xml @@ -0,0 +1,110 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/assets/shared/images/noteSkins/list.txt b/assets/shared/images/noteSkins/list.txt index 9c1e166..038c415 100644 --- a/assets/shared/images/noteSkins/list.txt +++ b/assets/shared/images/noteSkins/list.txt @@ -1,2 +1,3 @@ Future -Chip \ No newline at end of file +Chip +NotITG \ No newline at end of file diff --git a/assets/slushiEngineAssets/SLEAssets/BGs/SlushiBGMainMenu.png b/assets/slushiEngineAssets/BGs/SlushiBGMainMenu.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/BGs/SlushiBGMainMenu.png rename to assets/slushiEngineAssets/BGs/SlushiBGMainMenu.png diff --git a/assets/slushiEngineAssets/SLEAssets/BGs/SlushiBGModchartEditor.png b/assets/slushiEngineAssets/BGs/SlushiBGModchartEditor.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/BGs/SlushiBGModchartEditor.png rename to assets/slushiEngineAssets/BGs/SlushiBGModchartEditor.png diff --git a/assets/slushiEngineAssets/BGs/SlushiBGPauseSubState.png b/assets/slushiEngineAssets/BGs/SlushiBGPauseSubState.png new file mode 100644 index 0000000..60ec8b7 Binary files /dev/null and b/assets/slushiEngineAssets/BGs/SlushiBGPauseSubState.png differ diff --git a/assets/slushiEngineAssets/SLEAssets/Musics/SLE_HackNet_Resonance.ogg b/assets/slushiEngineAssets/Musics/SLE_HackNet_Resonance.ogg similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/Musics/SLE_HackNet_Resonance.ogg rename to assets/slushiEngineAssets/Musics/SLE_HackNet_Resonance.ogg diff --git a/assets/slushiEngineAssets/SLEAssets/OthersAssets/COMO QUE LO DETECTO COMO UN VIRUS MI ENGINE.png b/assets/slushiEngineAssets/OthersAssets/COMO QUE LO DETECTO COMO UN VIRUS MI ENGINE.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/OthersAssets/COMO QUE LO DETECTO COMO UN VIRUS MI ENGINE.png rename to assets/slushiEngineAssets/OthersAssets/COMO QUE LO DETECTO COMO UN VIRUS MI ENGINE.png diff --git a/assets/slushiEngineAssets/SLEAssets/OthersAssets/ImageNotFound.png b/assets/slushiEngineAssets/OthersAssets/ImageNotFound.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/OthersAssets/ImageNotFound.png rename to assets/slushiEngineAssets/OthersAssets/ImageNotFound.png diff --git a/assets/slushiEngineAssets/SLEAssets/OthersAssets/WhenTeRickrolean.png b/assets/slushiEngineAssets/OthersAssets/WhenTeRickrolean.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/OthersAssets/WhenTeRickrolean.png rename to assets/slushiEngineAssets/OthersAssets/WhenTeRickrolean.png diff --git a/assets/slushiEngineAssets/SLEAssets/OthersAssets/brutus.png b/assets/slushiEngineAssets/OthersAssets/brutus.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/OthersAssets/brutus.png rename to assets/slushiEngineAssets/OthersAssets/brutus.png diff --git a/assets/slushiEngineAssets/SLEAssets/OthersAssets/nothing.png b/assets/slushiEngineAssets/OthersAssets/nothing.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/OthersAssets/nothing.png rename to assets/slushiEngineAssets/OthersAssets/nothing.png diff --git a/assets/slushiEngineAssets/SLEAssets/OthersAssets/player.png b/assets/slushiEngineAssets/OthersAssets/player.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/OthersAssets/player.png rename to assets/slushiEngineAssets/OthersAssets/player.png diff --git a/assets/slushiEngineAssets/SLEAssets/OthersAssets/player.xml b/assets/slushiEngineAssets/OthersAssets/player.xml similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/OthersAssets/player.xml rename to assets/slushiEngineAssets/OthersAssets/player.xml diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiMainMenuAssets/CreditsOption.png b/assets/slushiEngineAssets/SLEAssets/SlushiMainMenuAssets/CreditsOption.png deleted file mode 100644 index fa5b1a2..0000000 Binary files a/assets/slushiEngineAssets/SLEAssets/SlushiMainMenuAssets/CreditsOption.png and /dev/null differ diff --git a/assets/slushiEngineAssets/SLEAssets/SLEHUDImages/BG.png b/assets/slushiEngineAssets/SlushiEngineHUDAssets/BG.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SLEHUDImages/BG.png rename to assets/slushiEngineAssets/SlushiEngineHUDAssets/BG.png diff --git a/assets/slushiEngineAssets/SLEAssets/SLEHUDImages/Notes.png b/assets/slushiEngineAssets/SlushiEngineHUDAssets/Notes.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SLEHUDImages/Notes.png rename to assets/slushiEngineAssets/SlushiEngineHUDAssets/Notes.png diff --git a/assets/slushiEngineAssets/SLEAssets/SLEHUDImages/SCEngineText.png b/assets/slushiEngineAssets/SlushiEngineHUDAssets/SCEngineText.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SLEHUDImages/SCEngineText.png rename to assets/slushiEngineAssets/SlushiEngineHUDAssets/SCEngineText.png diff --git a/assets/slushiEngineAssets/SLEAssets/SLEHUDImages/Slushi.png b/assets/slushiEngineAssets/SlushiEngineHUDAssets/Slushi.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SLEHUDImages/Slushi.png rename to assets/slushiEngineAssets/SlushiEngineHUDAssets/Slushi.png diff --git a/assets/slushiEngineAssets/SLEAssets/SLEHUDImages/SlushiEngineText.png b/assets/slushiEngineAssets/SlushiEngineHUDAssets/SlushiEngineText.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SLEHUDImages/SlushiEngineText.png rename to assets/slushiEngineAssets/SlushiEngineHUDAssets/SlushiEngineText.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSCE.png b/assets/slushiEngineAssets/SlushiEngineLogoSCE.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSCE.png rename to assets/slushiEngineAssets/SlushiEngineLogoSCE.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/Notes.png b/assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/Notes.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/Notes.png rename to assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/Notes.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/SCEngineText.png b/assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/SCEngineText.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/SCEngineText.png rename to assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/SCEngineText.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/Slushi.png b/assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/Slushi.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/Slushi.png rename to assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/Slushi.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/SlushiEngineText.png b/assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/SlushiEngineText.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/SlushiEngineText.png rename to assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/SlushiEngineText.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/blueNote.png b/assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/blueNote.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/blueNote.png rename to assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/blueNote.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/greenNote.png b/assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/greenNote.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/greenNote.png rename to assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/greenNote.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/purpleNote.png b/assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/purpleNote.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/purpleNote.png rename to assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/purpleNote.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/redNote.png b/assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/redNote.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiEngineLogoSeparatedParts/redNote.png rename to assets/slushiEngineAssets/SlushiEngineLogoSeparatedParts/redNote.png diff --git a/assets/slushiEngineAssets/SlushiFreeplayStateAssets/BG.png b/assets/slushiEngineAssets/SlushiFreeplayStateAssets/BG.png new file mode 100644 index 0000000..99ad8eb Binary files /dev/null and b/assets/slushiEngineAssets/SlushiFreeplayStateAssets/BG.png differ diff --git a/assets/slushiEngineAssets/SlushiFreeplayStateAssets/DANOTE.png b/assets/slushiEngineAssets/SlushiFreeplayStateAssets/DANOTE.png new file mode 100644 index 0000000..681e0e5 Binary files /dev/null and b/assets/slushiEngineAssets/SlushiFreeplayStateAssets/DANOTE.png differ diff --git a/assets/slushiEngineAssets/SlushiMainMenuAssets/CreditsOption.png b/assets/slushiEngineAssets/SlushiMainMenuAssets/CreditsOption.png new file mode 100644 index 0000000..693e1de Binary files /dev/null and b/assets/slushiEngineAssets/SlushiMainMenuAssets/CreditsOption.png differ diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiMainMenuAssets/FreeplayOption.png b/assets/slushiEngineAssets/SlushiMainMenuAssets/FreeplayOption.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiMainMenuAssets/FreeplayOption.png rename to assets/slushiEngineAssets/SlushiMainMenuAssets/FreeplayOption.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiMainMenuAssets/ModsOption.png b/assets/slushiEngineAssets/SlushiMainMenuAssets/ModsOption.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiMainMenuAssets/ModsOption.png rename to assets/slushiEngineAssets/SlushiMainMenuAssets/ModsOption.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiMainMenuAssets/OptionsOption.png b/assets/slushiEngineAssets/SlushiMainMenuAssets/OptionsOption.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiMainMenuAssets/OptionsOption.png rename to assets/slushiEngineAssets/SlushiMainMenuAssets/OptionsOption.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiMainMenuAssets/StoryModeOption.png b/assets/slushiEngineAssets/SlushiMainMenuAssets/StoryModeOption.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiMainMenuAssets/StoryModeOption.png rename to assets/slushiEngineAssets/SlushiMainMenuAssets/StoryModeOption.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/Particle0.png b/assets/slushiEngineAssets/SlushiTitleStateAssets/Particle0.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/Particle0.png rename to assets/slushiEngineAssets/SlushiTitleStateAssets/Particle0.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/Particle1.png b/assets/slushiEngineAssets/SlushiTitleStateAssets/Particle1.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/Particle1.png rename to assets/slushiEngineAssets/SlushiTitleStateAssets/Particle1.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/Particle2.png b/assets/slushiEngineAssets/SlushiTitleStateAssets/Particle2.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/Particle2.png rename to assets/slushiEngineAssets/SlushiTitleStateAssets/Particle2.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/Particle3.png b/assets/slushiEngineAssets/SlushiTitleStateAssets/Particle3.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/Particle3.png rename to assets/slushiEngineAssets/SlushiTitleStateAssets/Particle3.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/Particle4.png b/assets/slushiEngineAssets/SlushiTitleStateAssets/Particle4.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/Particle4.png rename to assets/slushiEngineAssets/SlushiTitleStateAssets/Particle4.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/Particle5.png b/assets/slushiEngineAssets/SlushiTitleStateAssets/Particle5.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/Particle5.png rename to assets/slushiEngineAssets/SlushiTitleStateAssets/Particle5.png diff --git a/assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/continueSprite.png b/assets/slushiEngineAssets/SlushiTitleStateAssets/continueSprite.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/SlushiTitleStateAssets/continueSprite.png rename to assets/slushiEngineAssets/SlushiTitleStateAssets/continueSprite.png diff --git a/assets/slushiEngineAssets/SLEAssets/Sounds/beep.ogg b/assets/slushiEngineAssets/Sounds/beep.ogg similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/Sounds/beep.ogg rename to assets/slushiEngineAssets/Sounds/beep.ogg diff --git a/assets/slushiEngineAssets/SLEAssets/Sounds/beep2.ogg b/assets/slushiEngineAssets/Sounds/beep2.ogg similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/Sounds/beep2.ogg rename to assets/slushiEngineAssets/Sounds/beep2.ogg diff --git a/assets/slushiEngineAssets/SLEAssets/Sounds/vineBoom.ogg b/assets/slushiEngineAssets/Sounds/vineBoom.ogg similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/Sounds/vineBoom.ogg rename to assets/slushiEngineAssets/Sounds/vineBoom.ogg diff --git a/assets/slushiEngineAssets/SLEAssets/Unused/SlushiWagSticker.gif b/assets/slushiEngineAssets/Unused/SlushiWagSticker.gif similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/Unused/SlushiWagSticker.gif rename to assets/slushiEngineAssets/Unused/SlushiWagSticker.gif diff --git a/assets/slushiEngineAssets/SLEAssets/WinSL_Assets/windowIcon.ico b/assets/slushiEngineAssets/WinSL_Assets/windowIcon.ico similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/WinSL_Assets/windowIcon.ico rename to assets/slushiEngineAssets/WinSL_Assets/windowIcon.ico diff --git a/assets/slushiEngineAssets/SLEAssets/optionsAssets/OptionsBG.png b/assets/slushiEngineAssets/optionsAssets/OptionsBG.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/optionsAssets/OptionsBG.png rename to assets/slushiEngineAssets/optionsAssets/OptionsBG.png diff --git a/assets/slushiEngineAssets/SLEAssets/optionsAssets/SLEWindow.png b/assets/slushiEngineAssets/optionsAssets/SLEWindow.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/optionsAssets/SLEWindow.png rename to assets/slushiEngineAssets/optionsAssets/SLEWindow.png diff --git a/assets/slushiEngineAssets/SLEAssets/optionsAssets/WindowCloseButton.png b/assets/slushiEngineAssets/optionsAssets/WindowCloseButton.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/optionsAssets/WindowCloseButton.png rename to assets/slushiEngineAssets/optionsAssets/WindowCloseButton.png diff --git a/assets/slushiEngineAssets/SLEAssets/optionsAssets/Windows10Cursor.png b/assets/slushiEngineAssets/optionsAssets/Windows10Cursor.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/optionsAssets/Windows10Cursor.png rename to assets/slushiEngineAssets/optionsAssets/Windows10Cursor.png diff --git a/assets/slushiEngineAssets/SLEAssets/optionsAssets/Windows11Notification.png b/assets/slushiEngineAssets/optionsAssets/Windows11Notification.png similarity index 100% rename from assets/slushiEngineAssets/SLEAssets/optionsAssets/Windows11Notification.png rename to assets/slushiEngineAssets/optionsAssets/Windows11Notification.png diff --git a/docs/development/BuildInstructions.md b/docs/development/BuildInstructions.md index 96a2c86..c0f3546 100644 --- a/docs/development/BuildInstructions.md +++ b/docs/development/BuildInstructions.md @@ -11,7 +11,8 @@ Set up [Visual Studio](https://aka.ms/vs/17/release/vs_BuildTools.exe) dependenc select "Individual Components" and make sure to download the following: - "MSVC v143 VS 2022 C++ x64/x86" and "Windows 10/11 SDK" + - MSVC v143 VS 2022 C++ x64/x86 + - Windows 10/11 SDK Set up Haxe libs of the engine: diff --git a/docs/development/SLELuaSpanish/sections/Others.lua b/docs/development/SLELuaSpanish/sections/Others.lua index 3eb3dfa..bdeb3bd 100644 --- a/docs/development/SLELuaSpanish/sections/Others.lua +++ b/docs/development/SLELuaSpanish/sections/Others.lua @@ -1,4 +1,18 @@ --- Others.lua -- Version: 1.1.0 -- Ultima modificación: 2/9/2024 +-- Others.lua -- Version: 1.2.0 -- Ultima modificación: 19/12/2024 + +-- retorna un string con el nombre de la cámara para Lua, pero puedes usarlo como una variable nativa de Lua +camGame = "game" +camHUD = "hud" +camOther = "other" +camNoteStuff = "notestuff" +camSLEHUD = "slehud" +camThings = "camthings" +camThings2 = "camthings2" +camThings3 = "camthings3" +camThings4 = "camthings4" +camThings5 = "camthings5" +camWaterMark = "camwatermark" + function printInGameplay(text, time) --[[ @@ -63,4 +77,19 @@ function tweenNumer(tag, startNum, endNum, duration, ease) duration: El tiempo del tween (float). ease: El tipo de easing a aplicar (por defecto "linear") (string). ]]-- +end + +function getSLEVersion() + --[[ + Obtiene la versión de Slushi Engine. + return: La versión de SLE (string). + ]]-- +end + +function getMTCurrentModifiers(equalizer) + --[[ + Obtiene los modifiers actuales con sus valores del modchart hecho con Modcharting Tools. + equalizer: String para separar los modifiers, por defecto ":" (string). + return: Los modifiers actuales (string). + ]]-- end \ No newline at end of file diff --git a/docs/development/SLELuaSpanish/sections/Shaders.lua b/docs/development/SLELuaSpanish/sections/Shaders.lua index a298be8..aa641de 100644 --- a/docs/development/SLELuaSpanish/sections/Shaders.lua +++ b/docs/development/SLELuaSpanish/sections/Shaders.lua @@ -1,4 +1,47 @@ --- Shaders.lua -- Versión 1.0 -- Ultima modificación: 23/08/2024 +-- Shaders.lua -- Versión 1.1.0 -- Ultima modificación: 23/12/2024 + +function addShader3DToCamStrumsAndCamNotes() + --[[ + Añade un shader 3D a la camara de los strums y las notas. + ]]-- +end + +function addShader3DToNotes() + --[[ + Añade un shader 3D a las notas. (acortacion de addShader3DToCamStrumsAndCamNotes) + ]]-- +end + +function removeShader3DFromCamStrumsAndCamNotes() + --[[ + Elimina el shader 3D de la camara de los strums y las notas. + ]]-- +end + +function removeShader3DFromNotes() + --[[ + Elimina el shader 3D de las notas (acortacion de removeShader3DFromCamStrumsAndCamNotes). + ]]-- +end + +function setNotesShader3DProperty(prop, value) + --[[ + Establece una propiedad del shader 3D de las notas. + prop: La propiedad a establecer (string). + value: El valor de la propiedad (Dynamic). + ]]-- +end + +function doTweenNotesShader3D(prop, tag, value, time, ease) + --[[ + Realiza un tween en una propiedad del shader 3D de las notas. + prop: La propiedad a establecer (string). + tag: La etiqueta de la interpolación (string). + value: El valor final del tween (Dynamic). + time: El tiempo de la interpolación (float). + ease: El tipo de easing a aplicar (por defecto "linear") (string). + ]]-- +end function addWhiteShaderToNotes() --[[ diff --git a/docs/development/SLELuaSpanish/sections/WinSL.lua b/docs/development/SLELuaSpanish/sections/WinSL.lua index 433744d..0a3cf80 100644 --- a/docs/development/SLELuaSpanish/sections/WinSL.lua +++ b/docs/development/SLELuaSpanish/sections/WinSL.lua @@ -1,4 +1,4 @@ --- WinSL.lua -- Version 1.0 -- Ultima modificación: 23/08/2024 +-- WinSL.lua -- Version 1.0.0 -- Ultima modificación: 23/08/2024 function winSL_console_getVersion() --[[ diff --git a/docs/development/SLELuaSpanish/sections/Window.lua b/docs/development/SLELuaSpanish/sections/Window.lua index 640d09e..f7e6f2d 100644 --- a/docs/development/SLELuaSpanish/sections/Window.lua +++ b/docs/development/SLELuaSpanish/sections/Window.lua @@ -1,70 +1,65 @@ --- Window.lua -- Versión 1.0 -- Ultima modificación: 23/08/2024 +-- Window.lua -- Versión 1.1.0 -- Ultima modificación: 23/12/2024 +--[[ + [Window.lua] es una seccion +]] -- -function windowTrans(trans, camToApply) +function windowTransparent(transparent, camToApply) --[[ Activa o desactiva la transparencia de la ventana. - trans: Booleano que indica si activar (true) o desactivar (false) la transparencia. + transparent: Booleano que indica si activar (true) o desactivar (false) la transparencia. camToApply: Nombre de la cámara a la cual se aplicará el efecto de transparencia (string). - ]]-- + ]] -- end -function windowAlpha(alpha) +function setWindowAlpha(alpha) --[[ Ajusta la opacidad de la ventana. alpha: Valor de opacidad a establecer (float). - ]]-- + ]] -- end -function doTweenWinAlpha(toValue, duration, ease) +function doTweenWinAlpha(value, duration, ease) --[[ Realiza un tween en la opacidad de la ventana. - fromValue: Valor inicial de opacidad (float). - toValue: Valor final de opacidad (float). + value: Valor de la opacidad (float). duration: Duración del tween (float). ease: Tipo de easing a aplicar (string). - ]]-- + ]] -- end function centerWindow() --[[ Centra la ventana en la pantalla. - ]]-- + ]] -- end -function setWindowVisible(visible) +function setMainWindowVisible(visible) --[[ Muestra u oculta la ventana. visible: Booleano que indica si la ventana debe ser visible (true) o no (false). - ]]-- -end -- USE_CAREFULLY + ]] -- +end -- USE_CAREFULLY -function winAlert(text, title) +function windowAlert(text, title) --[[ Muestra una alerta en la ventana. text: Texto del mensaje de alerta (string). title: Título de la ventana de alerta (string). - ]]-- + ]] -- end -function canResizableWindow(mode) +function resizableWindow(mode) --[[ Habilita o deshabilita la capacidad de cambiar el tamaño de la ventana. mode: Booleano que indica si habilitar (true) o deshabilitar (false) la capacidad de redimensionar. - ]]-- + ]] -- end function windowMaximized(mode) --[[ Maximiza o restaura la ventana. mode: Booleano que indica si maximizar (true) o restaurar (false) la ventana. - ]]-- -end - -function DisableCloseButton(mode) - --[[ - Habilita o deshabilita el botón de cierre de la ventana. - mode: Booleano que indica si deshabilitar (true) o habilitar (false) el botón de cierre. - ]]-- + ]] -- end function doTweenWinPos(mode, tag, value, duration, ease) @@ -75,13 +70,22 @@ function doTweenWinPos(mode, tag, value, duration, ease) value: Valor final de la posición (int). duration: Duración del tween (float). ease: Tipo de easing a aplicar (string). - ]]-- + ]] -- +end + +function centerWindowTween(tag, duration, ease) + --[[ + Centra la ventana en la pantalla con un tween. + tag: Etiqueta del tween (string). + duration: Duración del tween (float). + ease: Tipo de easing a aplicar (string). + ]] -- end function resetWindowParameters() --[[ Restaura los parámetros de la ventana a su configuración predeterminada. - ]]-- + ]] -- end function doTweenWinSize(mode, toValue, duration, ease) @@ -91,14 +95,21 @@ function doTweenWinSize(mode, toValue, duration, ease) toValue: Valor final del tamaño (float). duration: Duración del tween (float). ease: Tipo de easing a aplicar (por defecto "linear") (string). - ]]-- + ]] -- end -function winTitle(text) +function setWindowTitle(text) --[[ Cambia el título de la ventana. text: Nuevo título de la ventana (si pones "defualt", se pone el nombre por defecto del programa) (string). - ]]-- + ]] -- +end + +function getWindowTitle() + --[[ + Obtiene el título de la ventana. + return: El título de la ventana (string). + ]] -- end function setWindowPos(mode, value) @@ -106,31 +117,31 @@ function setWindowPos(mode, value) Establece la posición de la ventana. mode: La propiedad a establecer ("X" o "Y") (string). value: Valor de la posición (int). - ]]-- + ]] -- end function getWindowPos(mode) --[[ Obtiene la posición de la ventana. mode: La propiedad a obtener ("X" o "Y") (string). - ]]-- - return 0 + return: La posición de la ventana (int). + ]] -- end function getScreenSize(mode) --[[ Obtiene el tamaño de la pantalla. mode: La propiedad a obtener ("WIDTH", "W", "HEIGHT", "H") (string). - ]]-- - return 0 + return: El tamaño de la pantalla (int). + ]] -- end function getWindowSize(mode) --[[ Obtiene el tamaño de la ventana. mode: La propiedad a obtener ("WIDTH", "W", "HEIGHT", "H") (string). - ]]-- - return 0 + return: El tamaño de la ventana (int). + ]] -- end function setWindowSize(mode, value) @@ -138,15 +149,24 @@ function setWindowSize(mode, value) Establece el tamaño de la ventana. mode: La propiedad a establecer ("WIDTH", "W", "HEIGHT", "H") (string). value: Valor del tamaño (int). - ]]-- + ]] -- end -function setWindowBorderColor(r, g, b, mode) +function setWindowBorderColor(rgb, mode) --[[ Establece el color del borde de la ventana (solo Windows 11). - r: Valor rojo (int). - g: Valor verde (int). - b: Valor azul (int). + rgb: Color del borde (Array). + mode: Booleano que indica si permitir cambios de color con las notas (true) o no (false). + ]] -- +end + +function tweenWindowBorderColor(fromColor, toColor, duration, ease, mode) + --[[ + Realiza un tween en el color del borde de la ventana (solo Windows 11). + fromColor: Color inicial del borde (Array). + toColor: Color final del borde (Array). + duration: Duración del tween (float). + ease: Tipo de easing a aplicar (string). mode: Booleano que indica si permitir cambios de color con las notas (true) o no (false). - ]]-- + ]] -- end diff --git a/docs/development/SLELuaSpanish/sections/Windows.lua b/docs/development/SLELuaSpanish/sections/Windows.lua index b0db353..8622017 100644 --- a/docs/development/SLELuaSpanish/sections/Windows.lua +++ b/docs/development/SLELuaSpanish/sections/Windows.lua @@ -1,4 +1,4 @@ --- Windows.lua -- Versión 1.0 -- Ultima modificación: 23/08/2024 +-- Windows.lua -- Versión 1.1.0 -- Ultima modificación: 27/12/2024 function resetAllCPPFunctions() --[[ @@ -6,12 +6,6 @@ function resetAllCPPFunctions() ]]-- end -function getRAM() - --[[ - Obtiene la cantidad de memoria RAM disponible en el sistema. - ]]-- -end - function hideTaskBar(hide) --[[ Oculta o muestra la barra de tareas. @@ -22,7 +16,7 @@ end function setWallpaper(image) --[[ Establece una imagen como fondo de pantalla. - image: Nombre de la imagen a usar como fondo (string). + image: Nombre de la imagen a usar como fondo, si pones "defualt", se pone el fondo anterior o original (string). ]]-- end @@ -33,13 +27,7 @@ function winScreenCapture(nameToSave) ]]-- end -function setOldWindowsWallpaper() - --[[ - Restaura el fondo de pantalla anterior de Windows. - ]]-- -end - -function moveDesktopWindows(mode, value) +function setDesktopWindowsPos(mode, value) --[[ Mueve las iconos del escritorio en una dirección específica. mode: Dirección para mover ("X", "Y", "XY"). @@ -47,11 +35,11 @@ function moveDesktopWindows(mode, value) ]]-- end -function doTweenDesktopWindows(mode, toValue, duration, ease) +function doTweenDesktopWindowsPos(mode, value, duration, ease) --[[ Realiza un tween en las ventanas del escritorio. mode: Dirección del tween ("X", "Y", "XY"). - toValue: Valor final del tween. + value: Valor final del tween. duration: Duración del tween. ease: Tipo de easing (por defecto "linear"). ]]-- @@ -90,7 +78,7 @@ function getWindowsVersion() ]]-- end -function sendNoti(desc, title) +function sendNotification(desc, title) --[[ Envía una notificación en Windows. desc: Descripción de la notificación (string). @@ -122,33 +110,70 @@ end function setOtherWindowLayeredMode(window) --[[ Establece el modo de capa de otra ventana de Windows. - window: Nombre de la ventana ("desktop", "taskBar"). + window: Nombre de la ventana ("desktop", "taskBar") (string). + ]]-- +end + +-- EFECTOS GDI DE WINDOWS ------------------------------------------------------------- +--- En Windows, existe una manera de generar graficos, por medio de las funciones GDI +--- que estan en la API de Windows. +--- Son efectos vistos en virus o malware que esta hecho con ese proposito de generar tales efectos +--- Algunos de los malwares usan estos efectos pueden ser: +--- - MENZ +--- - Sulfoxide.exe +--- +--- Los efectos GDI, hacen un uso intensivo de la CPU +--- por eso en Slushi Engine, estos efectos corren en un hilo aparte del CPU para que +--- no afecte al juego principal. +--- +--- ============================================================ +--- Los efectos incluidos en SLE a la fecha de [19/12/2024] son: +--- - DrawIcons - Dibuja iconos de Windows en la pantalla en posiciones aleatorias. +--- - ScreenBlink - Realiza un efecto de parpadeo en la pantalla. +--- - ScreenGlitches - Realiza un efecto de errores graficos en la pantalla. +--- - ScreenShake - Realiza un efecto de agitación en la pantalla. +--- - ScreenTunnel - Realiza un efecto de túnel en la pantalla. +--- ============================================================ +--- +--- Los efectos GDI ocurren a pantalla completa modificnado todo lo que se muestre en esta +--- por ende pueden ser incomodos para algunos jugadores, por lo que se recomienda usarlos con precaucion. +--- Igualmente el jugador tiene la posibilidad de desactivar +--- estos efectos en las opciones de Slushi Engine. + +function startGDIThread() + --[[ + Prepara un hilo del CPU separado para correr los efectos GDI. ]]-- -end - ---------------------------------------------------------------- +end -- USE_CAREFULLY -function windowsEffectModifier(tag, gdiEffect, activeEffect) +function prepareGDIEffect(effect, wait) --[[ - Modifica un efecto GDI en Windows. - tag: Etiqueta del efecto (string). - gdiEffect: Tipo de efecto GDI (string). - activeEffect: true para activar, false para desactivar. + Inializa un efecto GDI, mas no necesariamente se muestra en la pantalla. + effect: Nombre del efecto GDI (string). + wait: Tiempo en milisegundos para esperar a que el efecto se muestre en pantalla, esto para + alentar el efecto cuanto mas alto sea el valor de wait (float). ]]-- end -- USE_CAREFULLY -function setWinEffectProperty(tag, prop, value) +function setGDIEffectWaitTime(effect, wait) --[[ - Establece una propiedad para un efecto GDI en Windows. - tag: Etiqueta del efecto (string). - prop: Propiedad a modificar (string). - value: Valor a establecer (dynamic). + Establece el tiempo en milisegundos para esperar a que el efecto se muestre en pantalla + effect: Nombre del efecto GDI (string). + wait: Tiempo en milisegundos para esperar a que el efecto se muestre en pantalla (float). ]]-- end -- USE_CAREFULLY -function setTitleTextToWindows(titleText) +function enableGDIEffect(effect, enabled) --[[ - Establece el texto del título en la ventana de Windows. - titleText: Texto del título (string). + Habilita o deshabilita un efecto GDI. + effect: Nombre del efecto GDI (string). + enabled: true para habilitar, false para deshabilitar. ]]-- end -- USE_CAREFULLY + +function removeGDIEffect(effect) + --[[ + Elimina un efecto GDI. + effect: Nombre del efecto GDI (string). + ]]-- +end -- USE_CAREFULLY \ No newline at end of file diff --git a/example_mods/C18H27NO3/data/songs/c18h27no3/c18h27no3-slushi.json b/example_mods/C18H27NO3/data/songs/c18h27no3/c18h27no3-slushi.json new file mode 100644 index 0000000..0985f8a --- /dev/null +++ b/example_mods/C18H27NO3/data/songs/c18h27no3/c18h27no3-slushi.json @@ -0,0 +1,2054 @@ +{ + "song": { + "speed": 3, + "stage": "", + "player1": "bf", + "player2": "gf", + "events": [], + "notes": [ + { + "gfSection": false, + "altAnim": false, + "typeOfSection": 0, + "sectionNotes": [ + [ + 12610.4285714286, + 0, + 0 + ], + [ + 12896.1428571429, + 2, + 0 + ], + [ + 13181.8571428571, + 1, + 0 + ], + [ + 13467.5714285714, + 3, + 0 + ], + [ + 13753.2857142857, + 2, + 0 + ], + [ + 14039, + 2, + 0 + ], + [ + 14181.8571428571, + 1, + 0 + ], + [ + 14324.7142857143, + 0, + 0 + ], + [ + 14610.4285714286, + 2, + 0 + ], + [ + 14896.1428571429, + 1, + 0 + ], + [ + 15181.8571428571, + 3, + 0 + ], + [ + 15467.5714285714, + 0, + 0 + ], + [ + 15753.2857142857, + 1, + 0 + ], + [ + 16039, + 2, + 0 + ], + [ + 16324.7142857143, + 3, + 0 + ], + [ + 16467.5714285714, + 1, + 0 + ], + [ + 16610.4285714286, + 3, + 0 + ], + [ + 16896.1428571429, + 2, + 0 + ], + [ + 17181.8571428571, + 1, + 0 + ], + [ + 17467.5714285714, + 0, + 0 + ], + [ + 17753.2857142857, + 2, + 0 + ], + [ + 18039, + 1, + 0 + ], + [ + 18324.7142857143, + 2, + 0 + ], + [ + 18610.4285714286, + 2, + 0 + ], + [ + 18753.2857142857, + 1, + 0 + ], + [ + 18896.1428571429, + 3, + 0 + ], + [ + 19181.8571428571, + 2, + 0 + ], + [ + 19467.5714285714, + 1, + 0 + ], + [ + 19753.2857142857, + 2, + 0 + ], + [ + 20039, + 3, + 0 + ], + [ + 20324.7142857143, + 0, + 0 + ], + [ + 20610.4285714286, + 2, + 0 + ], + [ + 20896.1428571429, + 1, + 0 + ], + [ + 21039, + 3, + 0 + ], + [ + 21181.8571428571, + 1, + 0 + ], + [ + 21467.5714285714, + 2, + 0 + ], + [ + 22896.1428571429, + 0, + 0 + ], + [ + 23181.8571428571, + 1, + 0 + ], + [ + 23467.5714285714, + 2, + 0 + ], + [ + 23753.2857142857, + 3, + 0 + ], + [ + 23896.1428571429, + 0, + 0 + ], + [ + 24181.8571428571, + 0, + 0 + ], + [ + 24467.5714285714, + 2, + 0 + ], + [ + 24610.4285714286, + 1, + 0 + ], + [ + 24896.1428571429, + 2, + 0 + ], + [ + 25181.8571428571, + 0, + 0 + ], + [ + 25467.5714285714, + 2, + 0 + ], + [ + 25753.2857142857, + 1, + 0 + ], + [ + 26039, + 3, + 0 + ], + [ + 26181.8571428571, + 2, + 0 + ], + [ + 26467.5714285714, + 2, + 0 + ], + [ + 26753.2857142857, + 1, + 0 + ], + [ + 26896.1428571429, + 0, + 0 + ], + [ + 27181.8571428571, + 2, + 0 + ], + [ + 27467.5714285714, + 1, + 0 + ], + [ + 27753.2857142857, + 2, + 0 + ], + [ + 28039, + 0, + 0 + ], + [ + 28324.7142857143, + 1, + 0 + ], + [ + 28467.5714285714, + 2, + 0 + ], + [ + 28753.2857142857, + 2, + 0 + ], + [ + 29039, + 1, + 0 + ], + [ + 29181.8571428571, + 0, + 0 + ], + [ + 29467.5714285714, + 3, + 0 + ], + [ + 29753.2857142857, + 1, + 0 + ], + [ + 30039, + 2, + 0 + ], + [ + 30324.7142857143, + 0, + 0 + ], + [ + 30610.4285714286, + 2, + 0 + ], + [ + 30753.2857142857, + 1, + 0 + ], + [ + 31039, + 1, + 0 + ], + [ + 31324.7142857143, + 3, + 0 + ], + [ + 31467.5714285714, + 2, + 0 + ], + [ + 31753.2857142857, + 3, + 0 + ], + [ + 32039, + 0, + 0 + ], + [ + 32324.7142857143, + 2, + 0 + ], + [ + 32610.4285714286, + 1, + 0 + ], + [ + 32896.1428571429, + 2, + 0 + ], + [ + 33039, + 0, + 0 + ], + [ + 33324.7142857143, + 0, + 0 + ], + [ + 33610.4285714286, + 1, + 0 + ], + [ + 33753.2857142857, + 2, + 0 + ], + [ + 34039, + 3, + 0 + ], + [ + 34324.7142857143, + 1, + 0 + ], + [ + 34610.4285714286, + 2, + 0 + ], + [ + 34896.1428571429, + 0, + 0 + ], + [ + 35181.8571428571, + 1, + 0 + ], + [ + 35324.7142857143, + 3, + 0 + ], + [ + 35610.4285714286, + 3, + 0 + ], + [ + 35896.1428571429, + 1, + 0 + ], + [ + 36039, + 2, + 0 + ], + [ + 36324.7142857143, + 3, + 0 + ], + [ + 36610.4285714286, + 1, + 0 + ], + [ + 36896.1428571429, + 3, + 0 + ], + [ + 37181.8571428571, + 2, + 0 + ], + [ + 37467.5714285714, + 1, + 0 + ], + [ + 37610.4285714286, + 2, + 0 + ], + [ + 37896.1428571429, + 2, + 0 + ], + [ + 38181.8571428571, + 1, + 0 + ], + [ + 38324.7142857143, + 0, + 0 + ], + [ + 38610.4285714286, + 2, + 0 + ], + [ + 38896.1428571429, + 1, + 0 + ], + [ + 39181.8571428571, + 3, + 0 + ], + [ + 39467.5714285714, + 0, + 0 + ], + [ + 39753.2857142857, + 2, + 0 + ], + [ + 39896.1428571429, + 1, + 0 + ], + [ + 40181.8571428571, + 3, + 0 + ], + [ + 40467.5714285714, + 1, + 0 + ], + [ + 40610.4285714286, + 2, + 0 + ], + [ + 40753.2857142857, + 1, + 0 + ], + [ + 40896.1428571429, + 3, + 0 + ], + [ + 41039, + 0, + 0 + ], + [ + 41181.8571428571, + 3, + 0 + ], + [ + 41467.5714285714, + 0, + 0 + ], + [ + 41753.2857142857, + 1, + 0 + ], + [ + 42039, + 0, + 0 + ], + [ + 42324.7142857143, + 2, + 0 + ], + [ + 42610.4285714286, + 1, + 0 + ], + [ + 42896.1428571429, + 3, + 0 + ], + [ + 43181.8571428571, + 2, + 0 + ], + [ + 43324.7142857143, + 2, + 0 + ], + [ + 43467.5714285714, + 2, + 0 + ], + [ + 43753.2857142857, + 1, + 0 + ], + [ + 44039, + 2, + 0 + ], + [ + 44324.7142857143, + 3, + 0 + ], + [ + 44610.4285714286, + 1, + 0 + ], + [ + 44896.1428571429, + 2, + 0 + ], + [ + 45181.8571428571, + 0, + 0 + ], + [ + 45467.5714285714, + 2, + 0 + ], + [ + 45610.4285714286, + 2, + 0 + ], + [ + 45753.2857142857, + 0, + 0 + ], + [ + 45896.1428571429, + 3, + 0 + ], + [ + 46039, + 0, + 0 + ], + [ + 46181.8571428571, + 3, + 0 + ], + [ + 46324.7142857143, + 0, + 0 + ], + [ + 46610.4285714286, + 1, + 0 + ], + [ + 46896.1428571429, + 2, + 0 + ], + [ + 47181.8571428571, + 1, + 0 + ], + [ + 47467.5714285714, + 2, + 0 + ], + [ + 47753.2857142857, + 3, + 0 + ], + [ + 48039, + 1, + 0 + ], + [ + 48324.7142857143, + 2, + 0 + ], + [ + 48610.4285714286, + 0, + 0 + ], + [ + 48896.1428571429, + 2, + 0 + ], + [ + 49181.8571428571, + 1, + 0 + ], + [ + 49467.5714285714, + 3, + 0 + ], + [ + 49753.2857142857, + 0, + 0 + ], + [ + 49896.1428571429, + 3, + 0 + ], + [ + 50039, + 0, + 0 + ], + [ + 50324.7142857143, + 1, + 0 + ], + [ + 50467.5714285714, + 2, + 0 + ], + [ + 50610.4285714286, + 1, + 0 + ], + [ + 50753.2857142857, + 2, + 0 + ], + [ + 50896.1428571429, + 1, + 0 + ], + [ + 51181.8571428571, + 0, + 0 + ], + [ + 51467.5714285714, + 2, + 0 + ], + [ + 51753.2857142857, + 1, + 0 + ], + [ + 52039, + 3, + 0 + ], + [ + 52324.7142857143, + 0, + 0 + ], + [ + 52396.1428571429, + 3, + 0 + ], + [ + 52467.5714285714, + 0, + 0 + ], + [ + 52539, + 3, + 0 + ], + [ + 52610.4285714286, + 0, + 0 + ], + [ + 52896.1428571429, + 1, + 0 + ], + [ + 53181.8571428571, + 2, + 0 + ], + [ + 53467.5714285714, + 3, + 0 + ], + [ + 53753.2857142857, + 1, + 0 + ], + [ + 54039, + 2, + 0 + ], + [ + 54324.7142857143, + 0, + 285.71428571429 + ], + [ + 54610.4285714286, + 3, + 285.714285714283 + ], + [ + 54896.1428571429, + 2, + 0 + ], + [ + 55181.8571428571, + 1, + 0 + ], + [ + 55467.5714285714, + 2, + 0 + ], + [ + 55753.2857142857, + 3, + 0 + ], + [ + 56039, + 1, + 0 + ], + [ + 56324.7142857143, + 2, + 0 + ], + [ + 56610.4285714286, + 0, + 0 + ], + [ + 56896.1428571429, + 2, + 0 + ], + [ + 57181.8571428571, + 1, + 0 + ], + [ + 57467.5714285714, + 3, + 0 + ], + [ + 57753.2857142857, + 2, + 0 + ], + [ + 58039, + 1, + 0 + ], + [ + 58324.7142857143, + 3, + 0 + ], + [ + 58610.4285714286, + 1, + 0 + ], + [ + 58896.1428571429, + 2, + 0 + ], + [ + 59181.8571428571, + 3, + 0 + ], + [ + 59467.5714285714, + 0, + 571.428571428565 + ], + [ + 60039, + 3, + 0 + ], + [ + 60181.8571428571, + 3, + 0 + ], + [ + 60324.7142857143, + 3, + 0 + ], + [ + 60467.5714285714, + 3, + 0 + ], + [ + 60610.4285714286, + 1, + 0 + ], + [ + 60753.2857142857, + 1, + 0 + ], + [ + 60896.1428571429, + 1, + 0 + ], + [ + 61039, + 3, + 0 + ], + [ + 61181.8571428571, + 2, + 0 + ], + [ + 61324.7142857143, + 2, + 428.571428571435 + ], + [ + 61753.2857142857, + 1, + 571.428571428565 + ], + [ + 62324.7142857143, + 0, + 0 + ], + [ + 62467.5714285714, + 0, + 0 + ], + [ + 62610.4285714286, + 0, + 0 + ], + [ + 62753.2857142857, + 0, + 0 + ], + [ + 62896.1428571429, + 3, + 0 + ], + [ + 63039, + 3, + 0 + ], + [ + 63181.8571428571, + 3, + 0 + ], + [ + 63324.7142857143, + 3, + 0 + ], + [ + 63467.5714285714, + 1, + 0 + ], + [ + 63610.4285714286, + 2, + 428.571428571428 + ], + [ + 64039, + 0, + 571.428571428572 + ], + [ + 64610.4285714286, + 3, + 0 + ], + [ + 64753.2857142857, + 3, + 0 + ], + [ + 64896.1428571429, + 3, + 0 + ], + [ + 65039, + 3, + 0 + ], + [ + 65181.8571428571, + 2, + 0 + ], + [ + 65324.7142857143, + 2, + 0 + ], + [ + 65467.5714285714, + 2, + 0 + ], + [ + 65610.4285714286, + 3, + 0 + ], + [ + 65753.2857142857, + 0, + 0 + ], + [ + 65896.1428571429, + 0, + 428.57142857142 + ], + [ + 66324.7142857143, + 3, + 0 + ], + [ + 66467.5714285714, + 2, + 0 + ], + [ + 66610.4285714286, + 1, + 0 + ], + [ + 66753.2857142857, + 0, + 0 + ], + [ + 66896.1428571429, + 3, + 0 + ], + [ + 67039, + 1, + 0 + ], + [ + 67181.8571428571, + 2, + 0 + ], + [ + 67324.7142857143, + 0, + 0 + ], + [ + 67467.5714285714, + 1, + 0 + ], + [ + 67753.2857142857, + 2, + 0 + ], + [ + 67896.1428571429, + 3, + 0 + ], + [ + 68039, + 0, + 0 + ], + [ + 68181.8571428571, + 3, + 0 + ], + [ + 68324.7142857143, + 2, + 0 + ], + [ + 68610.4285714286, + 3, + 571.42857142858 + ], + [ + 69181.8571428571, + 1, + 0 + ], + [ + 69324.7142857143, + 1, + 0 + ], + [ + 69467.5714285714, + 1, + 0 + ], + [ + 69610.4285714286, + 1, + 0 + ], + [ + 69753.2857142857, + 2, + 0 + ], + [ + 69896.1428571429, + 2, + 0 + ], + [ + 70039, + 2, + 0 + ], + [ + 70181.8571428571, + 1, + 0 + ], + [ + 70324.7142857143, + 3, + 0 + ], + [ + 70467.5714285714, + 3, + 428.571428571435 + ], + [ + 70896.1428571429, + 0, + 571.428571428565 + ], + [ + 71467.5714285714, + 1, + 0 + ], + [ + 71610.4285714286, + 1, + 0 + ], + [ + 71753.2857142857, + 1, + 0 + ], + [ + 71896.1428571429, + 1, + 0 + ], + [ + 72039, + 2, + 0 + ], + [ + 72181.8571428571, + 2, + 0 + ], + [ + 72324.7142857143, + 2, + 0 + ], + [ + 72467.5714285714, + 2, + 0 + ], + [ + 72610.4285714286, + 3, + 0 + ], + [ + 72753.2857142857, + 1, + 0 + ], + [ + 72896.1428571429, + 2, + 0 + ], + [ + 73039, + 0, + 0 + ], + [ + 73181.8571428571, + 3, + 571.428571428565 + ], + [ + 73467.5714285714, + 0, + 0 + ], + [ + 73753.2857142857, + 0, + 0 + ], + [ + 73896.1428571429, + 0, + 0 + ], + [ + 74039, + 0, + 0 + ], + [ + 74181.8571428571, + 0, + 0 + ], + [ + 74324.7142857143, + 2, + 0 + ], + [ + 74467.5714285714, + 2, + 0 + ], + [ + 74610.4285714286, + 2, + 0 + ], + [ + 74753.2857142857, + 0, + 0 + ], + [ + 74896.1428571429, + 1, + 0 + ], + [ + 75039, + 2, + 0 + ], + [ + 75181.8571428571, + 3, + 0 + ], + [ + 75467.5714285714, + 0, + 0 + ], + [ + 75610.4285714286, + 1, + 0 + ], + [ + 75753.2857142857, + 0, + 0 + ], + [ + 75896.1428571429, + 1, + 0 + ], + [ + 76039, + 2, + 0 + ], + [ + 76181.8571428571, + 3, + 0 + ], + [ + 76324.7142857143, + 2, + 0 + ], + [ + 76467.5714285714, + 3, + 0 + ], + [ + 76610.4285714286, + 0, + 0 + ], + [ + 76753.2857142857, + 2, + 0 + ], + [ + 76896.1428571429, + 0, + 0 + ], + [ + 77039, + 2, + 0 + ], + [ + 77181.8571428571, + 1, + 571.428571428565 + ], + [ + 77253.2857142857, + 3, + 500 + ], + [ + 78896.1428571429, + 1, + 0 + ], + [ + 78896.1428571429, + 2, + 0 + ], + [ + 80039, + 1, + 0 + ], + [ + 80039, + 3, + 0 + ], + [ + 81181.8571428571, + 2, + 0 + ], + [ + 81181.8571428571, + 3, + 0 + ], + [ + 82324.7142857143, + 0, + 0 + ], + [ + 82896.1428571429, + 2, + 0 + ], + [ + 83467.5714285714, + 1, + 0 + ], + [ + 84039, + 3, + 0 + ], + [ + 84610.4285714286, + 0, + 0 + ], + [ + 84610.4285714286, + 2, + 0 + ], + [ + 84896.1428571429, + 0, + 0 + ], + [ + 84896.1428571429, + 3, + 0 + ], + [ + 85181.8571428571, + 2, + 0 + ], + [ + 85181.8571428571, + 3, + 0 + ], + [ + 85467.5714285714, + 0, + 0 + ], + [ + 85467.5714285714, + 2, + 0 + ], + [ + 85753.2857142857, + 0, + 0 + ], + [ + 85896.1428571429, + 2, + 0 + ], + [ + 86039, + 0, + 0 + ], + [ + 86181.8571428571, + 2, + 0 + ], + [ + 86324.7142857143, + 1, + 0 + ], + [ + 86467.5714285714, + 3, + 0 + ], + [ + 86610.4285714286, + 1, + 0 + ], + [ + 86753.2857142857, + 3, + 0 + ], + [ + 86896.1428571429, + 2, + 1142.85714285713 + ], + [ + 86967.5714285714, + 1, + 1071.42857142857 + ], + [ + 90324.7142857143, + 0, + 0 + ], + [ + 90610.4285714286, + 2, + 0 + ], + [ + 90753.2857142857, + 1, + 0 + ], + [ + 90896.1428571429, + 2, + 0 + ], + [ + 91181.8571428571, + 2, + 0 + ], + [ + 91467.5714285714, + 0, + 0 + ], + [ + 91610.4285714286, + 3, + 0 + ], + [ + 91753.2857142857, + 0, + 0 + ], + [ + 92039, + 1, + 0 + ], + [ + 92324.7142857143, + 1, + 0 + ], + [ + 92610.4285714286, + 0, + 0 + ], + [ + 92896.1428571429, + 3, + 0 + ], + [ + 93039, + 2, + 0 + ], + [ + 93181.8571428571, + 3, + 0 + ], + [ + 93467.5714285714, + 3, + 0 + ], + [ + 93753.2857142857, + 0, + 0 + ], + [ + 93896.1428571429, + 2, + 0 + ], + [ + 94039, + 0, + 0 + ], + [ + 94181.8571428571, + 2, + 0 + ], + [ + 94324.7142857143, + 0, + 0 + ], + [ + 94610.4285714286, + 0, + 0 + ], + [ + 94896.1428571429, + 3, + 0 + ], + [ + 95181.8571428571, + 2, + 0 + ], + [ + 95324.7142857143, + 1, + 0 + ], + [ + 95467.5714285714, + 2, + 0 + ], + [ + 95753.2857142857, + 2, + 0 + ], + [ + 96039, + 3, + 0 + ], + [ + 96181.8571428571, + 0, + 0 + ], + [ + 96324.7142857143, + 3, + 0 + ], + [ + 96610.4285714286, + 1, + 0 + ], + [ + 96896.1428571429, + 2, + 0 + ], + [ + 97181.8571428571, + 0, + 0 + ], + [ + 97467.5714285714, + 0, + 0 + ], + [ + 97753.2857142857, + 1, + 0 + ], + [ + 98039, + 2, + 0 + ], + [ + 98324.7142857143, + 3, + 0 + ], + [ + 98610.4285714286, + 2, + 0 + ], + [ + 98896.1428571429, + 3, + 0 + ], + [ + 99181.8571428571, + 1, + 0 + ], + [ + 99467.5714285714, + 2, + 0 + ], + [ + 99753.2857142857, + 0, + 0 + ], + [ + 99896.1428571429, + 3, + 0 + ], + [ + 100039, + 0, + 0 + ], + [ + 100324.714285714, + 0, + 0 + ], + [ + 100610.428571429, + 1, + 0 + ], + [ + 100753.285714286, + 2, + 0 + ], + [ + 100896.142857143, + 1, + 0 + ], + [ + 101181.857142857, + 2, + 0 + ], + [ + 101467.571428571, + 2, + 0 + ], + [ + 101753.285714286, + 3, + 0 + ], + [ + 102039, + 1, + 0 + ], + [ + 102181.857142857, + 2, + 0 + ], + [ + 102324.714285714, + 1, + 0 + ], + [ + 102610.428571429, + 1, + 0 + ], + [ + 102896.142857143, + 3, + 0 + ], + [ + 103039, + 0, + 0 + ], + [ + 103181.857142857, + 3, + 0 + ], + [ + 103324.714285714, + 0, + 0 + ], + [ + 103467.571428571, + 3, + 0 + ], + [ + 103753.285714286, + 3, + 0 + ], + [ + 104039, + 0, + 0 + ], + [ + 104324.714285714, + 2, + 0 + ], + [ + 104467.571428571, + 1, + 0 + ], + [ + 104610.428571429, + 2, + 0 + ], + [ + 104896.142857143, + 2, + 0 + ], + [ + 105181.857142857, + 0, + 0 + ], + [ + 105324.714285714, + 1, + 0 + ], + [ + 105467.571428571, + 0, + 0 + ], + [ + 105610.428571429, + 1, + 0 + ], + [ + 105753.285714286, + 2, + 0 + ], + [ + 105896.142857143, + 3, + 0 + ], + [ + 106039, + 2, + 0 + ], + [ + 106181.857142857, + 3, + 0 + ], + [ + 106324.714285714, + 0, + 0 + ], + [ + 106467.571428571, + 2, + 0 + ], + [ + 106610.428571429, + 0, + 0 + ], + [ + 106753.285714286, + 2, + 0 + ], + [ + 106896.142857143, + 1, + 0 + ], + [ + 107039, + 3, + 0 + ], + [ + 107181.857142857, + 1, + 0 + ], + [ + 107324.714285714, + 3, + 0 + ], + [ + 107467.571428571, + 2, + 1142.85714285713 + ], + [ + 108610.428571429, + 3, + 571.42857142858 + ], + [ + 109181.857142857, + 0, + 571.428571428565 + ], + [ + 109753.285714286, + 2, + 285.71428571429 + ], + [ + 110039, + 1, + 285.71428571429 + ], + [ + 110324.714285714, + 2, + 285.714285714275 + ], + [ + 110610.428571429, + 0, + 285.714285714304 + ], + [ + 110896.142857143, + 1, + 571.428571428565 + ], + [ + 111467.571428571, + 2, + 285.714285714275 + ], + [ + 111753.285714286, + 1, + 285.71428571429 + ], + [ + 112039, + 0, + 571.428571428565 + ], + [ + 112610.428571429, + 3, + 571.42857142858 + ], + [ + 113181.857142857, + 1, + 2285.71428571429 + ], + [ + 115467.571428571, + 0, + 0 + ] + ], + "bpm": 210, + "sectionBeats": 4, + "changeBPM": false, + "mustHitSection": true + } + ], + "validScore": true, + "gfVersion": "gf", + "bpm": 210, + "needsVoices": false, + "notITG": true, + "song": "C18H27NO3", + "sleHUD": true + } +} \ No newline at end of file diff --git a/example_mods/C18H27NO3/data/songs/c18h27no3/modchart.json b/example_mods/C18H27NO3/data/songs/c18h27no3/modchart.json new file mode 100644 index 0000000..92ddc17 --- /dev/null +++ b/example_mods/C18H27NO3/data/songs/c18h27no3/modchart.json @@ -0,0 +1,1526 @@ +{ + "modifiers": [ + [ + "PosX", + "XModifier", + "Player", + -1, + -1 + ], + [ + "PosY", + "YModifier", + "Player", + -1, + -1 + ], + [ + "PosYD", + "YDModifier", + "Player", + -1, + -1 + ], + [ + "PosZ", + "ZModifier", + "Player", + -1, + -1 + ], + [ + "Confusion", + "ConfusionModifier", + "Player", + -1, + -1 + ], + [ + "SkewX", + "SkewXModifier", + "Player", + -1, + -1 + ], + [ + "DrunkX", + "DrunkXModifier", + "Player", + -1, + -1 + ], + [ + "DrunkZ", + "DrunkZModifier", + "Player", + -1, + -1 + ], + [ + "TipsyY", + "TipsyYModifier", + "Player", + -1, + -1 + ], + [ + "TipsyZ", + "TipsyZModifier", + "Player", + -1, + -1 + ], + [ + "Reverse", + "ReverseModifier", + "Player", + -1, + -1 + ], + [ + "Speed", + "SpeedModifier", + "Player", + -1, + -1 + ], + [ + "StrumAngle", + "StrumAngleModifier", + "Player", + -1, + -1 + ], + [ + "StrumLineRotate", + "StrumLineRotateModifier", + "Player", + -1, + -1 + ], + [ + "SlushiX", + "BeatXModifier", + "Player", + -1, + -1 + ], + [ + "IncomingAngle", + "IncomingAngleModifier", + "Player", + -1, + -1 + ], + [ + "InvertSine", + "InvertSineModifier", + "Player", + -1, + -1 + ], + [ + "Boost", + "BoostModifier", + "Player", + -1, + -1 + ], + [ + "Brake", + "BrakeModifier", + "Player", + -1, + -1 + ], + [ + "Boomerang", + "BoomerangModifier", + "Player", + -1, + -1 + ], + [ + "Tornado", + "TornadoModifier", + "Player", + -1, + -1 + ], + [ + "Invert", + "InvertModifier", + "Player", + -1, + -1 + ], + [ + "Flip", + "FlipModifier", + "Player", + -1, + -1 + ], + [ + "EaseX", + "EaseXModifier", + "Player", + -1, + -1 + ], + [ + "ShakyNotes", + "ShakyNotesModifier", + "Player", + -1, + -1 + ], + [ + "AlphaOpo", + "AlphaModifier", + "Opponent", + -1, + -1 + ], + [ + "AlphaPF1", + "AlphaModifier", + "Player", + 1, + -1 + ], + [ + "AlphaPF2", + "AlphaModifier", + "Player", + 2, + -1 + ], + [ + "AlphaPF0", + "AlphaModifier", + "Player", + 0, + -1 + ], + [ + "Wavering", + "WaveingModifier", + "Player", + -1, + -1 + ], + [ + "BounceZ", + "BounceZModifier", + "Player", + -1, + -1 + ], + [ + "Dizzy", + "DizzyModifier", + "Player", + -1, + -1 + ], + [ + "PosXPF1", + "XModifier", + "Player", + 1, + -1 + ], + [ + "PosYDPF1", + "YDModifier", + "Player", + 1, + -1 + ], + [ + "PosZPF1", + "ZModifier", + "Player", + 1, + -1 + ], + [ + "EaseXPF1", + "EaseXModifier", + "Player", + 1, + -1 + ], + [ + "EaseXPF0", + "EaseXModifier", + "Player", + 0, + -1 + ], + [ + "InvertSineZ", + "InvertSineZModifier", + "Player", + -1, + -1 + ], + [ + "Hidden", + "HiddenModifier", + "Player", + 1, + -1 + ], + [ + "laneAlpha", + "TargetAlphaModifier", + "Player", + 1, + -1 + ], + [ + "Sudden", + "SuddenModifier", + "Player", + 1, + -1 + ], + [ + "SpeedPF1", + "SpeedModifier", + "Player", + 1, + -1 + ], + [ + "noteAlphaPF0", + "NoteAlphaModifier", + "Player", + 0, + -1 + ], + [ + "ReversePF0", + "ReverseModifier", + "Player", + 0, + -1 + ], + [ + "BounceX", + "BounceXModifier", + "Player", + -1, + -1 + ], + [ + "EaseXPF2", + "EaseXModifier", + "Player", + 2, + -1 + ], + [ + "PosYDPF0", + "YDModifier", + "Player", + 0, + -1 + ], + [ + "PosYDPF2", + "YDModifier", + "Player", + 0, + -1 + ], + [ + "Alpha", + "AlphaModifier", + "Player", + -1, + -1 + ] + ], + "playfields": 3, + "events": [ + [ + "ease", + [ + 0, + "0", + "cubeInOut", + "1,AlphaOpo,1,AlphaPF1,1,AlphaPF2" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 0.25, + "0", + "cubeInOut", + "-315,PosX,-270,PosY,90,IncomingAngle:x,-130,IncomingAngle:y,1,Wavering,2,Boomerang,-0.5,InvertSine,,,400,PosZ,-4,BounceZ,0.5,BounceZ:speed,1,AlphaPF0,3,TipsyZ:speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 37.25, + "5", + "cubeInOut", + "0,PosZ,0,AlphaPF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 40.75, + "1", + "cubeInOut", + "0.8,TipsyZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 56.5, + "1", + "cubeInOut", + "2,TipsyZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 60, + "1", + "cubeInOut", + "4,TipsyZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 49, + "1", + "cubeInOut", + "1.5,TipsyZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 61.75, + "1", + "cubeInOut", + "5,TipsyZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 64.25, + "1", + "cubeInOut", + "7,TipsyZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 66.25, + "1", + "cubeInOut", + "9,TipsyZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 68.5, + "1", + "cubeInOut", + "11,TipsyZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 73.25, + "1", + "cubeInOut", + "13,TipsyZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 73.25, + "3", + "backInOut", + "360,Confusion,0,Dizzy" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 77, + "3", + "backInOut", + "0,Confusion,360,StrumLineRotate:x,0,PosY,1,Reverse,0,Boomerang,0,InvertSine,0,IncomingAngle:y,,,0,TipsyZ,0,BounceZ,0,Wavering" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 42.75, + "1", + "cubeInOut", + "0.1,Dizzy" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 80.25, + 1, + "cubeInOut", + "1,SlushiX,0.4,InvertSine,0.6,DrunkX" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 110, + "1.8", + "circOutIn", + "360,SkewX,0,StrumLineRotate:x,360,Confusion" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 126.25, + "1.8", + "circOutIn", + "0,SkewX,0,StrumLineRotate:x,0,Confusion,0,Reverse,," + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 136.25, + "1.8", + "backInOut", + "20,SkewX,20,IncomingAngle:y" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 131.5, + "0", + "backInOut", + "0,IncomingAngle:y,0,IncomingAngle:x" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 137.75, + "1.8", + "backInOut", + "-20,SkewX,-20,IncomingAngle:y" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 140.25, + "1.8", + "circInOut", + "360,SkewX,360,IncomingAngle:y,1,Reverse" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 142.5, + "0.7", + "circInOut", + "6,BounceZ,14,BounceZ:speed,12,ShakyNotes:speed,6,ShakyNotes" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 144.25, + "0.7", + "circInOut", + "0,BounceZ,0,BounceZ:speed,0,ShakyNotes" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 79.5, + 1, + "cubeInOut", + "2,DrunkX:speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 144.5, + "0.7", + "circInOut", + "-450,PosZPF1,0,AlphaPF1,-30,PosYD,10,EaseXPF1,7,EaseXPF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 144, + "0.7", + "circInOut", + "4,EaseXPF1:speed,6,EaseXPF0:speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 174.5, + "0.7", + "circInOut", + "10,StrumLineRotate:y" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 172.75, + "0", + "circInOut", + "0,IncomingAngle:x,0,IncomingAngle:y" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 175.75, + "0.7", + "circInOut", + "-10,StrumLineRotate:y" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 176.25, + "2", + "circInOut", + "360,StrumLineRotate:y" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 190.25, + "1", + "circInOut", + "-30,StrumLineRotate:x,," + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 191, + "1", + "circInOut", + "360,StrumLineRotate:x,," + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 200.25, + "1", + "circInOut", + "0.5,Speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 201.5, + "1", + "circInOut", + "1,Speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 204, + "1", + "circInOut", + "1.3,Speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 206.25, + "1", + "circInOut", + "0.7,Speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 208, + "1", + "circInOut", + "1.5,Speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 208.5, + "2", + "backInOut", + "1,Speed,0,StrumLineRotate:x,0,SlushiX,0,InvertSine,0,EaseXPF0,0,EaseXPF1,0,PosZPF1,1,AlphaPF1,0,DrunkX" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 212.25, + "0", + "backInOut", + "40,StrumLineRotate:x,10,InvertSineZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 212.25, + "2", + "backInOut", + "0,StrumLineRotate:x,0,InvertSineZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 220.25, + "0", + "backInOut", + "-40,StrumLineRotate:x,10,InvertSineZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 220.25, + "2", + "backInOut", + "0,StrumLineRotate:x,0,InvertSineZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 228.25, + "0", + "backInOut", + "40,StrumLineRotate:x,-10,InvertSineZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 228.25, + "2", + "backInOut", + "0,StrumLineRotate:x,0,InvertSineZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 244.25, + "0", + "backInOut", + "-40,StrumLineRotate:x,-10,InvertSineZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 244.25, + "2", + "backInOut", + "0,StrumLineRotate:x,0,InvertSineZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 252.25, + "0", + "backInOut", + "40,StrumLineRotate:x,-10,InvertSineZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 252.25, + "2", + "backInOut", + "0,StrumLineRotate:x,0,InvertSineZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 260.25, + "0", + "backInOut", + "-40,StrumLineRotate:x,-10,InvertSineZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 260.25, + "2", + "backInOut", + "0,StrumLineRotate:x,0,InvertSineZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 238, + "0.3", + "cubeInOut", + "3,BounceZ,20,BounceZ:speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 240.25, + "2", + "cubeInOut", + "0,BounceZ,0,BounceZ:speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 264, + "2", + "cubeInOut", + "3,ShakyNotes" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 272, + "2", + "cubeInOut", + "0,ShakyNotes,-120,PosZ,," + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 272.75, + "0", + "backInOut", + "-270,PosYDPF1,0,AlphaPF1,1,laneAlpha,1,noteAlphaPF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 273, + "0", + "backInOut", + "0.3,Hidden:start,4,Hidden:end,-0.2,Hidden:offset,22,Hidden,0.01,SpeedPF1" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 273.25, + "2", + "backInOut", + "2,TipsyZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 275.5, + "2", + "expoInOut", + "1,ReversePF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 279.5, + "2", + "expoInOut", + "0,ReversePF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 283.75, + "2", + "expoInOut", + "1,ReversePF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 287.75, + "2", + "expoInOut", + "0,ReversePF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 289.25, + "2", + "expoInOut", + "1,ReversePF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 291.5, + "2", + "expoInOut", + "0,ReversePF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 293.75, + "2", + "expoInOut", + "1,ReversePF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 297, + "1", + "expoInOut", + "1,ReversePF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 298.25, + "1", + "expoInOut", + "0,ReversePF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 295.99078125, + "1.3", + "expoInOut", + "0,ReversePF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 299, + "1", + "expoInOut", + "1,ReversePF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 299.5, + "1", + "expoInOut", + "0,noteAlphaPF0,1,AlphaPF1" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 304.5, + "4", + "backInOut", + "3,InvertSineZ,3,InvertSine,-2,Boomerang,-360,IncomingAngle:y,1,Reverse,0,ReversePF0,0,PosYDPF1" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 308, + "1", + "expoInOut", + "0,InvertSineZ,0,InvertSine,0,Boomerang,0,Tornado,0,Boomerang,0,TipsyZ,0,PosZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 303.5, + "1", + "expoInOut", + "3,InvertSineZ,90,IncomingAngle:x" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 316, + "1", + "expoInOut", + "-180,PosZ,-250,PosYDPF1,-140,PosYDPF2,40,PosYDPF0" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 316.25, + "1", + "expoInOut", + "0.3,AlphaPF2,0.2,AlphaPF1" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 315.75, + "1", + "expoInOut", + "0,Hidden,1,SpeedPF1,0,laneAlpha" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 316.5, + "1", + "expoInOut", + "9,EaseXPF1,8,EaseXPF1:speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 316.5, + "1", + "expoInOut", + "9,EaseXPF0,6,EaseXPF0:speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 316.5, + "1", + "expoInOut", + "9,EaseXPF2,10,EaseXPF2:speed" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 380.5, + "1", + "expoInOut", + "0,AlphaPF2,0,AlphaPF1,0,PosYDPF1,0,PosYDPF0,0,PosYDPF2,0,EaseXPF1,0,EaseXPF2,0,EaseXPF0,-270,PosYD,0.5,Flip" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 380.5, + "1", + "expoInOut", + "120,IncomingAngle:y,1,Boomerang,1,Tornado,-5,InvertSine,-4,InvertSineZ,2,BounceZ,0.2,BounceZ:speed,1,Brake" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 404.75, + "5", + "expoInOut", + "1,Alpha" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 399.5, + "3", + "backOutIn", + "-400,PosZ" + ], + [ + false, + 1, + 1 + ] + ], + [ + "ease", + [ + 404.25, + "1", + "backOutIn", + "0,PosZ" + ], + [ + false, + 1, + 1 + ] + ] + ] +} \ No newline at end of file diff --git a/example_mods/C18H27NO3/data/weeks/c18h27no3.json b/example_mods/C18H27NO3/data/weeks/c18h27no3.json new file mode 100644 index 0000000..72d719c --- /dev/null +++ b/example_mods/C18H27NO3/data/weeks/c18h27no3.json @@ -0,0 +1 @@ +{"songs":[["C18H27NO3","gf",[0,0,0]]],"hideFreeplay":false,"difficulties":"slushi","storyName":"","weekName":"c18h27no3-week","freeplayColor":[0,0,0],"hideStoryMode":true,"weekBefore":"none","startUnlocked":true,"blockOpponentMode":true} \ No newline at end of file diff --git a/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode1.png b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode1.png new file mode 100644 index 0000000..1a93d92 Binary files /dev/null and b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode1.png differ diff --git a/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode10.png b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode10.png new file mode 100644 index 0000000..3d43d4e Binary files /dev/null and b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode10.png differ diff --git a/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode2.png b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode2.png new file mode 100644 index 0000000..66f8c11 Binary files /dev/null and b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode2.png differ diff --git a/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode3.png b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode3.png new file mode 100644 index 0000000..6d92314 Binary files /dev/null and b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode3.png differ diff --git a/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode4.png b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode4.png new file mode 100644 index 0000000..82fa224 Binary files /dev/null and b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode4.png differ diff --git a/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode5.png b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode5.png new file mode 100644 index 0000000..0b6b7cb Binary files /dev/null and b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode5.png differ diff --git a/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode6.png b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode6.png new file mode 100644 index 0000000..dfd6da4 Binary files /dev/null and b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode6.png differ diff --git a/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode7.png b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode7.png new file mode 100644 index 0000000..76144a0 Binary files /dev/null and b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode7.png differ diff --git a/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode8.png b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode8.png new file mode 100644 index 0000000..20cfef3 Binary files /dev/null and b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode8.png differ diff --git a/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode9.png b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode9.png new file mode 100644 index 0000000..46b582a Binary files /dev/null and b/example_mods/C18H27NO3/images/slushiSongs/c18h27no3/slushiCodes/slushiCode9.png differ diff --git a/example_mods/C18H27NO3/scripts/songs/c18h27no3/modchart.lua b/example_mods/C18H27NO3/scripts/songs/c18h27no3/modchart.lua new file mode 100644 index 0000000..7fc4a20 --- /dev/null +++ b/example_mods/C18H27NO3/scripts/songs/c18h27no3/modchart.lua @@ -0,0 +1,369 @@ +-- Generated by StepMania to FNF Converter v1.3.5 (By Slushi) -- + +function onCreatePost() + startGDIThread(); -- :3 + prepareGDIEffect("ScreenGlitches", 0); + + resizableWindow(false); + addShader3DToNotes(); + initShaderFromSource("chromAB", "ChromAbBlueSwapEffect"); + initShaderFromSource("threeShader", "ThreeDEffect"); + initShaderFromSource("glitch", "GlitchedEffect"); + initShaderFromSource("mosaic", "MosaicEffect"); + initShaderFromSource("angel", "AngelEffect"); + initShaderFromSource("individualGlitches", "IndividualGlitchesEffect"); + + setCameraShader(camNoteStuff, "chromAB"); + setCameraShader(camSLEHUD, "chromAB"); + setCameraShader(camThings2, "chromAB"); + setCameraShader(camWaterMark, "chromAB"); + + setCameraShader(camSLEHUD, "threeShader"); + setCameraShader(camThings2, "threeShader"); + setCameraShader(camWaterMark, "threeShader"); + + setCameraShader(camNoteStuff, "mosaic"); + setCameraShader(camSLEHUD, "mosaic"); + setCameraShader(camThings2, "mosaic"); + setCameraShader(camWaterMark, "mosaic"); + + setCameraShader(camNoteStuff, "angel"); + setCameraShader(camSLEHUD, "angel"); + setCameraShader(camThings2, "angel"); + setCameraShader(camWaterMark, "angel"); + + setProperty('camZooming', false); + setProperty('healthBar.visible', false); + setProperty('healthBarBG.visible', false); + setProperty('scoreTxtSprite.visible', false); + setProperty('scoreTxt.visible', false); + setProperty('timeBar.visible', false); + setProperty('timeBarBG.visible', false); + setProperty('timeTxt.visible', false); + setProperty('camGame.visible', false); + setProperty('camHUD.visible', false); + tweenObjectFromSLEHUD("BLACKALPHA", 1, 0.1, "linear"); + setProperty('camSLEHUD.alpha', 0); + setProperty('camThings2.alpha', 0); + setPropertyFromClass("slushi.slushiUtils.SlushiEngineHUD", "instance.slushiSprite.visible", false); + + makeLuaText("mtModsText", "TEST", 0, 0.0, 0.0); + setTextFont("mtModsText", "vcr.ttf"); + setTextSize("mtModsText", 16); + setScrollFactor("mtModsText", 0.0, 0.0) + setTextAlignment("mtModsText", "CENTER"); + screenCenter("mtModsText", "XY"); + addLuaText("mtModsText"); + setObjectCamera("mtModsText", camThings2); + setProperty("mtModsText.y", getProperty("mtModsText.y") + 60); + + for i = 1, 10 do + makeLuaSprite("slushiCodeImage" .. i, "slushiSongs/c18h27no3/slushiCodes/slushiCode" .. i, 0, 0); + screenCenter("slushiCodeImage" .. i, "XY"); + addLuaSprite("slushiCodeImage" .. i, false); + setObjectCamera("slushiCodeImage" .. i, camThings); + setProperty("slushiCodeImage" .. i .. ".alpha", 0); + end +end + +local beat = 0; +local useNegative = false; +function onBeatHit() + beat = curBeat; + if curBeat >= 12 and curBeat <= 44 then + if curBeat % 4 == 0 then + useNegative = not useNegative; + local randomNumber = getRandomInt(1, 10); + local randomNumber2 = getRandomInt(0, 256); + local randomNumber3 = getRandomInt(350, 450); + startTween("tweenSLImgTween1A" .. randomNumber2, "slushiCodeImage" .. randomNumber, { alpha = 1 }, 1, + { ease = "linear" }); + setProperty("slushiCodeImage" .. randomNumber .. ".y", + getProperty("slushiCodeImage" .. randomNumber .. ".y") + 420); + if useNegative then + setProperty("slushiCodeImage" .. randomNumber .. ".x", + getProperty("slushiCodeImage" .. randomNumber .. ".x") - randomNumber3); + else + setProperty("slushiCodeImage" .. randomNumber .. ".x", + getProperty("slushiCodeImage" .. randomNumber .. ".x") + randomNumber3); + end + setProperty("slushiCodeImage" .. randomNumber .. ".angle", 5); + startTween("tweenSLImgTween2A" .. randomNumber2, "slushiCodeImage" .. randomNumber, { y = -1200 }, 8, + { ease = "linear" }); + end + end + + if curBeat == 60 then + tweenShaderFloat("chromABTweenA", "chromAB", "strength", 0.005, 1, "linear"); + end + + if curBeat == 62 then + tweenShaderFloat("chromABTween2", "chromAB", "strength", -0.005, 1, "linear"); + end + + if curBeat == 64 then + tweenShaderFloat("chromABTween3", "chromAB", "strength", 0.005, 1, "linear"); + end + + if curBeat == 66 then + tweenShaderFloat("chromABTween4", "chromAB", "strength", -0.005, 1, "linear"); + end + + if curBeat == 68 then + tweenShaderFloat("chromABTween5", "chromAB", "strength", 0.010, 1, "linear"); + end + + if curBeat == 73 then + tweenShaderFloat("chromABTween6", "chromAB", "strength", 0, 2, "elasticInOut"); + end + + if curBeat == 78 then + setProperty("camSLEHUD.zoom", getProperty("camSLEHUD.zoom") + 15); + setProperty("camSLEHUD.angle", 10); + setProperty('camSLEHUD.alpha', 1); + + setProperty("camThings2.zoom", getProperty("camThings2.zoom") + 15); + setProperty("camThings2.angle", 10); + setProperty('camThings2.alpha', 1); + tweenObjectFromSLEHUD("BLACKALPHA", 0.8, 1.5, "linear"); + startTween("camTween", "camSLEHUD", { zoom = 1 }, 1, { ease = "linear" }); + startTween("camTween2", "camSLEHUD", { angle = 0 }, 1, { ease = "linear" }); + startTween("camTween3", "camThings2", { zoom = 1 }, 1, { ease = "linear" }); + startTween("camTween4", "camThings2", { angle = 0 }, 1, { ease = "linear" }); + end + + if curBeat >= 80 and curBeat <= 144 then + if curBeat % 2 == 0 then + setWindowPos("X", getWindowPos("X") - 20); + doTweenWinPos("X", "windowTween1", getWindowPos("X") + 20, 0.2, "linear"); + + setWindowPos("Y", getWindowPos("Y") - 20); + doTweenWinPos("Y", "windowTween2", getWindowPos("Y") + 20, 0.2, "linear"); + else + setWindowPos("X", getWindowPos("X") + 20); + doTweenWinPos("X", "windowTween3", getWindowPos("X") - 20, 0.2, "linear"); + + setWindowPos("Y", getWindowPos("Y") + 20); + doTweenWinPos("Y", "windowTween4", getWindowPos("Y") - 20, 0.2, "linear"); + end + end + + if curBeat == 110 then + tweenShaderFloat("mosaicTween", "mosaic", "strength", 0, 1, "circoutin", 8); + end + + if curBeat == 126 then + tweenShaderFloat("mosaicTween2", "mosaic", "strength", 0, 1, "circoutin", 8); + end + + if curBeat == 136 then + tweenShaderFloat("mosaicTween3", "mosaic", "strength", 6, 0.6, "backinout"); + end + + if curBeat == 137 then + tweenShaderFloat("mosaicTween4", "mosaic", "strength", -6, 0.6, "backinout"); + end + + if curBeat == 140 then + tweenShaderFloat("mosaicTween5", "mosaic", "strength", 0, 0.6, "backinout"); + end + + if curBeat == 144 then + setCameraShader(camNoteStuff, "individualGlitches"); + setCameraShader(camSLEHUD, "individualGlitches"); + setCameraShader(camThings2, "individualGlitches"); + setCameraShader(camWaterMark, "individualGlitches"); + tweenShaderFloat("individualGlitchesTween", "individualGlitches", "binaryIntensity", 0.2, 0.6, "linear"); + end + + if curBeat == 208 then + removeCameraShader(camNoteStuff, "individualGlitches"); + removeCameraShader(camSLEHUD, "individualGlitches"); + removeCameraShader(camThings2, "individualGlitches"); + removeCameraShader(camWaterMark, "individualGlitches"); + startTween("camTween1", "camSLEHUD", { angle = 0 }, 0.8, { ease = "linear" }); + startTween("camTween2", "camThings2", { angle = 0 }, 0.8, { ease = "linear" }); + startTween("camTween3", "camWaterMark", { angle = 0 }, 0.8, { ease = "linear" }); + centerWindowTween("centerWindowTween", 0.8, "linear"); + end + + if curBeat == 212 then + tweenShaderFloat("chromABTween7", "chromAB", "strength", 0, 1, "linear", -0.015); + tweenShaderFloat("threeShaderTween2", "threeShader", "yrot", 0, 0.6, "linear", -0.4); + setNotesShader3DProperty("yrot", 0.4); + doTweenNotesShader3D("y", "threeShaderTween4", 0, 0.6, "linear"); + setWindowPos("X", getWindowPos("X") - 20); + doTweenWinPos("X", "windowTween1", getWindowPos("X") + 20, 0.2, "linear"); + setDesktopWindowsPos("X", getDesktopWindowsPos("X") - 40); + doTweenDesktopWindowsPos("X", getDesktopWindowsPos("X") + 40, 0.2, "linear"); + end + if curBeat == 220 then + tweenShaderFloat("chromABTween8", "chromAB", "strength", 0, 1, "linear", 0.015); + tweenShaderFloat("threeShaderTween3", "threeShader", "yrot", 0, 0.6, "linear", 0.4); + setNotesShader3DProperty("yrot", -0.4); + doTweenNotesShader3D("y", "threeShaderTween5", 0, 0.6, "linear"); + setWindowPos("X", getWindowPos("X") + 20) + doTweenWinPos("X", "windowTween2", getWindowPos("X") - 20, 0.2, "linear"); + setDesktopWindowsPos("X", getDesktopWindowsPos("X") + 40); + doTweenDesktopWindowsPos("X", getDesktopWindowsPos("X") - 40, 0.2, "linear"); + end + if curBeat == 228 then + tweenShaderFloat("chromABTween7", "chromAB", "strength", 0, 1, "linear", -0.015); + tweenShaderFloat("threeShaderTween4", "threeShader", "xrot", 0, 0.6, "linear", -0.4); + setNotesShader3DProperty("xrot", 0.4); + doTweenNotesShader3D("x", "threeShaderTween6", 0, 0.6, "linear"); + setWindowPos("Y", getWindowPos("Y") - 20); + doTweenWinPos("Y", "windowTween3", getWindowPos("Y") + 20, 0.2, "linear"); + setDesktopWindowsPos("Y", getDesktopWindowsPos("Y") - 40); + doTweenDesktopWindowsPos("Y", getDesktopWindowsPos("Y") + 40, 0.2, "linear"); + end + if curBeat == 240 then + tweenShaderFloat("chromABTween8", "chromAB", "strength", 0, 1, "linear", 0.015); + tweenShaderFloat("threeShaderTween5", "threeShader", "xrot", 0, 0.6, "linear", 0.4); + setNotesShader3DProperty("xrot", -0.4); + doTweenNotesShader3D("x", "threeShaderTween7", 0, 0.6, "linear"); + setWindowPos("Y", getWindowPos("Y") + 20); + doTweenWinPos("Y", "windowTween4", getWindowPos("Y") - 20, 0.2, "linear"); + setDesktopWindowsPos("Y", getDesktopWindowsPos("Y") + 40); + doTweenDesktopWindowsPos("Y", getDesktopWindowsPos("Y") - 40, 0.2, "linear"); + end + if curBeat == 244 then + tweenShaderFloat("chromABTween7", "chromAB", "strength", 0, 1, "linear", -0.015); + tweenShaderFloat("threeShaderTween6", "threeShader", "zrot", 0, 0.6, "linear", -0.4); + setNotesShader3DProperty("zrot", 0.4); + doTweenNotesShader3D("z", "threeShaderTween8", 0, 0.6, "linear"); + setWindowPos("X", getWindowPos("X") - 20); + setWindowPos("Y", getWindowPos("Y") - 20); + doTweenWinPos("X", "windowTween5", getWindowPos("X") + 20, 0.2, "linear"); + doTweenWinPos("Y", "windowTween6", getWindowPos("Y") + 20, 0.2, "linear"); + setDesktopWindowsPos("X", getDesktopWindowsPos("X") - 40); + setDesktopWindowsPos("Y", getDesktopWindowsPos("Y") - 40); + doTweenDesktopWindowsPos("X", getDesktopWindowsPos("X") + 40, 0.2, "linear"); + doTweenDesktopWindowsPos("Y", getDesktopWindowsPos("Y") + 40, 0.2, "linear"); + end + if curBeat == 252 then + tweenShaderFloat("chromABTween7", "chromAB", "strength", 0, 1, "linear", 0.015); + tweenShaderFloat("threeShaderTween7", "threeShader", "zrot", 0, 0.6, "linear", 0.4); + setNotesShader3DProperty("zrot", -0.4); + doTweenNotesShader3D("z", "threeShaderTween9", 0, 0.6, "linear"); + setWindowPos("X", getWindowPos("X") + 20); + setWindowPos("Y", getWindowPos("Y") + 20); + doTweenWinPos("X", "windowTween7", getWindowPos("X") - 20, 0.2, "linear"); + doTweenWinPos("Y", "windowTween8", getWindowPos("Y") - 20, 0.2, "linear"); + setDesktopWindowsPos("X", getDesktopWindowsPos("X") + 40); + setDesktopWindowsPos("Y", getDesktopWindowsPos("Y") + 40); + doTweenDesktopWindowsPos("X", getDesktopWindowsPos("X") - 40, 0.2, "linear"); + doTweenDesktopWindowsPos("Y", getDesktopWindowsPos("Y") - 40, 0.2, "linear"); + end + if curBeat == 260 then + tweenShaderFloat("chromABTween7", "chromAB", "strength", 0, 1, "linear", -0.015); + tweenShaderFloat("threeShaderTween8", "threeShader", "yrot", 0, 0.6, "linear", -0.4); + setNotesShader3DProperty("yrot", 0.4); + doTweenNotesShader3D("y", "threeShaderTween8", 0, 0.6, "linear"); + setWindowPos("X", getWindowPos("X") - 20) + doTweenWinPos("X", "windowTween8", getWindowPos("X") + 20, 0.2, "linear"); + setDesktopWindowsPos("X", getDesktopWindowsPos("X") - 40); + doTweenDesktopWindowsPos("X", getDesktopWindowsPos("X") + 40, 0.2, "linear"); + end + + if curBeat == 272 then + setCameraShader(camNoteStuff, "individualGlitches"); + setCameraShader(camSLEHUD, "individualGlitches"); + setCameraShader(camThings2, "individualGlitches"); + setCameraShader(camWaterMark, "individualGlitches"); + tweenShaderFloat("individualGlitchesTween", "individualGlitches", "binaryIntensity", 0.2, 3, "linear"); + tweenShaderFloat("angelTween", "angel", "strength", 0.4, 0.6, "linear"); + end + + if curBeat == 275 or curBeat == 279 or curBeat == 283 or curBeat == 287 or curBeat == 289 or curBeat == 291 or curBeat == 293 or curBeat == 295 or curBeat == 297 or curBeat == 298 or curBeat == 299 then + tweenShaderFloat("individualGlitchesTween", "individualGlitches", "binaryIntensity", 0, 0.6, "linear", 0.2); + tweenWindowBorderColor({255, 0, 0}, {0, 0, 0}, 0.6, "linear", false); + end + + if curBeat == 308 then + setShaderProperty("individualGlitches", "binaryIntensity", 0.2); + setShaderProperty("angel", "strength", 0.4); + end + + if curBeat == 316 then + removeCameraShader(camNoteStuff, "individualGlitches"); + removeCameraShader(camSLEHUD, "individualGlitches"); + removeCameraShader(camThings2, "individualGlitches"); + removeCameraShader(camWaterMark, "individualGlitches"); + setShaderProperty("angel", "strength", 0); + + enableGDIEffect("ScreenGlitches", true); + hideTaskBar(true); + -- enableGDIEffect("DrawIcons", true); + -- enableGDIEffect("ScreenShake", true); + end + + if curBeat >= 316 and curBeat <= 380 then + if curBeat % 2 == 0 then + setDesktopWindowsPos("X", getDesktopWindowsPos("X") - 40); + doTweenDesktopWindowsPos("X", getDesktopWindowsPos("X") + 40, 0.2, "linear"); + tweenWindowBorderColor({255, 0, 0}, {0, 0, 0}, 0.3, "linear", false); + else + setDesktopWindowsPos("X", getDesktopWindowsPos("X") + 40); + doTweenDesktopWindowsPos("X", getDesktopWindowsPos("X") - 40, 0.2, "linear"); + tweenWindowBorderColor({0, 0, 0}, {255, 0, 0}, 0.3, "linear", false); + end + end + + if curBeat == 404 then + enableGDIEffect("ScreenGlitches", false); + end +end + +function onStepHit() + if curStep >= 1250 and curStep < 1264 then + local screenWidth = getScreenSize("WIDTH") + local screenHeight = getScreenSize("HEIGHT") + local windowWidth = getWindowSize("WIDTH") + local windowHeight = getWindowSize("HEIGHT") + local maxX = screenWidth - windowWidth + local maxY = screenHeight - windowHeight + + local randomX = getRandomInt(0, maxX) + local randomY = getRandomInt(0, maxY) + + setWindowPos("X", randomX) + setWindowPos("Y", randomY) + end + + if curStep == 1265 then + centerWindowTween("centerWindowTween2", 0.6, "linear"); + end +end + +local speed = 2 +local elapsedTime = 0 +local angleRange = 8 + +local levitationSpeed = 1.6 +local levitationHeight = 0.4 +local elapsedTime2 = 0 +local initialWindowX = getWindowPos("X") + +function onUpdatePost(elapsed) + --[[ + getMTCurrentModifiers() only exists because the same code that has that function in source, did not work in HScript + So.. New function to SLE's Lua API XD + ]] + setTextString("mtModsText", "Actual modifiers:\n" .. getMTCurrentModifiers(":")); + screenCenter("mtModsText", "X"); + + elapsedTime = elapsedTime + (elapsed * speed) + local angle = math.sin(elapsedTime) * angleRange + + elapsedTime2 = elapsedTime2 + (elapsed * levitationSpeed) + local y = math.sin(elapsedTime2) * levitationHeight + setProperty("mtModsText.y", getProperty("mtModsText.y") + y); + + if beat >= 144 and beat <= 208 then + setProperty("camSLEHUD.angle", angle); + setProperty("camWaterMark.angle", angle); + setProperty("camThings2.angle", angle); + setWindowPos("X", 300 * math.cos(elapsedTime) / 5 + initialWindowX); + end +end diff --git a/example_mods/C18H27NO3/songs/c18h27no3/Inst.ogg b/example_mods/C18H27NO3/songs/c18h27no3/Inst.ogg new file mode 100644 index 0000000..9112129 Binary files /dev/null and b/example_mods/C18H27NO3/songs/c18h27no3/Inst.ogg differ diff --git a/funkinscsource/Main.hx b/funkinscsource/Main.hx index b696135..2f31672 100644 --- a/funkinscsource/Main.hx +++ b/funkinscsource/Main.hx @@ -53,8 +53,6 @@ class Main extends Sprite // utils.logging.CrashHandler.queryStatus(); // #end - // WindowsFuncs.initThreadForWindowRespondingHandler(); - setupGame(); } diff --git a/funkinscsource/codenameengine/scripting/Script.hx b/funkinscsource/codenameengine/scripting/Script.hx index a5b5e0d..637c33b 100644 --- a/funkinscsource/codenameengine/scripting/Script.hx +++ b/funkinscsource/codenameengine/scripting/Script.hx @@ -112,14 +112,14 @@ class Script extends FlxBasic implements IFlxDestroyable // Shaders "ColorSwap" => shaders.ColorSwap, // States - "FreeplayState" => states.freeplay.FreeplayState, + "FreeplayState" => slushi.states.freeplay.SlushiFreeplayState, "MainMenuState" => states.MainMenuState, "PlayState" => states.PlayState, "StoryMenuState" => states.StoryMenuState, "TitleState" => states.TitleState, // SubStates "GameOverSubstate" => substates.GameOverSubstate, - "PauseSubState" => substates.PauseSubState, + "PauseSubState" => slushi.substates.SlushiPauseSubState, // External Usages For Engine "Countdown" => backend.Countdown, diff --git a/funkinscsource/debug/FPSCounter.hx b/funkinscsource/debug/FPSCounter.hx index f8990e0..55b27d5 100644 --- a/funkinscsource/debug/FPSCounter.hx +++ b/funkinscsource/debug/FPSCounter.hx @@ -30,8 +30,6 @@ class FPSCounter extends TextField public var taskMemoryMegas:Dynamic = 0; - public static var currentTotalMemory:Dynamic = 0; - public var memoryUsage:String = ''; @:noCompletion private var cacheCount:Int; @@ -115,8 +113,6 @@ class FPSCounter extends TextField FlxTween.tween(this, {x: 0, y: 0}, 0.1, {ease: FlxEase.quadOut}); } - currentTotalMemory = memoryMegas; - text = 'FPS: $currentFPS' + (ClientPrefs.data.memoryDisplay ? ' | Memory: ${CoolUtil.getSizeString(memoryMegas)} / ${CoolUtil.getSizeString(taskMemoryMegas)}' : '') + (ClientPrefs.data.dateDisplay ? '\nDate: $stringTimeToReturn' : '') diff --git a/funkinscsource/import.hx b/funkinscsource/import.hx index b3f45a2..2b572c2 100644 --- a/funkinscsource/import.hx +++ b/funkinscsource/import.hx @@ -2,13 +2,14 @@ import lime.app.Application; import openfl.Lib; +import lime.system.System; // Windows things #if windows import slushi.windows.CppAPI; import slushi.windows.WindowsCPP; import slushi.windows.WindowsCPP.MessageBoxIcon; import slushi.windows.WindowsFuncs; -import slushi.windows.WinConsoleUtils; +import slushi.windows.WindowsTerminalCPP; #end // Window, main class of the engine and other things import slushi.windowThings.WindowFuncs; diff --git a/funkinscsource/objects/PsychVideoSprite.hx b/funkinscsource/objects/PsychVideoSprite.hx index 5c1c00c..678d02d 100644 --- a/funkinscsource/objects/PsychVideoSprite.hx +++ b/funkinscsource/objects/PsychVideoSprite.hx @@ -53,25 +53,25 @@ class PsychVideoSprite #if (VIDEOS_ALLOWED && hxvlc) extends FlxVideoSprite #end return b; } - public override function pause() - { - super.pause(); - if (FlxG.autoPause) - { - if (FlxG.signals.focusGained.has(bitmap.resume)) FlxG.signals.focusGained.remove(bitmap.resume); - if (FlxG.signals.focusLost.has(bitmap.pause)) FlxG.signals.focusLost.remove(bitmap.pause); - } - } - - public override function resume() - { - super.resume(); - if (FlxG.autoPause) - { - if (!FlxG.signals.focusGained.has(bitmap.resume)) FlxG.signals.focusGained.add(bitmap.resume); - if (!FlxG.signals.focusLost.has(bitmap.pause)) FlxG.signals.focusLost.add(bitmap.pause); - } - } + // public override function pause() + // { + // super.pause(); + // if (FlxG.autoPause) + // { + // if (FlxG.signals.focusGained.has(bitmap.resume)) FlxG.signals.focusGained.remove(bitmap.resume); + // if (FlxG.signals.focusLost.has(bitmap.pause)) FlxG.signals.focusLost.remove(bitmap.pause); + // } + // } + + // public override function resume() + // { + // super.resume(); + // if (FlxG.autoPause) + // { + // if (!FlxG.signals.focusGained.has(bitmap.resume)) FlxG.signals.focusGained.add(bitmap.resume); + // if (!FlxG.signals.focusLost.has(bitmap.pause)) FlxG.signals.focusLost.add(bitmap.pause); + // } + // } // maybe temp? public function addCallback(vidCallBack:String, func:Void->Void) diff --git a/funkinscsource/psychlua/FunkinLua.hx b/funkinscsource/psychlua/FunkinLua.hx index 857b98e..49f395f 100644 --- a/funkinscsource/psychlua/FunkinLua.hx +++ b/funkinscsource/psychlua/FunkinLua.hx @@ -19,7 +19,7 @@ import objects.Character; import objects.HealthIcon; import states.MainMenuState; import states.StoryMenuState; -import substates.PauseSubState; +import slushi.substates.SlushiPauseSubState; import substates.GameOverSubstate; import psychlua.LuaUtils; import psychlua.LuaUtils.LuaTweenOptions; @@ -1082,7 +1082,7 @@ class FunkinLua set("restartSong", function(?skipTransition:Bool = false) { game.persistentUpdate = false; FlxG.camera.followLerp = 0; - PauseSubState.restartSong(skipTransition); + SlushiPauseSubState.restartSong(skipTransition); return true; }); set("exitSong", function(?skipTransition:Bool = false) { @@ -1096,7 +1096,7 @@ class FunkinLua { if (PlayState.isStoryMode) MusicBeatState.switchState(new StoryMenuState()); else - MusicBeatState.switchState(new states.freeplay.FreeplayState()); + MusicBeatState.switchState(new slushi.states.freeplay.SlushiFreeplayState()); } #if BASE_GAME_FILES else @@ -1107,7 +1107,7 @@ class FunkinLua game.openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new StoryMenuState(sticker))); } else - game.openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new states.freeplay.FreeplayState(sticker))); + game.openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new slushi.states.freeplay.SlushiFreeplayState(sticker))); } #end diff --git a/funkinscsource/psychlua/LuaUtils.hx b/funkinscsource/psychlua/LuaUtils.hx index c0ee063..51c926e 100644 --- a/funkinscsource/psychlua/LuaUtils.hx +++ b/funkinscsource/psychlua/LuaUtils.hx @@ -857,16 +857,16 @@ class LuaUtils case 'camslehud' | 'slehud': return PlayState.instance.camSLEHUD; - case 'camfor3d': - return PlayState.instance.camFor3D; - case 'camfor3d2': - return PlayState.instance.camFor3D2; - case 'camfor3d3': - return PlayState.instance.camFor3D3; - case 'camfor3d4': - return PlayState.instance.camFor3D4; - case 'camfor3d5': - return PlayState.instance.camFor3D5; + case 'camthings': + return PlayState.instance.camThings; + case 'camthings2': + return PlayState.instance.camThings2; + case 'camthings3': + return PlayState.instance.camThings3; + case 'camthings4': + return PlayState.instance.camThings4; + case 'camthings5': + return PlayState.instance.camThings5; case 'camwatermark' | 'watermark': return PlayState.instance.camWaterMark; } @@ -900,16 +900,16 @@ class LuaUtils camera = 'mainCam'; case 'camslehud' | 'slehud': camera = 'camSLEHUD'; - case 'camfor3d': - camera = 'camFor3D'; - case 'camfor3d2': - camera = 'camFor3D2'; - case 'camfor3d3': - camera = 'camFor3D3'; - case 'camfor3d4': - camera = 'camFor3D4'; - case 'camfor3d5': - camera = 'camFor3D5'; + case 'camthings': + camera = 'camThings'; + case 'camthings2': + camera = 'camThings2'; + case 'camthings3': + camera = 'camThings3'; + case 'camthings4': + camera = 'camThings4'; + case 'camthings5': + camera = 'camThings5'; case 'camwatermark' | 'watermark': camera = 'camWaterMark'; default: @@ -1338,19 +1338,19 @@ class LuaUtils return FunkinLua.lua_Cameras.get("main"); case 'camslehud' | 'slehud': - return FunkinLua.lua_Cameras.get("slehud"); - case 'camfor3d': - return FunkinLua.lua_Cameras.get("camFor3D"); - case 'camfor3d2': - return FunkinLua.lua_Cameras.get("camFor3D2"); - case 'camfor3d3': - return FunkinLua.lua_Cameras.get("camFor3D3"); - case 'camfor3d4': - return FunkinLua.lua_Cameras.get("camFor3D4"); - case 'camfor3d5': - return FunkinLua.lua_Cameras.get("camFor3D5"); + return FunkinLua.lua_Cameras.get("camSLEHUD"); + case 'camthings': + return FunkinLua.lua_Cameras.get("camThings"); + case 'camthings2': + return FunkinLua.lua_Cameras.get("camThings2"); + case 'camthings3': + return FunkinLua.lua_Cameras.get("camThings3"); + case 'camthings4': + return FunkinLua.lua_Cameras.get("camThings4"); + case 'camthings5': + return FunkinLua.lua_Cameras.get("camThings5"); case 'camwatermark' | 'watermark': - return FunkinLua.lua_Cameras.get("camWatermark"); + return FunkinLua.lua_Cameras.get("camWaterWark"); } return FunkinLua.lua_Cameras.get("game"); diff --git a/funkinscsource/scripting/SCScript.hx b/funkinscsource/scripting/SCScript.hx index fd453ea..5ce141d 100644 --- a/funkinscsource/scripting/SCScript.hx +++ b/funkinscsource/scripting/SCScript.hx @@ -105,7 +105,7 @@ class SCScript extends flixel.FlxBasic "TitleState" => states.TitleState, // SubStates "GameOverSubstate" => substates.GameOverSubstate, - "PauseSubState" => substates.PauseSubState, + "PauseSubState" => slushi.substates.SlushiPauseSubState, // External Usages For Engine "Countdown" => backend.Countdown, diff --git a/funkinscsource/slushi/MainGame.hx b/funkinscsource/slushi/MainGame.hx index 7145b88..8d0e42f 100644 --- a/funkinscsource/slushi/MainGame.hx +++ b/funkinscsource/slushi/MainGame.hx @@ -3,8 +3,8 @@ package slushi; import flixel.FlxGame; import flixel.FlxState; import slushi.slushiUtils.crashHandler.CrashHandler; -import slushi.winSL.WinSLCrashHandler; import slushi.substates.DebugSubState; +import slushi.windows.winGDIThings.WinGDIThread; /* * This class is the base game, the FlxGame, modified to make the in-game crash handler that contains the Slushi Engine functional. @@ -24,6 +24,7 @@ class MainGame extends FlxGame #if windows WindowsFuncs.resetAllCPPFunctions(); WindowFuncs.resetWindowParameters(); + WinGDIThread.stopThread(); #end try @@ -38,7 +39,7 @@ class MainGame extends FlxGame { if (!crashHandlerAlredyOpen) { - CrashHandler.symbolPrevent(error); + CrashHandler.symbolPrevent(error, 0); crashHandlerAlredyOpen = true; } } @@ -48,10 +49,12 @@ class MainGame extends FlxGame { if (FlxG.keys.justPressed.F3) { - if (Type.getClass(FlxG.state) == PlayState) { + if (Type.getClass(FlxG.state) == PlayState) + { DebugSubState.onPlayState = true; } - else { + else + { DebugSubState.onPlayState = false; } FlxG.state.openSubState(new DebugSubState()); @@ -69,7 +72,7 @@ class MainGame extends FlxGame { if (!crashHandlerAlredyOpen) { - CrashHandler.symbolPrevent(error); + CrashHandler.symbolPrevent(error, 1); crashHandlerAlredyOpen = true; } } @@ -86,7 +89,7 @@ class MainGame extends FlxGame { if (!crashHandlerAlredyOpen) { - CrashHandler.symbolPrevent(error); + CrashHandler.symbolPrevent(error, 2); crashHandlerAlredyOpen = true; } } diff --git a/funkinscsource/slushi/SlushiMain.hx b/funkinscsource/slushi/SlushiMain.hx index 42357c3..5498fc0 100644 --- a/funkinscsource/slushi/SlushiMain.hx +++ b/funkinscsource/slushi/SlushiMain.hx @@ -6,6 +6,9 @@ import slushi.others.BuildDemoText; import slushi.slushiUtils.crashHandler.CrashHandler; import tjson.TJSON as Json; import slushi.states.SlushiTitleState; +import slushi.windows.winGDIThings.WinGDIThread; +import haxe.Http; +import slushi.others.EngineMacros; /* * This is the main class for the Slushi Engine initialization, this loads all initial functions of Windows C++ API @@ -15,22 +18,23 @@ import slushi.states.SlushiTitleState; */ class SlushiMain { - // Versions of the things in the engine and base engine (SCE) - public static var buildNumber:String = "19102024"; + // Versions of the things in the engine and SCE + public static var buildNumber:String = EngineMacros.prepareBuildNumber(); public static var sceGitCommit:String = "4eaf8c4"; - public static var slushiEngineVersion:String = '0.3.8'; - public static var winSLVersion:String = '1.3.0'; - public static var slCrashHandlerVersion:String = '1.4.0'; + public static var slushiEngineVersion:String = '0.4.0'; + public static var sleThingsVersions = { + winSLVersion: '1.3.0', + slCrashHandlerVersion: '1.4.0' + }; - public static var slushiColor = FlxColor.fromRGB(143, 217, 209); // 0xff8FD9D1 0xffd6f3de - private static var pathsToCreate:Array = ['./engineUtils', './engineUtils/SMToConvert']; + public static var slushiColor:FlxColor = FlxColor.fromRGB(143, 217, 209); // 0xff8FD9D1 0xffd6f3de + private static var pathsToCreate:Array = ['./slEngineUtils', './slEngineUtils/SMToConvert', './mods/images/windowsAssets/']; public static function loadSlushiEngineFunctions() { #if windows preventAdminExecution(); CppAPI._setWindowLayered(); - CppAPI.centerWindow(); WindowsFuncs.resetAllCPPFunctions(); WindowsFuncs.saveCurrentWindowsWallpaper(); if (ClientPrefs.data.useSavedWallpaper) @@ -39,12 +43,12 @@ class SlushiMain } WindowsFuncs.setSlushiColorToWindow(); #end + WindowFuncs.centerWindow(); + CrashHandler.initCrashHandler(); SystemInfo.init(); - createEngineUtilsFolder(); + createSLEngineFolders(); Application.current.window.onClose.add(SlushiMain.onCloseWindow); - CrashHandler.initCrashHandler(); - #if THIS_IS_A_BUILD_TEST var textWarn:BuildDemoText = new BuildDemoText(); Lib.current.stage.addChild(textWarn); @@ -53,8 +57,9 @@ class SlushiMain inline public static function getSLEPath(file:String = ''):String { - final finalFile = 'assets/slushiEngineAssets/SLEAssets/$file'; - if (FileSystem.exists(finalFile)) { + final finalFile = 'assets/slushiEngineAssets/$file'; + if (FileSystem.exists(finalFile)) + { return finalFile; } else if (finalFile.endsWith('.png')) @@ -74,42 +79,60 @@ class SlushiMain } } - public static function createEngineUtilsFolder() + private static function createSLEngineFolders() { - var paths:Array = pathsToCreate; - - for (path in paths) - if (!FileSystem.exists(path)) - FileSystem.createDirectory(path); + for (path in pathsToCreate) + { + try + { + if (!FileSystem.exists(path)) + { + FileSystem.createDirectory(path); + } + } + catch (e) + { + Debug.logSLEError('Error creating [$path]: $e'); + } + } } public static function onCloseWindow() { Sys.println("\033[0m"); + CustomFuncs.removeAllFilesFromCacheDirectory(); #if windows - Debug.logSLEInfo("Reseting all C++ functions...\n\n"); + Debug.logSLEInfo("Reseting all C++ functions...\n"); + WinGDIThread.stopThread(); WindowsFuncs.resetAllCPPFunctions(); // Delete the saved wallpaper if it exists @:privateAccess - if (FileSystem.exists(WindowsFuncs.savedWallpaperPath)) + try { - FileSystem.deleteFile(WindowsFuncs.savedWallpaperPath); + if (FileSystem.exists(WindowsFuncs.savedWallpaperPath)) + { + FileSystem.deleteFile(WindowsFuncs.savedWallpaperPath); + } + } + catch (e) + { + Debug.logSLEError('Error deleting saved wallpaper: $e'); } // Close the game without animations if it is in a crash, preventing a posible loop if (CrashHandler.inCrash) { - Sys.exit(1); + System.exit(1); return; } Application.current.window.onClose.cancel(); - var numTween:NumTween = FlxTween.num(CppAPI.getWindowOppacity(), 0, 0.7, { + var numTween:NumTween = FlxTween.num(CppAPI.getWindowOppacity(), 0, 0.6, { onComplete: function(twn:FlxTween) { - Sys.exit(0); + System.exit(0); } }); numTween.onUpdate = function(twn:FlxTween) @@ -117,7 +140,7 @@ class SlushiMain CppAPI.setWindowOppacity(numTween.value); } #else - Application.current.window.close(); + System.exit(0); #end } @@ -126,7 +149,7 @@ class SlushiMain if (ClientPrefs.data.checkForUpdates) { Debug.logSLEInfo('Checking for new version...'); - var http = new haxe.Http("https://raw.githubusercontent.com/Slushi-Github/Slushi-Engine/main/gitVersion.json"); + var http = new Http("https://raw.githubusercontent.com/Slushi-Github/Slushi-Engine/main/gitVersion.json"); var jsonData:Dynamic = null; http.onData = function(data:String) @@ -138,20 +161,33 @@ class SlushiMain catch (e) { Debug.logSLEError('Error parsing JSON: $e'); + return; } var currentVersion = slushiEngineVersion; var gitVersion = jsonData.engineVersion; - Debug.logInfo('version online: [' + gitVersion + '], this version: [' + currentVersion + ']'); - if (gitVersion != currentVersion) + + Debug.logSLEInfo('Version online: [' + gitVersion + '], this version: [' + currentVersion + ']'); + + var currentVersionNum = CustomFuncs.parseVersion(currentVersion); + var gitVersionNum = CustomFuncs.parseVersion(gitVersion); + + if (currentVersionNum > gitVersionNum) { - Debug.logSLEWarn('Versions arent matching!'); + Debug.logSLEInfo('The version is higher than the one on Github so this is a development version, skipping update check.'); + SlushiTitleState.gitVersion.needUpdate = false; + slushiEngineVersion += ' - [DEV]'; + } + else if (currentVersionNum < gitVersionNum) + { + Debug.logSLEWarn('A new version is available!'); SlushiTitleState.gitVersion.needUpdate = true; SlushiTitleState.gitVersion.newVersion = gitVersion; } else { Debug.logSLEInfo('Versions are matching!'); + SlushiTitleState.gitVersion.needUpdate = false; } } @@ -169,14 +205,24 @@ class SlushiMain /** * Even though SLE does not require administrator permissions for absolutely nothing, I do NOT want the engine * to be able to run with those permissions, it DOES NOT NEED THEM. + * + * Except when running SLE on Linux or MacOS through Wine, Wine will always run a + * Windows program with administrator permissions apparently, making it + * impossible to run SLE this way before. */ private static function preventAdminExecution() { #if windows + if (WindowsCPP.detectWine()) + { + Debug.logSLEWarn("Wine detected! Skipping admin check because Wine always runs as admin."); + return; + } + if (WindowsCPP.isRunningAsAdmin()) { CppAPI.showMessageBox("SLE is running as an administrator, please don't do that.", "Slushi Engine: HEY!!", MSG_WARNING); - Sys.exit(1); + System.exit(1); } #end } diff --git a/funkinscsource/slushi/others/CustomFuncs.hx b/funkinscsource/slushi/others/CustomFuncs.hx index 8479e31..be60e7e 100644 --- a/funkinscsource/slushi/others/CustomFuncs.hx +++ b/funkinscsource/slushi/others/CustomFuncs.hx @@ -1,6 +1,7 @@ package slushi.others; import haxe.io.Path; +import slushi.others.systemUtils.HiddenProcess; /** * This class contains custom functions for the engine, but not usually used in the engine itself @@ -31,56 +32,53 @@ class CustomFuncs return all; } - public static function getAllPath():String + public static function getProgramPath():String { var allPath:String = Path.directory(Sys.programPath()).replace("\\", "/"); return allPath; } - public static function realResetGame(?arg:String):Void + public static function realResetGame(?args:Array = null):Void { - #if windows - new Process("SLE.exe", [arg]); - Sys.exit(0); - #else - Sys.exit(0); - #end + new HiddenProcess(Sys.programPath(), args); + System.exit(0); } - public static function setWinBorderColorFromInt(color:Int):Void + public static function parseVersion(version:String):Int { - #if windows - var red:Int = (color >> 16) & 0xFF; - var green:Int = (color >> 8) & 0xFF; - var blue:Int = color & 0xFF; - var rgb:Array = [red, green, blue]; - WindowsFuncs.setWindowBorderColor(rgb); - #end + var parts = version.split("."); + var major = Std.parseInt(parts[0]); + var minor = parts.length > 1 ? Std.parseInt(parts[1]) : 0; + var patch = parts.length > 2 ? Std.parseInt(parts[2]) : 0; + return (major * 10000) + (minor * 100) + patch; // Ej: "1.2.3" -> 10203 } - // Thanks Glowsoony for this code - public static function getRGBFromFlxColor(red:FlxColor, green:FlxColor, blue:FlxColor):Array + public static function removeAllFilesFromCacheDirectory():Void { - // Función para convertir el valor entero a componentes RGB - function getRGB(color:Int):Array + final path = "./assets/slushiEngineAssets/OthersAssets/SLCache"; + try { - var red = (color >> 16) & 0xFF; - var green = (color >> 8) & 0xFF; - var blue = color & 0xFF; - return [red, green, blue]; + if (FileSystem.exists(path)) + { + var directory = FileSystem.readDirectory(path); + for (file in directory) + { + FileSystem.deleteFile(Path.join([path, file])); + } + } + } + catch (e:Dynamic) + { + Debug.logError('Error removing files from cache directory: $e'); } - - // Convertir cada FlxColor a su representación entera - var flxColorRed = cast red; // No es necesario volver a convertir desde RGB si ya tienes un FlxColor - var flxColorGreen = cast green; - var flxColorBlue = cast blue; - - // Obtener los valores RGB de cada color - var redRGB = getRGB(flxColorRed); - var greenRGB = getRGB(flxColorGreen); - var blueRGB = getRGB(flxColorBlue); - - // Devolver el arreglo con los componentes RGB - return [redRGB[0], greenRGB[1], blueRGB[2]]; } -} \ No newline at end of file + + public static function colorIntToRGB(color:Int):Array + { + var red:Int = (color >> 16) & 0xFF; + var green:Int = (color >> 8) & 0xFF; + var blue:Int = color & 0xFF; + var rgb:Array = [red, green, blue]; + return rgb; + } +} diff --git a/funkinscsource/slushi/others/EngineMacros.hx b/funkinscsource/slushi/others/EngineMacros.hx index de41937..5c0feae 100644 --- a/funkinscsource/slushi/others/EngineMacros.hx +++ b/funkinscsource/slushi/others/EngineMacros.hx @@ -1,55 +1,66 @@ package slushi.others; -import sys.io.File; +import CompileTime; /** * A simple macro for showing information about the engine compilation * * Author: Slushi */ - class EngineMacros { - #if macro - static var ENGINE_VERSION = "0.3.8"; - static var CUSTOM_BUILD_NAME = "not defined"; - - public static function initialize_compilation() { - Sys.println('\n\x1b[38;5;236m== STARTING COMPILATION ===================\033[0m'); - Sys.println('---- \033[96mSlushi Engine\033[0m version: \x1b[38;5;236m[\033[0m\x1b[38;5;11m${ENGINE_VERSION}\033[0m\x1b[38;5;236m]\033[0m ----'); - - Sys.println('\x1b[38;5;7mBuild info:\033[0m'); - #if SLUSHI_CPP_CODE - Sys.println('C++ Code is \x1b[38;5;10menabled\x1b[0m'); - #else - Sys.println('C++ Code is \x1b[38;5;1mdisabled\x1b[0m'); - #end - #if SLUSHI_LUA - Sys.println('Slushi Lua is \x1b[38;5;10menabled\x1b[0m'); - #else - Sys.println('Slushi Lua is \x1b[38;5;1mdisabled\x1b[0m'); - #end - #if CUSTOM_BUILD - Sys.println('This is a custom build?: \x1b[38;5;10mYES\x1b[0m'); - Sys.println('Custom build name: \x1b[38;5;242m${CUSTOM_BUILD_NAME}\x1b[0m'); - #else - Sys.println('This is a custom build?: \x1b[38;5;1mNO\x1b[0m'); - #end - #if THIS_IS_A_BUILD_TEST - Sys.println('Compiling a \x1b[38;5;11mtest build\x1b[0m!'); - #end - #if windows - Sys.println('Compiling for \x1b[38;5;4mWindows\x1b[0m'); - #elseif linux - Sys.println('Compiling for \x1b[38;5;5mLinux\x1b[0m'); - #elseif macos - Sys.println('Compiling for MacOS'); - #end - - Sys.println('-----------'); - Sys.println('Trying to initialize the compilation...'); - Sys.println('Date on start compilation: \033[32m${Date.now().toString()}\033[0m'); - Sys.println('\x1b[38;5;234m==========================\033[0m\n\x1b[38;5;8m'); - } - #end -} \ No newline at end of file + #if macro + static var ENGINE_VERSION = "0.4.0"; + static var CUSTOM_BUILD_NAME = "not defined"; + + public static function showBuildInfo() + { + Sys.println('\n\x1b[38;5;236m== STARTING COMPILATION ===================\033[0m'); + Sys.println('---- \033[96mSlushi Engine\033[0m version: \x1b[38;5;236m[\033[0m\x1b[38;5;11m${ENGINE_VERSION}\033[0m\x1b[38;5;236m]\033[0m ----'); + + Sys.println('\x1b[38;5;7mBuild info:\033[0m'); + #if SLUSHI_CPP_CODE + Sys.println('C++ Code is \x1b[38;5;10menabled\x1b[0m'); + #else + Sys.println('C++ Code is \x1b[38;5;1mdisabled\x1b[0m'); + #end + #if SLUSHI_LUA + Sys.println('Slushi Lua is \x1b[38;5;10menabled\x1b[0m'); + #else + Sys.println('Slushi Lua is \x1b[38;5;1mdisabled\x1b[0m'); + #end + #if CUSTOM_BUILD + Sys.println('This is a custom build?: \x1b[38;5;10mYES -- \x1b[38;5;242m${CUSTOM_BUILD_NAME}\x1b[0m'); + #else + Sys.println('This is a custom build?: \x1b[38;5;1mNO\x1b[0m'); + #end + #if THIS_IS_A_BUILD_TEST + Sys.println('Compiling a \x1b[38;5;11mtest build\x1b[0m!'); + #end + #if windows + Sys.println('Compiling for \x1b[38;5;4mWindows\x1b[0m'); + #elseif linux + Sys.println('Compiling for \x1b[38;5;5mLinux\x1b[0m'); + #elseif macos + Sys.println('Compiling for MacOS'); + #end + + Sys.println('-----------'); + Sys.println('Trying to initialize the compilation...'); + Sys.println('Date on start compilation: \033[32m${Date.now().toString()}\033[0m'); + Sys.println('\x1b[38;5;234m==========================\033[0m\n\x1b[38;5;8m'); + } + #end + + public static function prepareBuildNumber():String { + var currentDate = CompileTime.buildDate(); + + var day:String = Std.string(currentDate.getDate()); + var month:String = Std.string(currentDate.getMonth() + 1); + var year:String = Std.string(currentDate.getFullYear()); + + var finalText:String = day + month + year; + + return finalText; + } +} diff --git a/funkinscsource/slushi/others/SlushiSongs.hx b/funkinscsource/slushi/others/SlushiSongs.hx index 7e0cc2a..8d9cd7f 100644 --- a/funkinscsource/slushi/others/SlushiSongs.hx +++ b/funkinscsource/slushi/others/SlushiSongs.hx @@ -5,7 +5,20 @@ package slushi.others; * * Author: Slushi */ +class SlushiSongs +{ + private static var slSongs:Array> = [["C18H27NO3", "slushi"]]; -class SlushiSongs { - public static var slSongs:Array = []; -} \ No newline at end of file + public static function checkSong(songName:String, difficulty:String):Bool + { + for (i in slSongs) + { + if (songName == i[0] && difficulty == i[1]) + { + return true; + break; + } + } + return false; + } +} diff --git a/funkinscsource/slushi/slushiLua/OthersLua.hx b/funkinscsource/slushi/slushiLua/OthersLua.hx index 9e52b5b..de06151 100644 --- a/funkinscsource/slushi/slushiLua/OthersLua.hx +++ b/funkinscsource/slushi/slushiLua/OthersLua.hx @@ -2,11 +2,11 @@ package slushi.slushiLua; import slushi.slushiUtils.SlushiEngineHUD; import slushi.slushiUtils.SlushiDebugText; - import psychlua.FunkinLua; import psychlua.LuaUtils; - import lime.system.System; +import objects.note.StrumArrow; +import objects.note.Note; class OthersLua { @@ -14,6 +14,18 @@ class OthersLua { Debug.logSLEInfo('Loaded Slushi Others Lua functions!'); + funkLua.set("camGame", "game"); + funkLua.set("camHUD", "hud"); + funkLua.set("camOther", "other"); + funkLua.set("camNoteStuff", "notestuff"); + funkLua.set("camSLEHUD", "slehud"); + funkLua.set("camThings", "camthings"); + funkLua.set("camThings2", "camthings2"); + funkLua.set("camThings3", "camthings3"); + funkLua.set("camThings4", "camthings4"); + funkLua.set("camThings5", "camthings5"); + funkLua.set("camWaterMark", "camwatermark"); + funkLua.set("printInGameplay", function(text:Dynamic = '', time:Float = 6) { if (text == null) @@ -23,7 +35,8 @@ class OthersLua funkLua.set("tweenObjectFromSLEHUD", function(mode:String, value:Dynamic, time:Float, ease:String = "linear") { - switch(mode) { + switch (mode) + { case "X": SlushiEngineHUD.instance.moveSLELogoX(value, time, ease); case "Y": @@ -55,7 +68,7 @@ class OthersLua funkLua.set("CopyCamera", function(camTag:String, camToCopy:String) { - var variables = MusicBeatState.getVariables("Tween"); + var variables = MusicBeatState.getVariables("Camera"); if (!variables.exists(camTag)) { var camera = new backend.CameraCopy(LuaUtils.cameraFromString(camToCopy)); @@ -67,8 +80,9 @@ class OthersLua } }); - funkLua.set("removeCopyCamera", function(camTag:String) { - var variables = MusicBeatState.getVariables("Tween"); + funkLua.set("removeCopyCamera", function(camTag:String) + { + var variables = MusicBeatState.getVariables("Camera"); if (variables.exists(camTag)) { @@ -79,21 +93,64 @@ class OthersLua } }); - funkLua.set("tweenNumer", function(tag:String, startNum:Float, endNum:Float, duration:Float, ease:String = "linear") { - + funkLua.set("tweenNumer", function(tag:String, startNum:Float, endNum:Float, duration:Float, ease:String = "linear") + { var variables = MusicBeatState.getVariables("Tween"); variables.set(tag, FlxTween.num(startNum, endNum, duration, { ease: LuaUtils.getTweenEaseByString(ease), - onComplete: function(twn:FlxTween) { + onComplete: function(twn:FlxTween) + { variables.remove(tag); - if (PlayState.instance != null) PlayState.instance.callOnLuas('onTweenCompleted', [tag]); + if (PlayState.instance != null) + PlayState.instance.callOnLuas('onTweenCompleted', [tag]); return endNum; }, - onUpdate: function(tween:FlxTween) { + onUpdate: function(tween:FlxTween) + { return tween.percent; } })); }); + + funkLua.set("getSLEVersion", function():String + { + var version = SlushiMain.slushiEngineVersion; + + // This should not happen in an official build, but well, to avoid problems + if (version.contains(' - [DEV]')) + version = version.replace(' - [DEV]', ''); + + return version; + }); + + funkLua.set("getMTCurrentModifiers", function(equalizer:String = ":"):String + { + var leText = ''; + // if (!PlayState.instance.notITGMod) + // Debug.logSLEInfo('getMTCurrentModifiers called while not in ITG mode!'); + // return ''; + + // Code from Hitmans AD + for (modName => mod in PlayState.instance.playfieldRenderer.modifierTable.modifiers) + { + if (mod.currentValue != mod.baseValue) + { + leText += modName + equalizer + " " + FlxMath.roundDecimal(mod.currentValue, 2); + for (subModName => subMod in mod.subValues) + { + leText += " " + subModName + equalizer + " " + FlxMath.roundDecimal(subMod.value, 2); + } + leText += "\n"; + } + } + + return leText; + }); + + funkLua.set("colorIntToRGB", function(color:Int):Array + { + return CustomFuncs.colorIntToRGB(color); + }); } } diff --git a/funkinscsource/slushi/slushiLua/ShadersLua.hx b/funkinscsource/slushi/slushiLua/ShadersLua.hx index 35fe5b6..2321f46 100644 --- a/funkinscsource/slushi/slushiLua/ShadersLua.hx +++ b/funkinscsource/slushi/slushiLua/ShadersLua.hx @@ -14,11 +14,11 @@ class ShadersLua Debug.logSLEInfo('Loaded Slushi Shaders Lua functions!'); FunkinLua.lua_Cameras.set("camSLEHUD", {cam: PlayState.instance.camSLEHUD, shaders: [], shaderNames: []}); - FunkinLua.lua_Cameras.set("camFor3D", {cam: PlayState.instance.camFor3D, shaders: [], shaderNames: []}); - FunkinLua.lua_Cameras.set("camFor3D2", {cam: PlayState.instance.camFor3D2, shaders: [], shaderNames: []}); - FunkinLua.lua_Cameras.set("camFor3D3", {cam: PlayState.instance.camFor3D3, shaders: [], shaderNames: []}); - FunkinLua.lua_Cameras.set("camFor3D4", {cam: PlayState.instance.camFor3D4, shaders: [], shaderNames: []}); - FunkinLua.lua_Cameras.set("camFor3D5", {cam: PlayState.instance.camFor3D5, shaders: [], shaderNames: []}); + FunkinLua.lua_Cameras.set("camThings", {cam: PlayState.instance.camThings, shaders: [], shaderNames: []}); + FunkinLua.lua_Cameras.set("camThings2", {cam: PlayState.instance.camThings2, shaders: [], shaderNames: []}); + FunkinLua.lua_Cameras.set("camThings3", {cam: PlayState.instance.camThings3, shaders: [], shaderNames: []}); + FunkinLua.lua_Cameras.set("camThings4", {cam: PlayState.instance.camThings4, shaders: [], shaderNames: []}); + FunkinLua.lua_Cameras.set("camThings5", {cam: PlayState.instance.camThings5, shaders: [], shaderNames: []}); FunkinLua.lua_Cameras.set("camWaterWark", {cam: PlayState.instance.camWaterMark, shaders: [], shaderNames: []}); funkLua.set("addShader3DToCamStrumsAndCamNotes", function() diff --git a/funkinscsource/slushi/slushiLua/SlushiLua.hx b/funkinscsource/slushi/slushiLua/SlushiLua.hx index bae019a..766e33e 100644 --- a/funkinscsource/slushi/slushiLua/SlushiLua.hx +++ b/funkinscsource/slushi/slushiLua/SlushiLua.hx @@ -1,21 +1,23 @@ package slushi.slushiLua; +import psychlua.FunkinLua; + /* * This class contains ALL Lua functions for Slushi Engine, it is one of the most important files since it * is what allows to make modcharts using the features of the engine through Lua, and more. * * Author: Slushi -*/ - -import psychlua.FunkinLua; - + */ class SlushiLua { public static var apliedWindowTransparent:Bool = false; - public static var slushi_InternalSprites:Map = new Map(); + public static var slushi_InternalObjects:Map = new Map(); public static function loadSlushiLua(funkLua:FunkinLua) - { + { + if (slushi_InternalObjects != null) + slushi_InternalObjects.clear(); + Debug.logSLEInfo("Loading Slushi Lua functions..."); #if (SLUSHI_LUA && LUA_ALLOWED) WindowsLua.loadWindowsLua(funkLua); diff --git a/funkinscsource/slushi/slushiLua/WinSLLua.hx b/funkinscsource/slushi/slushiLua/WinSLLua.hx index 780a4fa..f35c652 100644 --- a/funkinscsource/slushi/slushiLua/WinSLLua.hx +++ b/funkinscsource/slushi/slushiLua/WinSLLua.hx @@ -14,7 +14,7 @@ class WinSLLua funkLua.set("winSL_console_getVersion", function() { - return SlushiMain.winSLVersion; + return SlushiMain.sleThingsVersions.winSLVersion; }); funkLua.set("winSL_console_printLetterByLetter", function(text:String, time:Float) @@ -27,28 +27,28 @@ class WinSLLua switch (mode) { case true: - WinConsoleUtils.allocConsole(); - WinConsoleUtils.setConsoleTitle('WinSL ${SlushiMain.winSLVersion}'); - WinConsoleUtils.setConsoleWindowIcon(SlushiMain.getSLEPath("WinSL_Assets/windowIcon.ico")); - WinConsoleUtils.setWinConsoleColor(); + WindowsTerminalCPP.allocConsole(); + WindowsTerminalCPP.setConsoleTitle('WinSL ${SlushiMain.sleThingsVersions.winSLVersion}'); + WindowsTerminalCPP.setConsoleWindowIcon(SlushiMain.getSLEPath("WinSL_Assets/windowIcon.ico")); + WindowsTerminalCPP.setWinConsoleColor(); case false: - WinConsoleUtils.hideConsoleWindow(); + WindowsTerminalCPP.hideConsoleWindow(); } }); funkLua.set("winSL_console_disableResize", function() { - WinConsoleUtils.disableResizeWindow(); + WindowsTerminalCPP.disableResizeWindow(); }); funkLua.set("winSL_console_disableClose", function() { - WinConsoleUtils.disableCloseWindow(); + WindowsTerminalCPP.disableCloseWindow(); }); funkLua.set("winSL_console_setTitle", function(title:String) { - WinConsoleUtils.setConsoleTitle(title); + WindowsTerminalCPP.setConsoleTitle(title); }); funkLua.set("winSL_console_setWinPos", function(mode:String, value:Int) @@ -56,9 +56,9 @@ class WinSLLua switch (mode) { case "X": - WinConsoleUtils.setConsoleWindowPositionX(value); + WindowsTerminalCPP.setConsoleWindowPositionX(value); case "Y" : - WinConsoleUtils.setConsoleWindowPositionY(value); + WindowsTerminalCPP.setConsoleWindowPositionY(value); default: printInDisplay("winSL_console_setWinPos: Invalid mode!", FlxColor.RED); } @@ -69,20 +69,20 @@ class WinSLLua switch (mode) { case "X": - var numTween:NumTween = FlxTween.num(WinConsoleUtils.returnConsolePositionX(), value, time, { + var numTween:NumTween = FlxTween.num(WindowsTerminalCPP.returnConsolePositionX(), value, time, { ease: LuaUtils.getTweenEaseByString(ease), }); numTween.onUpdate = function(twn:FlxTween) { - WinConsoleUtils.setConsoleWindowPositionX(Std.int(numTween.value)); + WindowsTerminalCPP.setConsoleWindowPositionX(Std.int(numTween.value)); } case "Y": - var numTween:NumTween = FlxTween.num(WinConsoleUtils.returnConsolePositionY(), value, time, { + var numTween:NumTween = FlxTween.num(WindowsTerminalCPP.returnConsolePositionY(), value, time, { ease: LuaUtils.getTweenEaseByString(ease), }); numTween.onUpdate = function(twn:FlxTween) { - WinConsoleUtils.setConsoleWindowPositionY(Std.int(numTween.value)); + WindowsTerminalCPP.setConsoleWindowPositionY(Std.int(numTween.value)); } default: printInDisplay("winSL_console_tweenWinPos: Invalid mode!", FlxColor.RED); @@ -94,9 +94,9 @@ class WinSLLua switch (mode) { case "X": - return WinConsoleUtils.returnConsolePositionX(); + return WindowsTerminalCPP.returnConsolePositionX(); case "Y": - return WinConsoleUtils.returnConsolePositionY(); + return WindowsTerminalCPP.returnConsolePositionY(); default: printInDisplay("winSL_console_getWinPos: Invalid mode!", FlxColor.RED); return 0; @@ -105,7 +105,7 @@ class WinSLLua funkLua.set("winSL_console_centerWindow", function() { - WinConsoleUtils.centerConsoleWindow(); + WindowsTerminalCPP.centerConsoleWindow(); }); #end } diff --git a/funkinscsource/slushi/slushiLua/WindowLua.hx b/funkinscsource/slushi/slushiLua/WindowLua.hx index 44bef67..d9fe673 100644 --- a/funkinscsource/slushi/slushiLua/WindowLua.hx +++ b/funkinscsource/slushi/slushiLua/WindowLua.hx @@ -10,7 +10,7 @@ class WindowLua { Debug.logSLEInfo("Loaded Slushi Window Lua functions!"); - funkLua.set("windowTrans", function(trans:Bool, camToApply:String = 'game') + funkLua.set("windowTransparent", function(transparent:Bool, camToApply:String = 'game') { #if windows var blackSprite:FlxSprite = null; @@ -24,7 +24,7 @@ class WindowLua PlayState.instance.add(blackSprite); } - if (trans) + if (transparent) { CppAPI.getWindowsTransparent(); SlushiLua.apliedWindowTransparent = true; @@ -40,25 +40,25 @@ class WindowLua } } #else - printInDisplay("windowTrans: Platform unsupported for Window transparent!", FlxColor.RED); + printInDisplay("windowTransparent: Platform unsupported for Window transparent!", FlxColor.RED); #end }); - funkLua.set("windowAlpha", function(alpha:Float) + funkLua.set("setWindowAlpha", function(alpha:Float) { #if windows if (ClientPrefs.data.windowAlpha) WindowFuncs.windowAlpha(alpha); #else - printInDisplay("WindowAlpha: Platform unsupported for this function", FlxColor.RED); + printInDisplay("setWindowAlpha: Platform unsupported for this function", FlxColor.RED); #end }); - funkLua.set("doTweenWinAlpha", function(toValue:Float, duration:Float, ease:String = "linear") + funkLua.set("doTweenWinAlpha", function(value:Float, duration:Float, ease:String = "linear") { #if windows if (ClientPrefs.data.windowAlpha) - WindowFuncs.doTweenWindowAlpha(toValue, duration, ease); + WindowFuncs.doTweenWindowAlpha(value, duration, ease); #else printInDisplay("doTweenWinAlpha: Platform unsupported for this function", FlxColor.RED); #end @@ -66,29 +66,24 @@ class WindowLua funkLua.set("centerWindow", function() { - #if windows - CppAPI.centerWindow(); - #else - printInDisplay("centerWindow: Platform unsupported for this function", FlxColor.RED); - #end + WindowFuncs.centerWindow(); }); - funkLua.set("setWindowVisible", function(visible:Bool) + funkLua.set("setMainWindowVisible", function(visible:Bool) { #if windows CppAPI.setWindowVisible(visible); #else - printInDisplay("setWindowVisible: Platform unsupported for this function", FlxColor.RED); + printInDisplay("setMainWindowVisible: Platform unsupported for this function", FlxColor.RED); #end }); - #if desktop funkLua.set("windowAlert", function(text:String, title:String) { WindowFuncs.windowAlert(text, title); }); - funkLua.set("canResizableWindow", function(mode:Bool) + funkLua.set("resizableWindow", function(mode:Bool) { WindowFuncs.windowResizable(mode); }); @@ -98,14 +93,6 @@ class WindowLua WindowFuncs.windowMaximized(mode); }); - funkLua.set("DisableCloseButton", function(mode:Bool) - { - if (mode) - { - Application.current.window.onClose.cancel(); - } - }); - funkLua.set("doTweenWinPos", function(mode:String, tag:String, value:Int, duration:Float, ease:String) { switch (mode) @@ -141,6 +128,28 @@ class WindowLua } }); + // funkLua.set("doubleWindowTweenX", function(offset:Float, duration:Float, ease:String) + // { + // WindowFuncs.doubleWindowTweenX(offset, duration, ease); + // }); + + funkLua.set("centerWindowTween", function(tag:String, duration:Float, ease:String) + { + var variables = MusicBeatState.getVariables("Tween"); + var valueX = Std.int((WindowFuncs.getScreenSizeInWidth() - WindowFuncs.getWindowSizeInWidth()) / 2); + var valueY = Std.int((WindowFuncs.getScreenSizeInHeight() - WindowFuncs.getWindowSizeInHeight()) / 2); + tag = LuaUtils.formatVariable('tween_$tag'); + + variables.set(tag, FlxTween.tween(Application.current.window, {x: valueX, y: valueY}, duration, { + ease: LuaUtils.getTweenEaseByString(ease), + onComplete: function(twn:FlxTween) + { + PlayState.instance.callOnLuas('onTweenCompleted', [tag]); + variables.remove(tag); + } + })); + }); + funkLua.set("resetWindowParameters", function() { WindowFuncs.resetWindowParameters(); @@ -159,11 +168,16 @@ class WindowLua } }); - funkLua.set("winTitle", function(text:String) + funkLua.set("setWindowTitle", function(text:String) { WindowFuncs.winTitle(text); }); + funkLua.set("getWindowTitle", function():String + { + return Application.current.window.title; + }); + funkLua.set("setWindowPos", function(mode:String, value:Int) { switch (mode) @@ -231,24 +245,28 @@ class WindowLua printInDisplay("setWindowSize: Invalid mode!", FlxColor.RED); } }); - #end - funkLua.set("setWindowBorderColor", function(r:Int = 0, g:Int = 0, b:Int = 0, mode:Bool = true) + funkLua.set("setWindowBorderColor", function(rgb:Array, mode:Bool = true) { #if windows - if (WindowsFuncs.getWindowsVersion() != 0 && WindowsFuncs.getWindowsVersion() == 11) + if (SlushiEngineHUD.instance != null) { - if (SlushiEngineHUD.instance != null) - { - SlushiEngineHUD.instance.canChangeWindowColorWithNoteHit = mode; - } - CppAPI.setWindowBorderColor(r, g, b); + SlushiEngineHUD.instance.canChangeWindowColorWithNoteHit = mode; } - else + WindowsFuncs.setWindowBorderColor(rgb); + #end + }); + + funkLua.set("tweenWindowBorderColor", function(fromColor:Array, toColor:Array, duration:Float, ease:String = "linear", mode:Bool = true) + { + #if windows + if (SlushiEngineHUD.instance != null) { - printInDisplay("setWindowBorderColor: You no are in Windows 11, sorry", FlxColor.RED); + SlushiEngineHUD.instance.canChangeWindowColorWithNoteHit = mode; } + + WindowsFuncs.tweenWindowBorderColor(fromColor, toColor, duration, ease); #end - }); + }); } } diff --git a/funkinscsource/slushi/slushiLua/WindowsLua.hx b/funkinscsource/slushi/slushiLua/WindowsLua.hx index 6538bbe..661ca83 100644 --- a/funkinscsource/slushi/slushiLua/WindowsLua.hx +++ b/funkinscsource/slushi/slushiLua/WindowsLua.hx @@ -1,7 +1,8 @@ package slushi.slushiLua; import psychlua.FunkinLua; -import slushi.windows.WindowsGDIEffects; +import slushi.windows.winGDIThings.SlushiWinGDI; +import slushi.windows.winGDIThings.WinGDIThread; class WindowsLua { @@ -31,20 +32,19 @@ class WindowsLua funkLua.set("setWallpaper", function(image:String) { #if (windows && SLUSHI_CPP_CODE) - var allPath:String = CustomFuncs.getAllPath() + 'mods/images/winAssets/' + image + '.png'; + var allPath:String = CustomFuncs.getProgramPath() + 'mods/images/windowsAssets/' + image + '.png'; if (ClientPrefs.data.changeWallPaper) { if (image == "default") { WindowsFuncs.setOldWindowsWallpaper(); + return; } - else - { - WindowsFuncs.changedWallpaper = true; - CppAPI.setWallpaper(allPath); - Debug.logSLEInfo("Wallpaper changed to: " + allPath); - } + + WindowsFuncs.changedWallpaper = true; + CppAPI.setWallpaper(allPath); + Debug.logSLEInfo("Wallpaper changed to: " + allPath); } #else printInDisplay("setWallpaper: Function disabled in this build!", FlxColor.RED); @@ -54,18 +54,18 @@ class WindowsLua funkLua.set("winScreenCapture", function(nameToSave:String) { #if (windows) - var allPath:String = CustomFuncs.getAllPath() + 'mods/images/winAssets/' + nameToSave + '.png'; + var allPath:String = CustomFuncs.getProgramPath() + 'mods/images/windowsAssets/' + nameToSave + '.png'; if (ClientPrefs.data.winScreenShots) { CppAPI.screenCapture(allPath); Debug.logSLEInfo("Screenshot saved to: " + allPath); } #else - printInDisplay("setWallpaper: Function disabled in this build!", FlxColor.RED); + printInDisplay("winScreenCapture: Function disabled in this build!", FlxColor.RED); #end }); - funkLua.set("moveDesktopWindows", function(mode:String, value:Int) + funkLua.set("setDesktopWindowsPos", function(mode:String, value:Int) { #if (windows && SLUSHI_CPP_CODE) if (ClientPrefs.data.winDesktopIcons) @@ -79,21 +79,21 @@ class WindowsLua case "XY": CppAPI.moveDesktopWindowsInXY(value, value); default: - printInDisplay("moveDesktopWindows: Invalid value!", FlxColor.RED); + printInDisplay("setDesktopWindowsPos: Invalid value!", FlxColor.RED); } } #else - printInDisplay("moveDesktopWindows: Platform unsupported for this function!", FlxColor.RED); + printInDisplay("setDesktopWindowsPos: Platform unsupported for this function!", FlxColor.RED); #end }); - funkLua.set("doTweenDesktopWindows", function(mode:String, toValue:Float, duration:Float, ease:String = "linear") + funkLua.set("doTweenDesktopWindowsPos", function(mode:String, toValue:Float, duration:Float, ease:String = "linear") { #if (windows && SLUSHI_CPP_CODE) if (ClientPrefs.data.winDesktopIcons) WindowsFuncs.doTweenDesktopWindows(mode, toValue, duration, ease); #else - printInDisplay("doTweenDesktopWindows: Platform unsupported for this function!", FlxColor.RED); + printInDisplay("doTweenDesktopWindowsPos: Platform unsupported for this function!", FlxColor.RED); #end }); @@ -103,7 +103,7 @@ class WindowsLua if (ClientPrefs.data.winDesktopIcons) WindowsFuncs.doTweenDesktopWindowsAlpha(fromValue, toValue, duration, ease); #else - printInDisplay("setDesktopWindowsAlpha: Platform unsupported for this function!", FlxColor.RED); + printInDisplay("doTweenDesktopWindowsAlpha: Platform unsupported for this function!", FlxColor.RED); #end }); @@ -113,7 +113,7 @@ class WindowsLua if (ClientPrefs.data.winDesktopIcons) WindowsFuncs.doTweenTaskBarAlpha(fromValue, toValue, duration, ease); #else - printInDisplay("setDesktopWindowsAlpha: Platform unsupported for this function!", FlxColor.RED); + printInDisplay("doTweenTaskBarAlpha: Platform unsupported for this function!", FlxColor.RED); #end }); @@ -147,13 +147,13 @@ class WindowsLua #end }); - funkLua.set("sendNoti", function(desc:String, title:String) + funkLua.set("sendNotification", function(desc:String, title:String) { #if windows if (ClientPrefs.data.windowsNotifications) WindowsFuncs.sendWindowsNotification(desc, title); #else - printInDisplay("sendNoti: Platform unsupported for this function!", FlxColor.RED); + printInDisplay("sendNotification: Platform unsupported for this function!", FlxColor.RED); #end }); @@ -221,23 +221,55 @@ class WindowsGDI { Debug.logSLEInfo("Loaded Slushi Windows GDI Lua functions!"); - funkLua.set("windowsEffectModifier", function(tag:String = "", gdiEffect:String, activeEffect:Bool) + funkLua.set("startGDIThread", function() + { + #if windows + if (ClientPrefs.data.gdiEffects) + { + WinGDIThread.initThread(); + } + #else + printInDisplay("startThread: Platform unsupported for this function", FlxColor.RED); + #end + }); + + funkLua.set("prepareGDIEffect", function(effect:String, wait:Float = 0) + { + #if windows + if (ClientPrefs.data.gdiEffects) + SlushiWinGDI.prepareGDIEffect(effect, wait); + #else + printInDisplay("prepareGDIEffect: Platform unsupported for this function", FlxColor.RED); + #end + }); + + funkLua.set("setGDIEffectWaitTime", function(effect:String, wait:Float = 0) + { + #if windows + if (ClientPrefs.data.gdiEffects) + SlushiWinGDI.setGDIEffectWaitTime(effect, wait); + #else + printInDisplay("setGDIEffectWaitTime: Platform unsupported for this function", FlxColor.RED); + #end + }); + + funkLua.set("enableGDIEffect", function(effect:String, enabled:Bool) { #if windows if (ClientPrefs.data.gdiEffects) - WindowsGDIEffects.checkEffect(tag, gdiEffect, activeEffect); + SlushiWinGDI.enableGDIEffect(effect, enabled); #else - printInDisplay("windowsEffectModifier: Platform unsupported for this function", FlxColor.RED); + printInDisplay("enableGDIEffect: Platform unsupported for this function", FlxColor.RED); #end }); - funkLua.set("setWinEffectProperty", function(tag:String, prop:String, value:Dynamic) + funkLua.set("removeGDIEffect", function(effect:String) { #if windows if (ClientPrefs.data.gdiEffects) - WindowsGDIEffects.setWinEffectProperty(tag, prop, value); + SlushiWinGDI.removeGDIEffect(effect); #else - printInDisplay("setWinEffectProperty: Platform unsupported for this function", FlxColor.RED); + printInDisplay("removeGDIEffect: Platform unsupported for this function", FlxColor.RED); #end }); @@ -245,7 +277,7 @@ class WindowsGDI { #if windows if (ClientPrefs.data.gdiEffects) - WindowsGDIEffects._setCustomTitleTextToWindows(titleText); + SlushiWinGDI._setCustomTitleTextToWindows(titleText); #else printInDisplay("setTitleTextToWindows: Platform unsupported for this function", FlxColor.RED); #end diff --git a/funkinscsource/slushi/slushiUtils/Debug.hx b/funkinscsource/slushi/slushiUtils/Debug.hx index d3d21c9..be5624c 100644 --- a/funkinscsource/slushi/slushiUtils/Debug.hx +++ b/funkinscsource/slushi/slushiUtils/Debug.hx @@ -19,6 +19,7 @@ class Debug static final LOG_STYLE_SLE_ERROR:LogStyle = new LogStyle('[ERROR] ', 'FF8888', 12, true, false, false, 'flixel/sounds/beep', true); static final LOG_STYLE_SLE_WARN:LogStyle = new LogStyle('[WARN] ', 'D9F85C', 12, true, false, false, 'flixel/sounds/beep', true); static final LOG_STYLE_SLE_INFO:LogStyle = new LogStyle('[INFO] ', '5CF878', 12, false); + static final LOG_STYLE_SLE_SUCCESS:LogStyle = new LogStyle('[TRACE] ', '5CF878', 12, false); static var logFileWriter:DebugLogWriter = null; @@ -110,6 +111,16 @@ class Debug writeToLogFile(output, 'SLEERROR'); } + + public static inline function logSLESuccess(input:Dynamic, ?pos:haxe.PosInfos):Void + { + if (input == null) + return; + var output = formatOutput(input, pos); + writeToFlxGLog(output, LOG_STYLE_SLE_SUCCESS); + writeToLogFile(output, 'SLE_INFO'); + } + /** * Displays a popup with the provided text. * This interrupts the game, so make sure it's REALLY important. @@ -370,7 +381,7 @@ class Debug class DebugLogWriter { static final LOG_FOLDER = "assets/debugLogs/logs"; - public static final LOG_LEVELS = ['SLE_INFO', 'SLE_WARN', 'SLE_ERROR', 'ERROR', 'WARN', 'INFO', 'TRACE']; + public static final LOG_LEVELS = ['SLE_INFO', 'SLE_WARN', 'SLE_ERROR', 'SLE_SUCCESS', 'ERROR', 'WARN', 'INFO', 'TRACE']; /** * Set this to the current timestamp that the game started. @@ -462,6 +473,8 @@ class DebugLogWriter return "\033[33;2m"; case 'SLE_ERROR': return "\033[31;2m"; + case 'SLE_SUCCESS': + return "\x1b[38;5;70m"; case 'ERROR': return "\033[31m"; case 'WARN': @@ -524,4 +537,4 @@ class DebugLogWriter haxe.Log.trace(msg, null); #end } -} +} \ No newline at end of file diff --git a/funkinscsource/slushi/slushiUtils/LyricsUtils.hx b/funkinscsource/slushi/slushiUtils/LyricsUtils.hx index be8c304..bf8a359 100644 --- a/funkinscsource/slushi/slushiUtils/LyricsUtils.hx +++ b/funkinscsource/slushi/slushiUtils/LyricsUtils.hx @@ -4,7 +4,7 @@ import tjson.TJSON as Json; import psychlua.LuaUtils; /* - * This class is used to display lyrics on the gameplay, using a json file + * This class is used to display lyrics on the gameplay, using a JSON file * * Author: Slushi */ @@ -59,7 +59,7 @@ class LyricsUtils extends FlxSprite if (lyricsJsonData.textConfig.textColor == null) mainText.color = FlxColor.WHITE; if (lyricsJsonData.textConfig.camera == null) - mainText.camera = LuaUtils.cameraFromString("camfor3d"); + mainText.camera = LuaUtils.cameraFromString("camthings"); } catch (e) { @@ -117,6 +117,7 @@ class LyricsUtils extends FlxSprite catch (e) { Debug.logSLEError('Failed to load lyrics file data: $e'); + stop = true; } } diff --git a/funkinscsource/slushi/slushiUtils/SlushiDebugText.hx b/funkinscsource/slushi/slushiUtils/SlushiDebugText.hx index e2e9083..be8897e 100644 --- a/funkinscsource/slushi/slushiUtils/SlushiDebugText.hx +++ b/funkinscsource/slushi/slushiUtils/SlushiDebugText.hx @@ -46,8 +46,6 @@ class SlushiDebugText extends FlxSpriteGroup FlxTween.tween(text, {x: text.x + 15}, 0.4, {ease: FlxEase.linear}); - logInfo("Text to print: " + textToPrint); - new FlxTimer().start(timeToHide, function(tmr:FlxTimer) { FlxTween.tween(txtSpriteBG, {alpha: 0}, 0.4, {ease: FlxEase.linear}); diff --git a/funkinscsource/slushi/slushiUtils/SlushiEngineHUD.hx b/funkinscsource/slushi/slushiUtils/SlushiEngineHUD.hx index 605bd59..0e43703 100644 --- a/funkinscsource/slushi/slushiUtils/SlushiEngineHUD.hx +++ b/funkinscsource/slushi/slushiUtils/SlushiEngineHUD.hx @@ -7,7 +7,6 @@ import psychlua.LuaUtils; * * Author: Slushi */ - class SlushiEngineHUD extends FlxSprite { public static var instance:SlushiEngineHUD; @@ -31,38 +30,40 @@ class SlushiEngineHUD extends FlxSprite posX: 20, posY: 52, // Colors: - SwagColor: 0xff8FD9D1, - SickColor: 0xFFFFFB00, - GoodColor: 0xFF00EB1F, - BadColor: 0xFFFF2600, - ShitColor: 0xFF555555 + swagColor: 0xff8FD9D1, + sickColor: 0xFFFFFB00, + goodColor: 0xFF00EB1F, + badColor: 0xFFFF2600, + shitColor: 0xFF555555 }; static var comboText:FlxText; - static var SwagText:FlxText; - static var SickText:FlxText; - static var GoodText:FlxText; - static var BadText:FlxText; - static var ShitText:FlxText; + static var swagText:FlxText; + static var sickText:FlxText; + static var goodText:FlxText; + static var badText:FlxText; + static var shitText:FlxText; public var sleVer:FlxText; public var scengine:FlxText; - static var camSLEHUD:FlxCamera; - static var camWaterMark:FlxCamera; - static var camHUD:FlxCamera; + private static var camSLEHUD:FlxCamera; + private static var camWaterMark:FlxCamera; + private static var camHUD:FlxCamera; + + private static var leftNoteColor:Array = [194, 75, 153]; + private static var downNoteColor:Array = [0, 253, 253]; + private static var upNoteColor:Array = [18, 250, 5]; + private static var rightNoteColor:Array = [249, 58, 63]; + private static var slushiWindowColor:Array = [214, 243, 222]; - static var leftNoteColor:Array = [194, 75, 153]; - static var downNoteColor:Array = [0, 253, 253]; - static var upNoteColor:Array = [18, 250, 5]; - static var rightNoteColor:Array = [249, 58, 63]; - static var slushiWindowColor:Array = [214, 243, 222]; public var canChangeWindowColorWithNoteHit:Bool = true; - static var tweenDuration:Float = 0.3; - static var windowColorNumTween:NumTween; - static var forward:Bool = false; - static var comboTxtTween:FlxTween; - static var comboAlphaTween:FlxTween; + private static var tweenDuration:Float = 0.3; + private static var windowColorNumTween:NumTween; + private static var forward:Bool = false; + + private static var comboTxtTween:FlxTween; + private static var comboAlphaTween:FlxTween; public function new() { @@ -82,14 +83,14 @@ class SlushiEngineHUD extends FlxSprite // camHUD.visible = false; bgSprite = new FlxSprite(0, 0); - bgSprite.loadGraphic(SlushiMain.getSLEPath('SLEHUDImages/BG.png')); + bgSprite.loadGraphic(SlushiMain.getSLEPath('SlushiEngineHUDAssets/BG.png')); bgSprite.scrollFactor.set(0, 0); bgSprite.antialiasing = ClientPrefs.data.antialiasing; bgSprite.cameras = [camSLEHUD]; addToCurrentState(bgSprite); slushiSprite = new FlxSprite(SLELogo.posX, SLELogo.posY); - slushiSprite.loadGraphic(SlushiMain.getSLEPath('SLEHUDImages/Slushi.png')); + slushiSprite.loadGraphic(SlushiMain.getSLEPath('SlushiEngineHUDAssets/Slushi.png')); slushiSprite.scrollFactor.set(0, 0); slushiSprite.scale.set(0.8, 0.8); slushiSprite.antialiasing = ClientPrefs.data.antialiasing; @@ -97,7 +98,7 @@ class SlushiEngineHUD extends FlxSprite addToCurrentState(slushiSprite); sceSprite = new FlxSprite(SLELogo.posX, SLELogo.posY); - sceSprite.loadGraphic(SlushiMain.getSLEPath('SLEHUDImages/SCEngineText.png')); + sceSprite.loadGraphic(SlushiMain.getSLEPath('SlushiEngineHUDAssets/SCEngineText.png')); sceSprite.scrollFactor.set(0, 0); sceSprite.scale.set(0.8, 0.8); sceSprite.antialiasing = ClientPrefs.data.antialiasing; @@ -105,7 +106,7 @@ class SlushiEngineHUD extends FlxSprite addToCurrentState(sceSprite); notesSprite = new FlxSprite(SLELogo.posX, SLELogo.posY); - notesSprite.loadGraphic(SlushiMain.getSLEPath('SLEHUDImages/Notes.png')); + notesSprite.loadGraphic(SlushiMain.getSLEPath('SlushiEngineHUDAssets/Notes.png')); notesSprite.scrollFactor.set(0, 0); notesSprite.scale.set(0.8, 0.8); notesSprite.antialiasing = ClientPrefs.data.antialiasing; @@ -113,7 +114,7 @@ class SlushiEngineHUD extends FlxSprite addToCurrentState(notesSprite); sleSprite = new FlxSprite(SLELogo.posX, SLELogo.posY); - sleSprite.loadGraphic(SlushiMain.getSLEPath('SLEHUDImages/SlushiEngineText.png')); + sleSprite.loadGraphic(SlushiMain.getSLEPath('SlushiEngineHUDAssets/SlushiEngineText.png')); sleSprite.scrollFactor.set(0, 0); sleSprite.scale.set(0.8, 0.8); sleSprite.antialiasing = ClientPrefs.data.antialiasing; @@ -140,52 +141,46 @@ class SlushiEngineHUD extends FlxSprite // COMBO: ////////////////////////////////////////// - SwagText = new FlxText(comboText.x + data_judgements.posX, data_judgements.posY, 0, "SICK!!!"); - SwagText.setFormat(Paths.font("wendy.ttf"), 30, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); - SwagText.scrollFactor.set(); - SwagText.borderSize = 1.25; - SwagText.color = data_judgements.SwagColor; - SwagText.cameras = [camSLEHUD]; - - SickText = new FlxText(comboText.x + data_judgements.posX, data_judgements.posY, 0, "SICK!!"); - SickText.setFormat(Paths.font("wendy.ttf"), 30, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); - SickText.scrollFactor.set(); - SickText.borderSize = 1.25; - SickText.color = data_judgements.SickColor; - SickText.cameras = [camSLEHUD]; - - GoodText = new FlxText(comboText.x + data_judgements.posX, data_judgements.posY, 0, "Good!"); - GoodText.setFormat(Paths.font("wendy.ttf"), 30, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); - GoodText.scrollFactor.set(); - GoodText.borderSize = 1.25; - GoodText.color = data_judgements.GoodColor; - GoodText.cameras = [camSLEHUD]; - - BadText = new FlxText(comboText.x + data_judgements.posX, data_judgements.posY, 0, "Bad"); - BadText.setFormat(Paths.font("wendy.ttf"), 30, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); - BadText.scrollFactor.set(); - BadText.borderSize = 1.25; - BadText.color = data_judgements.BadColor; - BadText.cameras = [camSLEHUD]; - - ShitText = new FlxText(comboText.x + data_judgements.posX, data_judgements.posY, 0, "Shit..."); - ShitText.setFormat(Paths.font("wendy.ttf"), 30, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); - ShitText.scrollFactor.set(); - ShitText.borderSize = 1.25; - ShitText.color = data_judgements.ShitColor; - ShitText.cameras = [camSLEHUD]; - - addToCurrentState(SwagText); - addToCurrentState(SickText); - addToCurrentState(GoodText); - addToCurrentState(BadText); - addToCurrentState(ShitText); - - SickText.alpha = 0; - SwagText.alpha = 0; - GoodText.alpha = 0; - BadText.alpha = 0; - ShitText.alpha = 0; + swagText = new FlxText(comboText.x + data_judgements.posX, data_judgements.posY, 0, "SICK!!!"); + swagText.setFormat(Paths.font("wendy.ttf"), 30, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); + swagText.scrollFactor.set(); + swagText.borderSize = 1.25; + swagText.color = data_judgements.swagColor; + swagText.cameras = [camSLEHUD]; + + sickText = new FlxText(comboText.x + data_judgements.posX, data_judgements.posY, 0, "SICK!!"); + sickText.setFormat(Paths.font("wendy.ttf"), 30, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); + sickText.scrollFactor.set(); + sickText.borderSize = 1.25; + sickText.color = data_judgements.sickColor; + sickText.cameras = [camSLEHUD]; + + goodText = new FlxText(comboText.x + data_judgements.posX, data_judgements.posY, 0, "Good!"); + goodText.setFormat(Paths.font("wendy.ttf"), 30, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); + goodText.scrollFactor.set(); + goodText.borderSize = 1.25; + goodText.color = data_judgements.goodColor; + goodText.cameras = [camSLEHUD]; + + badText = new FlxText(comboText.x + data_judgements.posX, data_judgements.posY, 0, "Bad"); + badText.setFormat(Paths.font("wendy.ttf"), 30, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); + badText.scrollFactor.set(); + badText.borderSize = 1.25; + badText.color = data_judgements.badColor; + badText.cameras = [camSLEHUD]; + + shitText = new FlxText(comboText.x + data_judgements.posX, data_judgements.posY, 0, "Shit..."); + shitText.setFormat(Paths.font("wendy.ttf"), 30, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); + shitText.scrollFactor.set(); + shitText.borderSize = 1.25; + shitText.color = data_judgements.shitColor; + shitText.cameras = [camSLEHUD]; + + for (comboTextobj in [swagText, sickText, goodText, badText, shitText]) + { + addToCurrentState(comboTextobj); + comboTextobj.alpha = 0; + } ///////////////////////////////////////////////////////////// } @@ -197,7 +192,7 @@ class SlushiEngineHUD extends FlxSprite sleVer.visible = !ClientPrefs.data.hideHud; addToCurrentState(sleVer); - scengine = new FlxText(10, FlxG.height - 42, 0, "SC Engine v" + states.MainMenuState.SCEVersion +' (${SlushiMain.sceGitCommit})', 10); + scengine = new FlxText(10, FlxG.height - 42, 0, "SC Engine v" + states.MainMenuState.SCEVersion + ' (${SlushiMain.sceGitCommit})', 10); scengine.setFormat(Paths.font("vcr.ttf"), 16, FlxColor.WHITE, LEFT, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); scengine.scrollFactor.set(); scengine.borderSize = 1.25; @@ -217,8 +212,10 @@ class SlushiEngineHUD extends FlxSprite if (PlayState.instance.useSLEHUD) { if (PlayState.instance != null) + { comboText.text = "COMBO: " + PlayState.instance.combo; - comboText.screenCenter(X); + } + comboText.screenCenter(X); } } @@ -273,12 +270,12 @@ class SlushiEngineHUD extends FlxSprite } /* Y gracias Trock por hacerme este codigo para en un principio Lua - (And thanks Trock for making me this code for Lua in the first place) - function onTimerCompleted(tag) - local nameAlpha = string.gsub(tag, "Timer", "Alpha") - local textAlpha = string.gsub(tag, "Timer", "Text") - doTweenAlpha(nameAlpha, textAlpha, 0, data_judgements.timeTween, "Linear") - end + (And thanks Trock for making me this code for Lua in the first place) + function onTimerCompleted(tag) + local nameAlpha = string.gsub(tag, "Timer", "Alpha") + local textAlpha = string.gsub(tag, "Timer", "Text") + doTweenAlpha(nameAlpha, textAlpha, 0, data_judgements.timeTween, "Linear") + end */ } @@ -287,40 +284,40 @@ class SlushiEngineHUD extends FlxSprite switch (rating) { case "swag": - SwagText.alpha = 1; + swagText.alpha = 1; doComboAlpha(0); - SickText.alpha = 0; - GoodText.alpha = 0; - BadText.alpha = 0; - ShitText.alpha = 0; + sickText.alpha = 0; + goodText.alpha = 0; + badText.alpha = 0; + shitText.alpha = 0; case "sick": - SickText.alpha = 1; + sickText.alpha = 1; doComboAlpha(1); - SwagText.alpha = 0; - GoodText.alpha = 0; - BadText.alpha = 0; - ShitText.alpha = 0; + swagText.alpha = 0; + goodText.alpha = 0; + badText.alpha = 0; + shitText.alpha = 0; case "good": - GoodText.alpha = 1; + goodText.alpha = 1; doComboAlpha(2); - BadText.alpha = 0; - SwagText.alpha = 0; - BadText.alpha = 0; - ShitText.alpha = 0; + badText.alpha = 0; + swagText.alpha = 0; + badText.alpha = 0; + shitText.alpha = 0; case "bad": - BadText.alpha = 1; + badText.alpha = 1; doComboAlpha(3); - GoodText.alpha = 0; - SwagText.alpha = 0; - SickText.alpha = 0; - ShitText.alpha = 0; + goodText.alpha = 0; + swagText.alpha = 0; + sickText.alpha = 0; + shitText.alpha = 0; case "shit": - ShitText.alpha = 1; + shitText.alpha = 1; doComboAlpha(4); - BadText.alpha = 0; - SwagText.alpha = 0; - GoodText.alpha = 0; - SickText.alpha = 0; + badText.alpha = 0; + swagText.alpha = 0; + goodText.alpha = 0; + sickText.alpha = 0; } } @@ -329,14 +326,14 @@ class SlushiEngineHUD extends FlxSprite if (!PlayState.instance.useSLEHUD) return; - var newScale = 1.2; + final newScale = 1.2; if (comboTxtTween != null) comboTxtTween.cancel(); comboText.scale.x = newScale; comboText.scale.y = newScale; - + comboTxtTween = PlayState.instance.createTween(comboText.scale, {x: 1, y: 1}, 0.2, { onComplete: function(twn:FlxTween) { @@ -353,40 +350,40 @@ class SlushiEngineHUD extends FlxSprite switch (comboToTween) { case 0: - SwagText.alpha = 1; - comboAlphaTween = PlayState.instance.createTween(SwagText, {alpha: 0}, 0.2, { + swagText.alpha = 1; + comboAlphaTween = PlayState.instance.createTween(swagText, {alpha: 0}, 0.2, { onComplete: function(twn:FlxTween) { comboAlphaTween = null; } }); case 1: - SickText.alpha = 1; - comboAlphaTween = PlayState.instance.createTween(SickText, {alpha: 0}, 0.2, { + sickText.alpha = 1; + comboAlphaTween = PlayState.instance.createTween(sickText, {alpha: 0}, 0.2, { onComplete: function(twn:FlxTween) { comboAlphaTween = null; } }); case 2: - GoodText.alpha = 1; - comboAlphaTween = PlayState.instance.createTween(GoodText, {alpha: 0}, 0.2, { + goodText.alpha = 1; + comboAlphaTween = PlayState.instance.createTween(goodText, {alpha: 0}, 0.2, { onComplete: function(twn:FlxTween) { comboAlphaTween = null; } }); case 3: - BadText.alpha = 1; - comboAlphaTween = PlayState.instance.createTween(BadText, {alpha: 0}, 0.2, { + badText.alpha = 1; + comboAlphaTween = PlayState.instance.createTween(badText, {alpha: 0}, 0.2, { onComplete: function(twn:FlxTween) { comboAlphaTween = null; } }); case 4: - ShitText.alpha = 1; - comboAlphaTween = PlayState.instance.createTween(ShitText, {alpha: 0}, 0.2, { + shitText.alpha = 1; + comboAlphaTween = PlayState.instance.createTween(shitText, {alpha: 0}, 0.2, { onComplete: function(twn:FlxTween) { comboAlphaTween = null; @@ -395,6 +392,77 @@ class SlushiEngineHUD extends FlxSprite } } + public static function setParamsFromPlayerNote(noteStrumTime:Float, isSustain:Bool, noteID:Int) + { + if (PlayState.instance.useSLEHUD) + { + setRatingText(noteStrumTime - Conductor.songPosition); + if (!isSustain) + { + doComboAngle(); + } + } + #if windows + if (ClientPrefs.data.changeWindowBorderColorWithNoteHit && instance.canChangeWindowColorWithNoteHit && !isSustain) + { + setWindowColorWithNoteHit(noteID); + } + #end + } + + public static function setNotITGNotesInSteps(curStep:Int):Void + { + // AHHH GACIAS EDWHAK POR ESTO!!!! + var animSkins:Array = ['Default', 'Future', 'NotITG']; + if ((PlayState.SONG.notITG || PlayState.SONG.options.notITG) && PlayState.instance.notITGMod) + { + for (i in 0...animSkins.length) + { + if (ClientPrefs.data.noteSkin.contains(animSkins[i])) + { + if (curStep % 4 == 0) + { + for (this2 in PlayState.instance.opponentStrums) + { + if (this2.animation.curAnim.name == 'static') + { + this2.rgbShader.r = 0xFF808080; + this2.rgbShader.b = 0xFF474747; + this2.rgbShader.enabled = true; + } + } + for (this2 in PlayState.instance.playerStrums) + { + if (this2.animation.curAnim.name == 'static') + { + this2.rgbShader.r = 0xFF808080; + this2.rgbShader.b = 0xFF474747; + this2.rgbShader.enabled = true; + } + } + } + else if (curStep % 4 == 1) + { + for (this2 in PlayState.instance.opponentStrums) + { + if (this2.animation.curAnim.name == 'static') + { + this2.rgbShader.enabled = false; + } + } + for (this2 in PlayState.instance.playerStrums) + { + if (this2.animation.curAnim.name == 'static') + { + this2.rgbShader.enabled = false; + } + } + } + } + } + } + } + public static function setOthersParamOfTheHUD() { if (PlayState.instance.useSLEHUD) @@ -421,7 +489,6 @@ class SlushiEngineHUD extends FlxSprite PlayState.instance.timeTxt.y = FlxG.height - 44; PlayState.instance.botplayTxt.y = PlayState.instance.timeBar.y - 78; - PlayState.instance.timeBarNew.camera = camSLEHUD; Debug.logSLEInfo('Trying to optimize and prepare the engine...'); for (i in [PlayState.instance.boyfriend, PlayState.instance.dad, PlayState.instance.gf]) if (i != null) @@ -437,7 +504,7 @@ class SlushiEngineHUD extends FlxSprite ////////////////////////////////////////////////////////////////////////////////////////////// #if windows - public static function setWindowColorWithNoteHit(note:Int/*, currentNoteColor:Array*/):Void + public static function setWindowColorWithNoteHit(note:Int /*, currentNoteColor:Array*/):Void { switch (note) { @@ -462,95 +529,89 @@ class SlushiEngineHUD extends FlxSprite } static function startColorTween(index:Int, forward:Bool, duration:Float):Void + { + var tweenActived:Bool = false; + + if (tweenActived) + return; + + var targetColor:Array = []; + var startColor:Array = []; + + switch (index) { - var tweenActived:Bool = false; - - if (tweenActived) - return; - - var targetColor:Array = []; - var startColor:Array = []; - - switch (index) - { - case 0: - startColor = slushiWindowColor; - targetColor = leftNoteColor; - case 1: - startColor = slushiWindowColor; - targetColor = downNoteColor; - case 2: - startColor = slushiWindowColor; - targetColor = upNoteColor; - case 3: - startColor = slushiWindowColor; - targetColor = rightNoteColor; - } - - if (!forward) - { - var temp:Array = startColor; - startColor = targetColor; - targetColor = temp; - } - - tweenActived = true; - if (windowColorNumTween != null) + case 0: + startColor = slushiWindowColor; + targetColor = leftNoteColor; + case 1: + startColor = slushiWindowColor; + targetColor = downNoteColor; + case 2: + startColor = slushiWindowColor; + targetColor = upNoteColor; + case 3: + startColor = slushiWindowColor; + targetColor = rightNoteColor; + } + + if (!forward) + { + var temp:Array = startColor; + startColor = targetColor; + targetColor = temp; + } + + tweenActived = true; + if (windowColorNumTween != null) + { + windowColorNumTween.cancel(); + windowColorNumTween = null; + } + + windowColorNumTween = FlxTween.num(0, 1, duration, { + onComplete: function(tween:FlxTween) { - windowColorNumTween.cancel(); - windowColorNumTween = null; - } - - windowColorNumTween = FlxTween.num(0, 1, duration, { - onComplete: function(tween:FlxTween) + if (forward) { - if (forward) - { - startColorTween(index, false, duration); - } + startColorTween(index, false, duration); } - }); - - windowColorNumTween.onUpdate = function(tween:FlxTween) + } + }); + + windowColorNumTween.onUpdate = function(tween:FlxTween) + { + var interpolatedColor:Array = []; + for (i in 0...3) { - var interpolatedColor:Array = []; - for (i in 0...3) - { - var newValue:Int = startColor[i] + Std.int((targetColor[i] - startColor[i]) * windowColorNumTween.value); - newValue = Std.int(Math.max(0, Math.min(255, newValue))); - interpolatedColor.push(newValue); - } - WindowsFuncs.setWindowBorderColor(interpolatedColor); - tweenActived = false; - }; - } + var newValue:Int = startColor[i] + Std.int((targetColor[i] - startColor[i]) * windowColorNumTween.value); + newValue = Std.int(Math.max(0, Math.min(255, newValue))); + interpolatedColor.push(newValue); + } + WindowsFuncs.setWindowBorderColor(interpolatedColor); + tweenActived = false; + }; + } // static function startColorTween(index:Int, forward:Bool, duration:Float, currentNoteColor:Array):Void // { // var tweenActived:Bool = false; - // if (tweenActived) // return; - // Debug.logSLEInfo("Note color RGB: " + currentNoteColor[0] + ", " + currentNoteColor[1] + ", " + currentNoteColor[2]); - // var targetColor:Array = currentNoteColor; // var startColor:Array = slushiWindowColor; - // if (!forward) // { // var temp:Array = startColor; // startColor = targetColor; // targetColor = temp; // } - // tweenActived = true; // if (windowColorNumTween != null) // { // windowColorNumTween.cancel(); // windowColorNumTween = null; // } - // windowColorNumTween = FlxTween.num(0, 1, duration, { // onComplete: function(tween:FlxTween) // { @@ -560,7 +621,6 @@ class SlushiEngineHUD extends FlxSprite // } // } // }); - // windowColorNumTween.onUpdate = function(tween:FlxTween) // { // var interpolatedColor:Array = []; @@ -575,46 +635,44 @@ class SlushiEngineHUD extends FlxSprite // }; // } #end - ////////////////////////////////////////////////////////////////////////////////////////////// public function moveSLELogoX(xValue:Float, time:Float, ease:String) { - FlxTween.tween(slushiSprite, {x: xValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(sceSprite, {x: xValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(notesSprite, {x: xValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(sleSprite, {x: xValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); + for (sleHUDObj in [slushiSprite, sceSprite, notesSprite, sleSprite]) + { + FlxTween.tween(sleHUDObj, {x: xValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); + } if (xValue == -1) { - FlxTween.tween(slushiSprite, {x: SLELogo.posX}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(sceSprite, {x: SLELogo.posX}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(notesSprite, {x: SLELogo.posX}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(sleSprite, {x: SLELogo.posX}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); + for (sleHUDObj in [slushiSprite, sceSprite, notesSprite, sleSprite]) + { + FlxTween.tween(sleHUDObj, {x: SLELogo.posX}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); + } } } public function moveSLELogoY(yValue:Float, time:Float, ease:String) { - FlxTween.tween(slushiSprite, {y: yValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(sceSprite, {y: yValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(notesSprite, {y: yValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(sleSprite, {y: yValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - + for (sleHUDObj in [slushiSprite, sceSprite, notesSprite, sleSprite]) + { + FlxTween.tween(sleHUDObj, {y: yValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); + } if (yValue == -1) { - FlxTween.tween(slushiSprite, {y: SLELogo.posY}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(sceSprite, {y: SLELogo.posY}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(notesSprite, {y: SLELogo.posY}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(sleSprite, {y: SLELogo.posY}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); + for (sleHUDObj in [slushiSprite, sceSprite, notesSprite, sleSprite]) + { + FlxTween.tween(sleHUDObj, {y: SLELogo.posY}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); + } } } public function moveSLELogoAngle(angleValue:Float, time:Float, ease:String) { - FlxTween.tween(slushiSprite, {angle: angleValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(sceSprite, {angle: angleValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(notesSprite, {angle: angleValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); - FlxTween.tween(sleSprite, {angle: angleValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); + for (sleHUDObj in [slushiSprite, sceSprite, notesSprite, sleSprite]) + { + FlxTween.tween(sleHUDObj, {angle: angleValue}, time, {ease: LuaUtils.getTweenEaseByString(ease)}); + } } public function setblackAlpha(alphaValue:Float, time:Float) @@ -626,4 +684,4 @@ class SlushiEngineHUD extends FlxSprite FlxTween.tween(blackGraphic, {alpha: SLELogo.blackAlpha}, time, {ease: FlxEase.quadInOut}); } } -} \ No newline at end of file +} diff --git a/funkinscsource/slushi/slushiUtils/crashHandler/CrashHandler.hx b/funkinscsource/slushi/slushiUtils/crashHandler/CrashHandler.hx index 78123d3..0b7485f 100644 --- a/funkinscsource/slushi/slushiUtils/crashHandler/CrashHandler.hx +++ b/funkinscsource/slushi/slushiUtils/crashHandler/CrashHandler.hx @@ -5,10 +5,8 @@ import haxe.CallStack; import haxe.io.Path; import flixel.system.scaleModes.*; import flixel.group.FlxGroup; - import lime.system.System; import utils.DateUtil; - import states.StoryMenuState; import states.freeplay.FreeplayState; import states.MainMenuState; @@ -19,11 +17,15 @@ import states.MainMenuState; class CrashHandler { public static var inCrash:Bool = false; + public static var crashes:Int = 0; + public static var crashesLimit:Int = 5; public static var createdCrashInGame:Bool = false; + private static var flxFuncNum:Int = -1; - public static function symbolPrevent(error:Dynamic) + public static function symbolPrevent(error:Dynamic, ?flxFuncInt:Int = -1):Void { onUncaughtError(error); + flxFuncNum = flxFuncInt; } public static function initCrashHandler() @@ -41,19 +43,17 @@ class CrashHandler private static function onCPPError(message:Dynamic):Void { - var randomsMsg:String = ""; - var errMsg:String = ""; var mainText:String = 'C++ side critical error!:\n'; #if cpp throw Std.string(message); - Sys.exit(1); + System.exit(1); #if windows CppAPI.showMessageBox(mainText + message, "Slushi Engine [C++]: Crash Handler", MSG_ERROR); - Sys.exit(1); + System.exit(1); #else WindowFuncs.windowAlert(mainText + message, "Slushi Engine [C++]: Crash Handler"); - Sys.exit(1); + System.exit(1); #end #end } @@ -65,20 +65,36 @@ class CrashHandler "It was Bolo!", // Glowsoony "El pollo ardiente", // Edwhak "Apuesto que este error viene de SCE y no SLE, verdad..?", // Slushi - "Null References: The Billion Dollar Mistake" // Trock + "Null References: The Billion Dollar Mistake", // Trock + "GLOW PAGAME EL POLLO", // Slushi ]; static function onUncaughtError(e:Dynamic):Void { - if (inCrash) { - Debug.logSLEWarn("Trying to make a second crash while is already in a crash with error: [" + e + "], skipping this..."); + if (inCrash) + { + Debug.logSLEWarn("Trying to make a another crash while is already in a crash with error: [" + e + "]. Crash counter: [" + crashes + "], skipping it..."); + crashes++; + if (crashes == crashesLimit) + { + Debug.logSLEWarn("Too many crashes, quitting..."); + #if windows + CppAPI.showMessageBox("Many crashes occurred in a short time, SLE will close to avoid entering a loop.\n\nThe logs can be found in [./assets/debugLogs/crashes/]\nPlease contact with @slushi_ds in Discord or add an issue in the engine repository if you think it is a bug in SLE.", + "Slushi Engine: Crash Handler", MSG_INFORMATION); + #else + WindowFuncs.windowAlert("Too many crashes, the engine will close!\n\nThe logs can be found in [./assets/debugLogs/crashes/]\nPlease contact with @slushi_ds in Discord or add an issue in the engine repository if you think it is a bug in SLE.", + "Slushi Engine: Crash Handler"); + #end + System.exit(1); + } return; }; + inCrash = true; var randomsMsg:String = ""; - var errMsg:String = ""; - var callstackText:String = ""; + var callStackText:String = ""; + var callStackForEditorText:String = ""; var path:String; var callStack:Array = CallStack.exceptionStack(true); var dateNow:String = Date.now().toString().replace(" ", "_").replace(":", "'"); @@ -91,11 +107,20 @@ class CrashHandler switch (stackItem) { case FilePos(s, file, line, column): - callstackText += errMsg + file + " (line " + line + ")\n"; + callStackText += file + " (line " + line + ")\n"; + if (callStackForEditorText == "") + { + // Underline only the first line + callStackForEditorText += "\033[4m" + file + "#" + line + "\033[24m\n"; + } + else + { + callStackForEditorText += file + "#" + line + "\n"; + } case CFunction: - callstackText += "Non-Haxe (C) Function"; + callStackText += "Non-Haxe (C) Function"; case Module(c): - callstackText += 'Module ${c}'; + callStackText += 'Module ${c}'; default: Sys.println(stackItem); } @@ -104,13 +129,13 @@ class CrashHandler randomsMsg = quotes[Std.random(quotes.length)]; var finalTerminalText:String = ""; - finalTerminalText += "Call Stack:\n" + callstackText; + finalTerminalText += "Call Stack:\n" + callStackForEditorText; finalTerminalText += "\nUncaught Error:\n" + e; var finalGameplayText:String = ""; - finalGameplayText += "Call Stack:\n" + callstackText; + finalGameplayText += "Call Stack:\n" + callStackText; finalGameplayText += "\n---------------------" - + "\n" + + "\nCrash on Flixel function: [" + whereItCrashes(flxFuncNum) + "]\n" + randomsMsg + "\n---------------------" + "\n\nThis build is running in " @@ -119,18 +144,22 @@ class CrashHandler + SlushiMain.slushiEngineVersion + " -- SCE v" + MainMenuState.SCEVersion - + " (" + SlushiMain.sceGitCommit + ")" - + "\nPlease contact with @slushi_ds in Discord or add an issue in the engine repository if you think this is a bug of SLE." + + " (" + + SlushiMain.sceGitCommit + + ")" + + "\nPlease contact with @slushi_ds in Discord or add an issue in the repository \nif you think this is a bug of SLE." + "\n\n" + "Uncaught Error:\n" + e + "\n\n" - + "For more info go to: [assets/debugLogs/crashes]"; + + "For more info go to: [assets/debugLogs/crashes/SLEngineCrash_" + + dateNow + + ".log]"; if (!FileSystem.exists("./assets/debugLogs/crashes/")) FileSystem.createDirectory("./assets/debugLogs/crashes/"); - File.saveContent(path, buildCrashReportForFile(e, callstackText, randomsMsg)); + File.saveContent(path, buildCrashReportForFile(e, callStackText, randomsMsg)); Debug.logError("\nCRASH:\n\x1b[38;5;1m" + finalTerminalText + "\033[0m\n\n"); @@ -140,6 +169,7 @@ class CrashHandler #if SLUSHI_CPP_CODE WindowsFuncs.resetAllCPPFunctions(); #end + WindowFuncs.resetWindowParameters(); } static function buildCrashReportForFile(errorMessage:String, callStack:String, randomQuote:String):String @@ -148,7 +178,7 @@ class CrashHandler fullContents += 'Slushi Engine Crash Report\n'; fullContents += '=====================\n'; - fullContents += 'Slushi Crash Handler util v${SlushiMain.slCrashHandlerVersion}\n'; + fullContents += 'Slushi Engine Crash Handler Util v${SlushiMain.sleThingsVersions.slCrashHandlerVersion}\n'; fullContents += '=====================\n'; @@ -157,10 +187,10 @@ class CrashHandler fullContents += 'Generated by: Slushi Engine v${SlushiMain.slushiEngineVersion} - SC Engine v${MainMenuState.SCEVersion} (${SlushiMain.sceGitCommit})\n'; fullContents += 'System timestamp: ${DateUtil.generateTimestamp(true)}\n'; var driverInfo = FlxG?.stage?.context3D?.driverInfo ?? 'N/A'; - fullContents += 'GPU Driver info: ${driverInfo}\n'; + fullContents += 'GPU Driver info: \n${driverInfo}\n'; fullContents += 'Platform: ${System.platformLabel}\n'; @:privateAccess - fullContents += 'Render method: ${utils.logging.CrashHandler.renderMethod()}\n'; + fullContents += 'Render method: ${utils.logging.CrashHandler.renderMethod()}\n'; fullContents += '\n'; @@ -182,7 +212,7 @@ class CrashHandler fullContents += 'More info:\n'; - fullContents += 'Please contact with @slushi_ds in Discord or add an issue in the Slushi Engine repository if you think it is a bug in SLE.\n'; + fullContents += 'Please contact with @slushi_ds in Discord or add an issue in the engine repository if you think it is a bug in SLE.\n'; fullContents += '\n'; @@ -191,6 +221,7 @@ class CrashHandler fullContents += 'Flixel Current State: ${currentState}\n'; fullContents += 'Flixel Current SubState: ${currentSubState}\n'; + fullContents += 'Crashed on Flixel function: [${whereItCrashes(flxFuncNum)}]\n'; fullContents += '\n'; @@ -232,14 +263,27 @@ class CrashHandler fullContents += 'Version: ${SlushiMain.slushiEngineVersion}\n'; fullContents += 'Build number: ${SlushiMain.buildNumber}\n'; - fullContents += 'SCE Github commit: ${SlushiMain.sceGitCommit}\n'; - - fullContents += '\n'; - + fullContents += 'SCE build Github commit: ${SlushiMain.sceGitCommit}\n'; fullContents += 'C++ Code: ' + #if SLUSHI_CPP_CODE 'YES' #else 'NO' #end + '\n'; fullContents += 'Slushi Lua: ' + #if SLUSHI_LUA 'YES' #else 'NO' #end + '\n'; fullContents += 'Custom build: ' + #if CUSTOM_BUILD 'YES' #else 'NO' #end + '\n'; return fullContents; } -} \ No newline at end of file + + private static function whereItCrashes(number:Int):String + { + switch (number) { + case 0: + return "Create"; + case 1: + return "Update"; + case 2: + return "Draw"; + default: + return "Unknown"; + } + + return "Unknown"; + } +} diff --git a/funkinscsource/slushi/slushiUtils/crashHandler/GameplayCrashHandler.hx b/funkinscsource/slushi/slushiUtils/crashHandler/GameplayCrashHandler.hx index a20cec8..5cf49be 100644 --- a/funkinscsource/slushi/slushiUtils/crashHandler/GameplayCrashHandler.hx +++ b/funkinscsource/slushi/slushiUtils/crashHandler/GameplayCrashHandler.hx @@ -2,10 +2,10 @@ package slushi.slushiUtils.crashHandler; import flixel.system.scaleModes.*; import flixel.group.FlxGroup; - import states.StoryMenuState; import states.freeplay.FreeplayState; import states.MainMenuState; +import slushi.states.freeplay.SlushiFreeplayState; class GameplayCrashHandler { @@ -23,7 +23,15 @@ class GameplayCrashHandler return; } + // Stop the PlayState, to avoid a loop if the crash occurred in an update function + if (Type.getClass(FlxG.state) == PlayState) + { + PlayState.instance.paused = true; + } + WindowFuncs.winTitle("Slushi Engine: Crash Handler Mode"); + WindowFuncs.resetWindowParameters(); + WindowsFuncs.setWindowBorderColor([0, 46, 114]); if (Main.fpsVar != null) Main.fpsVar.visible = false; FlxG.mouse.useSystemCursor = false; @@ -43,12 +51,12 @@ class GameplayCrashHandler var split:Array = contents.split("\n"); - var bg:FlxSprite = new FlxSprite().makeGraphic(FlxG.width, FlxG.height, FlxColor.BLACK); + var bg:FlxSprite = new FlxSprite().makeGraphic(FlxG.width + 100, FlxG.height + 100, FlxColor.BLACK); bg.scrollFactor.set(); assetGrp.add(bg); bg.alpha = 0.7; - var watermark = new FlxText(10, 0, 0, "Slushi Engine Crash Handler [v" + SlushiMain.slCrashHandlerVersion + "] by Slushi"); + var watermark = new FlxText(10, 0, 0, "Slushi Engine Crash Handler [v" + SlushiMain.sleThingsVersions.slCrashHandlerVersion + "] by Slushi"); watermark.setFormat(Paths.font("vcr.ttf"), 20, FlxColor.WHITE, LEFT, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); watermark.scrollFactor.set(); watermark.borderSize = 1.25; @@ -116,21 +124,24 @@ class GameplayCrashHandler Main.fpsVar.visible = ClientPrefs.data.showFPS; WindowFuncs.windowResizable(true); WindowFuncs.winTitle("default"); + if (Type.getClass(FlxG.state) == PlayState) { - if (!PlayState.isStoryMode) + if (PlayState.isStoryMode) { MainGame.crashHandlerAlredyOpen = false; - MusicBeatState.switchState(new FreeplayState()); + MusicBeatState.switchState(new StoryMenuState()); CrashHandler.inCrash = false; CrashHandler.createdCrashInGame = false; + CrashHandler.crashes = 0; } else { MainGame.crashHandlerAlredyOpen = false; - MusicBeatState.switchState(new StoryMenuState()); + MusicBeatState.switchState(new SlushiFreeplayState()); CrashHandler.inCrash = false; CrashHandler.createdCrashInGame = false; + CrashHandler.crashes = 0; } } else @@ -139,7 +150,23 @@ class GameplayCrashHandler FlxG.switchState(Type.createInstance(Type.getClass(MainGame.oldState), [])); CrashHandler.inCrash = false; CrashHandler.createdCrashInGame = false; + CrashHandler.crashes = 0; } + + for (obj in assetGrp) + { + if (obj != null) + { + obj.destroy(); + } + } + + if (camCrashHandler != null) + { + camCrashHandler.destroy(); + } + + Paths.clearUnusedMemory(); }); }); } diff --git a/funkinscsource/slushi/slushiUtils/shaders/SLEFlxShaderUtil.hx b/funkinscsource/slushi/slushiUtils/shaders/SLEFlxShaderUtil.hx deleted file mode 100644 index b7aedda..0000000 --- a/funkinscsource/slushi/slushiUtils/shaders/SLEFlxShaderUtil.hx +++ /dev/null @@ -1,88 +0,0 @@ -package slushi.slushiUtils.shaders; - -import openfl.display3D._internal.GLShader; -import openfl.display3D._internal.GLProgram; - -import flixel.system.FlxAssets.FlxShader; - -/** - * This code helps the program itself to both alert the user that a - * shader did not compile correctly (due to its GPU/GPU driver) and to - * prevent the program from crashing. - * The object or camera where it was applied could be have unexpected results - * that would have been expected if the shader compiled correctly. - * - * @:author Slushi - */ - -class SLEFlxShaderUtil extends FlxShader -{ - public var shaderName:String = "UNKNOWN"; - - @:noCompletion override private function __createGLShader(source:String, type:Int):GLShader - { - #if (openfl >= "9.2.2") - @:privateAccess - var gl = __context.gl; - - var shader = gl.createShader(type); - gl.shaderSource(shader, source); - gl.compileShader(shader); - var shaderInfoLog = gl.getShaderInfoLog(shader); - var hasInfoLog = shaderInfoLog != null && StringTools.trim(shaderInfoLog) != ""; - var compileStatus = gl.getShaderParameter(shader, gl.COMPILE_STATUS); - - if (hasInfoLog || compileStatus == 0) - { - var message = (type == gl.VERTEX_SHADER) ? "Can\'t compile [VERTEX] shader:\n" : "Can\'t compile [FRAGMENT] shader:\n"; - message += shaderInfoLog; - if (compileStatus == 0) { - #if windows - CppAPI.showMessageBox(message, "Slushi Engine: Error compiling shader!", MSG_ERROR); - #else - WindowFuncs.windowAlert(message, "Slushi Engine: Error compiling shader!"); - #end - Debug.logError("Error compiling shader: \n" + message + "\n"); - } - else if (hasInfoLog){ - Debug.logInfo(message); - } - } - return shader; - #end - } - - override private function __createGLProgram(vertexSource:String, fragmentSource:String):GLProgram - { - @:privateAccess - var gl = __context.gl; - - var vertexShader = __createGLShader(vertexSource, gl.VERTEX_SHADER); - var fragmentShader = __createGLShader(fragmentSource, gl.FRAGMENT_SHADER); - - var program = gl.createProgram(); - - // Fix support for drivers that don't draw if attribute 0 is disabled - for (param in __paramFloat) - { - if (param.name.indexOf("Position") > -1 && StringTools.startsWith(param.name, "openfl_")) - { - gl.bindAttribLocation(program, 0, param.name); - break; - } - } - - gl.attachShader(program, vertexShader); - gl.attachShader(program, fragmentShader); - gl.linkProgram(program); - - if (gl.getProgramParameter(program, gl.LINK_STATUS) == 0) - { - var message = "Unable to initialize the shader program"; - message += "\n" + gl.getProgramInfoLog(program); - Debug.logError("\nError initializing shader program:\n" + message + "\n"); - } - - return program; - } -} \ No newline at end of file diff --git a/funkinscsource/slushi/states/SlushiMainMenuState.hx b/funkinscsource/slushi/states/SlushiMainMenuState.hx index 1bca84d..ce0df53 100644 --- a/funkinscsource/slushi/states/SlushiMainMenuState.hx +++ b/funkinscsource/slushi/states/SlushiMainMenuState.hx @@ -4,7 +4,6 @@ import flixel.effects.FlxFlicker; import flixel.graphics.frames.FlxFilterFrames; import flash.filters.GlowFilter; import slushi.substates.ConsoleSubState; - import states.CreditsState; import states.MainMenuState; import states.editors.MasterEditorMenu; @@ -12,16 +11,15 @@ import states.freeplay.FreeplayState; import states.StoryMenuState; import options.OptionsState; import states.ModsMenuState; +import slushi.states.freeplay.SlushiFreeplayState; /** * The main menu state for Slushi Engine * * Author: Slushi */ - class SlushiMainMenuState extends MusicBeatState { - public static final psychEngineVersion:String = MainMenuState.psychEngineVersion; public static var SCEVersion:String = MainMenuState.SCEVersion; public static var slushiEngineVersion:String = SlushiMain.slushiEngineVersion; @@ -39,12 +37,17 @@ class SlushiMainMenuState extends MusicBeatState var sleLogoCamShader:ThreeDEffect; + var curOption:Int = 0; + var finishedIntro:Bool = false; var clickedOption:Bool = false; - var danceIntro:Bool = false; var shaderSpeed:Int = 4; var sineElap:Float = 0; var numTween:NumTween; + var tweenOptionAlphaData = { + tween: null, + currentOption: 0 + }; var camOther:FlxCamera; var camSLELogo:FlxCamera; @@ -69,7 +72,7 @@ class SlushiMainMenuState extends MusicBeatState super.create(); persistentUpdate = true; - + camOther = new FlxCamera(); camOptions = new FlxCamera(); camSLELogo = new FlxCamera(); @@ -146,6 +149,14 @@ class SlushiMainMenuState extends MusicBeatState glowFilter2 = new GlowFilter(SlushiMain.slushiColor, 1, 40, 40, 1.5, 1); glowFilter3 = new GlowFilter(SlushiMain.slushiColor, 1, 40, 40, 1.5, 1); glowFilter4 = new GlowFilter(SlushiMain.slushiColor, 1, 40, 40, 1.5, 1); + + // for (glowFilter in [glowFilter0, glowFilter1, glowFilter2, glowFilter3, glowFilter4]) + // { + // glowFilter = new GlowFilter(SlushiMain.slushiColor, 1, 40, 40, 1.5, 1); + // glowFilter.blurX = 0; + // glowFilter.blurY = 0; + // } + sprFilter0 = createFilterFrames(freeplaySprite, glowFilter0); sprFilter1 = createFilterFrames(storyModeSprite, glowFilter1); sprFilter2 = createFilterFrames(modsSprite, glowFilter2); @@ -237,15 +248,16 @@ class SlushiMainMenuState extends MusicBeatState ease: FlxEase.elasticInOut, onComplete: function(twn:FlxTween) { - MusicBeatState.switchState(new FreeplayState()); + MusicBeatState.switchState(new SlushiFreeplayState()); } }); } FlxTween.tween(camOther, {alpha: 1}, time, {ease: FlxEase.linear}); FlxG.sound.play(Paths.sound('confirmMenu')); FlxFlicker.flicker(freeplaySprite, 1.2, 0.06, false, false); - FlxTween.tween(freeplaySprite, {x: (FlxG.width - freeplaySprite.width) / 2, y: (FlxG.height - freeplaySprite.height) / 2}, time, + FlxTween.tween(freeplaySprite, {x: (FlxG.width - freeplaySprite.width) / 2, y: (FlxG.height - freeplaySprite.height) / 2, alpha: 0}, time, {ease: FlxEase.elasticInOut}); + FlxTween.tween(freeplaySprite.scale, {x: 1.3, y: 1.3}, time, {ease: FlxEase.linear}); clickedOption = true; numTween = FlxTween.num(0, shaderValue, 1.2); numTween.onUpdate = function(twn:FlxTween) @@ -267,8 +279,9 @@ class SlushiMainMenuState extends MusicBeatState } FlxTween.tween(camOther, {alpha: 1}, time, {ease: FlxEase.linear}); FlxG.sound.play(Paths.sound('confirmMenu')); - FlxTween.tween(storyModeSprite, {x: (FlxG.width - storyModeSprite.width) / 2, y: (FlxG.height - storyModeSprite.height) / 2}, time, + FlxTween.tween(storyModeSprite, {x: (FlxG.width - storyModeSprite.width) / 2, y: (FlxG.height - storyModeSprite.height) / 2, alpha: 0}, time, {ease: FlxEase.elasticInOut}); + FlxTween.tween(storyModeSprite.scale, {x: 1.3, y: 1.3}, time, {ease: FlxEase.linear}); FlxFlicker.flicker(storyModeSprite, 1.2, 0.06, false, false); clickedOption = true; numTween = FlxTween.num(0, shaderValue, 1.2); @@ -291,7 +304,8 @@ class SlushiMainMenuState extends MusicBeatState } FlxTween.tween(camOther, {alpha: 1}, time, {ease: FlxEase.linear}); FlxG.sound.play(Paths.sound('confirmMenu')); - FlxTween.tween(modsSprite, {x: (FlxG.width - modsSprite.width) / 2, y: (FlxG.height - modsSprite.height) / 2}, time, {ease: FlxEase.linear}); + FlxTween.tween(modsSprite, {x: (FlxG.width - modsSprite.width) / 2, y: (FlxG.height - modsSprite.height) / 2, alpha: 0}, time, {ease: FlxEase.elasticInOut}); + FlxTween.tween(modsSprite.scale, {x: 1.3, y: 1.3}, time, {ease: FlxEase.linear}); FlxFlicker.flicker(modsSprite, 1.2, 0.06, false, false); clickedOption = true; numTween = FlxTween.num(0, shaderValue, 1.2); @@ -314,8 +328,9 @@ class SlushiMainMenuState extends MusicBeatState } FlxTween.tween(camOther, {alpha: 1}, time, {ease: FlxEase.linear}); FlxG.sound.play(Paths.sound('confirmMenu')); - FlxTween.tween(creditsSprite, {x: (FlxG.width - creditsSprite.width) / 2, y: (FlxG.height - creditsSprite.height) / 2}, time, + FlxTween.tween(creditsSprite, {x: (FlxG.width - creditsSprite.width) / 2, y: (FlxG.height - creditsSprite.height) / 2, alpha: 0}, time, {ease: FlxEase.elasticInOut}); + FlxTween.tween(creditsSprite.scale, {x: 1.3, y: 1.3}, time, {ease: FlxEase.linear}); FlxFlicker.flicker(creditsSprite, 1.2, 0.06, false, false); clickedOption = true; numTween = FlxTween.num(0, shaderValue, 1.2); @@ -345,8 +360,9 @@ class SlushiMainMenuState extends MusicBeatState } FlxTween.tween(camOther, {alpha: 1}, time, {ease: FlxEase.linear}); FlxG.sound.play(Paths.sound('confirmMenu')); - FlxTween.tween(optionsSprite, {x: (FlxG.width - optionsSprite.width) / 2, y: (FlxG.height - optionsSprite.height) / 2}, time, + FlxTween.tween(optionsSprite, {x: (FlxG.width - optionsSprite.width) / 2, y: (FlxG.height - optionsSprite.height) / 2, alpha: 0}, time, {ease: FlxEase.elasticInOut}); + FlxTween.tween(optionsSprite.scale, {x: 1.3, y: 1.3}, time, {ease: FlxEase.linear}); FlxFlicker.flicker(optionsSprite, 1.2, 0.06, false, false); clickedOption = true; numTween = FlxTween.num(0, shaderValue, 1.2); diff --git a/funkinscsource/slushi/states/SlushiTitleState.hx b/funkinscsource/slushi/states/SlushiTitleState.hx index 0210572..620e388 100644 --- a/funkinscsource/slushi/states/SlushiTitleState.hx +++ b/funkinscsource/slushi/states/SlushiTitleState.hx @@ -38,7 +38,8 @@ class SlushiTitleState extends MusicBeatState public static var gitVersion = { needUpdate: false, - newVersion: "" + newVersion: "", + alreadyChecked: false }; override public function create() @@ -69,7 +70,12 @@ class SlushiTitleState extends MusicBeatState Highscore.load(); Assets.cache.enabled = true; - SlushiMain.getBuildVer(); + + if (!gitVersion.alreadyChecked) + { + SlushiMain.getBuildVer(); + gitVersion.alreadyChecked = true; + } if(gitVersion.needUpdate) { var finalText:FlxText = new FlxText(0, 0, 0, "Hey! You are using an old version of Slushi Engine\n\nVersion: " + gitVersion.newVersion + " > " + SlushiMain.slushiEngineVersion + "\n\nPlease download the latest version\nThanks for use SLE :3", 12); @@ -78,7 +84,6 @@ class SlushiTitleState extends MusicBeatState finalText.screenCenter(); finalText.y -= 20; add(finalText); - // finalText.alpha = 0; FlxTween.tween(finalText, {alpha: 1}, 0.3, {ease: FlxEase.quadOut}); FlxTween.tween(finalText, {y: finalText.y + 20}, 0.3, {ease: FlxEase.quadOut, onComplete: function(twn:FlxTween) { new FlxTimer().start(3, function(twn:FlxTimer) @@ -290,7 +295,7 @@ class SlushiTitleState extends MusicBeatState { super.stepHit(); - if (curStep == 15 && curStep != 266) + if (curStep >= 15 && curStep <= 266) { if (curStep % 16 == 0) { diff --git a/funkinscsource/slushi/states/freeplay/SlushiFreeplayHealthIcon.hx b/funkinscsource/slushi/states/freeplay/SlushiFreeplayHealthIcon.hx new file mode 100644 index 0000000..667782e --- /dev/null +++ b/funkinscsource/slushi/states/freeplay/SlushiFreeplayHealthIcon.hx @@ -0,0 +1,20 @@ +package slushi.states.freeplay; + +import objects.HealthIcon; + +class SlushiFreeplayHealthIcon extends HealthIcon +{ + public var songTxtTracker:FlxSprite; + + override public function update(elapsed:Float) + { + super.update(elapsed); + + if (songTxtTracker != null) { + setPosition( + songTxtTracker.x + (songTxtTracker.width / 2) - (this.width / 2) + offsetX, + songTxtTracker.y - 100 + offsetY + ); + } + } +} \ No newline at end of file diff --git a/funkinscsource/slushi/states/freeplay/SlushiFreeplayState.hx b/funkinscsource/slushi/states/freeplay/SlushiFreeplayState.hx new file mode 100644 index 0000000..1bed50f --- /dev/null +++ b/funkinscsource/slushi/states/freeplay/SlushiFreeplayState.hx @@ -0,0 +1,1374 @@ +package slushi.states.freeplay; + +import flixel.effects.FlxFlicker; +import flixel.math.FlxMath; +import flixel.util.FlxStringUtil; +import flixel.ui.FlxBar; +import haxe.Json; +import backend.WeekData; +import backend.Highscore; +import openfl.utils.Assets as OpenFlAssets; +import slushi.states.freeplay.SlushiMusicPlayer; +import objects.CoolText; +import substates.GameplayChangersSubstate; +import substates.ResetScoreSubState; +import vslice.transition.StickerSubState; +import utils.SoundUtil; +import states.freeplay.FreeplaySongMetaData; +import slushi.states.freeplay.SlushiFreeplayHealthIcon; +import states.MainMenuState; +import states.StoryMenuState; +import states.editors.WeekEditorState; +import states.ErrorState; +import objects.Character.CharacterFile; +import objects.Character; +import flixel.addons.effects.FlxTrail; +import backend.PsychCamera; +import objects.note.*; +import slushi.others.SlushiSongs; +import shaders.FunkinSourcedShaders.WaveBurstEffect; + +/** + * The freeplay state for Slushi Engine + * + * Author: Slushi + */ +class SlushiFreeplayState extends MusicBeatState +{ + public static var instance:SlushiFreeplayState = null; + private static var lastDifficultyName:String = Difficulty.getDefault(); + private static var curSelected:Int = 0; + + private var grpSongs:FlxTypedGroup; + private var curPlaying:Bool = false; + private var iconArray:Array = []; + + public var rate:Float = 1.0; + public var lastRate:Float = 1.0; + + public var curInstPlaying:Int = -1; + + public var scoreBG:FlxSprite; + public var scoreText:CoolText; + public var opponentText:CoolText; + public var diffText:CoolText; + public var comboText:CoolText; + public var downText:CoolText; + + public var leText:String = ""; + + public var scorecolorDifficulty:Map = [ + 'EASY' => FlxColor.GREEN, + 'NORMAL' => FlxColor.YELLOW, + 'HARD' => FlxColor.RED, + 'ERECT' => FlxColor.fromString('#FD579D'), + 'NIGHTMARE' => FlxColor.fromString('#4E28FB') + ]; + + public var curStringDifficulty:String = 'NORMAL'; + + var songs:Array = []; + + var selector:FlxText; + var lerpSelected:Float = 0; + var curDifficulty:Int = -1; + + var lerpScore:Int; + var lerpAccuracy:Float = 0; + var intendedScore:Int = 0; + var intendedAccuracy:Float = 0; + var rating:String; + var combo:String = 'N/A'; + + var missingTextBG:FlxSprite; + var missingText:FlxText; + + var opponentMode:Bool = false; + + var bg:FlxSprite; + var intendedColor:Int; + var player:SlushiMusicPlayer; + + #if BASE_GAME_FILES + var stickerSubState:StickerSubState; + + var camNotes:FlxCamera; + var camBG:FlxCamera; + + public var camSongs:FlxCamera; + + public function new(?stickers:StickerSubState) + { + if (stickers != null) + stickerSubState = stickers; + super(); + } + #end + + override function create() + { + instance = this; + + persistentUpdate = true; + PlayState.isStoryMode = false; + WeekData.reloadWeekFiles(false); + + if (WeekData.weeksList.length < 1) + { + FlxTransitionableState.skipNextTransIn = true; + persistentUpdate = false; + MusicBeatState.switchState(new ErrorState("NO WEEKS ADDED FOR FREEPLAY\n\nPress ACCEPT to go to the Week Editor Menu.\nPress BACK to return to Main Menu.", + function() MusicBeatState.switchState(new WeekEditorState()), function() + { + FlxG.sound.play(Paths.sound('cancelMenu')); + MusicBeatState.switchState(new MainMenuState()); + })); + return; + } + + camNotes = initPsychCamera(); + camBG = new FlxCamera(); + camSongs = new FlxCamera(); + camNotes.bgColor.alpha = 0; + camBG.bgColor.alpha = 0; + camSongs.bgColor.alpha = 0; + FlxG.cameras.add(camNotes, false); + FlxG.cameras.add(camBG, false); + FlxG.cameras.add(camSongs, false); + + #if BASE_GAME_FILES + if (stickerSubState != null) + { + openSubState(stickerSubState); + stickerSubState.degenStickers(); + } + #end + + #if DISCORD_ALLOWED + // Updating Discord Rich Presence + DiscordClient.changePresence('Searching to play song - SL Freeplay Menu', null); + #end + + for (i in 0...WeekData.weeksList.length) + { + if (weekIsLocked(WeekData.weeksList[i])) + continue; + + var leWeek:WeekData = WeekData.weeksLoaded.get(WeekData.weeksList[i]); + var leSongs:Array = []; + var leChars:Array = []; + + for (j in 0...leWeek.songs.length) + { + leSongs.push(leWeek.songs[j][0]); + leChars.push(leWeek.songs[j][1]); + } + + WeekData.setDirectoryFromWeek(leWeek); + for (song in leWeek.songs) + { + addSong(song[0], i, song[1], + (song[2] == null || song[2].length < 3) ? FlxColor.fromRGB(146, 113, 253) : FlxColor.fromRGB(song[2][0], song[2][1], song[2][2]), + song[3] != null ? song[3] : false); + } + } + Mods.loadTopMod(); + + bg = new FlxSprite().loadGraphic(SlushiMain.getSLEPath('SlushiFreeplayStateAssets/BG.png')); + bg.antialiasing = ClientPrefs.data.antialiasing; + add(bg); + bg.screenCenter(); + bg.camera = camBG; + + grpSongs = new FlxTypedGroup(); + + for (i in 0...songs.length) + { + var songText:Alphabet = new Alphabet(90, 320, songs[i].songName, true); + songText.targetY = i; + + songText.screenCenter(X); + songText.scaleX = Math.min(1, 980 / songText.width); + songText.snapToPosition(); + + Mods.currentModDirectory = songs[i].folder; + var icon:SlushiFreeplayHealthIcon = new SlushiFreeplayHealthIcon(songs[i].songCharacter); + icon.songTxtTracker = songText; + + // too laggy with a lot of songs, so i had to recode the logic for it + songText.visible = songText.active = songText.isMenuItem = false; + icon.visible = icon.active = false; + + if (curPlaying && i == instPlaying) + { + if (icon.hasWinning) + icon.animation.curAnim.curFrame = 2; + } + + // using a FlxGroup is too much fuss! + iconArray.push(icon); + add(icon); + icon.camera = camSongs; + grpSongs.add(songText); + } + + add(grpSongs); + grpSongs.camera = camSongs; + + WeekData.setDirectoryFromWeek(); + + scoreText = new CoolText(FlxG.width * 0.6525, 10, 31, 31, Paths.bitmapFont('fonts/vcr')); + scoreText.autoSize = true; + scoreText.fieldWidth = FlxG.width; + scoreText.antialiasing = FlxG.save.data.antialiasing; + + scoreBG = new FlxSprite((FlxG.width * 0.65) - 6, 0).makeGraphic(Std.int(FlxG.width * 0.4), 270, 0xFF000000); + scoreBG.color = FlxColor.fromString('0xFF000000'); + scoreBG.alpha = 0.6; + add(scoreBG); + + comboText = new CoolText(scoreText.x, scoreText.y + 36, 23, 23, Paths.bitmapFont('fonts/vcr')); + comboText.autoSize = true; + + comboText.antialiasing = ClientPrefs.data.antialiasing; + add(comboText); + + opponentText = new CoolText(scoreText.x, scoreText.y + 66, 23, 23, Paths.bitmapFont('fonts/vcr')); + opponentText.autoSize = true; + + opponentText.antialiasing = ClientPrefs.data.antialiasing; + add(opponentText); + + diffText = new CoolText(scoreText.x - 4, scoreText.y + 96, 23, 23, Paths.bitmapFont('fonts/vcr')); + diffText.antialiasing = ClientPrefs.data.antialiasing; + add(diffText); + + add(scoreText); + + missingTextBG = new FlxSprite().makeGraphic(FlxG.width, FlxG.height, FlxColor.BLACK); + missingTextBG.alpha = 0.6; + missingTextBG.visible = false; + add(missingTextBG); + + missingText = new FlxText(50, 0, FlxG.width - 100, '', 24); + missingText.setFormat(Paths.font("vcr.ttf"), 24, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); + missingText.scrollFactor.set(); + missingText.visible = false; + add(missingText); + + var textBG:FlxSprite = new FlxSprite(0, FlxG.height - 26).makeGraphic(FlxG.width, 27, 0xFF000000); + textBG.alpha = 0.6; + add(textBG); + + leText = Language.getPhrase("freeplay_tip", + "Press SPACE to listen to the Song / Press CTRL to open the Gameplay Changers Menu / Press RESET to Reset your Score and Accuracy."); + downText = new CoolText(textBG.x - 600, textBG.y + 4, 14.5, 16, Paths.bitmapFont('fonts/vcr')); + // downText.autoSize = true; + downText.antialiasing = ClientPrefs.data.antialiasing; + downText.scrollFactor.set(); + downText.updateHitbox(); + downText.text = leText; + add(downText); + + for (obj in [ + scoreText, + comboText, + opponentText, + diffText, + downText, + missingText, + textBG, + missingTextBG, + scoreBG, + ]) + obj.camera = camSongs; + + if (curSelected >= songs.length) + curSelected = 0; + bg.color = songs[curSelected].color; + intendedColor = bg.color; + lerpSelected = curSelected; + + // Set the window border color from the current song's color + // Idea from VS Camellia ALT (https://gamebanana.com/mods/413258) (They use my code to set the window border color XD) + WindowsFuncs.setWindowBorderColorFromInt(intendedColor); + + curDifficulty = Math.round(Math.max(0, Difficulty.list.indexOf(lastDifficultyName))); + + player = new SlushiMusicPlayer(this); + add(player); + + if (MainMenuState.freakyPlaying) + { + if (!FlxG.sound.music.playing) + FlxG.sound.playMusic(SlushiMain.getSLEPath("Musics/SLE_HackNet_Resonance.ogg")); + } + + if (inst != null) + inst = null; + + changeSelection(); + updateTexts(); + super.create(); + + if (FlxG.sound.music != null && !FlxG.sound.music.playing && !MainMenuState.freakyPlaying && !resetSong) + { + playSong(); + } + } + + override function closeSubState() + { + changeSelection(0, false); + opponentMode = ClientPrefs.getGameplaySetting('opponent'); + opponentText.text = "OPPONENT MODE: " + (opponentMode ? "ON" : "OFF"); + opponentText.updateHitbox(); + changeDiff(0); + persistentUpdate = true; + super.closeSubState(); + } + + public function addSong(songName:String, weekNum:Int, songCharacter:String, color:Int, blockOpponentMode:Bool) + { + songs.push(new FreeplaySongMetaData(songName, weekNum, songCharacter, color, blockOpponentMode)); + } + + function weekIsLocked(name:String):Bool + { + var leWeek:WeekData = WeekData.weeksLoaded.get(name); + return (!leWeek.startUnlocked + && leWeek.weekBefore.length > 0 + && (!StoryMenuState.weekCompleted.exists(leWeek.weekBefore) || !StoryMenuState.weekCompleted.get(leWeek.weekBefore))); + } + + public var curInstPlayingtxt:String = "N/A"; + + public var inst:FlxSound = null; + public var vocals:FlxSound = null; + public var opponentVocals:FlxSound = null; + + public var instPlayingtxt:String = "N/A"; // its not really a text but who cares? + public var canSelectSong:Bool = true; + + var completed:Bool = false; + var holdTime:Float = 0; + var instPlaying:Int = -1; + var startedBopping:Bool = false; + + var stopMusicPlay:Bool = false; + + override function update(elapsed:Float) + { + if (WeekData.weeksList.length < 1) + { + super.update(elapsed); + return; + } + + lerpScore = Math.floor(FlxMath.lerp(intendedScore, lerpScore, Math.exp(-elapsed * 24))); + lerpAccuracy = FlxMath.lerp(intendedAccuracy, lerpAccuracy, Math.exp(-elapsed * 12)); + + if (player != null && player.playingMusic) + { + var bpmRatio = Conductor.bpm / 100; + if (ClientPrefs.data.camZooms) + { + FlxG.camera.zoom = FlxMath.lerp(1, FlxG.camera.zoom, CoolUtil.boundTo(1 - (elapsed * 3.125 * bpmRatio * player.playbackRate), 0, 1)); + } + + for (i in 0...iconArray.length) + { + if (iconArray[i] != null) + { + var mult:Float = FlxMath.lerp(1, iconArray[i].scale.x, CoolUtil.boundTo(1 - (elapsed * 35 * player.playbackRate), 0, 1)); + iconArray[i].scale.set(mult, mult); + iconArray[i].updateHitbox(); + } + } + + if (PlayState.SONG != null) + { + if (Conductor.bpm != PlayState.SONG.bpm) + { + Conductor.bpm = PlayState.SONG.bpm; + } + } + + #if DISCORD_ALLOWED + DiscordClient.changePresence('Listening to ' + Paths.formatToSongPath(songs[curSelected].songName), null); + #end + } + + if (!player.playingMusic) + { + if (FlxG.camera.zoom != 1) + FlxG.camera.zoom = 1; + #if DISCORD_ALLOWED + DiscordClient.changePresence('Searching to play song - SL Freeplay Menu', null); + #end + } + + for (icon in iconArray) + { + if (curSelected != iconArray.indexOf(icon)) + { + if (icon.animation.curAnim != null && icon.getLastAnimationPlayed() != 'normal') + icon.playAnim('normal', true); + continue; + } + icon.playAnim('losing', false); + + if (!player.playingMusic) + { + icon.scale.set(1, 1); + icon.updateHitbox(); + } + } + + var mult:Float = FlxMath.lerp(1, bg.scale.x, CoolUtil.clamp(1 - (elapsed * 9), 0, 1)); + bg.scale.set(mult, mult); + bg.updateHitbox(); + bg.offset.set(); + + if (Math.abs(lerpScore - intendedScore) <= 10) + lerpScore = intendedScore; + if (Math.abs(lerpAccuracy - intendedAccuracy) <= 0.01) + lerpAccuracy = intendedAccuracy; + + var ratingSplit:Array = Std.string(CoolUtil.floorDecimal(lerpAccuracy * 100, 2)).split('.'); + if (ratingSplit.length < 2) // No decimals, add an empty space + ratingSplit.push(''); + + while (ratingSplit[1].length < 2) // Less than 2 decimals in it, add decimals then + ratingSplit[1] += '0'; + + scoreText.text = Language.getPhrase('personal_best', 'PERSONAL BEST: {1}', [lerpScore]); + scoreText.updateHitbox(); + + if (combo == "") + { + comboText.text = Language.getPhrase('fp_unknown_rank', "RANK: N/A"); + comboText.alpha = 0.5; + } + else + { + comboText.text = Language.getPhrase('fp_ranking', "RANK: {1} | {2} ({3}" + "%)\n", [rating, combo, ratingSplit.join('.')]); + comboText.alpha = 1; + } + + comboText.updateHitbox(); + + opponentMode = (ClientPrefs.getGameplaySetting('opponent') && !songs[curSelected].blockOpponentMode); + opponentText.text = Language.getPhrase('fp_opponent_mode', "OPPONENT MODE: {1}", [opponentMode ? "ON" : "OFF"]); + opponentText.updateHitbox(); + + var shiftMult:Int = 1; + if (FlxG.keys.pressed.SHIFT) + shiftMult = 3; + + if (player != null && !player.playingMusic) + { + if (songs.length > 1) + { + if (FlxG.keys.justPressed.HOME) + { + curSelected = 0; + changeSelection(); + holdTime = 0; + } + else if (FlxG.keys.justPressed.END) + { + curSelected = songs.length - 1; + changeSelection(); + holdTime = 0; + } + if (controls.UI_UP_P) + { + changeSelection(-shiftMult); + holdTime = 0; + } + if (controls.UI_DOWN_P) + { + 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 (FlxG.mouse.wheel != 0) + { + FlxG.sound.play(Paths.sound('scrollMenu'), 0.2); + changeSelection(-shiftMult * FlxG.mouse.wheel, false); + } + + if (FlxG.mouse.justPressedRight) + { + changeDiff(1); + _updateSongLastDifficulty(); + } + if (FlxG.mouse.justPressedRight) + { + changeDiff(-1); + _updateSongLastDifficulty(); + } + } + + if (controls.UI_LEFT_P) + { + changeDiff(-1); + _updateSongLastDifficulty(); + } + else if (controls.UI_RIGHT_P) + { + changeDiff(1); + _updateSongLastDifficulty(); + } + else if (controls.UI_UP_P || controls.UI_DOWN_P) + changeDiff(); + } + + if (controls.BACK || completed && exit) + { + if (player != null && !player.playingMusic) + { + MusicBeatState.switchState(new slushi.states.SlushiMainMenuState()); + FlxG.sound.play(Paths.sound('cancelMenu')); + if (!MainMenuState.freakyPlaying) + { + MainMenuState.freakyPlaying = true; + Conductor.bpm = 102.0; + FlxG.sound.playMusic(SlushiMain.getSLEPath("Musics/SLE_HackNet_Resonance.ogg")); + } + } + else + { + alreadyPlayingSong = false; + instPlaying = -1; + + Conductor.bpm = 102.0; + Conductor.songPosition = 0; + + exit = true; + completed = false; + + player.playingMusic = false; + player.switchPlayMusic(); + + if (inst != null) + { + remove(inst); + inst.stop(); + inst.volume = 0; + inst.time = 0; + } + inst = null; + + if (vocals != null) + { + vocals.stop(); + vocals.volume = 0; + vocals.time = 0; + vocals = null; + } + + if (opponentVocals != null) + { + opponentVocals.stop(); + opponentVocals.volume = 0; + opponentVocals.time = 0; + opponentVocals = null; + } + } + } + + if (FlxG.keys.justPressed.CONTROL && !player.playingMusic) + { + persistentUpdate = false; + openSubState(new GameplayChangersSubstate()); + } + else if (FlxG.keys.justPressed.SPACE) + { + playSong(); + } + else if (controls.RESET && !player.playingMusic) + { + persistentUpdate = false; + openSubState(new ResetScoreSubState(songs[curSelected].songName, curDifficulty, songs[curSelected].songCharacter, -1, opponentMode)); + FlxG.sound.play(Paths.sound('scrollMenu')); + } + else + { + try + { + for (item in grpSongs.members) + if ((controls.ACCEPT + || ((FlxG.mouse.overlaps(item) || (FlxG.mouse.overlaps(iconArray[curSelected]))) && FlxG.mouse.pressed)) + && !FlxG.keys.justPressed.SPACE + && canSelectSong) + { + canSelectSong = false; + var llll = FlxG.sound.play(Paths.sound('confirmMenu')).length; + updateTexts(elapsed, true); + grpSongs.forEach(function(e:Alphabet) + { + if (e.text == songs[curSelected].songName) + { + try + { + tryLeaving(e, llll); + } + catch (e:haxe.Exception) + { + Debug.logError('ERROR! ${e.message}'); + + var errorStr:String = e.message; + if (errorStr.contains('There is no TEXT asset with an ID of')) + errorStr = 'Missing file: ' + + errorStr.substring(errorStr.indexOf(Paths.formatToSongPath(songs[curSelected].songName)), + errorStr.length - 1); // Missing chart + missingText.text = 'ERROR WHILE LOADING CHART:\n$errorStr'; + missingText.screenCenter(Y); + missingText.visible = true; + missingTextBG.visible = true; + FlxG.sound.play(Paths.sound('cancelMenu')); + } + } + }); + break; + } + + #if (MODS_ALLOWED && DISCORD_ALLOWED) + DiscordClient.loadModRPC(); + #end + } + catch (e:haxe.Exception) + { + Debug.logError('ERROR! ${e.message}'); + + var errorStr:String = e.message; + if (errorStr.contains('There is no TEXT asset with an ID of')) + errorStr = 'Missing file: ' + + errorStr.substring(errorStr.indexOf(Paths.formatToSongPath(songs[curSelected].songName)), errorStr.length - 1); // Missing chart + else + errorStr += '\n\n' + e.stack; + + missingText.screenCenter(Y); + missingText.visible = true; + missingTextBG.visible = true; + FlxG.sound.play(Paths.sound('cancelMenu')); + + updateTexts(elapsed); + super.update(elapsed); + return; + } + } + + if (canSelectSong) + updateTexts(elapsed); + + super.update(elapsed); + } + + function tryLeaving(e:Alphabet, llll:Float = 0) + { + if (player != null) + player.fadingOut = true; + FlxFlicker.flicker(e); + for (i in [bg, scoreBG, scoreText, opponentText, diffText, comboText]) + FlxTween.tween(i, {alpha: 0}, llll / 1000); + if (inst != null) + inst.fadeOut(llll / 1000, 0); + if (vocals != null) + vocals.fadeOut(llll / 1000, 0); + if (opponentVocals != null) + opponentVocals.fadeOut(llll / 1000, 0); + if (FlxG.sound.music != null) + FlxG.sound.music.fadeOut(llll / 1000, 0); + + FlxG.camera.fade(FlxColor.BLACK, llll / 1000, false, moveToSong, true); + } + + var alreadyPlayingSong:Bool = false; + var resetSong:Bool = false; + var exit:Bool = true; + + private function playSong():Void + { + try + { + if (instPlaying == curSelected && player.playingMusic && !resetSong) + { + player.pauseOrResume(!player.playing); + } + else + { + if (MainMenuState.freakyPlaying != false) + MainMenuState.freakyPlaying = false; + if (FlxG.sound.music != null) + { + FlxG.sound.music.stop(); + } + if (inst != null) + inst.stop(); + if (vocals != null) + vocals.stop(); + if (opponentVocals != null) + opponentVocals.stop(); + + if (instPlaying != curSelected) + { + instPlaying = -1; + if (inst != null) + { + remove(inst); + inst.destroy(); + inst = null; + } + + Mods.currentModDirectory = songs[curSelected].folder; + + var poop:String = Highscore.formatSong(songs[curSelected].songName.toLowerCase(), curDifficulty); + Song.loadFromJson(poop, songs[curSelected].songName.toLowerCase()); + curInstPlayingtxt = instPlayingtxt = songs[curSelected].songName.toLowerCase(); + + var songPath:String = null; + songPath = PlayState.SONG.songId; + + if (PlayState.SONG.needsVoices) + { + final currentPrefix:String = (PlayState.SONG.options.vocalsPrefix != null ? PlayState.SONG.options.vocalsPrefix : ''); + final currentSuffix:String = (PlayState.SONG.options.vocalsSuffix != null ? PlayState.SONG.options.vocalsSuffix : ''); + + vocals = new FlxSound(); + try + { + final vocalPl:String = getFromCharacter(PlayState.SONG.characters.player).vocals_file; + final vocalSuffix:String = (vocalPl != null && vocalPl.length > 0) ? vocalPl : 'Player'; + final normalVocals = Paths.voices(currentPrefix, songPath, currentSuffix); + var loadedPlayerVocals = SoundUtil.findVocalOrInst((PlayState.SONG._extraData != null + && PlayState.SONG._extraData._vocalSettings != null) ? PlayState.SONG._extraData._vocalSettings : { + song: songPath, + prefix: currentPrefix, + suffix: currentSuffix, + externVocal: vocalSuffix, + character: PlayState.SONG.characters.player, + difficulty: Difficulty.getString(curDifficulty) + }); + if (loadedPlayerVocals == null && normalVocals != null) + loadedPlayerVocals = normalVocals; + + if (loadedPlayerVocals != null && loadedPlayerVocals.length > 0) + { + vocals.loadEmbedded(loadedPlayerVocals); + vocals.volume = 0; + add(vocals); + } + else + { + remove(vocals); + vocals = null; + } + } + catch (e:haxe.Exception) + { + Debug.logError('vocal couldn\'t load ${e.message}'); + remove(vocals); + vocals = null; + } + + opponentVocals = new FlxSound(); + try + { + final vocalOp:String = getFromCharacter(PlayState.SONG.characters.opponent).vocals_file; + final vocalSuffix:String = (vocalOp != null && vocalOp.length > 0) ? vocalOp : 'Opponent'; + var loadedVocals = SoundUtil.findVocalOrInst((PlayState.SONG._extraData != null + && PlayState.SONG._extraData._vocalOppSettings != null) ? PlayState.SONG._extraData._vocalOppSettings : { + song: songPath, + prefix: currentPrefix, + suffix: currentSuffix, + externVocal: vocalSuffix, + character: PlayState.SONG.characters.opponent, + difficulty: Difficulty.getString(curDifficulty) + }); + if (loadedVocals != null && loadedVocals.length > 0) + { + opponentVocals.loadEmbedded(loadedVocals); + opponentVocals.volume = 0; + add(opponentVocals); + } + else + { + remove(opponentVocals); + opponentVocals = null; + } + } + catch (e:haxe.Exception) + { + Debug.logError('opponent vocal couldn\'t load ${e.message}'); + remove(opponentVocals); + opponentVocals = null; + } + } + + inst = new FlxSound(); + try + { + final currentPrefix:String = (PlayState.SONG.options.instrumentalPrefix != null ? PlayState.SONG.options.instrumentalPrefix : ''); + final currentSuffix:String = (PlayState.SONG.options.instrumentalSuffix != null ? PlayState.SONG.options.instrumentalSuffix : ''); + inst.loadEmbedded(SoundUtil.findVocalOrInst((PlayState.SONG._extraData != null + && PlayState.SONG._extraData._instSettings != null) ? PlayState.SONG._extraData._instSettings : { + song: songPath, + prefix: currentPrefix, + suffix: currentSuffix, + externVocal: "", + character: "", + difficulty: Difficulty.getString(curDifficulty) + }, 'INST')); + inst.volume = 0; + add(inst); + } + catch (e:haxe.Exception) + { + Debug.logError('inst couldn\'t load ${e.message}'); + remove(inst); + inst = null; + } + + songPath = null; + } + + Conductor.bpm = PlayState.SONG.bpm; + Conductor.mapBPMChanges(PlayState.SONG); + + player.curTime = 0; + + inst.time = 0; + if (vocals != null) + vocals.time = 0; + if (opponentVocals != null) + opponentVocals.volume = 0; + + inst.play(); + if (vocals != null) + vocals.play(); + if (opponentVocals != null) + opponentVocals.play(); + instPlaying = curSelected; + + player.playingMusic = true; + player.curTime = 0; + player.switchPlayMusic(); + // player.pauseOrResume(true); + + exit = false; + + if (inst != null) + { + inst.onComplete = function() + { + if (vocals != null) + vocals.time = 0; + if (opponentVocals != null) + opponentVocals.time = 0; + inst.time = 0; + remove(inst); + if (vocals != null) + remove(vocals); + if (opponentVocals != null) + remove(opponentVocals); + inst.destroy(); + if (vocals != null) + vocals.destroy(); + if (opponentVocals != null) + opponentVocals.destroy(); + vocals = null; + opponentVocals = null; + inst = null; + completed = true; + exit = false; + + player.curTime = 0; + player.playingMusic = false; + player.switchPlayMusic(); + + for (i in 0...iconArray.length) + { + iconArray[i].scale.set(1, 1); + iconArray[i].updateHitbox(); + iconArray[i].angle = 0; + } + } + } + } + } + catch (e:haxe.Exception) + { + Debug.logError('ERROR! ${e.message}'); + } + } + + function getFromCharacter(char:String):CharacterFile + { + try + { + var path:String = Paths.getPath('data/characters/$char.json', TEXT); + #if MODS_ALLOWED + var character:Dynamic = Json.parse(File.getContent(path)); + #else + var character:Dynamic = Json.parse(Assets.getText(path)); + #end + return character; + } + catch (e:Dynamic) + { + } + return null; + } + + public function moveToSong() + { + if (inst != null) + inst = null; + if (vocals != null) + vocals = null; + if (opponentVocals != null) + opponentVocals = null; + Conductor.songPosition = 0; + Conductor.bpmChangeMap = []; + player.playingMusic = false; + persistentUpdate = false; + curInstPlayingtxt = instPlayingtxt = ''; + MainMenuState.freakyPlaying = false; + FlxG.sound.music.stop(); + + Debug.logInfo('CURRENT WEEK: ' + WeekData.getWeekFileName()); + + try + { + var poop:String = Highscore.formatSong(Paths.formatToSongPath(songs[curSelected].songName), curDifficulty); + Song.loadFromJson(poop, Paths.formatToSongPath(songs[curSelected].songName)); + PlayState.isStoryMode = false; + PlayState.storyDifficulty = curDifficulty; + Debug.logInfo(poop); + } + catch (e:haxe.Exception) + { + Debug.logError('ERROR! ${e.message}'); + + var errorStr:String = e.message; + if (errorStr.contains('There is no TEXT asset with an ID of')) + errorStr = 'Missing file: ' + + errorStr.substring(errorStr.indexOf(Paths.formatToSongPath(songs[curSelected].songName)), errorStr.length - 1); // Missing chart + missingText.text = 'ERROR WHILE LOADING CHART:\n$errorStr'; + missingText.screenCenter(Y); + missingText.visible = true; + missingTextBG.visible = true; + FlxG.sound.play(Paths.sound('cancelMenu')); + canSelectSong = true; + persistentUpdate = true; + return; + } + + // restore this functionality + LoadingState.prepareToSong(); + LoadingState.loadAndSwitchState(new states.PlayState()); + #if !SHOW_LOADING_SCREEN + if (FlxG.sound.music != null) + FlxG.sound.music.volume = 0; + #end + stopMusicPlay = true; + } + + function changeDiff(change:Int = 0) + { + if (player.playingMusic) + return; + curDifficulty = FlxMath.wrap(curDifficulty + change, 0, Difficulty.list.length - 1); + + final songData = Highscore.getSongScore(songs[curSelected].songName, curDifficulty, opponentMode); + #if !switch + intendedScore = songData.mainData.score; + intendedAccuracy = songData.rankData.accuracy; + combo = songData.rankData.comboRank; + rating = songData.rankData.rating; + #end + + lastDifficultyName = Difficulty.getString(curDifficulty, false); + var displayDiff:String = Difficulty.getString(curDifficulty); + if (Difficulty.list.length > 1) + diffText.text = 'DIFFICULTY: < ' + displayDiff.toUpperCase() + ' >'; + else + diffText.text = 'DIFFICULTY: ' + displayDiff.toUpperCase(); + + curStringDifficulty = lastDifficultyName; + + missingText.visible = false; + missingTextBG.visible = false; + diffText.alpha = 1; + + diffText.useTextColor = true; + FlxTween.color(diffText, 0.3, diffText.textColor, + scorecolorDifficulty.exists(curStringDifficulty) ? scorecolorDifficulty.get(curStringDifficulty) : FlxColor.WHITE, { + ease: FlxEase.quadInOut + }); + } + + function changeSelection(change:Int = 0, playSound:Bool = true) + { + if (player.playingMusic) + return; + + curSelected = FlxMath.wrap(curSelected + change, 0, songs.length - 1); + _updateSongLastDifficulty(); + if (playSound) + FlxG.sound.play(Paths.sound('scrollMenu'), 0.4); + + var newColor:Int = songs[curSelected].color; + if (newColor != intendedColor) + { + intendedColor = newColor; + + FlxTween.cancelTweensOf(bg); + FlxTween.color(bg, 1, bg.color, intendedColor); + + // Set the window border color with a tween from the current song's color + // Idea from VS Camellia ALT (https://gamebanana.com/mods/413258) (They use my code to set the window border color XD) + WindowsFuncs.cancelWindowBorderColorTween(); + WindowsFuncs.tweenWindowBorderColor(CustomFuncs.colorIntToRGB(bg.color), CustomFuncs.colorIntToRGB(intendedColor), 1, "linear"); + } + + for (num => item in grpSongs.members) + { + var icon:SlushiFreeplayHealthIcon = iconArray[num]; + icon.alpha = item.alpha = (item.targetY == curSelected) ? 1 : 0.2; + if (icon.hasWinning) + icon.animation.curAnim.curFrame = (icon == iconArray[curSelected]) ? 2 : 0; + } + + Mods.currentModDirectory = songs[curSelected].folder; + PlayState.storyWeek = songs[curSelected].week; + Difficulty.loadFromWeek(); + bg.loadGraphic(SlushiMain.getSLEPath('SlushiFreeplayStateAssets/BG.png')); + + var savedDiff:String = songs[curSelected].lastDifficulty; + var lastDiff:Int = Difficulty.list.indexOf(lastDifficultyName); + if (savedDiff != null && !Difficulty.list.contains(savedDiff) && Difficulty.list.contains(savedDiff)) + curDifficulty = Math.round(Math.max(0, Difficulty.list.indexOf(savedDiff))); + else if (lastDiff > -1) + curDifficulty = lastDiff; + else if (Difficulty.list.contains(Difficulty.getDefault())) + curDifficulty = Math.round(Math.max(0, Difficulty.list.indexOf(Difficulty.getDefault()))); + else + curDifficulty = 0; + + changeDiff(); + _updateSongLastDifficulty(); + } + + inline private function _updateSongLastDifficulty() + { + if (curDifficulty < 1) + songs[curSelected].lastDifficulty = Difficulty.list[0]; + else if (Difficulty.list.length < 1) + songs[curSelected].lastDifficulty = Difficulty.list[0]; + else + songs[curSelected].lastDifficulty = Difficulty.getString(curDifficulty, false); + } + + var _drawDistance:Int = 4; + var _lastVisibles:Array = []; + + public function updateTexts(elapsed:Float = 0.0, accepted:Bool = false) + { + lerpSelected = FlxMath.lerp(curSelected, lerpSelected, Math.exp(-elapsed * 9.6)); + for (i in _lastVisibles) + { + grpSongs.members[i].visible = grpSongs.members[i].active = false; + iconArray[i].visible = iconArray[i].active = false; + } + _lastVisibles = []; + + var min:Int = Math.round(Math.max(0, Math.min(songs.length, lerpSelected - _drawDistance))); + var max:Int = Math.round(Math.max(0, Math.min(songs.length, lerpSelected + _drawDistance))); + for (i in min...max) + { + var item:Alphabet = grpSongs.members[i]; + item.visible = item.active = true; + + if (item.text == songs[curSelected].songName) + { + player.songTextY = item.y; + } + + if (accepted) + { + var musicLength:Float = FlxG.sound.play(Paths.sound('confirmMenu')).length; + if (item.text != songs[curSelected].songName) + { + for (cam in [camNotes, camBG, camSongs]) + { + FlxTween.tween(cam, {angle: 10}, musicLength / 1000); + FlxTween.tween(cam, {zoom: 1.6}, musicLength / 1000); + } + + + if (SlushiSongs.checkSong(songs[curSelected].songName, Difficulty.getString(curDifficulty)) && ClientPrefs.data.shaders) + { + var shader:WaveBurstEffect = new WaveBurstEffect(); + for (cam in [camNotes, camBG, camSongs]) + { + cam.setFilters([new ShaderFilter(shader.shader)]); + } + + var numTween = FlxTween.num(0, 0.2, musicLength / 1000, {ease: FlxEase.quartOut}); + numTween.onUpdate = function(twn:FlxTween) + { + shader.strength = numTween.value; + } + } + + FlxTween.tween(item, {y: 6000}, musicLength / 1000); + var randomInt = FlxG.random.int(0, 1); + if (randomInt == 0) + FlxTween.tween(item, {angle: 10}, musicLength / 1000); + else if (randomInt == 1) + FlxTween.tween(item, {angle: -10}, musicLength / 1000); + } + else + { + // FlxTween.tween(item.scale, {x: 1.35, y: 1.35}, musicLength / 1000, {ease: FlxEase.quartOut}); + FlxTween.tween(item, {y: item.y + 30}, musicLength / 1000); + } + } + else + { + item.x = ((item.targetY - lerpSelected) * item.distancePerItem.x) + item.startPosition.x; + item.screenCenter(X); + } + + item.y = ((item.targetY - lerpSelected) * 1.8 * item.distancePerItem.y) + item.startPosition.y; + + var icon:SlushiFreeplayHealthIcon = iconArray[i]; + icon.visible = icon.active = true; + _lastVisibles.push(i); + } + } + + function loadCharacterFile(char:String):CharacterFile + { + var characterPath:String = 'data/characters/$char.json'; + #if MODS_ALLOWED + var path:String = Paths.modFolders(characterPath); + if (!FileSystem.exists(path)) + { + path = Paths.getSharedPath(characterPath); + } + + if (!FileSystem.exists(path)) + #else + var path:String = Paths.getSharedPath(characterPath); + if (!OpenFlAssets.exists(path)) + #end + { + path = Paths.getSharedPath('data/characters/' + Character.DEFAULT_CHARACTER + + '.json'); // If a character couldn't be found, change him to BF just to prevent a crash + } + + #if MODS_ALLOWED + var rawJson = File.getContent(path); + #else + var rawJson = OpenFlAssets.getText(path); + #end + return cast haxe.Json.parse(rawJson); + } + + /** + * [noteEffect] and [noteEffectUP] are code from Hitmans AD + */ + private function noteEffect() + { + // if (!ClientPrefs.data.lowQuality) + // return; + + var note:FlxSprite = new FlxSprite().loadGraphic(SlushiMain.getSLEPath("SlushiFreeplayStateAssets/DANOTE.png")); + note.antialiasing = ClientPrefs.data.antialiasing; + note.cameras = [camNotes]; + var randomFloat:Float = FlxG.random.float(0.3, 0.6); + note.scale.set(randomFloat, randomFloat); + note.updateHitbox(); + note.y = -200; + note.x = FlxG.random.int(0, FlxG.width); + note.angle = FlxG.random.int(0, 360); + note.alpha = 0.3; + + var noteRGBFirstColumn:Array = []; + for (row in ClientPrefs.data.arrowRGB) + { + noteRGBFirstColumn.push(row[0]); + } + + var randomIndex:Int = FlxG.random.int(0, noteRGBFirstColumn.length - 1); + note.color = noteRGBFirstColumn[randomIndex]; + add(note); + + var noteTrail = new FlxTrail(note, null, 2, 4, 0.15, 0.10); + noteTrail.cameras = [camNotes]; + noteTrail.alpha = 0.3; + noteTrail.color = note.color; + add(noteTrail); + FlxTween.tween(noteTrail, {alpha: 0}, 2, {ease: FlxEase.quadInOut}); + FlxTween.tween(note, { + x: note.x - 125, + y: 730, + angle: note.angle + 360, + alpha: 0 + }, 2, { + ease: FlxEase.quadInOut, + onComplete: function(twn:FlxTween) + { + remove(note); + remove(noteTrail); + } + }); + } + + private function noteEffectUP() + { + // if (!ClientPrefs.data.lowQuality) + // return; + + var note:FlxSprite = new FlxSprite().loadGraphic(SlushiMain.getSLEPath("SlushiFreeplayStateAssets/DANOTE.png")); + note.antialiasing = ClientPrefs.data.antialiasing; + note.cameras = [camNotes]; + note.scale.set(0.5, 0.5); + note.updateHitbox(); + note.y = FlxG.height + 100; + note.x = FlxG.random.int(0, FlxG.width); + note.angle = FlxG.random.int(0, 360); + note.alpha = 0.3; + + var firstColumn:Array = []; + for (row in ClientPrefs.data.arrowRGB) + { + firstColumn.push(row[0]); + } + + var randomIndex:Int = FlxG.random.int(0, firstColumn.length - 1); + note.color = firstColumn[randomIndex]; + add(note); + + var noteTrail = new FlxTrail(note, null, 2, 4, 0.15, 0.10); + noteTrail.cameras = [camNotes]; + noteTrail.alpha = 0.3; + noteTrail.color = note.color; + insert(members.indexOf(note), noteTrail); + FlxTween.tween(noteTrail, {alpha: 0}, 2, {ease: FlxEase.quadInOut}); + FlxTween.tween(note, { + x: note.x - 125, + y: 0, + angle: note.angle + 360, + alpha: 0 + }, 2, { + ease: FlxEase.quadInOut, + onComplete: function(twn:FlxTween) + { + remove(note); + remove(noteTrail); + } + }); + } + + override function stepHit() + { + super.stepHit(); + + if (!player.playingMusic) + return; + + if (curStep % 4 == 0) + { + noteEffect(); + } + else + { + noteEffectUP(); + } + } + + override function beatHit() + { + super.beatHit(); + + if (!player.playingMusic) + return; + + if (!Application.current.window.maximized) + { + // SlushiModifier moment XDD + if (curBeat % 2 == 0) + { + WindowFuncs.setWinPositionInX(WindowFuncs.getWindowPositionInX() - 10); + FlxTween.tween(Application.current.window, {x: WindowFuncs.getWindowPositionInX() + 10}, 0.2, {ease: FlxEase.quadOut}); + } + else + { + WindowFuncs.setWinPositionInX(WindowFuncs.getWindowPositionInX() + 10); + FlxTween.tween(Application.current.window, {x: WindowFuncs.getWindowPositionInX() - 10}, 0.2, {ease: FlxEase.quadOut}); + } + } + + if (curBeat % 2 == 0) + bg.scale.set(1.06, 1.06); + bg.updateHitbox(); + bg.offset.set(); + for (icon in iconArray) + { + if (curSelected == iconArray.indexOf(icon)) + continue; + icon.playAnim('normal', true); + } + for (i in 0...iconArray.length) + { + iconArray[i].iconBopSpeed = 1; + iconArray[i].beatHit(curBeat); + } + } + + override function sectionHit() + { + super.sectionHit(); + + if (player.playingMusic) + { + if (ClientPrefs.data.camZooms && FlxG.camera.zoom < 1.35) + { + FlxG.camera.zoom += 0.03 / rate; + } + } + } + + override function destroy() + { + #if desktop + for (music in [inst, vocals, opponentVocals]) + { + if (music != null) + { + remove(music); + music.destroy(); + music = null; + } + } + #end + player.destroy(); + super.destroy(); + } +} diff --git a/funkinscsource/slushi/states/freeplay/SlushiMusicPlayer.hx b/funkinscsource/slushi/states/freeplay/SlushiMusicPlayer.hx new file mode 100644 index 0000000..4e4071a --- /dev/null +++ b/funkinscsource/slushi/states/freeplay/SlushiMusicPlayer.hx @@ -0,0 +1,382 @@ +package slushi.states.freeplay; + +import flixel.group.FlxGroup; +import flixel.ui.FlxBar; +import slushi.states.freeplay.SlushiFreeplayState; +import flixel.util.FlxStringUtil; + +/** + * Music player used for Freeplay + * + * Author: ??? - Modified by Slushi + */ +@:access(slushi.states.freeplay.SlushiFreeplayState) +class SlushiMusicPlayer extends FlxGroup +{ + public var instance:SlushiFreeplayState; + public var controls:Controls; + + public var playing(get, never):Bool; + + public var playingMusic:Bool = false; + public var curTime:Float; + + var timeTxt:FlxText; + var progressBar:FlxBar; + var playbackSymbols:Array = []; + var playbackTxt:FlxText; + + public var wasPlaying:Bool; + + public var holdPitchTime:Float = 0; + public var playbackRate(default, set):Float = 1; + + public var fadingOut:Bool; + + public var backgroundLol:FlxSprite; + + public var songTextY:Float = 0; + + public var sineValue:Float = 0; + + public function new(instance:SlushiFreeplayState) + { + super(); + + this.instance = instance; + this.controls = instance.controls; + + var xPos:Float = FlxG.width * 0.7; + + timeTxt = new FlxText(xPos, 0, 0, "", 32); + timeTxt.setFormat(Paths.font("vcr.ttf"), 32, FlxColor.WHITE, RIGHT); + add(timeTxt); + + for (i in 0...2) + { + var text:FlxText = new FlxText(); + text.setFormat(Paths.font('vcr.ttf'), 32, FlxColor.WHITE, CENTER); + text.text = '^'; + if (i == 1) + text.flipY = true; + text.visible = false; + playbackSymbols.push(text); + add(text); + } + + progressBar = new FlxBar(timeTxt.x, timeTxt.y + timeTxt.height, LEFT_TO_RIGHT, Std.int(timeTxt.width), 8, null, "", 0, Math.POSITIVE_INFINITY); + progressBar.createFilledBar(FlxColor.WHITE, SlushiMain.slushiColor); + add(progressBar); + + playbackTxt = new FlxText(FlxG.width * 0.6, 20, 0, "", 32); + playbackTxt.setFormat(Paths.font("vcr.ttf"), 32, FlxColor.WHITE); + add(playbackTxt); + + backgroundLol = new FlxSprite(0, 0).makeGraphic(Std.int(FlxG.width), Std.int(FlxG.height), 0xFF000000); + backgroundLol.alpha = 0; + add(backgroundLol); + + switchPlayMusic(); + + camera = SlushiFreeplayState.instance.camSongs; + } + + override function update(elapsed:Float) + { + super.update(elapsed); + + if (!playingMusic) + { + Conductor.songPosition = -5000 / Conductor.songPosition; + return; + } + + Conductor.songPosition = SlushiFreeplayState.instance.inst.time; + + if (playing && !wasPlaying) + { + timeTxt.alpha = 1; + } + else + { + if (timeTxt != null && timeTxt.visible) + { + sineValue += 180 * elapsed; + timeTxt.alpha = 1 - Math.sin((Math.PI * sineValue) / 180); + } + } + + if (controls.UI_LEFT_P) + { + if (playing) + wasPlaying = true; + + pauseOrResume(); + + curTime = SlushiFreeplayState.instance.inst.time - 1000; + instance.holdTime = 0; + + if (curTime < 0) + curTime = 0; + + SlushiFreeplayState.instance.inst.time = curTime; + setVocalsTime(curTime); + } + if (controls.UI_RIGHT_P) + { + if (playing) + wasPlaying = true; + + pauseOrResume(); + + curTime = SlushiFreeplayState.instance.inst.time + 1000; + instance.holdTime = 0; + + if (curTime > SlushiFreeplayState.instance.inst.length) + curTime = SlushiFreeplayState.instance.inst.length; + + SlushiFreeplayState.instance.inst.time = curTime; + setVocalsTime(curTime); + } + + if (controls.UI_LEFT || controls.UI_RIGHT) + { + instance.holdTime += elapsed; + if (instance.holdTime > 0.5) + { + curTime += 40000 * elapsed * (controls.UI_LEFT ? -1 : 1); + } + + var difference:Float = Math.abs(curTime - SlushiFreeplayState.instance.inst.time); + if (curTime + difference > SlushiFreeplayState.instance.inst.length) + curTime = SlushiFreeplayState.instance.inst.length; + else if (curTime - difference < 0) + curTime = 0; + + SlushiFreeplayState.instance.inst.time = curTime; + setVocalsTime(curTime); + } + + if (controls.UI_LEFT_R || controls.UI_RIGHT_R) + { + SlushiFreeplayState.instance.inst.time = curTime; + setVocalsTime(curTime); + + if (wasPlaying) + { + pauseOrResume(true); + wasPlaying = false; + } + } + if (controls.UI_UP_P) + { + holdPitchTime = 0; + playbackRate += 0.05; + setPlaybackRate(); + } + else if (controls.UI_DOWN_P) + { + holdPitchTime = 0; + playbackRate -= 0.05; + setPlaybackRate(); + } + if (controls.UI_DOWN || controls.UI_UP) + { + holdPitchTime += elapsed; + if (holdPitchTime > 0.6) + { + playbackRate += 0.05 * (controls.UI_UP ? 1 : -1); + setPlaybackRate(); + } + } + + if (controls.RESET) + { + playbackRate = 1; + setPlaybackRate(); + + SlushiFreeplayState.instance.inst.time = 0; + setVocalsTime(0); + + updateTimeTxt(); + } + + if (playing && !fadingOut) + { + if (SlushiFreeplayState.instance.inst != null) + SlushiFreeplayState.instance.inst.volume = 0.8; + if (SlushiFreeplayState.instance.vocals != null) + SlushiFreeplayState.instance.vocals.volume = (SlushiFreeplayState.instance.vocals.length > SlushiFreeplayState.instance.inst.time) ? 0.8 : 0; + if (SlushiFreeplayState.instance.opponentVocals != null) + SlushiFreeplayState.instance.opponentVocals.volume = (SlushiFreeplayState.instance.opponentVocals.length > SlushiFreeplayState.instance.inst.time) ? 0.8 : 0; + + if ((SlushiFreeplayState.instance.vocals != null + && SlushiFreeplayState.instance.vocals.length > SlushiFreeplayState.instance.inst.time + && Math.abs(SlushiFreeplayState.instance.inst.time - SlushiFreeplayState.instance.vocals.time) >= 25) + || (SlushiFreeplayState.instance.opponentVocals != null + && SlushiFreeplayState.instance.opponentVocals.length > SlushiFreeplayState.instance.inst.time + && Math.abs(SlushiFreeplayState.instance.inst.time - SlushiFreeplayState.instance.opponentVocals.time) >= 25)) + { + pauseOrResume(); + setVocalsTime(SlushiFreeplayState.instance.inst.time); + pauseOrResume(true); + } + } + if (playingMusic) + { + positionSong(); + updateTimeTxt(); + updatePlaybackTxt(); + } + } + + function setVocalsTime(time:Float) + { + if (SlushiFreeplayState.instance.vocals != null && SlushiFreeplayState.instance.vocals.length > time) + SlushiFreeplayState.instance.vocals.time = time; + if (SlushiFreeplayState.instance.opponentVocals != null && SlushiFreeplayState.instance.opponentVocals.length > time) + SlushiFreeplayState.instance.opponentVocals.time = time; + } + + public function pauseOrResume(resume:Bool = false) + { + if (resume) + { + if (!SlushiFreeplayState.instance.inst.playing) + SlushiFreeplayState.instance.inst.resume(); + + if (SlushiFreeplayState.instance.vocals != null + && SlushiFreeplayState.instance.vocals.length > SlushiFreeplayState.instance.inst.time + && !SlushiFreeplayState.instance.vocals.playing) + SlushiFreeplayState.instance.vocals.resume(); + if (SlushiFreeplayState.instance.opponentVocals != null + && SlushiFreeplayState.instance.opponentVocals.length > SlushiFreeplayState.instance.inst.time + && !SlushiFreeplayState.instance.opponentVocals.playing) + SlushiFreeplayState.instance.opponentVocals.resume(); + } + else + { + SlushiFreeplayState.instance.inst.pause(); + + if (SlushiFreeplayState.instance.vocals != null) + SlushiFreeplayState.instance.vocals.pause(); + + if (SlushiFreeplayState.instance.opponentVocals != null) + SlushiFreeplayState.instance.opponentVocals.pause(); + } + } + + function positionSong() + { + timeTxt.y = songTextY + 90; + timeTxt.screenCenter(X); + + progressBar.setGraphicSize(Std.int(timeTxt.width), 5); + progressBar.y = timeTxt.y + timeTxt.height; + progressBar.screenCenter(X); + + playbackTxt.screenCenter(); + playbackTxt.y = progressBar.y + 50; + + for (i in 0...2) + { + var text = playbackSymbols[i]; + text.x = playbackTxt.x + playbackTxt.width / 2 - 10; + text.y = playbackTxt.y; + if (i == 0) + text.y -= playbackTxt.height; + else + text.y += playbackTxt.height; + } + } + + public function switchPlayMusic() + { + active = visible = playingMusic; + + instance.scoreBG.visible = instance.diffText.visible = instance.scoreText.visible = instance.comboText.visible = instance.opponentText.visible = !playingMusic; // Hide Freeplay texts and boxes if playingMusic is true + + timeTxt.visible = playbackTxt.visible = progressBar.visible = playingMusic; // Show Music Player texts and boxes if playingMusic is true + + for (i in playbackSymbols) + i.visible = playingMusic; + + holdPitchTime = 0; + instance.holdTime = 0; + playbackRate = 1; + updatePlaybackTxt(); + + if (playingMusic) + { + instance.downText.text = Language.getPhrase('musicplayer_tip', "Press SPACE to Pause / Press ESCAPE to Exit / Press R to Reset the Song"); + instance.downText.x = -210; + positionSong(); + + progressBar.setRange(0, SlushiFreeplayState.instance.inst.length); + progressBar.setParent(SlushiFreeplayState.instance.inst, "time"); + progressBar.numDivisions = 1600; + + updateTimeTxt(); + // backgroundLol.alpha = .5; + } + else + { + progressBar.setRange(0, Math.POSITIVE_INFINITY); + progressBar.setParent(null, ""); + progressBar.numDivisions = 0; + + instance.downText.text = instance.leText; + instance.downText.x = -600; + // backgroundLol.alpha = 0; + } + progressBar.updateBar(); + } + + function updatePlaybackTxt() + { + var text = ""; + if (playbackRate is Int) + text = playbackRate + '.00'; + else + { + var playbackRate = Std.string(playbackRate); + if (playbackRate.split('.')[1].length < 2) + playbackRate += '0'; + + text = playbackRate; + } + playbackTxt.text = text + 'x'; + } + + function updateTimeTxt() + { + var text = FlxStringUtil.formatTime(FlxMath.roundDecimal(Conductor.songPosition / 1000 / playbackRate, 2), false) + + ' / ' + + FlxStringUtil.formatTime(FlxMath.roundDecimal(SlushiFreeplayState.instance.inst.length / 1000 / playbackRate, 2), false); + timeTxt.text = '< ' + text + ' >'; + } + + function setPlaybackRate() + { + SlushiFreeplayState.instance.inst.pitch = playbackRate; + if (SlushiFreeplayState.instance.vocals != null) + SlushiFreeplayState.instance.vocals.pitch = playbackRate; + if (SlushiFreeplayState.instance.opponentVocals != null) + SlushiFreeplayState.instance.opponentVocals.pitch = playbackRate; + } + + function get_playing():Bool + { + return SlushiFreeplayState.instance.inst.playing; + } + + function set_playbackRate(value:Float):Float + { + var value = FlxMath.roundDecimal(value, 2); + if (value > 3) + value = 3; + else if (value <= 0.25) + value = 0.25; + return playbackRate = value; + } +} diff --git a/funkinscsource/slushi/substates/DebugSubState.hx b/funkinscsource/slushi/substates/DebugSubState.hx index e43fcca..da9e91f 100644 --- a/funkinscsource/slushi/substates/DebugSubState.hx +++ b/funkinscsource/slushi/substates/DebugSubState.hx @@ -21,6 +21,8 @@ class DebugSubState extends MusicBeatSubState '[In Gameplay] F3 + P: Active Practice mode', 'F3 + C: Center the window', 'F3 + F: Force crash', + 'F3 + S: Show a terminal', + 'F3 + W: Enter WinSL mode' ]; public static var onPlayState:Bool = false; @@ -51,7 +53,6 @@ class DebugSubState extends MusicBeatSubState buildNumber.setFormat("VCR OSD Mono", 25, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); buildNumber.scrollFactor.set(); buildNumber.screenCenter(X); - // buildNumber.x -= 200; buildNumber.alpha = 0.6; add(buildNumber); @@ -150,13 +151,23 @@ class DebugSubState extends MusicBeatSubState }); } - if (FlxG.keys.pressed.F3 && FlxG.keys.pressed.C && !Application.current.window.maximized && !Application.current.window.fullscreen) + if (FlxG.keys.pressed.F3 + && FlxG.keys.justPressed.C + && !Application.current.window.maximized + && !Application.current.window.fullscreen) { - #if windows - CppAPI.centerWindow(); - #else WindowFuncs.setWinPositionInX(Std.int((WindowFuncs.getScreenSizeInWidth() - WindowFuncs.getWindowSizeInWidth()) / 2)); WindowFuncs.setWinPositionInY(Std.int((WindowFuncs.getScreenSizeInHeight() - WindowFuncs.getWindowSizeInHeight()) / 2)); + } + + if (FlxG.keys.pressed.F3 && FlxG.keys.justPressed.S) + { + #if windows + WindowsTerminalCPP.allocConsole(); + WindowsTerminalCPP.setConsoleTitle('WinSL [${SlushiMain.sleThingsVersions.winSLVersion}] - Viewing SlushiEngine_${SlushiMain.buildNumber}.vm terminal'); + WindowsTerminalCPP.setConsoleWindowIcon(SlushiMain.getSLEPath("WinSL_Assets/windowIcon.ico")); + WindowsTerminalCPP.setWinConsoleColor(); + WindowsTerminalCPP.disableCloseWindow(); #end } @@ -166,4 +177,4 @@ class DebugSubState extends MusicBeatSubState } super.update(elapsed); } -} \ No newline at end of file +} diff --git a/funkinscsource/slushi/substates/SlushiPauseSubState.hx b/funkinscsource/slushi/substates/SlushiPauseSubState.hx new file mode 100644 index 0000000..6d569ff --- /dev/null +++ b/funkinscsource/slushi/substates/SlushiPauseSubState.hx @@ -0,0 +1,772 @@ +package slushi.substates; + +import backend.WeekData; +import backend.Highscore; +import states.StoryMenuState; +import options.OptionsState; +import flixel.util.FlxStringUtil; + +class SlushiPauseSubState extends MusicBeatSubState +{ + public static var songName:String = null; + + var grpMenuShit:FlxTypedGroup; + + var menuItems:Array = []; + var menuItemsOG:Array = ['Resume', 'Restart Song', 'Change Difficulty', 'Options', 'Exit to menu']; + var difficultyChoices = []; + var optionChoices = []; + var curSelected:Int = 0; + + var pauseMusic:FlxSound; + var optionsText:FlxText; + var practiceText:FlxText; + var skipTimeText:FlxText; + var skipTimeTracker:Alphabet; + var curTime:Float = Math.max(0, Conductor.songPosition); + + var missingTextBG:FlxSprite; + var missingText:FlxText; + + var music:FlxSound = FlxG.sound.music; + + var settings = { + music: ClientPrefs.data.pauseMusic + }; + + var num:Int = 0; + + var bg:FlxSprite; + var slBG:FlxSprite; + + override function create() + { + game.paused = true; + + if (Difficulty.list.length < 2) + menuItemsOG.remove('Change Difficulty'); // No need to change difficulty if there is only one! + + if (PlayState.chartingMode) + { + menuItemsOG.insert(2, 'Leave Charting Mode'); + } + else if (PlayState.modchartMode) + { + menuItemsOG.insert(2, 'Leave ModChart Mode'); + } + + if (PlayState.chartingMode || PlayState.modchartMode) + { + if (!game.startingSong) + { + num = 1; + menuItemsOG.insert(3, 'Skip Time'); + } + menuItemsOG.insert(3 + num, 'End Song'); + menuItemsOG.insert(4 + num, 'Toggle Practice Mode'); + menuItemsOG.insert(5 + num, 'Toggle Botplay'); + } + menuItems = menuItemsOG; + + for (i in 0...Difficulty.list.length) + { + var diff:String = Difficulty.getString(i); + difficultyChoices.push(diff); + } + difficultyChoices.push('BACK'); + + for (i in OptionsState.options) + { + optionChoices.push(i); + } + optionChoices.push('BACK'); + + if (pauseMusic != null) + pauseMusic = null; + + pauseMusic = new FlxSound(); + try + { + var pauseSong:String = getPauseSong(); + if (pauseSong != null) + pauseMusic.loadEmbedded(Paths.music(pauseSong), true, true); + } + catch (e:Dynamic) + { + } + pauseMusic.volume = 0; + pauseMusic.play(false, FlxG.random.int(0, Std.int(pauseMusic.length / 2))); + FlxG.sound.list.add(pauseMusic); + + bg = new FlxSprite().makeGraphic(1, 1, FlxColor.BLACK); + bg.scale.set(FlxG.width, FlxG.height); + bg.updateHitbox(); + bg.alpha = 0; + bg.scrollFactor.set(); + add(bg); + + slBG = new FlxSprite().loadGraphic(SlushiMain.getSLEPath('BGs/SlushiBGPauseSubState.png')); + slBG.antialiasing = ClientPrefs.data.antialiasing; + slBG.updateHitbox(); + slBG.screenCenter(); + slBG.alpha = 0; + slBG.color = SlushiMain.slushiColor; + add(slBG); + + var levelInfo:FlxText = new FlxText(20, 15, 0, 'Song: ' + PlayState.SONG.songId, 32); + levelInfo.scrollFactor.set(); + levelInfo.setFormat(Paths.font("vcr.ttf"), 32); + levelInfo.updateHitbox(); + add(levelInfo); + + var levelDifficulty:FlxText = new FlxText(20, 15 + 32, 0, 'Difficulty: ' + Difficulty.getString().toUpperCase(), 32); + levelDifficulty.scrollFactor.set(); + levelDifficulty.setFormat(Paths.font('vcr.ttf'), 32); + levelDifficulty.updateHitbox(); + add(levelDifficulty); + + var blueballedTxt:FlxText = new FlxText(20, 15 + 64, 0, Language.getPhrase("blueballed", "Blueballed: {1}", [PlayState.deathCounter]), 32); + blueballedTxt.scrollFactor.set(); + blueballedTxt.setFormat(Paths.font('vcr.ttf'), 32); + blueballedTxt.updateHitbox(); + add(blueballedTxt); + + practiceText = new FlxText(20, 15 + 101, 0, Language.getPhrase("Practice Mode").toUpperCase(), 32); + practiceText.scrollFactor.set(); + practiceText.setFormat(Paths.font('vcr.ttf'), 32); + practiceText.x = FlxG.width - (practiceText.width + 20); + practiceText.updateHitbox(); + practiceText.visible = game.practiceMode; + add(practiceText); + + var chartingText:FlxText = new FlxText(20, 15 + 101, 0, "", 32); + chartingText.scrollFactor.set(); + if (PlayState.chartingMode) + chartingText.text = Language.getPhrase("Charting Mode").toUpperCase(); + else if (PlayState.modchartMode) + chartingText.text = Language.getPhrase("Modchart Mode").toUpperCase(); + else + chartingText.text = ""; + chartingText.setFormat(Paths.font('vcr.ttf'), 32); + chartingText.x = FlxG.width - (chartingText.width + 20); + chartingText.y = FlxG.height - (chartingText.height + 20); + chartingText.updateHitbox(); + chartingText.visible = (PlayState.chartingMode || PlayState.modchartMode); + add(chartingText); + + var notITGText:FlxText = new FlxText(20, 15 + 101, 0, Language.getPhrase("Modchart Disabled").toUpperCase(), 32); + notITGText.scrollFactor.set(); + notITGText.setFormat(Paths.font('vcr.ttf'), 32); + notITGText.x = FlxG.width - (notITGText.width + 20); + notITGText.y = FlxG.height - (notITGText.height + 60); + notITGText.updateHitbox(); + notITGText.visible = !ClientPrefs.getGameplaySetting('modchart'); + add(chartingText); + + blueballedTxt.alpha = 0; + levelDifficulty.alpha = 0; + levelInfo.alpha = 0; + chartingText.alpha = 0; + practiceText.alpha = 0; + practiceText.y -= 5; + + levelInfo.x = FlxG.width - (levelInfo.width + 20); + levelDifficulty.x = FlxG.width - (levelDifficulty.width + 20); + blueballedTxt.x = FlxG.width - (blueballedTxt.width + 20); + + // thank you crowplexus for the portuguese translation!! - subpurr + optionsText = new FlxText(20, 15 + 101, 0, + Language.getPhrase("options_in_pause_warning", "WARNING: Not all options are supported!\nSome options may not update until you restart."), 32); + optionsText.scrollFactor.set(); + optionsText.setFormat(Paths.font('vcr.ttf'), 32, FlxColor.WHITE, LEFT, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); + optionsText.borderSize = 4; + optionsText.y = FlxG.height - (optionsText.height + 20); + optionsText.updateHitbox(); + + FlxTween.tween(bg, {alpha: 0.6}, 0.4, {ease: FlxEase.quartInOut}); + FlxTween.tween(slBG, {alpha: 0.8}, 0.4, {ease: FlxEase.quartInOut}); + FlxTween.tween(chartingText, {alpha: 1}, 0.4, {ease: FlxEase.quartInOut}); + FlxTween.tween(levelInfo, {alpha: 1, y: 20}, 0.4, {ease: FlxEase.quartInOut, startDelay: 0.3}); + FlxTween.tween(levelDifficulty, {alpha: 1, y: levelDifficulty.y + 5}, 0.4, {ease: FlxEase.quartInOut, startDelay: 0.5}); + FlxTween.tween(blueballedTxt, {alpha: 1, y: blueballedTxt.y + 5}, 0.4, {ease: FlxEase.quartInOut, startDelay: 0.7}); + FlxTween.tween(practiceText, {alpha: 1, y: practiceText.y + 5}, 0.4, {ease: FlxEase.quartInOut, startDelay: 0.9}); + + grpMenuShit = new FlxTypedGroup(); + add(grpMenuShit); + + missingTextBG = new FlxSprite().makeGraphic(1, 1, FlxColor.BLACK); + missingTextBG.scale.set(FlxG.width, FlxG.height); + missingTextBG.updateHitbox(); + missingTextBG.alpha = 0.6; + missingTextBG.visible = false; + add(missingTextBG); + + missingText = new FlxText(50, 0, FlxG.width - 100, '', 24); + missingText.setFormat(Paths.font("vcr.ttf"), 24, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); + missingText.scrollFactor.set(); + missingText.visible = false; + add(missingText); + + regenMenu(); + cameras = [FlxG.cameras.list[FlxG.cameras.list.length - 1]]; + + super.create(); + } + + function getPauseSong() + { + var formattedSongName:String = (songName != null ? Paths.formatToSongPath(songName) : ''); + var formattedPauseMusic:String = Paths.formatToSongPath(ClientPrefs.data.pauseMusic); + if (formattedSongName == 'none' || (formattedSongName != 'none' && formattedPauseMusic == 'none')) + return null; + + return (formattedSongName != '') ? formattedSongName : formattedPauseMusic; + } + + var holdTime:Float = 0; + var cantUnpause:Float = 0.1; + + public var getReady:FlxSprite; + public var countdownReady:FlxSprite; + public var countdownSet:FlxSprite; + public var countdownGo:FlxSprite; + public var inCountDown:Bool = false; + public var unPauseTimer:FlxTimer; + + var stoppedUpdatingMusic:Bool = false; + + override function update(elapsed:Float) + { + if (controls.BACK) + { + close(); + game.canResync = true; + return; + } + + if (game != null) + game.paused = true; + cantUnpause -= elapsed; + if (!stoppedUpdatingMusic) + { // Reason to no put != null outside is to not confuse the game to not "stop" when intended. + if (pauseMusic != null && pauseMusic.volume < 0.5) + pauseMusic.volume += 0.01 * elapsed; + } + else + { + if (pauseMusic != null) + pauseMusic.volume = 0; + } + + super.update(elapsed); + + updateSkipTextStuff(); + + if (controls.UI_UP_P && !inCountDown) + { + changeSelection(-1); + } + if (controls.UI_DOWN_P && !inCountDown) + { + changeSelection(1); + } + if (FlxG.mouse.wheel != 0) + changeSelection(-FlxG.mouse.wheel); + + var daSelected:String = menuItems[curSelected]; + switch (daSelected) + { + case 'Skip Time': + if (controls.UI_LEFT_P) + { + FlxG.sound.play(Paths.sound('scrollMenu'), 0.4); + curTime -= 1000; + holdTime = 0; + } + if (controls.UI_RIGHT_P) + { + FlxG.sound.play(Paths.sound('scrollMenu'), 0.4); + curTime += 1000; + holdTime = 0; + } + + if (controls.UI_LEFT || controls.UI_RIGHT) + { + holdTime += elapsed; + if (holdTime > 0.5) + { + curTime += 45000 * elapsed * (controls.UI_LEFT ? -1 : 1); + } + + if (curTime >= music.length) + curTime -= music.length; + else if (curTime < 0) + curTime += music.length; + updateSkipTimeText(); + } + } + + if (FlxG.keys.justPressed.F5 && !inCountDown) + { + FlxTransitionableState.skipNextTransIn = true; + FlxTransitionableState.skipNextTransOut = true; + PlayState.nextReloadAll = true; + MusicBeatState.resetState(); + } + + if ((controls.ACCEPT && (cantUnpause <= 0 || !controls.controllerMode)) && !inCountDown) + { + // Finally + if (menuItems == difficultyChoices) + { + var songLowercase:String = Paths.formatToSongPath(PlayState.SONG.songId); + var poop:String = Highscore.formatSong(songLowercase, curSelected); + try + { + if (menuItems.length - 1 != curSelected && difficultyChoices.contains(daSelected)) + { + Song.loadFromJson(poop, songLowercase); + PlayState.storyDifficulty = curSelected; + LoadingState.loadAndSwitchState(new PlayState()); + music.volume = 0; + PlayState.changedDifficulty = true; + PlayState.chartingMode = false; + PlayState.modchartMode = false; + return; + } + } + catch (e:haxe.Exception) + { + Debug.logError('ERROR! ${e.message}'); + + var errorStr:String = e.message; + if (errorStr.startsWith('[lime.utils.Assets] ERROR:')) + errorStr = 'Missing file: ' + errorStr.substring(errorStr.indexOf(songLowercase), errorStr.length - 1); // Missing chart + else + errorStr += '\n\n' + e.stack; + missingText.text = 'ERROR WHILE LOADING CHART:\n$errorStr'; + missingText.screenCenter(Y); + missingText.visible = true; + missingTextBG.visible = true; + FlxG.sound.play(Paths.sound('cancelMenu')); + + super.update(elapsed); + return; + } + + menuItems = menuItemsOG; + regenMenu(); + } + + if (menuItems == optionChoices) + { + switch (daSelected) + { + case 'Note Options': + OptionsState.onPlayState = true; + FlxTransitionableState.skipNextTransOut = true; + FlxTransitionableState.skipNextTransIn = true; + MusicBeatState.switchState(new options.NoteOptions()); + game.canResync = false; + case 'Controls': + openSubState(new options.ControlsSubState()); + case 'Graphics': + openSubState(new options.GraphicsSettingsSubState()); + case 'Visuals': + openSubState(new options.VisualsSettingsSubState()); + case 'Gameplay': + openSubState(new options.GameplaySettingsSubState()); + case 'Misc': + openSubState(new options.MiscSettingsSubState()); + case 'Adjust Delay and Combo': + OptionsState.onPlayState = true; + MusicBeatState.switchState(new options.NoteOffsetState()); + game.canResync = false; + case 'Language': + openSubState(new options.LanguageSubState()); + default: + ClientPrefs.saveSettings(); + ClientPrefs.loadPrefs(); + ClientPrefs.keybindSaveLoad(); + menuItems = menuItemsOG; + regenMenu(); + remove(optionsText); // no need for visible, just remove it + } + return; + } + + if (!stoppedUpdatingMusic) + { + stoppedUpdatingMusic = true; + destroyMusic(); + } + menuOptions(daSelected); + } + } + + var isCountDown:Bool = false; + + function menuOptions(daSelected:String) + { + switch (daSelected) + { + case "Resume": + if (ClientPrefs.data.pauseCountDown) + { + unPauseTimer = new FlxTimer().start(Conductor.crochet / 1000 / music.pitch, function(hmmm:FlxTimer) + { + switch (hmmm.loopsLeft) + { + case 4 | 3 | 2 | 1: + pauseCountDown(); + case 0: + if (hmmm.finished) + pauseCountDown(); + } + }, 5); + isCountDown = true; + for (item in grpMenuShit.members) + { + FlxTween.tween(item, {alpha: 0}, 0.56, {ease: FlxEase.quadOut}); + } + } + inCountDown = true; + if (!isCountDown) + close(); + case 'Change Difficulty': + menuItems = difficultyChoices; + deleteSkipTimeText(); + regenMenu(); + case 'Toggle Practice Mode': + game.practiceMode = !game.practiceMode; + PlayState.changedDifficulty = true; + practiceText.visible = game.practiceMode; + case "Restart Song", "Leave Charting Mode", "Leave ModChart Mode": + LoadingState.loadAndSwitchState(new PlayState()); + + switch (daSelected) + { + case "Leave Charting Mode": + PlayState.chartingMode = false; + case "Leave ModChart Mode": + PlayState.modchartMode = false; + } + case 'Skip Time': + if (curTime < Conductor.songPosition) + { + PlayState.startOnTime = curTime; + restartSong(true); + } + else + { + if (curTime != Conductor.songPosition) + { + game.clearNotesBefore(curTime); + game.setSongTime(curTime); + } + close(); + } + case 'Toggle Botplay': + game.cpuControlled = !game.cpuControlled; + PlayState.changedDifficulty = true; + game.botplayTxt.visible = game.cpuControlled; + game.botplayTxt.alpha = 1; + game.botplaySine = 0; + case 'Options': + menuItems = optionChoices; + deleteSkipTimeText(); + regenMenu(); + add(optionsText); // ensure it's at front + case 'End Song': + close(); + game.notes.clear(); + game.unspawnNotes.clear(); + game.finishSong(true); + case "Exit to menu": + #if DISCORD_ALLOWED DiscordClient.resetClientID(); #end + PlayState.deathCounter = 0; + PlayState.seenCutscene = false; + + Mods.loadTopMod(); + + if (ClientPrefs.data.behaviourType != 'VSLICE') + { + if (PlayState.isStoryMode) + MusicBeatState.switchState(new StoryMenuState()); + else + MusicBeatState.switchState(new slushi.states.freeplay.SlushiFreeplayState()); + } + #if BASE_GAME_FILES + else + { + if (PlayState.isStoryMode) + { + PlayState.storyPlaylist = []; + openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new StoryMenuState(sticker))); + } + else + openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new slushi.states.freeplay.SlushiFreeplayState(sticker))); + } + #end + + game.canResync = false; + FlxG.sound.playMusic(SlushiMain.getSLEPath("Musics/SLE_HackNet_Resonance.ogg")); + PlayState.changedDifficulty = false; + PlayState.chartingMode = false; + PlayState.modchartMode = false; + game.alreadyEndedSong = false; + FlxG.camera.followLerp = 0; + if (PlayState.forceMiddleScroll) + { + if (PlayState.savePrefixScrollR && PlayState.prefixRightScroll) + { + ClientPrefs.data.middleScroll = false; + } + } + else if (PlayState.forceRightScroll) + { + if (PlayState.savePrefixScrollM && PlayState.prefixMiddleScroll) + { + ClientPrefs.data.middleScroll = true; + } + } + } + } + + function destroyMusic() + { + pauseMusic.volume = 0; + pauseMusic.destroy(); + pauseMusic = null; + } + + var CDANumber:Int = 5; + var game:PlayState = PlayState.instance; + + function pauseCountDown() + { + if (game == null) + return; + game.stageIntroSoundsSuffix = game.stage.stageIntroSoundsSuffix != null ? game.stage.stageIntroSoundsSuffix : ''; + game.stageIntroSoundsPrefix = game.stage.stageIntroSoundsPrefix != null ? game.stage.stageIntroSoundsPrefix : ''; + + var introAssets:Map> = new Map>(); + var introImagesArray:Array = switch (PlayState.stageUI) + { + case "pixel": [ + '${PlayState.stageUI}UI/ready-pixel', + '${PlayState.stageUI}UI/set-pixel', + '${PlayState.stageUI}UI/date-pixel' + ]; + case "normal": ["ready", "set", "go"]; + default: [ + '${PlayState.stageUI}UI/ready', + '${PlayState.stageUI}UI/set', + '${PlayState.stageUI}UI/go' + ]; + } + if (game.stage.stageIntroAssets != null) + introAssets.set(PlayState.curStage, game.stage.stageIntroAssets); + else + introAssets.set(PlayState.stageUI, introImagesArray); + + var isPixelated:Bool = PlayState.isPixelStage; + var introAlts:Array = (game.stage.stageIntroAssets != null ? introAssets.get(PlayState.curStage) : introAssets.get(PlayState.stageUI)); + var antialias:Bool = (ClientPrefs.data.antialiasing && !isPixelated); + for (value in introAssets.keys()) + { + if (value == PlayState.curStage) + { + introAlts = introAssets.get(value); + + if (game.stageIntroSoundsSuffix != null && game.stageIntroSoundsSuffix.length > 0) + game.introSoundsSuffix = game.stageIntroSoundsSuffix; + else + game.introSoundsSuffix = ''; + + if (game.stageIntroSoundsPrefix != null && game.stageIntroSoundsPrefix.length > 0) + game.introSoundsPrefix = game.stageIntroSoundsPrefix; + else + game.introSoundsPrefix = ''; + } + } + + CDANumber -= 1; + + var introArrays0:Array = []; + var introArrays1:Array = []; + var introArrays2:Array = []; + var introArrays3:Array = []; + if (game.stage.stageIntroSpriteScales != null) + { + introArrays0 = game.stage.stageIntroSpriteScales[0]; + introArrays1 = game.stage.stageIntroSpriteScales[1]; + introArrays2 = game.stage.stageIntroSpriteScales[2]; + introArrays3 = game.stage.stageIntroSpriteScales[3]; + } + + switch (CDANumber) + { + case 4: + var isNotNull = (introAlts.length > 3 ? introAlts[0] : "missingRating"); + getReady = createCountdownSprite(isNotNull, antialias, game.introSoundsPrefix + 'intro3' + game.introSoundsSuffix, introArrays0); + case 3: + countdownReady = createCountdownSprite(introAlts[introAlts.length - 3], antialias, game.introSoundsPrefix + 'intro2' + game.introSoundsSuffix, + introArrays1); + case 2: + countdownSet = createCountdownSprite(introAlts[introAlts.length - 2], antialias, game.introSoundsPrefix + 'intro1' + game.introSoundsSuffix, + introArrays2); + case 1: + countdownGo = createCountdownSprite(introAlts[introAlts.length - 1], antialias, game.introSoundsPrefix + 'introGo' + game.introSoundsSuffix, + introArrays3); + case 0: + close(); + } + } + + inline private function createCountdownSprite(image:String, antialias:Bool, soundName:String, scale:Array = null):FlxSprite + { + var spr:FlxSprite = new FlxSprite(-100).loadGraphic(Paths.image(image)); + spr.scrollFactor.set(); + spr.updateHitbox(); + + if (image.contains("-pixel") && scale == null) + spr.setGraphicSize(Std.int(spr.width * PlayState.daPixelZoom)); + + if (scale != null) + spr.scale.set(scale[0], scale[1]); + + spr.screenCenter(); + spr.antialiasing = antialias; + add(spr); + FlxTween.tween(spr, {y: spr.y + 100, alpha: 0}, Conductor.crochet / 1000, { + ease: FlxEase.cubeInOut, + onComplete: function(twn:FlxTween) + { + remove(spr); + spr.destroy(); + } + }); + if (!game.stage.disabledIntroSounds) + FlxG.sound.play(Paths.sound(soundName), 0.6); + return spr; + } + + function deleteSkipTimeText() + { + if (skipTimeText != null) + { + skipTimeText.kill(); + remove(skipTimeText); + skipTimeText.destroy(); + } + skipTimeText = null; + skipTimeTracker = null; + } + + public static function restartSong(noTrans:Bool = false) + { + if (PlayState.instance != null) + { + PlayState.instance.paused = true; // For lua + if (PlayState.instance.vocals != null) + { + PlayState.instance.vocals.volume = 0; + } + + if (PlayState.instance.splitVocals && PlayState.instance.opponentVocals != null) + { + PlayState.instance.opponentVocals.volume = 0; + } + } + if (FlxG.sound.music != null) + FlxG.sound.music.volume = 0; + + if (noTrans) + { + FlxTransitionableState.skipNextTransIn = true; + FlxTransitionableState.skipNextTransOut = true; + } + MusicBeatState.resetState(); + } + + override function destroy() + { + if (pauseMusic != null) + pauseMusic.destroy(); + game.canResync = true; + + super.destroy(); + } + + function changeSelection(change:Int = 0):Void + { + curSelected = FlxMath.wrap(curSelected + change, 0, menuItems.length - 1); + for (num => item in grpMenuShit.members) + { + item.targetY = num - curSelected; + item.alpha = (item.targetY == 0) ? 1 : 0.6; + + if (item.targetY == 0 && item == skipTimeTracker) + { + curTime = Math.max(0, Conductor.songPosition); + updateSkipTimeText(); + } + } + + missingText.visible = false; + missingTextBG.visible = false; + FlxG.sound.play(Paths.sound('scrollMenu'), 0.4); + } + + function regenMenu():Void + { + for (i in 0...grpMenuShit.members.length) + { + var obj:Alphabet = grpMenuShit.members[0]; + obj.kill(); + grpMenuShit.remove(obj, true); + obj.destroy(); + } + for (num => str in menuItems) + { + var item = new Alphabet(90, 320, Language.getPhrase('pause_$str', str), true); + item.isMenuItem = true; + item.targetY = num; + grpMenuShit.add(item); + if (!PlayState.chartingMode || !PlayState.modchartMode) + item.screenCenter(X); + + if (str == 'Skip Time') + { + skipTimeText = new FlxText(0, 0, 0, '', 64); + skipTimeText.setFormat(Paths.font("vcr.ttf"), 64, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK); + skipTimeText.scrollFactor.set(); + skipTimeText.borderSize = 2; + skipTimeTracker = item; + add(skipTimeText); + + updateSkipTextStuff(); + updateSkipTimeText(); + } + } + + curSelected = 0; + changeSelection(); + } + + function updateSkipTextStuff() + { + if (skipTimeText == null || skipTimeTracker == null) + return; + + skipTimeText.x = skipTimeTracker.x + skipTimeTracker.width + 60; + skipTimeText.y = skipTimeTracker.y; + skipTimeText.visible = (skipTimeTracker.alpha >= 1); + } + + function updateSkipTimeText() + skipTimeText.text = FlxStringUtil.formatTime(Math.max(0, Math.floor(curTime / 1000)), false) + + ' / ' + + FlxStringUtil.formatTime(Math.max(0, Math.floor(music.length / 1000)), false); +} diff --git a/funkinscsource/slushi/winSL/Main.hx b/funkinscsource/slushi/winSL/Main.hx index d132d50..b35f1bf 100644 --- a/funkinscsource/slushi/winSL/Main.hx +++ b/funkinscsource/slushi/winSL/Main.hx @@ -2,7 +2,6 @@ package slushi.winSL; import Sys; import haxe.Timer; - import sys.io.File; import sys.FileSystem; import sys.io.FileInput; @@ -20,62 +19,73 @@ import haxe.io.Path; * * Author: Trock (Modified by Slushi) */ +class Main +{ + public static var finishedStartup:Bool = false; -class Main { - static function clear():Void { - Modules.ModuleUtils.clearConsole(); - } + static function clear():Void + { + Modules.ModuleUtils.clearConsole(); + } - static function startup():Void { - clear(); + static function startup():Void + { + clear(); - Sys.sleep(0.5); - Sys.println('WinSL [${SlushiMain.winSLVersion}] - Running on ${Sys.systemName()}'); - Sys.sleep(1.2); - var userName:String = Sys.environment().get("USERNAME"); - if (userName == null) - userName = Sys.environment().get("USER"); - Sys.println("Started by " + (userName != null ? userName : "an unknown user")); - Sys.sleep(1.2); - Sys.println("Already initialized all Microsoft Windows API functions"); - Sys.sleep(0.6); - // Sys.println('Warning: Possible [MODCHARTS] detected in WinSL/SlushiEngine_${SlushiMain.buildNumber}.vm that may cause an overload and break the Sandbox provided by WinSL.'); - Sys.sleep(0.6); - Sys.println("Loading WinSL environment..."); - WinSLConsoleUtils.printLetterByLetter('Loading internal Modules....Done\n', 0.035); - Sys.sleep(0.6); - WinSLConsoleUtils.printLetterByLetter('Finalizing WinSL environment initialization....Done\n', 0.035); - WinSLConsoleUtils.printLetterByLetter('-------------\n\n', 0.045); - Sys.sleep(0.4); - } + Sys.sleep(0.5); + Sys.println('WinSL [${SlushiMain.sleThingsVersions.winSLVersion}] - Running on ${Sys.systemName()}'); + Sys.sleep(1.2); + var userName:String = Sys.environment().get("USERNAME"); + if (userName == null) + userName = Sys.environment().get("USER"); + Sys.println("Started by " + (userName != null ? userName : "an unknown user")); + Sys.sleep(1.2); + #if windows + Sys.println("Already initialized all Microsoft Windows API functions"); + #else + Sys.println("Cannot initialize Microsoft Windows API functions, platform not supported"); + #end + Sys.sleep(0.6); + // Sys.println('Warning: Possible [MODCHARTS] detected in WinSL/SlushiEngine_${SlushiMain.buildNumber}.vm that may cause an overload and break the Sandbox provided by WinSL.'); + Sys.sleep(0.6); + Sys.println("Loading WinSL environment..."); + WinSLConsoleUtils.printLetterByLetter('Loading internal Modules....Done\n', 0.035); + Sys.sleep(0.6); + WinSLConsoleUtils.printLetterByLetter('Finalizing WinSL environment initialization....Done\n', 0.035); + WinSLConsoleUtils.printLetterByLetter('-------------\n\n', 0.045); + Sys.sleep(0.4); + } - static public function main():Void { - startup(); + static public function main():Void + { + startup(); - var parser = new Parser([ - new Module(ModuleType.TOKENIZER, Others.tokenize), - new Module(ModuleType.EXTRACTOR, Others.extract), - new Module(ModuleType.OPERATOR_HANDLER, Others.process) - ]); + var parser = new Parser([ + new Module(ModuleType.TOKENIZER, Others.tokenize), + new Module(ModuleType.EXTRACTOR, Others.extract), + new Module(ModuleType.OPERATOR_HANDLER, Others.process) + ]); - var stdin = Sys.stdin(); - var stdout = Sys.stdout(); + var stdin = Sys.stdin(); + var stdout = Sys.stdout(); - var cwd = Sys.getCwd() + "/assets/slushiEngineAssets/SLEAssets/WinSL_Assets/"; - var pathStr = Path.join([cwd, 'sandbox']); + var cwd = Sys.getCwd() + "/assets/slushiEngineAssets/WinSL_Assets/"; + var pathStr = Path.join([cwd, 'sandbox']); - if (!FileSystem.exists(pathStr)) { - FileSystem.createDirectory(pathStr); - } + if (!FileSystem.exists(pathStr)) + { + FileSystem.createDirectory(pathStr); + } - var path = FileSystem.exists(pathStr) ? pathStr : FileSystem.fullPath("sandbox"); + var path = FileSystem.exists(pathStr) ? pathStr : FileSystem.fullPath("sandbox"); - var terminal = new Terminal(parser, stdin, stdout, {'path': path, 'sandbox_path': path}); + var terminal = new Terminal(parser, stdin, stdout, {'path': path, 'sandbox_path': path}); - for (module in Modules.getModules()) { - terminal.registerCommandModule(module); - } + for (module in Modules.getModules()) + { + terminal.registerCommandModule(module); + } - terminal.run(); - } -} \ No newline at end of file + terminal.run(); + } +} diff --git a/funkinscsource/slushi/winSL/Modules.hx b/funkinscsource/slushi/winSL/Modules.hx index b40cd00..1d0561d 100644 --- a/funkinscsource/slushi/winSL/Modules.hx +++ b/funkinscsource/slushi/winSL/Modules.hx @@ -4,396 +4,459 @@ import slushi.winSL.termvm.Terminal; import slushi.winSL.termvm.CommandModule; /** - * Custom modules for the WinSL terminal. + * Custom sourced modules for the WinSL terminal. * * Author: Slushi */ - -class Modules { - public static var modules:Array = []; - - public static function getModules():Array { - modules = [ - new CommandModule(["soy"], SoyModule.soy), - new CommandModule(["itsthisforthat", "ittft"], ItsThisForThatModule.itsthisforthat), - new CommandModule(["WriteTheWord", "writetheword"], WriteTheWordModule.writeTheWord), - new CommandModule(["convertSM", "convertsm"], ConvertToFNFModule.main) - ]; - return modules; - } +class Modules +{ + public static var modules:Array = []; + + public static function getModules():Array + { + modules = [ + new CommandModule(["soy"], SoyModule.soy), + new CommandModule(["itsthisforthat", "ittft"], ItsThisForThatModule.itsthisforthat), + new CommandModule(["WriteTheWord", "writetheword"], WriteTheWordModule.writeTheWord), + new CommandModule(["convertSM", "convertsm"], ConvertToFNFModule.main) + ]; + return modules; + } } -class ModuleUtils { - public static function clearConsole():Void { - #if windows - return WinConsoleUtils.clearTerminal(); - #else - Sys.print("\033[3J\033[H\033[2J"); - #end - } - - public static function getSandboxPath():String { - return SlushiMain.getSLEPath("WinSL_Assets/sandbox/"); - } - - public static function getWinSLVersion():String { - return SlushiMain.winSLVersion; - } - - public static function printAlert(text:String, alertType:String):Void { - switch(alertType) { - case "error": - Sys.println("\033[31m" + text + "\033[0m"); - case "warning": - Sys.println("\033[33m" + text + "\033[0m"); - case "success": - Sys.println("\033[32m" + text + "\033[0m"); - case "info": - Sys.println("\033[34m" + text + "\033[0m"); - default: - Sys.println(text); - } - } - - public static function wait(time:Float):Void { - Sys.sleep(time); - } +class ModuleUtils +{ + public static function clearConsole():Void + { + #if windows + return WindowsTerminalCPP.clearTerminal(); + #else + Sys.print("\033[3J\033[H\033[2J"); + #end + } + + public static function getSandboxPath():String + { + return SlushiMain.getSLEPath("WinSL_Assets/sandbox/"); + } + + public static function getWinSLVersion():String + { + return SlushiMain.sleThingsVersions.winSLVersion; + } + + public static function printAlert(text:String, alertType:String):Void + { + switch (alertType) + { + case "error": + Sys.println("\033[31m[ERROR]\033[0m " + text); + case "warning": + Sys.println("\033[33m[WARNING]\033[0m " + text); + case "success": + Sys.println("\033[32m[SUCCESS]\033[0m " + text); + case "info": + Sys.println("\033[34m[INFO]\033[0m " + text); + default: + Sys.println(text); + } + } + + public static function wait(time:Float):Void + { + Sys.sleep(time); + } } -class SoyModule { - public static function soy(terminal:Terminal, command:String, args:Array, metadata:Dynamic):Void { - if(args[0] != null){ - terminal.stdout.writeString("hola " + args[0] + "!\n"); - } - else{ - terminal.stdout.writeString("Necesitas introducir un argumento.\n"); - } - } +class SoyModule +{ + public static function soy(terminal:Terminal, command:String, args:Array, metadata:Dynamic):Void + { + if (args[0] != null) + { + terminal.stdout.writeString("hola " + args[0] + "!\n"); + } + else + { + terminal.stdout.writeString("Necesitas introducir un argumento.\n"); + } + } } -class ItsThisForThatModule extends ModuleUtils { - public static function itsthisforthat(terminal:Terminal, command:String, args:Array, metadata:Dynamic):Void { - var urlToRequest:String = "https://itsthisforthat.com/api.php?text"; - var http = new Http(urlToRequest); - - http.onData = function(response:String) { - terminal.stdout.writeString(response + "\n"); - } - - http.onError = function(error:String) { - printAlert('Error while getting [itsthisforthat.com] API data: ' + error, 'error'); - } - - http.request(); - } +class ItsThisForThatModule extends ModuleUtils +{ + public static function itsthisforthat(terminal:Terminal, command:String, args:Array, metadata:Dynamic):Void + { + var urlToRequest:String = "https://itsthisforthat.com/api.php?text"; + var http = new Http(urlToRequest); + + http.onData = function(response:String) + { + terminal.stdout.writeString(response + "\n"); + } + + http.onError = function(error:String) + { + printAlert('Error while getting [itsthisforthat.com] API data: ' + error, 'error'); + } + + http.request(); + } } -class WriteTheWordModule extends ModuleUtils { - - static var points = 0; +class WriteTheWordModule extends ModuleUtils +{ + static var points = 0; - static var terminalForGame:Terminal; + static var terminalForGame:Terminal; - public static function writeTheWord(terminal:Terminal, command:String, args:Array, metadata:Dynamic):Void { + public static function writeTheWord(terminal:Terminal, command:String, args:Array, metadata:Dynamic):Void + { + terminalForGame = terminal; - terminalForGame = terminal; + terminal.stdout.writeString("Welcome to Write The Word!\n"); + terminal.stdout.writeString("Type the word as fast as you can, and accumulate as many points as possible.\n"); - terminal.stdout.writeString("Welcome to Write The Word!\n"); - terminal.stdout.writeString("Type the word as fast as you can, and accumulate as many points as possible.\n"); + wait(3); - wait(3); + clearConsole(); - clearConsole(); + game(); - game(); + wait(0.8); - wait(0.8); + terminal.stdout.writeString('You want to continue? (y/n) '); - terminal.stdout.writeString('You want to continue? (y/n) '); + if (terminal.stdin.readLine().toString() == 'y') + { + game(); + } + else + { + terminal.stdout.writeString("Your total points: " + points + "\n"); + terminal.stdout.writeString('Bye!\n\n'); + } + } - if (terminal.stdin.readLine().toString() == 'y') { - game(); - } - else { - terminal.stdout.writeString("Your total points: " + points + "\n"); - terminal.stdout.writeString('Bye!\n\n'); - } - } + static function game():Void + { + var startTime:Float; + var endTime:Float; + var input:String; - static function game():Void { - var startTime:Float; - var endTime:Float; - var input:String; + var word = getWord(); - var word = getWord(); + terminalForGame.stdout.writeString("Press Enter to start\n"); - terminalForGame.stdout.writeString("Press Enter to start\n"); + terminalForGame.stdin.readLine(); - terminalForGame.stdin.readLine(); + wait(1); - wait(1); + terminalForGame.stdout.writeString("Go!\n"); - terminalForGame.stdout.writeString("Go!\n"); + terminalForGame.stdout.writeString("Type the word!: " + word + "\n--> "); - terminalForGame.stdout.writeString("Type the word!: " + word + "\n--> "); + startTime = Date.now().getTime(); - startTime = Date.now().getTime(); + input = terminalForGame.stdin.readLine(); - input = terminalForGame.stdin.readLine(); + endTime = Date.now().getTime(); - endTime = Date.now().getTime(); + var elapsedTime = endTime - startTime; - var elapsedTime = endTime - startTime; + var finalTime = Math.floor(elapsedTime / 1000); - var finalTime = Math.floor(elapsedTime / 1000); + if (input == word) + { + if (elapsedTime < 1000) + { + terminalForGame.stdout.writeString('Great job! you took ' + finalTime + ' seconds, +10 points\n'); + points += 10; + } + else if (elapsedTime < 2000) + { + terminalForGame.stdout.writeString('Good! you took ' + finalTime + ' seconds, +7 points\n'); + points += 7; + } + else if (elapsedTime < 3000) + { + terminalForGame.stdout.writeString('Well done! you took ' + finalTime + ' seconds, +5 points\n'); + points += 5; + } + else + { + terminalForGame.stdout.writeString('You took ' + finalTime + ' seconds, +2 points\n'); + } + } + else + { + terminalForGame.stdout.writeString('Wrong! The word was ' + word + ', you took ' + finalTime + ' seconds, -5 points\n'); + points -= 5; + } + } - if (input == word) { - if (elapsedTime < 1000) { - terminalForGame.stdout.writeString('Great job! you took ' + finalTime + ' seconds, +10 points\n'); - points += 10; - } else if (elapsedTime < 2000) { - terminalForGame.stdout.writeString('Good! you took ' + finalTime + ' seconds, +7 points\n'); - points += 7; - } else if (elapsedTime < 3000) { - terminalForGame.stdout.writeString('Well done! you took ' + finalTime + ' seconds, +5 points\n'); - points += 5; - } - else { - terminalForGame.stdout.writeString('You took ' + finalTime + ' seconds, +2 points\n'); - } - } else { - terminalForGame.stdout.writeString('Wrong! The word was ' + word + ', you took ' + finalTime + ' seconds, -5 points\n'); - points -= 5; - } - } + static function getWord():String + { + var urlToRequest:String = "https://random-word-api.herokuapp.com/word"; + var http = new Http(urlToRequest); + var word:String = null; - static function getWord():String { - var urlToRequest:String = "https://random-word-api.herokuapp.com/word"; - var http = new Http(urlToRequest); - var word:String = null; + http.onData = function(response:String) + { + word = response; + } - http.onData = function(response:String) { - word = response; - } - - http.onError = function(error:String) { - printAlert('Error while getting [random-word-api.herokuapp.com] API data: ' + error, 'error'); - } + http.onError = function(error:String) + { + printAlert('Error while getting [random-word-api.herokuapp.com] API data: ' + error, 'error'); + } - http.request(); + http.request(); - final finalWord = word.replace('["', '').replace('"]', ''); + final finalWord = word.replace('["', '').replace('"]', ''); - return finalWord; - } + return finalWord; + } } -class ConvertToFNFModule { - static var curSMFile:SMFile; - static var finalFNFFile:String = ''; - static var finalFNFFileName:String = ''; - static var finalFNFFileNameLowerCase:String = ''; - static var finalDifficulty:String = ''; - static var finalSpeed:Float = 1.0; - - public static function main(terminal:Terminal, command:String, args:Array, metadata:Dynamic):Void { - if (args[0] == null) { - return terminal.stdout.writeString("You need to specify the path to an SM file.\n"); - } - - var smFilePath:String = "./engineUtils/SMToConvert/" + args[0]; - - if (!smFilePath.endsWith(".sm")) { - return terminal.stdout.writeString("You need to specify a .sm file.\n"); - } - - if (!FileSystem.exists(smFilePath)) { - terminal.stdout.writeString("File not found: [" + args[0] + "]\n"); - terminal.stdout.writeString('You can put it in "engineUtils/SMToConvert"\n'); - return; - } - - terminal.stdout.writeString("Welcome to StepMania to FNF converter v1.3!\n"); - - terminal.stdout.writeString("Loading SM file...\n"); - Sys.sleep(1.2); - - try { - parseSMFile(smFilePath); - } - catch (e) { - terminal.stdout.writeString("Error: " + e.toString() + "\n"); - return; - } - - terminal.stdout.writeString("Enter the desired song name (press Enter to use SM file name): "); - var songName:String = terminal.stdin.readLine().toString(); - if (songName == "") { - songName = curSMFile.title; - } - - while (true) { - terminal.stdout.writeString("Enter the desired difficulty: "); - var difficulty:String = terminal.stdin.readLine().toString(); - if (difficulty == "") { - return terminal.stdout.writeString("You need to specify a difficulty.\n"); - } - else{ - finalDifficulty = difficulty; - break; - } - } - - terminal.stdout.writeString("Enter the desired speed (press Enter to use 3.0): "); - var speed:String = terminal.stdin.readLine().toString(); - if (speed == "") { - finalSpeed = 3.0; - } - else{ - finalSpeed = Std.parseFloat(speed); - } - - Sys.sleep(1.2); - - terminal.stdout.writeString("Generating FNF chart...\n"); - generateChart(songName); - - while (true) { - terminal.stdout.writeString("Do you like delete the original SM file? (y/n): "); - if (terminal.stdin.readLine().toString() == "y") { - if(FileSystem.exists(smFilePath)) - FileSystem.deleteFile(smFilePath); - terminal.stdout.writeString("Done!\n"); - break; - } - else { - break; - } - } - - while (true) { - terminal.stdout.writeString("Do you want create the rest of the files for the FNF Song (like week JSON)? (y/n): "); - if (terminal.stdin.readLine().toString() == "y") { - createMoreFiles(); - terminal.stdout.writeString("Done!\n"); - break; - } - else { - break; - } - } - } - - static function parseSMFile(smFilePath:String):Void { - var smContent:String = File.getContent(smFilePath); - smContent = smContent.replace('\r\n', '\n'); - curSMFile = new SMFile(smContent); - - Sys.println("Song name: " + curSMFile.title); - Sys.println("Song BPMS: " + curSMFile.bpms); - Sys.println("Song offset: " + curSMFile.chartOffset + "\n"); - } - - static function generateChart(songName:String):Void { - var cfg: SongConfig = { - song: (songName != '') ? songName : 'SMSong', - speed: finalSpeed, // You can set the default speed or ask the user for input - player1: 'bf', - player2: 'gf', - gfVersion: 'gf' - }; - - var fnfchart:Dynamic = curSMFile.makeFNFChart(0, cfg, true); - - var jsonContent:String = haxe.Json.stringify(fnfchart, null, '\t'); - - var outputFileName:String = cfg.song; - var outputFilePath:String = "./engineUtils/SMToConvert/" + outputFileName.toLowerCase() + ".json"; - - if (FileSystem.exists(outputFilePath)) { - FileSystem.deleteFile(outputFilePath); - Sys.println("Deleted existing file: " + outputFilePath + "\n"); - } - - File.saveContent(outputFilePath, jsonContent); - - finalFNFFileNameLowerCase = outputFileName.toLowerCase().replace(' ', '-'); - finalFNFFileName = outputFileName; - finalFNFFile = outputFilePath; - - Sys.println("Conversion complete! Check the output file\n"); - Sys.sleep(1.4); - } - - static function createMoreFiles() { - var modsChartsFolder:String = './mods/data/songs/'; - var modsWeeksFolder:String = './mods/data/weeks/'; - var modsSongOGGFolder:String = './mods/songs/'; - var modsLuaFolder:String = './mods/scripts/songs/'; - var finalPath:String = ''; - - var oggFile = ""; - - var directory = FileSystem.readDirectory("./engineUtils/SMToConvert"); - - for (file in directory) { - if(file.endsWith(".ogg")) { - oggFile = file; - break; - } - } - - if(FileSystem.exists(finalFNFFile)) { - if(!FileSystem.exists('$modsChartsFolder$finalFNFFileNameLowerCase')){ - FileSystem.createDirectory('$modsChartsFolder$finalFNFFileNameLowerCase'); - } - finalPath = '$modsChartsFolder$finalFNFFileNameLowerCase/'; - File.copy(finalFNFFile, '$finalPath$finalFNFFileNameLowerCase-$finalDifficulty.json'); - Sys.println("Copied " + finalFNFFile + " to " + finalPath + finalFNFFileNameLowerCase + "-" + finalDifficulty + ".json"); - Sys.sleep(0.8); - } - - if(FileSystem.exists("./engineUtils/SMToConvert/" + oggFile)) { - { - if(!FileSystem.exists('$modsSongOGGFolder$finalFNFFileNameLowerCase')){ - FileSystem.createDirectory('$modsSongOGGFolder$finalFNFFileNameLowerCase'); - } - finalPath = '$modsSongOGGFolder$finalFNFFileNameLowerCase/'; - File.copy("./engineUtils/SMToConvert/" + oggFile, '$finalPath' + 'Inst.ogg'); - Sys.println("Copied " + "./engineUtils/SMToConvert/" + oggFile + " to " + finalPath + 'Inst.ogg'); - Sys.sleep(0.8); - } - } - else { - Sys.println("File not found: [" + oggFile + "]\n"); - return; - } +typedef WeekJSONFile = +{ + // JSON variables + var songs:Array; + + var weekBefore:String; + var storyName:String; + var weekName:String; + var freeplayColor:Array; + var startUnlocked:Bool; + var hideStoryMode:Bool; + var hideFreeplay:Bool; + var difficulties:String; + var blockOpponentMode:Null; +} - var weekStructure:String = ' +class ConvertToFNFModule +{ + static var converterVersion = "1.3.5"; + static var curSMFile:SMFile; + static var finalFNFFile:String = ""; + static var finalFNFFileName:String = ""; + static var finalFNFFileNameLowerCase:String = ""; + static var finalDifficulty:String = ""; + static var finalSpeed:Float = 3.0; + static var smFilePath:String = "./slEngineUtils/SMToConvert/"; + + public static function main(terminal:Terminal, command:String, args:Array, metadata:Dynamic):Void + { + if (args[0] == null) + { + return terminal.stdout.writeString("You need to specify the path to an SM file.\n"); + } + + smFilePath += args[0]; + + if (!smFilePath.endsWith(".sm")) + { + return terminal.stdout.writeString("You need to specify a .sm file.\n"); + } + + if (!FileSystem.exists(smFilePath)) + { + terminal.stdout.writeString("File not found: [" + args[0] + "]\n"); + terminal.stdout.writeString('You can put it in "slEngineUtils/SMToConvert"\n'); + return; + } + + terminal.stdout.writeString("Welcome to StepMania to FNF converter v" + converterVersion + "!\n"); + + terminal.stdout.writeString("Loading SM file...\n"); + wait(1.2); + + try + { + parseSMFile(smFilePath); + } + catch (e) + { + terminal.stdout.writeString("Error: " + e.toString() + "\n"); + return; + } + + terminal.stdout.writeString("Enter the desired song name (press Enter to use SM file name): "); + var songName:String = terminal.stdin.readLine().toString(); + if (songName == "") + { + songName = curSMFile.title; + } + + while (true) + { + terminal.stdout.writeString("Enter the desired difficulty: "); + var difficulty:String = terminal.stdin.readLine().toString().toLowerCase(); + if (difficulty != "") + { + finalDifficulty = difficulty; + break; + } + } + + terminal.stdout.writeString("Enter the desired speed (press Enter to use 3.0): "); + var speed:String = terminal.stdin.readLine().toString(); + if (speed != "") + { + finalSpeed = Std.parseFloat(speed); + } + + wait(1.2); + + terminal.stdout.writeString("Generating FNF chart...\n"); + generateChart(songName); + + while (true) + { + terminal.stdout.writeString("Do you want create the rest of the files for the FNF Song (like week JSON)? (y/n): "); + if (terminal.stdin.readLine().toString() == "y") + { + createMoreFiles(); + terminal.stdout.writeString("Done!\n"); + break; + } + if (terminal.stdin.readLine().toString() == "n") + { + terminal.stdout.writeString("Finished!\n"); + break; + } + } + } + + static function parseSMFile(smFilePath:String):Void + { + var smContent:String = File.getContent(smFilePath); + smContent = smContent.replace('\r\n', '\n'); + curSMFile = new SMFile(smContent); + + Sys.println("SM name: " + curSMFile.title); + Sys.println("SM BPMS: " + curSMFile.bpms.join(', ')); + Sys.println("SM offset: " + curSMFile.chartOffset + "\n"); + } + + static function generateChart(songName:String):Void + { + var cfg:SongConfig = { + song: (songName != '') ? songName : 'SMSong', + speed: finalSpeed, + player1: 'bf', + player2: 'gf', + gfVersion: 'gf' + }; + + var fnfchart:Dynamic = curSMFile.makeFNFChart(0, cfg, true); + var jsonContent:String = Json.stringify(fnfchart, null, '\t'); + + var outputFileName:String = cfg.song; + var outputFilePath:String = "./slEngineUtils/SMToConvert/converted/" + outputFileName.toLowerCase() + ".json"; + + if (FileSystem.exists(outputFilePath)) + { + FileSystem.deleteFile(outputFilePath); + Sys.println("Deleted existing file [" + outputFilePath + "]"); + } + + if (!FileSystem.exists("./slEngineUtils/SMToConvert/converted")) { - "songs": [ - ["$finalFNFFileName", "gf", [0, 0, 0]] - ], - - "difficulties": "$finalDifficulty", - - "storyName": "", - "weekBefore": "none", - "weekName": "", - "startUnlocked": true, - "hideStoryMode": true, - "hideFreeplay": false, - }'; - - File.saveContent('$modsWeeksFolder$finalFNFFileNameLowerCase.json', weekStructure); - Sys.println('Created $modsWeeksFolder$finalFNFFileNameLowerCase.json file'); - Sys.sleep(0.8); - - var luaStructure:String = '-- Generated by StepMania to FNF Converter v1.3 (By Slushi) --\n\nfunction onCreatePost()\nend\n\nfunction onBeatHit()\nend\n\nfunction onUpdatePost(elapsed)\nend'; - if(!FileSystem.exists('$modsLuaFolder$finalFNFFileNameLowerCase')) { - FileSystem.createDirectory('$modsLuaFolder$finalFNFFileNameLowerCase'); + FileSystem.createDirectory("./slEngineUtils/SMToConvert/converted"); } - File.saveContent('$modsLuaFolder$finalFNFFileNameLowerCase/modchart.lua', luaStructure); - Sys.println('Created $modsLuaFolder$finalFNFFileNameLowerCase/modchart.lua file'); - } -} \ No newline at end of file + + File.saveContent(outputFilePath, jsonContent); + + finalFNFFileNameLowerCase = outputFileName.toLowerCase().replace(' ', '-'); + finalFNFFileName = outputFileName; + finalFNFFile = outputFilePath; + + Sys.println("Conversion complete in [" + outputFilePath + "]!\n"); + wait(1.4); + } + + static function createMoreFiles() + { + var modsChartsFolder:String = "./mods/data/songs/"; + var modsWeeksFolder:String = "./mods/data/weeks/"; + var modsSongOGGFolder:String = "./mods/songs/"; + var modsLuaFolder:String = "./mods/scripts/songs/"; + var finalPath:String = ""; + var oggFile = ""; + + var directory = FileSystem.readDirectory("./slEngineUtils/SMToConvert"); + + for (file in directory) + { + if (file.endsWith(".ogg")) + { + oggFile = file; + break; + } + } + + if (FileSystem.exists(finalFNFFile)) + { + if (!FileSystem.exists('$modsChartsFolder$finalFNFFileNameLowerCase')) + { + FileSystem.createDirectory('$modsChartsFolder$finalFNFFileNameLowerCase'); + } + finalPath = '$modsChartsFolder$finalFNFFileNameLowerCase/'; + File.copy(finalFNFFile, '$finalPath$finalFNFFileNameLowerCase-$finalDifficulty.json'); + Sys.println("Copied [" + finalFNFFile + "] to [" + finalPath + finalFNFFileNameLowerCase + "-" + finalDifficulty + ".json]"); + wait(0.8); + } + + if (FileSystem.exists("./slEngineUtils/SMToConvert/" + oggFile)) + { + { + if (!FileSystem.exists('$modsSongOGGFolder$finalFNFFileNameLowerCase')) + { + FileSystem.createDirectory('$modsSongOGGFolder$finalFNFFileNameLowerCase'); + } + finalPath = '$modsSongOGGFolder$finalFNFFileNameLowerCase/'; + File.copy("./slEngineUtils/SMToConvert/" + oggFile, '$finalPath' + 'Inst.ogg'); + Sys.println("Copied " + "[./slEngineUtils/SMToConvert/" + oggFile + "] to [" + finalPath + "Inst.ogg]"); + wait(0.8); + } + } + else + { + Sys.println("OGG file not found: [" + oggFile + "]"); + Sys.println('You can put it in [$modsSongOGGFolder$finalFNFFileNameLowerCase/] and rename it to "Inst.ogg"'); + Sys.println("Continuing...\n"); + } + + /** + * All this is just to be able to format the JSON + * file correctly, instead of being a string that is stored in a JSON file. + */ + var weekJsonStructure:WeekJSONFile = { + songs: [[finalFNFFileName, "gf", [0, 0, 0]]], + + difficulties: finalDifficulty, + storyName: "", + weekBefore: "none", + weekName: finalFNFFileNameLowerCase + "-week", + startUnlocked: true, + hideStoryMode: true, + hideFreeplay: false, + freeplayColor: [0, 0, 0], + blockOpponentMode: true + } + + File.saveContent('$modsWeeksFolder$finalFNFFileNameLowerCase.json', Json.stringify(weekJsonStructure)); + Sys.println('Created [$modsWeeksFolder$finalFNFFileNameLowerCase.json] file'); + wait(0.8); + + var luaStructure:String = '-- Generated by StepMania to FNF Converter v${converterVersion} (By Slushi) --\n\nfunction onCreatePost()\nend\n\nfunction onBeatHit()\nend\n\nfunction onStepHit()\nend\n\nfunction onUpdatePost(elapsed)\nend'; + if (!FileSystem.exists('$modsLuaFolder$finalFNFFileNameLowerCase')) + { + FileSystem.createDirectory('$modsLuaFolder$finalFNFFileNameLowerCase'); + } + File.saveContent('$modsLuaFolder$finalFNFFileNameLowerCase/modchart.lua', luaStructure); + Sys.println('Created [$modsLuaFolder$finalFNFFileNameLowerCase/modchart.lua] file'); + } +} diff --git a/funkinscsource/slushi/winSL/WinSLConsoleUtils.hx b/funkinscsource/slushi/winSL/WinSLConsoleUtils.hx index 4a2c4dc..d90c338 100644 --- a/funkinscsource/slushi/winSL/WinSLConsoleUtils.hx +++ b/funkinscsource/slushi/winSL/WinSLConsoleUtils.hx @@ -16,12 +16,12 @@ class WinSLConsoleUtils FlxG.sound.music.stop(); } Sys.println("\033[0m"); - WinConsoleUtils.allocConsole(); - WinConsoleUtils.setConsoleTitle('WinSL ${SlushiMain.winSLVersion}'); - WinConsoleUtils.setConsoleWindowIcon(SlushiMain.getSLEPath("WinSL_Assets/windowIcon.ico")); - WinConsoleUtils.centerConsoleWindow(); - WinConsoleUtils.setWinConsoleColor(); - WinConsoleUtils.hideMainWindow(); + WindowsTerminalCPP.allocConsole(); + WindowsTerminalCPP.setConsoleTitle('WinSL [${SlushiMain.sleThingsVersions.winSLVersion}]'); + WindowsTerminalCPP.setConsoleWindowIcon(SlushiMain.getSLEPath("WinSL_Assets/windowIcon.ico")); + WindowsTerminalCPP.centerConsoleWindow(); + WindowsTerminalCPP.setWinConsoleColor(); + WindowsTerminalCPP.hideMainWindow(); Main.main(); #end } diff --git a/funkinscsource/slushi/winSL/WinSLCrashHandler.hx b/funkinscsource/slushi/winSL/WinSLCrashHandler.hx index 4bb3a62..2814adf 100644 --- a/funkinscsource/slushi/winSL/WinSLCrashHandler.hx +++ b/funkinscsource/slushi/winSL/WinSLCrashHandler.hx @@ -67,6 +67,6 @@ class WinSLCrashHandler { #end } - Sys.exit(1); + System.exit(1); } } \ No newline at end of file diff --git a/funkinscsource/slushi/winSL/import.hx b/funkinscsource/slushi/winSL/import.hx index c948c47..fc5caad 100644 --- a/funkinscsource/slushi/winSL/import.hx +++ b/funkinscsource/slushi/winSL/import.hx @@ -3,3 +3,4 @@ import slushi.winSL.Modules.ModuleUtils.*; // ConvertToFNFModule import slushi.slushiUtils.stepManiaTools.*; import slushi.slushiUtils.stepManiaTools.SMFile.SongConfig; +import haxe.Json; diff --git a/funkinscsource/slushi/winSL/termvm/Terminal.hx b/funkinscsource/slushi/winSL/termvm/Terminal.hx index 8062fb9..d26c938 100644 --- a/funkinscsource/slushi/winSL/termvm/Terminal.hx +++ b/funkinscsource/slushi/winSL/termvm/Terminal.hx @@ -8,14 +8,15 @@ import haxe.io.Output; import haxe.io.Bytes; import slushi.winSL.termvm.Parser; import haxe.CallStack; +#if (fuzzaldrin && WINSL_SUGGEST_COMMAND) import fuzzaldrin.Fuzzaldrin; +#end /** * The main class of WinSL, the terminal for SLE. * * Author: Trock (Modified by Slushi) */ - class Terminal { public var parser:Parser; @@ -27,7 +28,8 @@ class Terminal public var numberOfCrashes:Int = 0; public var commandRoot:String = ""; - public var defaultString:String = "> "; + public var defaultString:String = "\x1b[38;5;236m>\x1b[0m "; + public static var instance:Terminal = null; public function new(parser:Parser, stdin:Input, stdout:Output, ?metadata:Dynamic) @@ -45,7 +47,7 @@ class Terminal registerCommandModule(new CommandModule(["exit", "EXIT"], ExitModule.execute)); registerCommandModule(new CommandModule(["cls", "clear", "CLS", "CLEAR"], ClearModule.execute)); registerCommandModule(new CommandModule(["stop", "STOP"], StopModule.execute)); - registerCommandModule(new CommandModule(["resetVM", "resetvm", "backToVM", "backtovm", "reset"], ResetVMModule.execute)); + registerCommandModule(new CommandModule(["resetVM", "resetvm", "backToVM", "backtovm", "reset"], ResetVMModule.execute)); registerCommandModule(new CommandModule(["set", "SET"], SetVariableModule.execute)); registerCommandModule(new CommandModule(["get", "GET"], GetVariableModule.execute)); } @@ -78,23 +80,30 @@ class Terminal return commandNames; } - public function runOnce():Array { - stdout.writeString(defaultString); - stdout.flush(); - try { - var commandLine:String = stdin.readLine(); - if (commandLine != null && commandLine.length > 0 && commandLine != "") { - var parsedCommands:Array = parser.parse(commandLine); - for (parsedCommand in parsedCommands) { - commandRoot = parsedCommand.command[0]; - var args:Array = processArguments(parsedCommand.command.slice(1)); - - if (commandModules.exists(commandRoot)) { - var module:CommandModule = commandModules.get(commandRoot); - module.execute(this, commandRoot, args, metadata); - } else { + public function runOnce():Array + { + stdout.writeString(defaultString); + stdout.flush(); + try + { + var commandLine:String = stdin.readLine(); + if (commandLine != null && commandLine.length > 0 && commandLine != "") + { + var parsedCommands:Array = parser.parse(commandLine); + for (parsedCommand in parsedCommands) + { + commandRoot = parsedCommand.command[0]; + var args:Array = processArguments(parsedCommand.command.slice(1)); + + if (commandModules.exists(commandRoot)) + { + var module:CommandModule = commandModules.get(commandRoot); + module.execute(this, commandRoot, args, metadata); + } + else + { #if (fuzzaldrin && WINSL_SUGGEST_COMMAND) - var candidates = extractCommandNames(commandModules); + var candidates = extractCommandNames(commandModules); var results = Fuzzaldrin.filter(candidates, commandRoot); if (results.length > 0) stdout.writeString("Command " + commandRoot + " not found. Did you mean: \"" + results[0] + "\"?\n"); @@ -103,19 +112,22 @@ class Terminal #else stdout.writeString("Command " + commandRoot + " not found.\n"); #end - } - } - stdout.flush(); - return parsedCommands; - } - else { - stdout.writeString(""); - } - } catch (e:Eof) { - getCrashHandler(e); - } - return []; - } + } + } + stdout.flush(); + return parsedCommands; + } + else + { + stdout.writeString(""); + } + } + catch (e:Eof) + { + getCrashHandler(e); + } + return []; + } public function run():Void { @@ -132,23 +144,29 @@ class Terminal } } - private function processArguments(args:Array):Array { - return args.map(function(arg:String):String { - var regExp = ~/^\$\{(.+)\}$/; - var result:String = arg; - if (regExp.match(arg)) { - var varName:String = regExp.replace(arg, "$1"); - var value:Dynamic = getVariable(varName); - if (value != null) { - result = value.toString(); - } else { - result = "NullVar"; - stdout.writeString("\x1b[38;5;235mVariable " + varName + " not found.\x1b[0m\n"); - } - } - return result; - }); - } + private function processArguments(args:Array):Array + { + return args.map(function(arg:String):String + { + var regExp = ~/^\$\{(.+)\}$/; + var result:String = arg; + if (regExp.match(arg)) + { + var varName:String = regExp.replace(arg, "$1"); + var value:Dynamic = getVariable(varName); + if (value != null) + { + result = value.toString(); + } + else + { + result = "NullVar"; + stdout.writeString("\x1b[38;5;235mVariable " + varName + " not found.\x1b[0m\n"); + } + } + return result; + }); + } function getCrashHandler(input:Dynamic) { @@ -158,7 +176,7 @@ class Terminal { WinSLCrashHandler.onVMCrash(input, true); } - Sys.println('\n\x1b[38;5;236m-------\x1b[0m\n\x1b[38;5;1mWinSL Critical Error!\x1b[0m\nERROR: $input\n\x1b[38;5;236m-------\x1b[0m\nCall Stack:\n${getSomeInfoOfCrash()}\n\n'); + Sys.println('\n\x1b[38;5;236m-------\x1b[0m\n\x1b[38;5;1mWinSL Critical Error!\x1b[0m\n\x1b[38;5;1mERROR:\x1b[0m $input\n\nCall Stack:\n${getSomeInfoOfCrash()}\x1b[38;5;236m-------\x1b[0m\n'); } function getSomeInfoOfCrash():String @@ -185,14 +203,14 @@ class Terminal /** * Internal or default commands for the terminal. */ - class ExitModule { public static function execute(terminal:Terminal, commandRoot:String, args:Array, metadata:Dynamic):Void { terminal.stdout.writeString("Bye!\n"); Sys.sleep(1.2); - Sys.exit(0); + slushi.winSL.Modules.ModuleUtils.clearConsole(); + System.exit(0); } } @@ -208,7 +226,7 @@ class StopModule { public static function execute(terminal:Terminal, command:String, args:Array, metadata:Dynamic):Void { - Sys.exit(0); + System.exit(0); } } @@ -216,11 +234,12 @@ class SetVariableModule { public static function execute(terminal:Terminal, command:String, args:Array, metadata:Dynamic):Void { - if (args.length != 2 || args[0] == null || args[1] == "") { - terminal.stdout.writeString("Usage: set \n"); - return; - } - + if (args.length != 2 || args[0] == null || args[1] == "") + { + terminal.stdout.writeString("Usage: set \n"); + return; + } + terminal.setVariable(args[0], args[1]); } } @@ -233,12 +252,13 @@ class GetVariableModule } } -class ResetVMModule { - public static function execute(terminal:Terminal, command:String, args:Array, metadata:Dynamic):Void { - - terminal.stdout.writeString("Resetting VM and exiting of WinSL terminal...\n"); - Sys.sleep(2); +class ResetVMModule +{ + public static function execute(terminal:Terminal, command:String, args:Array, metadata:Dynamic):Void + { + terminal.stdout.writeString("Resetting VM and exiting of WinSL terminal...\n"); + Sys.sleep(2); CustomFuncs.realResetGame(); - Sys.exit(0); - } -} \ No newline at end of file + System.exit(0); + } +} diff --git a/funkinscsource/slushi/windowThings/WindowFuncs.hx b/funkinscsource/slushi/windowThings/WindowFuncs.hx index 72f2545..4534ede 100644 --- a/funkinscsource/slushi/windowThings/WindowFuncs.hx +++ b/funkinscsource/slushi/windowThings/WindowFuncs.hx @@ -115,6 +115,12 @@ class WindowFuncs #end } + public static function centerWindow() + { + setWinPositionInX(Std.int((getScreenSizeInWidth() - getWindowSizeInWidth()) / 2)); + setWinPositionInY(Std.int((getScreenSizeInHeight() - getWindowSizeInHeight()) / 2)); + } + public static function doTweenWindowAlpha(toValue:Float, duration:Float, ease:String = "linear") { #if windows @@ -145,6 +151,17 @@ class WindowFuncs } } + // public static function doubleWindowTweenX(offset:Float, duration:Float, ease:String):Void + // { + // var startX:Int = getWindowPositionInX(); + + // var numTween:NumTween = FlxTween.num(startX + offset, startX, duration, {ease: psychlua.LuaUtils.getTweenEaseByString(ease)}); + // numTween.onUpdate = function(twn:FlxTween) + // { + // Application.current.window.x -= Std.int(numTween.value); + // } + // } + public static function resetWindowParameters() { #if windows @@ -153,12 +170,7 @@ class WindowFuncs if (!Application.current.window.maximized || !Application.current.window.fullscreen) { - #if windows - CppAPI.centerWindow(); - #else - setWinPositionInX(Std.int((getScreenSizeInWidth() - getWindowSizeInWidth()) / 2)); - setWinPositionInY(Std.int((getScreenSizeInHeight() - getWindowSizeInHeight()) / 2)); - #end + centerWindow(); } if (!Application.current.window.resizable) diff --git a/funkinscsource/slushi/windows/CppAPI.hx b/funkinscsource/slushi/windows/CppAPI.hx index e7646fe..8a21052 100644 --- a/funkinscsource/slushi/windows/CppAPI.hx +++ b/funkinscsource/slushi/windows/CppAPI.hx @@ -6,15 +6,9 @@ package slushi.windows; * * Author: Slushi */ - class CppAPI { #if (windows && cpp) - public static function screenCapture(path:String) - { - WindowsCPP.windowsScreenShot(path); - } - public static function showMessageBox(message:String, caption:String, icon:MessageBoxIcon = MSG_WARNING) { WindowsCPP.showMessageBox(caption, message, icon); @@ -50,11 +44,6 @@ class CppAPI WindowsCPP._setWindowLayered(); } - public static function centerWindow() - { - WindowsCPP.centerWindow(); - } - public static function setSlushiColorToWindow() { return WindowsCPP.setSlushiWindowColor(); @@ -66,6 +55,11 @@ class CppAPI } #if SLUSHI_CPP_CODE + public static function screenCapture(path:String) + { + WindowsCPP.windowsScreenShot(path); + } + public static function hideTaskbar(hide:Bool) { WindowsCPP.hideTaskbar(hide); diff --git a/funkinscsource/slushi/windows/ProgramRespondingUtil.hx b/funkinscsource/slushi/windows/ProgramRespondingUtil.hx deleted file mode 100644 index adec8e1..0000000 --- a/funkinscsource/slushi/windows/ProgramRespondingUtil.hx +++ /dev/null @@ -1,60 +0,0 @@ -package slushi.windows; - -#if windows -@:cppFileCode(' -#include -#include -#include -#include -#include - -#define TIMEOUT 5000 - -bool IsWindowResponsive(HWND hwnd, DWORD timeoutMs) { - LRESULT result = SendMessageTimeout( - hwnd, - WM_NULL, - 0, 0, - SMTO_ABORTIFHUNG, - timeoutMs, - nullptr - ); - - return (result != 0); -} - -void CheckIfWindowResponsive(HWND hwnd) { - while (true) { - std::this_thread::sleep_for(std::chrono::seconds(10)); - - if (!IsWindowResponsive(hwnd, TIMEOUT)) { - std::cout << "[C++ Function - CheckIfWindowResponsive] The engine window is not responding!" << std::endl; - int response = MessageBox(hwnd, - "The engine window is not responding. Do you want to close it?", - "Slushi Engine [C++] - Info", - MB_ICONINFORMATION | MB_YESNO); - - if (response == IDNO) { - PostMessage(hwnd, WM_CLOSE, 0, 0); - break; - } - } - } -} -') -#end -class ProgramRespondingUtil -{ - #if windows - @:functionCode(' - HWND hwnd = GetActiveWindow(); - - // Crear un hilo separado para monitorear la ventana ya existente - std::thread monitorThread(CheckIfWindowResponsive, hwnd); - monitorThread.detach(); // Ejecutar en segundo plano - ') - public static function initThread() - { - } - #end -} diff --git a/funkinscsource/slushi/windows/WindowsCPP.hx b/funkinscsource/slushi/windows/WindowsCPP.hx index ae840b3..debc2fe 100644 --- a/funkinscsource/slushi/windows/WindowsCPP.hx +++ b/funkinscsource/slushi/windows/WindowsCPP.hx @@ -9,6 +9,7 @@ package slushi.windows; * Author: Slushi */ // Windows API for Haxe v1.0.0 + @:buildXml(' @@ -170,6 +171,21 @@ int screenCapture(int x, int y, int w, int h, LPCSTR fname) class WindowsCPP { #if windows + @:functionCode(' + HMODULE ntdll = GetModuleHandleA("ntdll.dll"); + if (ntdll) { + void* wine_get_version = GetProcAddress(ntdll, "wine_get_version"); + if (wine_get_version) { + return true; + } + } + return false; + ') + public static function detectWine():Bool + { + return false; + } + @:functionCode(' MessageBox(GET_ENGINE_WINDOW(), message, caption, icon | MB_SETFOREGROUND); ') @@ -177,6 +193,14 @@ class WindowsCPP { } + @:functionCode(' + // Play a Beep sound, in the computer default sound device (not the motherboard speaker), with the given frequency and duration + Beep(freq, duration); + ') + public static function beep(freq:Int, duration:Int) + { + } + @:functionCode(' globalWindowTitle = windowTitle; ') @@ -261,9 +285,37 @@ class WindowsCPP { } + // @:functionCode(' + // HWND window = GET_ENGINE_WINDOW(); + + // COLORREF color = 0; + + // // Obtener el color del borde de la ventana (atributo 34) + // if (S_OK == DwmGetWindowAttribute(window, 34, &color, sizeof(COLORREF))) { + // std::vector rgb; + // rgb.emplace_back(GetRValue(color)); // Red + // rgb.emplace_back(GetGValue(color)); // Green + // rgb.emplace_back(GetBValue(color)); // Blue + + // Array_obj* hxRGB = new Array_obj(rgb.size(), rgb.size()); + // for (int i = 0; i < rgb.size(); i++) { + // hxRGB->Item(i) = rgb[i]; + // } + // return hxRGB; + // } else { + // // Devolver un array vacío si falla + // std::cerr << "[C++ Function - getWindowBorderColor] Error getting window border color. Error code: " << GetLastError() << std::endl; + // return new Array_obj(0, 0); + // } + // ') + // public static function getWindowBorderColor():Array + // { + // return []; + // } + @:functionCode(' - HWND window = GET_ENGINE_WINDOW(); - SetWindowLong(window, GWL_EXSTYLE, GetWindowLong(window, GWL_EXSTYLE) ^ WS_EX_LAYERED); + HWND window = GET_ENGINE_WINDOW(); + SetWindowLong(window, GWL_EXSTYLE, GetWindowLong(window, GWL_EXSTYLE) ^ WS_EX_LAYERED); ') public static function _setWindowLayered() { @@ -308,48 +360,6 @@ class WindowsCPP return 0; } - @:functionCode(' - HWND hwnd = GET_ENGINE_WINDOW(); - int screenWidth = GetSystemMetrics(SM_CXSCREEN); - int screenHeight = GetSystemMetrics(SM_CYSCREEN); - - RECT windowRect; - GetWindowRect(hwnd, &windowRect); - int windowWidth = windowRect.right - windowRect.left; - int windowHeight = windowRect.bottom - windowRect.top; - - int centerX = (screenWidth - windowWidth) / 2; - int centerY = (screenHeight - windowHeight) / 2; - - SetWindowPos(hwnd, NULL, centerX, centerY, 0, 0, SWP_NOSIZE | SWP_NOZORDER); - ') - @:noCompletion - public static function centerWindow() - { - } - - @:functionCode(' - POINT MousePoint; - GetCursorPos(&MousePoint); - - return MousePoint.x; - ') - static public function getCursorPositionX() - { - return 0; - } - - @:functionCode(' - POINT MousePoint; - GetCursorPos(&MousePoint); - - return MousePoint.y; - ') - static public function getCursorPositionY() - { - return 0; - } - @:functionCode(' BOOL isAdmin = FALSE; SID_IDENTIFIER_AUTHORITY ntAuthority = SECURITY_NT_AUTHORITY; @@ -374,6 +384,7 @@ class WindowsCPP } // thx Trock for this + @:functionCode(' int screenWidth = GetSystemMetrics(SM_CXSCREEN); int screenHeight = GetSystemMetrics(SM_CYSCREEN); @@ -549,25 +560,25 @@ class WindowsCPP } @:functionCode(' - HWND window; - HWND window2; - - switch (numberMode) { - case 0: - window = FindWindowW(L"Progman", L"Program Manager"); - window = GetWindow(window, GW_CHILD); - case 1: - window = FindWindowA("Shell_traywnd", nullptr); - window2 = FindWindowA("Shell_SecondaryTrayWnd", nullptr); - } + HWND window; + HWND window2; + + switch (numberMode) { + case 0: + window = FindWindowW(L"Progman", L"Program Manager"); + window = GetWindow(window, GW_CHILD); + case 1: + window = FindWindowA("Shell_traywnd", nullptr); + window2 = FindWindowA("Shell_SecondaryTrayWnd", nullptr); + } - if (numberMode != 1) { - SetWindowLong(window, GWL_EXSTYLE, GetWindowLong(window, GWL_EXSTYLE) ^ WS_EX_LAYERED); - } - else { - SetWindowLong(window, GWL_EXSTYLE, GetWindowLong(window, GWL_EXSTYLE) ^ WS_EX_LAYERED); - SetWindowLong(window2, GWL_EXSTYLE, GetWindowLong(window2, GWL_EXSTYLE) ^ WS_EX_LAYERED); - } + if (numberMode != 1) { + SetWindowLong(window, GWL_EXSTYLE, GetWindowLong(window, GWL_EXSTYLE) ^ WS_EX_LAYERED); + } + else { + SetWindowLong(window, GWL_EXSTYLE, GetWindowLong(window, GWL_EXSTYLE) ^ WS_EX_LAYERED); + SetWindowLong(window2, GWL_EXSTYLE, GetWindowLong(window2, GWL_EXSTYLE) ^ WS_EX_LAYERED); + } ') public static function _setWindowLayeredMode(numberMode:Int) { diff --git a/funkinscsource/slushi/windows/WindowsFuncs.hx b/funkinscsource/slushi/windows/WindowsFuncs.hx index ab42412..17e365a 100644 --- a/funkinscsource/slushi/windows/WindowsFuncs.hx +++ b/funkinscsource/slushi/windows/WindowsFuncs.hx @@ -1,10 +1,9 @@ package slushi.windows; -import sys.io.Process; +import slushi.others.systemUtils.HiddenProcess; import sys.io.File; import lime.system.System; import psychlua.LuaUtils; -import slushi.windows.ProgramRespondingUtil; /* * This file is one that facilitates the use of Windows functions that come from WindowsCPP.hx within SLE. @@ -17,13 +16,14 @@ class WindowsFuncs private static var _windowsWallpaperPath:String = null; public static var changedWallpaper:Bool = false; - private static final savedWallpaperPath:String = "assets/slushiEngineAssets/SLEAssets/OthersAssets/Cache/savedWindowswallpaper.png"; + private static final savedWallpaperPath:String = "assets/slushiEngineAssets/OthersAssets/Cache/savedWindowswallpaper.png"; + + private static var windowBorderColorTween:NumTween; public static function changeWindowsWallpaper(path:String) { #if windows - var allPath:String = CustomFuncs.getAllPath() + 'assets/' + path; - allPath = allPath.split("\\").join("/"); + var allPath:String = CustomFuncs.getProgramPath() + 'assets/' + path; CppAPI.setWallpaper(allPath); changedWallpaper = true; Debug.logSLEInfo("Wallpaper changed to: " + allPath); @@ -33,8 +33,7 @@ class WindowsFuncs public static function screenCapture(path:String) { #if windows - var allPath:String = CustomFuncs.getAllPath() + 'assets/images/SLEAssets/Cache/' + path; - allPath = allPath.split("\\").join("/"); + var allPath:String = CustomFuncs.getProgramPath() + 'assets/slushiEngineAssets/OthersAssets/Cache/' + path; CppAPI.screenCapture(allPath); Debug.logSLEInfo("Screenshot saved to: " + allPath); #end @@ -64,10 +63,8 @@ class WindowsFuncs var finalPath = savedWallpaperPath; try { - if (!FileSystem.exists('assets/slushiEngineAssets/SLEAssets/OthersAssets/Cache')) - FileSystem.createDirectory('assets/slushiEngineAssets/SLEAssets/OthersAssets/Cache'); - File.copy(_windowsWallpaperPath, finalPath); + Debug.logSLEInfo("Saved a copy of the wallpaper"); } catch (e) { @@ -79,7 +76,7 @@ class WindowsFuncs public static function setOldWindowsWallpaper() { #if windows - if (changedWallpaper == false) + if (!changedWallpaper) return; changedWallpaper = false; @@ -120,7 +117,7 @@ class WindowsFuncs + "$notifier.Show($toast);}\""; if (title != null && title != "" && desc != null && desc != "" && getWindowsVersion() != 7) - new Process(powershellCommand); + new HiddenProcess(powershellCommand); #end } @@ -191,23 +188,85 @@ class WindowsFuncs #end } - public static function getCursorPos():{x:Int, y:Int} + public static function setWindowBorderColorFromInt(color:Int):Void { - var mousePos = {x: 0, y: 0}; #if windows - mousePos = {x: WindowsCPP.getCursorPositionX(), y: WindowsCPP.getCursorPositionY()}; + if (getWindowsVersion() != 11) + return; + + var red:Int = (color >> 16) & 0xFF; + var green:Int = (color >> 8) & 0xFF; + var blue:Int = color & 0xFF; + var rgb:Array = [red, green, blue]; + WindowsFuncs.setWindowBorderColor(rgb); #end - return mousePos; } - public static function initThreadForWindowRespondingHandler() + public static function tweenWindowBorderColor(fromColor:Array, toColor:Array, duration:Float, ease:String):Void { #if windows - Sys.println("[slushi.windows.WindowsFuncs.initThreadForWindowRespondingHandler] - Starting thread for window responding handler..."); - ProgramRespondingUtil.initThread(); + if (getWindowsVersion() != 11) + return; + + windowBorderColorTween = FlxTween.num(0, 1, duration, { + ease: LuaUtils.getTweenEaseByString(ease) + }); + + var startColor:Array = fromColor; + var targetColor:Array = toColor; + + windowBorderColorTween.onUpdate = function(tween:FlxTween) + { + var interpolatedColor:Array = []; + for (i in 0...3) + { + var newValue:Int = startColor[i] + Std.int((targetColor[i] - startColor[i]) * windowBorderColorTween.value); + newValue = Std.int(Math.max(0, Math.min(255, newValue))); + interpolatedColor.push(newValue); + } + WindowsFuncs.setWindowBorderColor(interpolatedColor); + }; #end } + // public static function tweenWindowBorderColorFromActualColor(toColor:Array, duration:Float, ease:String):Void + // { + // #if windows + // if (getWindowsVersion() != 11) + // return; + + // var fromColor:Array = WindowsCPP.getWindowBorderColor(); + + // windowBorderColorTween = FlxTween.num(0, 1, duration, { + // ease: LuaUtils.getTweenEaseByString(ease) + // }); + + // var startColor:Array = fromColor; + // var targetColor:Array = toColor; + + // windowBorderColorTween.onUpdate = function(tween:FlxTween) + // { + // var interpolatedColor:Array = []; + // for (i in 0...3) + // { + // var newValue:Int = startColor[i] + Std.int((targetColor[i] - startColor[i]) * windowBorderColorTween.value); + // newValue = Std.int(Math.max(0, Math.min(255, newValue))); + // interpolatedColor.push(newValue); + // } + // WindowsFuncs.setWindowBorderColor(interpolatedColor); + // }; + // #end + // } + + public static function cancelWindowBorderColorTween():Void + { + if (windowBorderColorTween != null) + { + windowBorderColorTween.cancel(); + windowBorderColorTween = null; + } + } + ////////////////////////////////////////////////////////////////////////////////////////// #if windows public static function doTweenDesktopWindows(mode:String, toValue:Float, duration:Float, ease:String) @@ -250,26 +309,3 @@ class WindowsFuncs } #end } - -class DeprecatedFuncs -{ - #if windows - public static function doTweenDesktopWindowsInX(fromValue:Float, toValue:Float, duration:Float, ease:String = "linear") - { - var numTween:NumTween = FlxTween.num(fromValue, toValue, duration, {ease: LuaUtils.getTweenEaseByString(ease)}); - numTween.onUpdate = function(twn:FlxTween) - { - CppAPI.moveDesktopWindowsInX(Std.int(numTween.value)); - } - } - - public static function doTweenDesktopWindowsInY(fromValue:Float, toValue:Float, duration:Float, ease:String = "linear") - { - var numTween:NumTween = FlxTween.num(fromValue, toValue, duration, {ease: LuaUtils.getTweenEaseByString(ease)}); - numTween.onUpdate = function(twn:FlxTween) - { - CppAPI.moveDesktopWindowsInY(Std.int(numTween.value)); - } - } - #end -} diff --git a/funkinscsource/slushi/windows/WindowsGDIEffects.hx b/funkinscsource/slushi/windows/WindowsGDIEffects.hx deleted file mode 100644 index dc0d122..0000000 --- a/funkinscsource/slushi/windows/WindowsGDIEffects.hx +++ /dev/null @@ -1,281 +0,0 @@ -package slushi.windows; - -/** - * This file has the functions related to the Windows GDI, there are MENZ virus GDI effects. - * - * Author: Slushi - */ - -#if windows -@:cppFileCode(' -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include - -#include -#include - -#define UNICODE - -#pragma comment(lib, "Dwmapi") -#pragma comment(lib, "ntdll.lib") -#pragma comment(lib, "User32.lib") -#pragma comment(lib, "Shell32.lib") -#pragma comment(lib, "gdi32.lib") - -///////////////////////////////////////////////////////////////////////////// - -#define elapsedTime 0 - -int payloadDrawErrors(BOOLEAN mode) { - if (mode) { - int ix = GetSystemMetrics(SM_CXICON) / 2; - int iy = GetSystemMetrics(SM_CYICON) / 2; - - HWND hwnd = GetDesktopWindow(); - HDC hdc = GetWindowDC(hwnd); - - POINT cursor; - GetCursorPos(&cursor); - - DrawIcon(hdc, cursor.x - ix, cursor.y - iy, LoadIcon(NULL, IDI_ERROR)); - - if (rand() % (int)(10/(elapsedTime/500.0+1)+1) == 0) { - DrawIcon(hdc, rand()%GetSystemMetrics(SM_CXSCREEN), rand()%GetSystemMetrics(SM_CYSCREEN), LoadIcon(NULL, IDI_WARNING)); - } - - ReleaseDC(hwnd, hdc); - - out: return 2; - } -} - -int payloadBlink(BOOLEAN mode) { - if (mode) { - HWND hwnd = GetDesktopWindow(); - HDC hdc = GetWindowDC(hwnd); - RECT rekt; - GetWindowRect(hwnd, &rekt); - BitBlt(hdc, 0, 0, rekt.right - rekt.left, rekt.bottom - rekt.top, hdc, 0, 0, NOTSRCCOPY); - ReleaseDC(hwnd, hdc); - - out: return 100; - } -} - -int payloadGlitchs(BOOLEAN mode) { - if (mode) { - HWND hwnd = GetDesktopWindow(); - HDC hdc = GetWindowDC(hwnd); - RECT rekt; - GetWindowRect(hwnd, &rekt); - - int x1 = rand() % (rekt.right - 100); - int y1 = rand() % (rekt.bottom - 100); - int x2 = rand() % (rekt.right - 100); - int y2 = rand() % (rekt.bottom - 100); - int width = rand() % 600; - int height = rand() % 600; - - BitBlt(hdc, x1, y1, width, height, hdc, x2, y2, SRCCOPY); - ReleaseDC(hwnd, hdc); - - out: return 200.0 / (elapsedTime / 5.0 + 1) + 3; - } -} - -int payloadTunnel(BOOLEAN mode) { - if (mode) { - HWND hwnd = GetDesktopWindow(); - HDC hdc = GetWindowDC(hwnd); - RECT rekt; - GetWindowRect(hwnd, &rekt); - StretchBlt(hdc, 50, 50, rekt.right - 100, rekt.bottom - 100, hdc, 0, 0, rekt.right, rekt.bottom, SRCCOPY); - ReleaseDC(hwnd, hdc); - - out: return 200.0 / (elapsedTime / 5.0 + 1) + 4; - } -} - -int payloadScreenShake(BOOLEAN mode) { - if (mode) { - HDC hdc = GetDC(0); - int x = SM_CXSCREEN; - int y = SM_CYSCREEN; - int w = GetSystemMetrics(0); - int h = GetSystemMetrics(1); - BitBlt(hdc, rand() % 2, rand() % 2, w, h, hdc, rand() % 2, rand() % 2, SRCCOPY); - Sleep(10); - ReleaseDC(0, hdc); - } - return 0; -} - -///////////////////////////////////////////////////////////////////////////// - -BOOL CALLBACK EnumChildProc(HWND hwnd, LPARAM lParam) { - - LPWSTR newText = (LPWSTR)lParam; - - SendMessageTimeoutW(hwnd, WM_SETTEXT, NULL, (LPARAM)newText, SMTO_ABORTIFHUNG, 0, NULL); - - return TRUE; -} - -') -#end -class WindowsGDIEffects -{ - #if windows - @:functionCode(' - payloadDrawErrors(mode); - ') - public static function _drawIcons(mode:Bool) {} - - @:functionCode(' - payloadBlink(mode); - ') - public static function _screenBlink(mode:Bool) {} - - @:functionCode(' - payloadGlitchs(mode); - ') - public static function _payloadGlitchs(mode:Bool) {} - - @:functionCode(' - payloadTunnel(mode); - ') - public static function _payloadTunnel(mode:Bool) {} - - @:functionCode(' - payloadScreenShake(mode); - ') - public static function _payloadScreenShake(mode:Bool) {} - - @:functionCode(' - std::string s = text; - std::wstring_convert> converter; - std::wstring wide = converter.from_bytes(s); - - LPCWSTR result = wide.c_str(); - - EnumChildWindows(GetDesktopWindow(), EnumChildProc, (LPARAM)result); - ') - public static function _setCustomTitleTextToWindows(text:String = "...") {} - #end - - ///////////////////////////////////////////////////////////////////////////// - - static var gdiEffects:Array = [ - "drawIcons", "screenBlink", "screenGlitches", "screenTunnel" - ]; - - static var invalidGDIEffects:Array = [ - "SetTitleTextToWindows" - ]; - - public static var slushi_WinGDIEffect:Map = []; - - public static function checkEffect(tag:String = "", gdiEffect:String, ?initalValue:Dynamic = true) { - #if windows - if(invalidGDIEffects.contains(gdiEffect)) - return printInDisplay('WindowsGDIEffects/checkEffect: [${gdiEffect}] is not supported for this function!', FlxColor.RED); - - var effectClass = Type.resolveClass('slushi.windows.WinGDI_' + gdiEffect); - if (effectClass != null) - { - var initEffect = Type.createInstance(effectClass, []); - slushi_WinGDIEffect.set(tag, initEffect); - Debug.logSLEInfo('created [${gdiEffect}] GDI effect from class [WinGDI_${gdiEffect}]'); - } - else{ - Debug.logSLEError('[WinGDI_${gdiEffect}] not found!'); - printInDisplay('WindowsGDIEffects/checkEffect: [${gdiEffect}] not found!', FlxColor.RED); - } - #end - } - - public static function setWinEffectProperty(tag:String, prop:String, ?initalValue:Dynamic = true) { - #if windows - var effect = slushi_WinGDIEffect.get(tag); - - if(effect != null){ - Reflect.setProperty(effect, prop, initalValue); - } - else{ - Debug.logSLEWarn('Uknown tag [${tag}]'); - printInDisplay('WindowsGDIEffects/setWinEffectProperty: [${tag}] not found', FlxColor.WHITE); - } - #end - } -} - -class SlushiWindowsEffects -{ - public var activeGDIEffect:Bool = true; - public var effectSpeed:Float = 1.0; - - public var aditionalValue:Dynamic; - - // thx TheoDevelop - var progress:Float; - var defaultTime:Float = 1; - - // ANTI CRASH !!!!!!!!!!!!!!!!!!!!!!!! - final antiCrash = (num) -> return Math.min(0.00001, num); - var reset:Null; - - public function update(elapsed:Float){ - progress += elapsed; - - reset = (antiCrash(defaultTime) / antiCrash(effectSpeed)); - } -} - -#if windows -class WinGDI_ScreenBlink extends SlushiWindowsEffects -{ - override public function update(elapsed:Float):Void - { - if (activeGDIEffect) - { - if(progress >= reset) - { - WindowsGDIEffects._screenBlink(activeGDIEffect); - progress = 0; - } - } - super.update(elapsed); - } -} - -class WinGDI_SetTitleTextToWindows extends SlushiWindowsEffects -{ - public var titleText:String = "Null"; - - public function new() - { - WindowsGDIEffects._setCustomTitleTextToWindows(titleText); - } -} - -class WinGDI_ScreenShake extends SlushiWindowsEffects -{ - override public function update(elapsed:Float):Void - { - if(activeGDIEffect) - WindowsGDIEffects._payloadScreenShake(activeGDIEffect); - } -} -#end \ No newline at end of file diff --git a/funkinscsource/slushi/windows/WinConsoleUtils.hx b/funkinscsource/slushi/windows/WindowsTerminalCPP.hx similarity index 99% rename from funkinscsource/slushi/windows/WinConsoleUtils.hx rename to funkinscsource/slushi/windows/WindowsTerminalCPP.hx index faae31b..689ac21 100644 --- a/funkinscsource/slushi/windows/WinConsoleUtils.hx +++ b/funkinscsource/slushi/windows/WindowsTerminalCPP.hx @@ -30,7 +30,7 @@ package slushi.windows; #pragma comment(lib, "gdi32.lib") ') #end -class WinConsoleUtils +class WindowsTerminalCPP { #if windows @:functionCode(' diff --git a/funkinscsource/slushi/windows/winGDIThings/SlushiWinGDI.hx b/funkinscsource/slushi/windows/winGDIThings/SlushiWinGDI.hx new file mode 100644 index 0000000..1f0fd89 --- /dev/null +++ b/funkinscsource/slushi/windows/winGDIThings/SlushiWinGDI.hx @@ -0,0 +1,315 @@ +package slushi.windows.winGDIThings; + +/* + * This is the main class of the Windows GDI effects in SLE, it has the C++ code of the effects, + * and there are functions to prepare, start and remove an added effect + * (some of the GDI effect code is taken from the MENZ malware source code) + * + * Author: Slushi + */ +#if windows +@:cppFileCode(' +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include + +#include +#include + +#define UNICODE + +#pragma comment(lib, "Dwmapi") +#pragma comment(lib, "ntdll.lib") +#pragma comment(lib, "User32.lib") +#pragma comment(lib, "Shell32.lib") +#pragma comment(lib, "gdi32.lib") + +///////////////////////////////////////////////////////////////////////////// + +static float elapsedTime = 0; + +int payloadDrawErrors() { + int ix = GetSystemMetrics(SM_CXICON) / 2; + int iy = GetSystemMetrics(SM_CYICON) / 2; + + HWND hwnd = GetDesktopWindow(); + HDC hdc = GetWindowDC(hwnd); + + POINT cursor; + GetCursorPos(&cursor); + + DrawIcon(hdc, cursor.x - ix, cursor.y - iy, LoadIcon(NULL, IDI_ERROR)); + + if (rand() % (int)(10/(elapsedTime/500.0+1)+1) == 0) { + DrawIcon(hdc, rand()%GetSystemMetrics(SM_CXSCREEN), rand()%GetSystemMetrics(SM_CYSCREEN), LoadIcon(NULL, IDI_WARNING)); + } + + ReleaseDC(hwnd, hdc); + + out: return 2; +} + +int payloadBlink() { + HWND hwnd = GetDesktopWindow(); + HDC hdc = GetWindowDC(hwnd); + RECT rekt; + GetWindowRect(hwnd, &rekt); + BitBlt(hdc, 0, 0, rekt.right - rekt.left, rekt.bottom - rekt.top, hdc, 0, 0, NOTSRCCOPY); + ReleaseDC(hwnd, hdc); + + out: return 100; +} + +int payloadGlitchs() { + HWND hwnd = GetDesktopWindow(); + HDC hdc = GetWindowDC(hwnd); + RECT rekt; + GetWindowRect(hwnd, &rekt); + + int x1 = rand() % (rekt.right - 100); + int y1 = rand() % (rekt.bottom - 100); + int x2 = rand() % (rekt.right - 100); + int y2 = rand() % (rekt.bottom - 100); + int width = rand() % 600; + int height = rand() % 600; + + BitBlt(hdc, x1, y1, width, height, hdc, x2, y2, SRCCOPY); + ReleaseDC(hwnd, hdc); + + out: return 200.0 / (elapsedTime / 5.0 + 1) + 3; +} + +int payloadTunnel() { + HWND hwnd = GetDesktopWindow(); + HDC hdc = GetWindowDC(hwnd); + RECT rekt; + GetWindowRect(hwnd, &rekt); + StretchBlt(hdc, 50, 50, rekt.right - 100, rekt.bottom - 100, hdc, 0, 0, rekt.right, rekt.bottom, SRCCOPY); + ReleaseDC(hwnd, hdc); + + out: return 200.0 / (elapsedTime / 5.0 + 1) + 4; +} + +int payloadScreenShake() { + HDC hdc = GetDC(0); + int x = SM_CXSCREEN; + int y = SM_CYSCREEN; + int w = GetSystemMetrics(0); + int h = GetSystemMetrics(1); + BitBlt(hdc, rand() % 2, rand() % 2, w, h, hdc, rand() % 2, rand() % 2, SRCCOPY); + Sleep(10); + ReleaseDC(0, hdc); + return 0; +} + +///////////////////////////////////////////////////////////////////////////// + +BOOL CALLBACK EnumChildProc(HWND hwnd, LPARAM lParam) { + + LPWSTR newText = (LPWSTR)lParam; + + SendMessageTimeoutW(hwnd, WM_SETTEXT, NULL, (LPARAM)newText, SMTO_ABORTIFHUNG, 0, NULL); + + return TRUE; +} + +') +#end +class SlushiWinGDI +{ + #if windows + @:functionCode(' + elapsedTime = elapsed; + ') + public static function setElapsedTime(elapsed:Float) + { + } + + @:functionCode(' + payloadDrawErrors(); + ') + public static function _drawIcons() + { + } + + @:functionCode(' + payloadBlink(); + ') + public static function _screenBlink() + { + } + + @:functionCode(' + payloadGlitchs(); + ') + public static function _screenGlitches() + { + } + + @:functionCode(' + payloadTunnel(); + ') + public static function _screenTunnel() + { + } + + @:functionCode(' + payloadScreenShake(); + ') + public static function _screenShake() + { + } + + @:functionCode(' + std::string s = text; + std::wstring_convert> converter; + std::wstring wide = converter.from_bytes(s); + + LPCWSTR result = wide.c_str(); + + EnumChildWindows(GetDesktopWindow(), EnumChildProc, (LPARAM)result); + ') + public static function _setCustomTitleTextToWindows(text:String = "...") + { + } + #end + + ///////////////////////////////////////////////////////////////////////////// + public static function prepareGDIEffect(effect:String, wait:Float = 0) + { + #if windows + var effectClass = Type.resolveClass('slushi.windows.winGDIThings.SLWinEffect_' + effect); + if (effectClass != null) + { + var initEffect = Type.createInstance(effectClass, []); + WinGDIThread.gdiEffects.set(effect, new SlushiWinGDIEffectData(initEffect, wait, false)); + Debug.logSLEInfo('created [${effect}] GDI effect from class [SLWinEffect_${effect}]'); + } + else + { + Debug.logSLEError('[SLWinEffect_${effect}] not found!'); + printInDisplay('SlushiWinGDI/prepareGDIEffect: [${effect}] not found!', FlxColor.RED); + } + #end + } + + public static function setGDIEffectWaitTime(effect:String, wait:Float) + { + #if windows + var gdi = WinGDIThread.gdiEffects.get(effect); + if (gdi != null) + { + gdi.wait = wait; + } + else + { + Debug.logSLEError('[SLWinEffect_${effect}] not found!'); + printInDisplay('SlushiWinGDI/setGDIEFfectProperty: [${effect}] not found!', FlxColor.RED); + } + #end + } + + public static function removeGDIEffect(effect:String) + { + #if windows + var gdi = WinGDIThread.gdiEffects.get(effect); + if (gdi != null) + { + WinGDIThread.gdiEffects.remove(effect); + } + else + { + Debug.logSLEError('[SLWinEffect_${effect}] not found!'); + printInDisplay('SlushiWinGDI/removeGDIEffect: [${effect}] not found!', FlxColor.RED); + } + #end + } + + public static function enableGDIEffect(effect:String, enabled:Bool = true) + { + #if windows + var gdi = WinGDIThread.gdiEffects.get(effect); + if (gdi != null) + { + gdi.enabled = enabled; + } + else + { + Debug.logSLEError('[SLWinEffect_${effect}] not found!'); + printInDisplay('SlushiWinGDI/enableGDIEffect: [${effect}] not found!', FlxColor.RED); + } + #end + } +} + +class SlushiWinGDIEffect +{ + #if windows + public function update() + { + } + #end +} + +#if windows +class SLWinEffect_DrawIcons extends SlushiWinGDIEffect +{ + override public function update() + { + SlushiWinGDI._drawIcons(); + } +} + +class SLWinEffect_ScreenBlink extends SlushiWinGDIEffect +{ + override public function update() + { + SlushiWinGDI._screenBlink(); + } +} + +class SLWinEffect_ScreenGlitches extends SlushiWinGDIEffect +{ + override public function update() + { + SlushiWinGDI._screenGlitches(); + } +} + +class SLWinEffect_ScreenShake extends SlushiWinGDIEffect +{ + override public function update() + { + SlushiWinGDI._screenShake(); + } +} + +class SLWinEffect_ScreenTunnel extends SlushiWinGDIEffect +{ + override public function update() + { + SlushiWinGDI._screenTunnel(); + } +} + +class SLWinEffect_SetTitleTextToWindows extends SlushiWinGDIEffect +{ + public var text:String = ""; + + override public function update() + { + SlushiWinGDI._setCustomTitleTextToWindows(text); + } +} +#end diff --git a/funkinscsource/slushi/windows/winGDIThings/SlushiWinGDIEffectData.hx b/funkinscsource/slushi/windows/winGDIThings/SlushiWinGDIEffectData.hx new file mode 100644 index 0000000..b140ca2 --- /dev/null +++ b/funkinscsource/slushi/windows/winGDIThings/SlushiWinGDIEffectData.hx @@ -0,0 +1,22 @@ +package slushi.windows.winGDIThings; + +import slushi.windows.winGDIThings.SlushiWinGDI.SlushiWinGDIEffect; + +/* + * This is a simple class that contains data from the GDI effect before it is started + * + * Author: Slushi + */ +class SlushiWinGDIEffectData +{ + public var gdiEffect:SlushiWinGDIEffect; + public var wait:Float = 0; + public var enabled:Bool = false; + + public function new(_gdiEffect:SlushiWinGDIEffect, _wait:Float = 0, _enabled:Bool = false) + { + this.gdiEffect = _gdiEffect; + this.wait = _wait; + this.enabled = _enabled; + } +} diff --git a/funkinscsource/slushi/windows/winGDIThings/WinGDIThread.hx b/funkinscsource/slushi/windows/winGDIThings/WinGDIThread.hx new file mode 100644 index 0000000..302014b --- /dev/null +++ b/funkinscsource/slushi/windows/winGDIThings/WinGDIThread.hx @@ -0,0 +1,87 @@ +package slushi.windows.winGDIThings; + +import sys.thread.Thread; + +/* + * This class starts an external thread to the main one of the engine, it is used so that + * Windows GDI effects do not generate lag in the game due to the fact that they consume quite some + * + * Author: Slushi + */ +class WinGDIThread +{ + public static var mainThread:Thread; + public static var gdiEffects:Map = []; + public static var runningThread:Bool = true; + public static var elapsedTime:Float = 0; + public static var temporarilyPaused:Bool = false; + + public static function initThread() + { + if (mainThread != null) + return; + + Debug.logSLEInfo('Starting Windows GDI Thread...'); + + mainThread = Thread.create(() -> + { + Debug.logSLEInfo('Windows GDI Thread running...'); + while (runningThread) + { + /** + * Check if the game is focused or if the PlayState is paused or the player is dead + * This prevents GDI effects from continuing to be generated at times when they should not be + */ + if (!Main.focused) + { + return; + } + if (PlayState.instance != null) + { + if (PlayState.instance.paused) + { + return; + } + else if (PlayState.instance.isDead) + { + return; + } + } + if (temporarilyPaused) + { + return; + } + + elapsedTime++; + SlushiWinGDI.setElapsedTime(elapsedTime); + + for (gdi in gdiEffects) + { + if (!gdi.enabled) + continue; + + if (gdi.wait > 0) + { + // Wait if wait time is greater than 0, slows down the effect + Sys.sleep(gdi.wait); + } + gdi.gdiEffect.update(); + } + } + }); + } + + public static function stopThread() + { + if (mainThread != null) + { + Debug.logSLEInfo('Stopping Windows GDI Thread...'); + runningThread = false; + temporarilyPaused = false; + mainThread = null; + } + gdiEffects.clear(); + elapsedTime = 0; + SlushiWinGDI.setElapsedTime(elapsedTime); + } +} diff --git a/funkinscsource/states/MainMenuState.hx b/funkinscsource/states/MainMenuState.hx index 4ed2f0f..38be709 100644 --- a/funkinscsource/states/MainMenuState.hx +++ b/funkinscsource/states/MainMenuState.hx @@ -310,7 +310,7 @@ class MainMenuState extends MusicBeatState } case RIGHT: - if (controls.UI_LEFT_P) + if (controls.UI_LEFT_P) { curColumn = CENTER; changeItem(); @@ -370,7 +370,7 @@ class MainMenuState extends MusicBeatState case 'story_mode': MusicBeatState.switchState(new StoryMenuState()); case 'freeplay': - MusicBeatState.switchState(new states.freeplay.FreeplayState()); + MusicBeatState.switchState(new slushi.states.freeplay.SlushiFreeplayState()); #if MODS_ALLOWED case 'mods': MusicBeatState.switchState(new ModsMenuState()); diff --git a/funkinscsource/states/PlayState.hx b/funkinscsource/states/PlayState.hx index 6a60e4a..b39e233 100644 --- a/funkinscsource/states/PlayState.hx +++ b/funkinscsource/states/PlayState.hx @@ -43,7 +43,7 @@ import states.MusicBeatState.subStates; import states.freeplay.FreeplayState; import states.editors.ChartingState; import states.editors.CharacterEditorState; -import substates.PauseSubState; +import slushi.substates.SlushiPauseSubState; import substates.GameOverSubstate; import substates.ResultsScreenKadeSubstate; import openfl.filters.ShaderFilter; @@ -237,11 +237,11 @@ class PlayState extends MusicBeatState // Slushi Engine cameras public var camSLEHUD:FlxCamera; - public var camFor3D:FlxCamera; - public var camFor3D2:FlxCamera; - public var camFor3D3:FlxCamera; - public var camFor3D4:FlxCamera; - public var camFor3D5:FlxCamera; + public var camThings:FlxCamera; + public var camThings2:FlxCamera; + public var camThings3:FlxCamera; + public var camThings4:FlxCamera; + public var camThings5:FlxCamera; public var camWaterMark:FlxCamera; public var cameraSpeed:Float = 1; @@ -480,7 +480,7 @@ class PlayState extends MusicBeatState if (SONG == null) { Debug.displayAlert("PlayState Was Not Able To Load Any Songs!", "PlayState Error"); - MusicBeatState.switchState(new FreeplayState()); + MusicBeatState.switchState(new slushi.states.freeplay.SlushiFreeplayState()); return; } @@ -646,7 +646,7 @@ class PlayState extends MusicBeatState // for lua instance = this; - PauseSubState.songName = null; // Reset to default + SlushiPauseSubState.songName = null; // Reset to default playbackRate = ClientPrefs.getGameplaySetting('songspeed'); swagHits = sickHits = goodHits = badHits = shitHits = songMisses = highestCombo = 0; @@ -732,18 +732,18 @@ class PlayState extends MusicBeatState camPause.bgColor.alpha = 0; camSLEHUD = new FlxCamera(); - camFor3D = new FlxCamera(); - camFor3D2 = new FlxCamera(); - camFor3D3 = new FlxCamera(); - camFor3D4 = new FlxCamera(); - camFor3D5 = new FlxCamera(); + camThings = new FlxCamera(); + camThings2 = new FlxCamera(); + camThings3 = new FlxCamera(); + camThings4 = new FlxCamera(); + camThings5 = new FlxCamera(); camWaterMark = new FlxCamera(); camSLEHUD.bgColor.alpha = 0; - camFor3D.bgColor.alpha = 0; - camFor3D2.bgColor.alpha = 0; - camFor3D3.bgColor.alpha = 0; - camFor3D4.bgColor.alpha = 0; - camFor3D5.bgColor.alpha = 0; + camThings.bgColor.alpha = 0; + camThings2.bgColor.alpha = 0; + camThings3.bgColor.alpha = 0; + camThings4.bgColor.alpha = 0; + camThings5.bgColor.alpha = 0; camWaterMark.bgColor.alpha = 0; // Video Camera if you put funni videos or smth @@ -756,11 +756,11 @@ class PlayState extends MusicBeatState FlxG.cameras.add(camHUD, false); FlxG.cameras.add(camSLEHUD, false); - FlxG.cameras.add(camFor3D, false); - FlxG.cameras.add(camFor3D2, false); - FlxG.cameras.add(camFor3D3, false); - FlxG.cameras.add(camFor3D4, false); - FlxG.cameras.add(camFor3D5, false); + FlxG.cameras.add(camThings, false); + FlxG.cameras.add(camThings2, false); + FlxG.cameras.add(camThings3, false); + FlxG.cameras.add(camThings4, false); + FlxG.cameras.add(camThings5, false); // for jumescares and shit FlxG.cameras.add(camOther, false); @@ -1420,7 +1420,7 @@ class PlayState extends MusicBeatState } Paths.image('alphabet'); - if (PauseSubState.songName != null) Paths.music(PauseSubState.songName); + if (SlushiPauseSubState.songName != null) Paths.music(SlushiPauseSubState.songName); else if (Paths.formatToSongPath(ClientPrefs.data.pauseMusic) != 'none') Paths.music(Paths.formatToSongPath(ClientPrefs.data.pauseMusic)); resetRPC(); @@ -3424,7 +3424,7 @@ class PlayState extends MusicBeatState { if (endCallback != null) endCallback(); else - MusicBeatState.switchState(new FreeplayState()); + MusicBeatState.switchState(new slushi.states.freeplay.SlushiFreeplayState()); super.update(elapsed); return; } @@ -4273,7 +4273,7 @@ class PlayState extends MusicBeatState } } - var pauseSubState = new PauseSubState(); + var pauseSubState = new SlushiPauseSubState(); openSubState(pauseSubState); pauseSubState.camera = camPause; @@ -5344,7 +5344,7 @@ class PlayState extends MusicBeatState Debug.logTrace('WENT BACK TO FREEPLAY??'); Mods.loadTopMod(); #if DISCORD_ALLOWED DiscordClient.resetClientID(); #end - MusicBeatState.switchState(new FreeplayState()); + MusicBeatState.switchState(new slushi.states.freeplay.SlushiFreeplayState()); FlxG.sound.playMusic(SlushiMain.getSLEPath("Musics/SLE_HackNet_Resonance.ogg")); changedDifficulty = false; } @@ -6678,19 +6678,8 @@ class PlayState extends MusicBeatState note.wasGoodHit = true; - if (useSLEHUD) { - SlushiEngineHUD.setRatingText(note.strumTime - Conductor.songPosition); - if(!isSus) { - SlushiEngineHUD.doComboAngle(); - } - } - #if windows - if(ClientPrefs.data.changeWindowBorderColorWithNoteHit && SlushiEngineHUD.instance.canChangeWindowColorWithNoteHit && !isSus) - { - // var convertedColor = CustomFuncs.getRGBFromFlxColor(note.rgbShader.r, note.rgbShader.g, note.rgbShader.b); - SlushiEngineHUD.setWindowColorWithNoteHit(leData/*, convertedColor*/); - } - #end + // Simpler just leave this line for future times when you want to port SLE to another version of SCE. + SlushiEngineHUD.setParamsFromPlayerNote(note.strumTime, isSus, leData); if (note.hitsound != null && note.hitsoundVolume > 0 && !note.hitsoundDisabled) FlxG.sound.play(Paths.sound(note.hitsound), note.hitsoundVolume); @@ -7083,6 +7072,8 @@ class PlayState extends MusicBeatState } } + SlushiEngineHUD.setNotITGNotesInSteps(curStep); + if (bopOnStep) { if (camZooming && camZoomingBopStep > 0 && camZoomingMultStep > 0 && FlxG.camera.zoom < maxCamZoom && ClientPrefs.data.camZooms diff --git a/funkinscsource/states/WarnFreeplay.hx b/funkinscsource/states/WarnFreeplay.hx index e40c887..ac5e38a 100644 --- a/funkinscsource/states/WarnFreeplay.hx +++ b/funkinscsource/states/WarnFreeplay.hx @@ -48,7 +48,7 @@ class WarnFreeplay extends states.MusicBeatState FlxG.sound.play(Paths.sound('confirmMenu')); FlxFlicker.flicker(warnText, 1, 0.1, false, true, function(flk:FlxFlicker) { new FlxTimer().start(0.5, function(tmr:FlxTimer) { - MusicBeatState.switchState(new states.freeplay.FreeplayState()); + MusicBeatState.switchState(new slushi.states.freeplay.SlushiFreeplayState()); }); }); } diff --git a/funkinscsource/states/freeplay/FreeplayState.hx b/funkinscsource/states/freeplay/FreeplayState.hx index 8662ed4..f0f3d97 100644 --- a/funkinscsource/states/freeplay/FreeplayState.hx +++ b/funkinscsource/states/freeplay/FreeplayState.hx @@ -271,7 +271,7 @@ class FreeplayState extends MusicBeatState // Set the window border color from the current song's color // Idea from VS Camellia ALT (https://gamebanana.com/mods/413258) (They use my code to set the window border color XD) - CustomFuncs.setWinBorderColorFromInt(intendedColor); + WindowsFuncs.setWindowBorderColorFromInt(intendedColor); curDifficulty = Math.round(Math.max(0, Difficulty.list.indexOf(lastDifficultyName))); @@ -999,7 +999,7 @@ class FreeplayState extends MusicBeatState // Set the window border color from the current song's color // Idea from VS Camellia ALT (https://gamebanana.com/mods/413258) (They use my code to set the window border color XD) - CustomFuncs.setWinBorderColorFromInt(intendedColor); + WindowsFuncs.setWindowBorderColorFromInt(intendedColor); FlxTween.cancelTweensOf(bg); FlxTween.color(bg, 1, bg.color, intendedColor); diff --git a/funkinscsource/substates/GameOverSubstate.hx b/funkinscsource/substates/GameOverSubstate.hx index a3e134b..5284633 100644 --- a/funkinscsource/substates/GameOverSubstate.hx +++ b/funkinscsource/substates/GameOverSubstate.hx @@ -60,6 +60,8 @@ class GameOverSubstate extends MusicBeatSubState { instance = this; + WindowsFuncs.tweenWindowBorderColor([255, 0, 0], [0, 0, 0], 1, 'linear'); + Conductor.songPosition = 0; if (boyfriend == null) @@ -170,7 +172,7 @@ class GameOverSubstate extends MusicBeatSubState { if (PlayState.isStoryMode) MusicBeatState.switchState(new StoryMenuState()); else - MusicBeatState.switchState(new states.freeplay.FreeplayState()); + MusicBeatState.switchState(new slushi.states.freeplay.SlushiFreeplayState()); } #if BASE_GAME_FILES else @@ -181,7 +183,7 @@ class GameOverSubstate extends MusicBeatSubState openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new StoryMenuState(sticker))); } else - openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new states.freeplay.FreeplayState(sticker))); + openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new slushi.states.freeplay.SlushiFreeplayState(sticker))); } #end @@ -240,6 +242,9 @@ class GameOverSubstate extends MusicBeatSubState { if (!isEnding) { + + WindowsFuncs.tweenWindowBorderColor([185, 157, 0], CustomFuncs.colorIntToRGB(SlushiMain.slushiColor), 2, 'linear'); + isEnding = true; if (boyfriend.hasOffsetAnimation('deathConfirm')) boyfriend.playAnim('deathConfirm', true); diff --git a/funkinscsource/substates/PauseSubState.hx b/funkinscsource/substates/PauseSubState.hx index 325c8da..40c24d2 100644 --- a/funkinscsource/substates/PauseSubState.hx +++ b/funkinscsource/substates/PauseSubState.hx @@ -467,7 +467,7 @@ class PauseSubState extends MusicBeatSubState { if (PlayState.isStoryMode) MusicBeatState.switchState(new StoryMenuState()); else - MusicBeatState.switchState(new states.freeplay.FreeplayState()); + MusicBeatState.switchState(new slushi.states.freeplay.SlushiFreeplayState()); } #if BASE_GAME_FILES else @@ -478,7 +478,7 @@ class PauseSubState extends MusicBeatSubState openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new StoryMenuState(sticker))); } else - openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new states.freeplay.FreeplayState(sticker))); + openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new slushi.states.freeplay.SlushiFreeplayState(sticker))); } #end diff --git a/funkinscsource/substates/ResultsScreenKadeSubstate.hx b/funkinscsource/substates/ResultsScreenKadeSubstate.hx index 91da8c7..eb74c40 100644 --- a/funkinscsource/substates/ResultsScreenKadeSubstate.hx +++ b/funkinscsource/substates/ResultsScreenKadeSubstate.hx @@ -264,7 +264,7 @@ class ResultsScreenKadeSubstate extends substates.MusicBeatSubState close(); if (PlayState.isStoryMode) MusicBeatState.switchState(new StoryMenuState()); else - MusicBeatState.switchState(new states.freeplay.FreeplayState()); + MusicBeatState.switchState(new slushi.states.freeplay.SlushiFreeplayState()); }, true); } }); diff --git a/funkinscsource/substates/vslice/ResultState.hx b/funkinscsource/substates/vslice/ResultState.hx index 8752c42..24b855c 100644 --- a/funkinscsource/substates/vslice/ResultState.hx +++ b/funkinscsource/substates/vslice/ResultState.hx @@ -106,6 +106,8 @@ class ResultState extends MusicBeatSubState score = new ResultScore(35, 305, 10, params.scoreData.mainData.score); rankBg = new FunkinSCSprite(0, 0); + + WindowsFuncs.setWindowBorderColor([254, 199, 92]); } override function create():Void @@ -895,7 +897,7 @@ class ResultState extends MusicBeatSubState Debug.logInfo('WENT BACK TO FREEPLAY?? - HIGH SCORE'); Mods.loadTopMod(); #if DISCORD_ALLOWED DiscordClient.resetClientID(); #end - MusicBeatState.switchState(new FreeplayState()); + MusicBeatState.switchState(new slushi.states.freeplay.SlushiFreeplayState()); FlxG.sound.playMusic(SlushiMain.getSLEPath("Musics/SLE_HackNet_Resonance.ogg")); } }); @@ -905,7 +907,7 @@ class ResultState extends MusicBeatSubState Debug.logInfo('rank is lower...... and/or equal'); Debug.logInfo('WENT BACK TO FREEPLAY?? - LOW SCORE'); Mods.loadTopMod(); - openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new FreeplayState(sticker))); + openSubState(new vslice.transition.StickerSubState(null, (sticker) -> new slushi.states.freeplay.SlushiFreeplayState(sticker))); FlxG.sound.playMusic(SlushiMain.getSLEPath("Musics/SLE_HackNet_Resonance.ogg")); } } diff --git a/funkinscsource/utils/logging/CrashHandler.hx b/funkinscsource/utils/logging/CrashHandler.hx index 4455a2e..6f7b403 100644 --- a/funkinscsource/utils/logging/CrashHandler.hx +++ b/funkinscsource/utils/logging/CrashHandler.hx @@ -84,7 +84,7 @@ class CrashHandler #if DISCORD_ALLOWED DiscordClient.shutdown(); #end - Sys.exit(1); + System.exit(1); } catch (e:Dynamic) { diff --git a/gitVersion.json b/gitVersion.json index 3048e47..3e0bf39 100644 --- a/gitVersion.json +++ b/gitVersion.json @@ -1,3 +1,3 @@ { - "engineVersion": "0.3.8" + "engineVersion": "0.4.0" } \ No newline at end of file diff --git a/hmm.json b/hmm.json index 3c08c1b..3afd1fb 100644 --- a/hmm.json +++ b/hmm.json @@ -60,6 +60,11 @@ "type": "haxelib", "version": null }, + { + "name": "compiletime", + "type": "haxelib", + "version": null + }, { "name": "flixel", "type": "git", @@ -72,7 +77,7 @@ "type": "git", "dir": null, "ref": "dev", - "url": "https://github.com/glowsoony/flixel-addons" + "url": "https://github.com/Slushi-Github/SLE-flixel-addons" }, { "name": "fnf-modcharting-tools",