diff --git a/src/activities/util/DirectoryPickerActivity.cpp b/src/activities/util/DirectoryPickerActivity.cpp index a10b4302..4902d3a4 100644 --- a/src/activities/util/DirectoryPickerActivity.cpp +++ b/src/activities/util/DirectoryPickerActivity.cpp @@ -63,6 +63,14 @@ void DirectoryPickerActivity::loadDirectories() { StringUtils::sortFileList(directories); } +void DirectoryPickerActivity::navigateToParent() { + auto slash = basepath.find_last_of('/'); + basepath = (slash == 0) ? "/" : basepath.substr(0, slash); + selectorIndex = 0; + loadDirectories(); + requestUpdate(); +} + void DirectoryPickerActivity::loop() { // Absorb the Confirm release from the parent activity that launched us if (waitForConfirmRelease) { @@ -72,14 +80,16 @@ void DirectoryPickerActivity::loop() { return; } - // Index 0 = "Save Here", indices 1..N = directory entries - const int totalItems = 1 + static_cast(directories.size()); + const int offset = directoryOffset(); + const int totalItems = offset + static_cast(directories.size()); if (mappedInput.wasReleased(MappedInputManager::Button::Confirm)) { if (selectorIndex == 0) { onSelect(basepath); + } else if (showGoUp() && selectorIndex == 1) { + navigateToParent(); } else { - const auto& dirName = directories[selectorIndex - 1]; + const auto& dirName = directories[selectorIndex - offset]; // Strip trailing '/' std::string folderName = dirName.substr(0, dirName.length() - 1); basepath = (basepath.back() == '/' ? basepath : basepath + "/") + folderName; @@ -94,11 +104,7 @@ void DirectoryPickerActivity::loop() { if (basepath == "/") { onCancel(); } else { - auto slash = basepath.find_last_of('/'); - basepath = (slash == 0) ? "/" : basepath.substr(0, slash); - selectorIndex = 0; - loadDirectories(); - requestUpdate(); + navigateToParent(); } return; } @@ -139,21 +145,24 @@ void DirectoryPickerActivity::render(Activity::RenderLock&&) { const int contentTop = metrics.topPadding + metrics.headerHeight + metrics.verticalSpacing; const int contentHeight = pageHeight - contentTop - metrics.buttonHintsHeight - metrics.verticalSpacing; - const int totalItems = 1 + static_cast(directories.size()); + const int offset = directoryOffset(); + const int totalItems = offset + static_cast(directories.size()); + const bool goUp = showGoUp(); GUI.drawList( renderer, Rect{0, contentTop, pageWidth, contentHeight}, totalItems, selectorIndex, - [this](int index) -> std::string { + [this, offset, goUp](int index) -> std::string { if (index == 0) { - std::string label = std::string(tr(STR_SAVE_HERE)) + " (" + basepath + ")"; - return label; + return std::string(tr(STR_SAVE_HERE)) + " (" + basepath + ")"; } - // Strip trailing '/' for display - const auto& dir = directories[index - 1]; + if (goUp && index == 1) { + return ".."; + } + const auto& dir = directories[index - offset]; return dir.substr(0, dir.length() - 1); }, nullptr, - [this](int index) -> UIIcon { + [](int index) -> UIIcon { return (index == 0) ? UIIcon::File : UIIcon::Folder; }); diff --git a/src/activities/util/DirectoryPickerActivity.h b/src/activities/util/DirectoryPickerActivity.h index f4eb4aca..aa8c9855 100644 --- a/src/activities/util/DirectoryPickerActivity.h +++ b/src/activities/util/DirectoryPickerActivity.h @@ -41,4 +41,7 @@ class DirectoryPickerActivity final : public Activity { std::function onCancel; void loadDirectories(); + void navigateToParent(); + [[nodiscard]] bool showGoUp() const { return basepath != "/"; } + [[nodiscard]] int directoryOffset() const { return showGoUp() ? 2 : 1; } };