diff --git a/Makefile b/Makefile index 2bbe6cb..f405ec1 100644 --- a/Makefile +++ b/Makefile @@ -40,7 +40,7 @@ INCLUDES := include ./Libraries/FsLib/Switch/FsLib/include ./Libraries/SDLLib/SD EXEFS_SRC := exefs_src APP_TITLE := JKSV APP_AUTHOR := JK -APP_VERSION := 11.16.2025 +APP_VERSION := 11.29.2025 ROMFS := romfs ICON := icon.jpg diff --git a/include/builddate.hpp b/include/builddate.hpp index 72e191e..f894a9c 100644 --- a/include/builddate.hpp +++ b/include/builddate.hpp @@ -3,6 +3,6 @@ namespace builddate { inline constexpr int MONTH = 11; - inline constexpr int DAY = 16; + inline constexpr int DAY = 29; inline constexpr int YEAR = 2025; } diff --git a/include/stringutil.hpp b/include/stringutil.hpp index bd58bea..1c81e0a 100644 --- a/include/stringutil.hpp +++ b/include/stringutil.hpp @@ -6,8 +6,11 @@ namespace stringutil /// @brief Enum for creating date strings. enum class DateFormat : uint8_t { + Year_Month_Day, + Year_Day_Month, YearMonthDay, - YearDayMonth + YearDayMonth, + AscTime }; /// @brief Returns a formatted string as a C++ string. This uses C instead of std::format because std::format bloats the NRO @@ -38,5 +41,10 @@ namespace stringutil /// @brief Returns a date string. /// @param format Optional. Format to use. Default is Year_Month_Day-Time /// @return Date string. - std::string get_date_string(stringutil::DateFormat format = stringutil::DateFormat::YearMonthDay); + std::string get_date_string(stringutil::DateFormat format = stringutil::DateFormat::Year_Month_Day); + + /// @brief Attempts to generate an abbreviated version of the title passed by detecting spaces. + /// @param title Title string to generate abbreviation from. + /// @return String containing abbreviation. + std::string generate_abbreviated_title(std::string_view title); } // namespace stringutil diff --git a/source/appstates/BackupMenuState.cpp b/source/appstates/BackupMenuState.cpp index bee932b..674555d 100644 --- a/source/appstates/BackupMenuState.cpp +++ b/source/appstates/BackupMenuState.cpp @@ -274,14 +274,21 @@ void BackupMenuState::name_and_create_backup() std::snprintf(name, SIZE_NAME_LENGTH, "%s - %s", nickname, date.c_str()); } - // Doing thing like this so the strings don't linger. + // Doing this like this so the strings don't linger. keyboard::Dictionary dictionary{}; { - const std::string dateA = stringutil::get_date_string(); - const std::string dateB = stringutil::get_date_string(stringutil::DateFormat::YearDayMonth); - const std::string user = m_user->get_path_safe_nickname(); + // Start with all available date formats. + const std::string dateA = stringutil::get_date_string(stringutil::DateFormat::Year_Month_Day); + const std::string dateB = stringutil::get_date_string(stringutil::DateFormat::Year_Day_Month); + const std::string dateC = stringutil::get_date_string(stringutil::DateFormat::YearMonthDay); + const std::string dateD = stringutil::get_date_string(stringutil::DateFormat::YearDayMonth); + const std::string dateE = stringutil::get_date_string(stringutil::DateFormat::AscTime); - dictionary.add_list({dateA, dateB, user, ".zip"}); + // Path safe nickname. + const std::string user = m_user->get_path_safe_nickname(); + + // Add them before continuing. + dictionary.add_list({dateA, dateB, dateC, dateD, dateE, user, STRING_ZIP_EXT}); } const char *keyboardHeader = strings::get_by_name(strings::names::KEYBOARD, 0); diff --git a/source/keyboard/keyboard.cpp b/source/keyboard/keyboard.cpp index 85230b1..f4eb0a0 100644 --- a/source/keyboard/keyboard.cpp +++ b/source/keyboard/keyboard.cpp @@ -16,18 +16,10 @@ bool keyboard::get_input(SwkbdType keyboardType, // Cache instead of repeated calls. const bool hasDictionary = dictionary.has_value(); + const size_t wordCount = hasDictionary ? dictionary->get().get_count() : 0; - // This changes whether or not we're passed a dictionary here. - bool createError{}; - if (hasDictionary) - { - // Getting this out of the optional looks confusing... - const size_t wordCount = dictionary->get().get_count(); - createError = error::libnx(swkbdCreate(&keyboard, wordCount)); - } - else { createError = error::libnx(swkbdCreate(&keyboard, 0)); } - - // Just return false if we can't init the keyboard. + // If this fails, immediately return false. + const bool createError = error::libnx(swkbdCreate(&keyboard, wordCount)); if (createError) { return false; } // Standard swkbd init. @@ -46,6 +38,9 @@ bool keyboard::get_input(SwkbdType keyboardType, const SwkbdDictWord *words = reinterpret_cast(dictionary->get().get_words()); const size_t wordCount = dictionary->get().get_count(); + // Set the flags. + swkbdConfigSetDicFlag(&keyboard, 1); + // Add our word dictionary. swkbdConfigSetDictionary(&keyboard, words, wordCount); } diff --git a/source/remote/GoogleDrive.cpp b/source/remote/GoogleDrive.cpp index ae659ad..8e099bc 100644 --- a/source/remote/GoogleDrive.cpp +++ b/source/remote/GoogleDrive.cpp @@ -51,8 +51,6 @@ namespace remote::GoogleDrive::GoogleDrive() : Storage("[GD]", true) { - static constexpr const char *STRING_ERROR_READING_CONFIG = "Error reading Google Drive config: %s"; - // Load the json file. json::Object clientJson = json::new_object(json_object_from_file, remote::PATH_GOOGLE_DRIVE_CONFIG.data()); if (!clientJson) { return; } diff --git a/source/stringutil.cpp b/source/stringutil.cpp index 7e620a5..d68d84e 100644 --- a/source/stringutil.cpp +++ b/source/stringutil.cpp @@ -110,30 +110,73 @@ bool stringutil::sanitize_string_for_path(const char *stringIn, char *stringOut, std::string stringutil::get_date_string(stringutil::DateFormat format) { + // This is the size of the buffer used for C functions. static constexpr size_t STRING_BUFFER_SIZE = 0x80; - char stringBuffer[STRING_BUFFER_SIZE] = {0}; - + // Grab local system time. std::time_t timer{}; std::time(&timer); const std::tm localTime = *std::localtime(&timer); + // String to return + std::string returnString{}; + switch (format) { + case stringutil::DateFormat::Year_Month_Day: + { + // These are like this because the final one needs a character stripped from the string to be safe. + char buffer[STRING_BUFFER_SIZE]{}; + std::strftime(buffer, STRING_BUFFER_SIZE, "%Y-%m-%d_%H-%M-%S", &localTime); + returnString = buffer; + } + break; + + case stringutil::DateFormat::Year_Day_Month: + { + char buffer[STRING_BUFFER_SIZE]{}; + std::strftime(buffer, STRING_BUFFER_SIZE, "%Y-%d-%m_%H-%M-%S", &localTime); + returnString = buffer; + } + break; + case stringutil::DateFormat::YearMonthDay: { - std::strftime(stringBuffer, STRING_BUFFER_SIZE, "%Y-%m-%d_%H-%M-%S", &localTime); + char buffer[STRING_BUFFER_SIZE]{}; + std::strftime(buffer, STRING_BUFFER_SIZE, "%Y%d%m_%H%M%S", &localTime); + returnString = buffer; } break; case stringutil::DateFormat::YearDayMonth: { - std::strftime(stringBuffer, STRING_BUFFER_SIZE, "%Y-%d-%m_%H-%M-%S", &localTime); + char buffer[STRING_BUFFER_SIZE]{}; + std::strftime(buffer, STRING_BUFFER_SIZE, "%Y%m%d_%H%M%S", &localTime); + returnString = buffer; + } + break; + + case stringutil::DateFormat::AscTime: + { + // Just assign to asctime. + returnString = std::asctime(&localTime); + // Strip the colons. + stringutil::replace_in_string(returnString, ":", "-"); + stringutil::strip_character('\n', returnString); } break; } - return std::string(stringBuffer); + return returnString; +} + +std::string stringutil::generate_abbreviated_title(std::string_view title) +{ + size_t space = title.find_first_of(' '); + // Don't bother. + if (title.empty() || space == title.npos) { return {}; } + + // } static const std::unordered_map &get_replacement_table()