diff --git a/include/utils/cia.h b/include/utils/cia.h index 5f4794d..0ff14a4 100644 --- a/include/utils/cia.h +++ b/include/utils/cia.h @@ -2,4 +2,8 @@ #include "common.hpp" +#include <3ds.h> + +Result CIA_LaunchTitle(u64 titleId, FS_MediaType mediaType); +Result deletePrevious(u64 titleid, FS_MediaType media); Result installCia(const char * ciaPath); \ No newline at end of file diff --git a/include/utils/scriptHelper.hpp b/include/utils/scriptHelper.hpp index ae388b9..5612470 100644 --- a/include/utils/scriptHelper.hpp +++ b/include/utils/scriptHelper.hpp @@ -45,6 +45,9 @@ namespace ScriptHelper { void displayTimeMsg(std::string message, int seconds); bool checkIfValid(std::string scriptFile, int mode = 0); + + void deleteTitle(const std::string TitleID, bool isNAND, std::string message); + void bootTitle(const std::string TitleID, bool isNAND, std::string message); } #endif \ No newline at end of file diff --git a/romfs/lang/en/app.json b/romfs/lang/en/app.json index f165dc9..aa2a584 100644 --- a/romfs/lang/en/app.json +++ b/romfs/lang/en/app.json @@ -111,5 +111,10 @@ "OWNER_AND_REPO": "Owner & Repo", "FILENAME": "Filename", "OK": "OK", - "DELETE_STORE": "Would you like to delete this store?" + "DELETE_STORE": "Would you like to delete this store?", + + "DELETE_TITLE": "Would you like to delete this title?", + "MEDIATYPE_SD": "MediaType SD", + "MEDIATYPE_NAND": "MediaType NAND", + "BOOT_TITLE": "Would you like to boot this title?" } diff --git a/source/init.cpp b/source/init.cpp index 87ff5d9..cd820e3 100644 --- a/source/init.cpp +++ b/source/init.cpp @@ -84,6 +84,7 @@ void Init::stopMusic(void) { Result Init::Initialize() { gfxInitDefault(); romfsInit(); + amInit(); Gui::init(); Gui::loadSheet("romfs:/gfx/sprites.t3x", sprites); sdmcInit(); @@ -116,12 +117,12 @@ Result Init::Initialize() { playMusic(); } - return 0; + return 0; } Result Init::MainLoop() { - // Initialize everything. - Initialize(); + // Initialize everything. + Initialize(); // Loop as long as the status is not exiting. while (aptMainLoop() && !exiting) @@ -146,11 +147,13 @@ Result Init::MainLoop() { } } } - // Exit all services and exit the app. - Exit(); - return 0; + // Exit all services and exit the app. + Exit(); + return 0; } +extern void freeSheet(); + Result Init::Exit() { if (songIsFound == true) { stopMusic(); @@ -159,12 +162,16 @@ Result Init::Exit() { if (dspFound == true) { ndspExit(); } + + // Free UniStore spritesheet, just in case. + freeSheet(); Config::save(); Gui::exit(); Gui::unloadSheet(sprites); gfxExit(); cfguExit(); acExit(); + amExit(); romfsExit(); sdmcExit(); return 0; diff --git a/source/screens/scriptlist.cpp b/source/screens/scriptlist.cpp index cc03ecd..25f8b16 100644 --- a/source/screens/scriptlist.cpp +++ b/source/screens/scriptlist.cpp @@ -211,6 +211,28 @@ void runFunctions(nlohmann::json &json) { if(!missing) ScriptHelper::displayTimeMsg(message, seconds); } else if (type == "saveConfig") { Config::save(); + } else if (type == "deleteTitle") { + std::string TitleID = ""; + std::string message = ""; + bool isNAND = false, missing = false; + if(json.at(choice).at(i).contains("TitleID")) TitleID = json.at(choice).at(i).at("TitleID"); + else missing = true; + if (json.at(choice).at(i).contains("NAND") && json.at(choice).at(i).at("NAND").is_boolean()) isNAND = json.at(choice).at(i).at("NAND"); + else missing = true; + if(json.at(choice).at(i).contains("message")) message = json.at(choice).at(i).at("message"); + else missing = true; + if(!missing) ScriptHelper::deleteTitle(TitleID, isNAND, message); + } else if (type == "bootTitle") { + std::string TitleID = ""; + std::string message = ""; + bool isNAND = false, missing = false; + if(json.at(choice).at(i).contains("TitleID")) TitleID = json.at(choice).at(i).at("TitleID"); + else missing = true; + if (json.at(choice).at(i).contains("NAND") && json.at(choice).at(i).at("NAND").is_boolean()) isNAND = json.at(choice).at(i).at("NAND"); + else missing = true; + if(json.at(choice).at(i).contains("message")) message = json.at(choice).at(i).at("message"); + else missing = true; + if(!missing) ScriptHelper::bootTitle(TitleID, isNAND, message); } } doneMsg(); diff --git a/source/screens/unistore.cpp b/source/screens/unistore.cpp index 820c258..c7572ec 100644 --- a/source/screens/unistore.cpp +++ b/source/screens/unistore.cpp @@ -49,7 +49,6 @@ extern u32 TextColor; extern u32 progressBar; extern u32 selected; extern u32 unselected; - C2D_SpriteSheet appStoreSheet; struct storeInfo2 { @@ -120,12 +119,16 @@ std::string storeDesc = ""; bool sheetHasLoaded = false; // Sheet / Icon stuff. void loadStoreSheet(int pos) { - appStoreSheet = C2D_SpriteSheetLoad(storeInfo[pos].storeSheet.c_str()); - sheetHasLoaded = true; + if (sheetHasLoaded == false) { + appStoreSheet = C2D_SpriteSheetLoad(storeInfo[pos].storeSheet.c_str()); + sheetHasLoaded = true; + } } void freeSheet() { - C2D_SpriteSheetFree(appStoreSheet); - sheetHasLoaded = false; + if (sheetHasLoaded == true) { + C2D_SpriteSheetFree(appStoreSheet); + sheetHasLoaded = false; + } } void drawBlend(int key, int x, int y) { @@ -857,6 +860,28 @@ void UniStore::execute() { Config::save(); } else if (type == "notImplemented") { notImplemented(); + } else if (type == "deleteTitle") { + std::string TitleID = ""; + std::string message = ""; + bool isNAND = false, missing = false; + if(appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).contains("TitleID")) TitleID = appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).at("TitleID"); + else missing = true; + if (appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).contains("NAND") && appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).at("NAND").is_boolean()) isNAND = appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).at("NAND"); + else missing = true; + if(appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).contains("message")) message = appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).at("message"); + else missing = true; + if(!missing) ScriptHelper::deleteTitle(TitleID, isNAND, message); + } else if (type == "bootTitle") { + std::string TitleID = ""; + std::string message = ""; + bool isNAND = false, missing = false; + if(appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).contains("TitleID")) TitleID = appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).at("TitleID"); + else missing = true; + if (appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).contains("NAND") && appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).at("NAND").is_boolean()) isNAND = appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).at("NAND"); + else missing = true; + if(appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).contains("message")) message = appStoreJson.at("storeContent").at(selectedOptionAppStore).at("script").at(i).at("message"); + else missing = true; + if(!missing) ScriptHelper::bootTitle(TitleID, isNAND, message); } } doneMsg(); diff --git a/source/utils/cia.c b/source/utils/cia.c index 51d818e..9db7d9d 100644 --- a/source/utils/cia.c +++ b/source/utils/cia.c @@ -2,7 +2,7 @@ bool updatingSelf = false; -static Result CIA_LaunchTitle(u64 titleId, FS_MediaType mediaType) { +Result CIA_LaunchTitle(u64 titleId, FS_MediaType mediaType) { Result ret = 0; u8 param[0x300]; u8 hmac[0x20]; @@ -74,12 +74,6 @@ Result installCia(const char * ciaPath) AM_TitleEntry info; Result ret = 0; - ret = amInit(); - if (R_FAILED(ret)) { - printf("Error in:\namInit();\n"); - return ret; - } - FS_MediaType media = MEDIATYPE_SD; ret = openFile(&fileHandle, ciaPath, false); @@ -140,6 +134,5 @@ Result installCia(const char * ciaPath) if (R_FAILED(ret = CIA_LaunchTitle(info.titleID, MEDIATYPE_SD))) return ret; } - amExit(); return 0; } \ No newline at end of file diff --git a/source/utils/scriptHelper.cpp b/source/utils/scriptHelper.cpp index ec66f19..d32fbc6 100644 --- a/source/utils/scriptHelper.cpp +++ b/source/utils/scriptHelper.cpp @@ -148,4 +148,36 @@ bool ScriptHelper::checkIfValid(std::string scriptFile, int mode) { } return true; +} + +void ScriptHelper::deleteTitle(const std::string TitleID, bool isNAND, std::string message) { + std::string MSG = Lang::get("DELETE_TITLE") + "\n\n"; + if (isNAND) MSG += Lang::get("MEDIATYPE_NAND") + "\n" + TitleID; + else MSG += Lang::get("MEDIATYPE_SD") + "\n" + TitleID; + u64 ID = std::stoull(TitleID, 0, 16); + if (Msg::promptMsg(MSG)) { + if (isNAND == true) { + Msg::DisplayMsg(message); + deletePrevious(ID, MEDIATYPE_NAND); + } else { + Msg::DisplayMsg(message); + deletePrevious(ID, MEDIATYPE_SD); + } + } +} + +void ScriptHelper::bootTitle(const std::string TitleID, bool isNAND, std::string message) { + std::string MSG = Lang::get("BOOT_TITLE") + "\n\n"; + if (isNAND) MSG += Lang::get("MEDIATYPE_NAND") + "\n" + TitleID; + else MSG += Lang::get("MEDIATYPE_SD") + "\n" + TitleID; + u64 ID = std::stoull(TitleID, 0, 16); + if (Msg::promptMsg(MSG)) { + if (isNAND == true) { + Msg::DisplayMsg(message); + CIA_LaunchTitle(ID, MEDIATYPE_NAND); + } else { + Msg::DisplayMsg(message); + CIA_LaunchTitle(ID, MEDIATYPE_SD); + } + } } \ No newline at end of file