From 7502393f4014fd19fac4823d5a2a67a306563bf0 Mon Sep 17 00:00:00 2001 From: schroda <50052685+schroda@users.noreply.github.com> Date: Thu, 30 Oct 2025 00:19:39 +0100 Subject: [PATCH] Fix back button when previous page should be ignored In case the previous page in the history should be ignored, the back button just went back to the root page (library). Instead, it should try to go back to the next page in the history until there is no page to go back to anymore. --- CHANGELOG.md | 3 ++- src/base/hooks/useBackButton.ts | 40 ++++++++++++++++++++++++++------- 2 files changed, 34 insertions(+), 9 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index fa35e812..2fd77c62 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -23,6 +23,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/). ### Fixed - (**General**) Fix tooltips sometimes causing a layout shift +- (**General**) Fix back button under some specific conditions (e.g., `library category X` → `mange` → `reader` → `manga` → back button → `library`; should have opened `library category X`) - (**Manga**) Fix failing migration with disabled "tracking" data - (**Manga**) Fix showing private tracking option for trackers which do not support the option - (**Manga**) Fix redirection to tracker settings in case no tracker is logged in @@ -154,7 +155,7 @@ Thanks to everyone that contributed to this release ### Fixed - (**General**) Fix custom long press causing native mobile long press menu to get opened - (**General**) Fix refreshing data after importing a backup -- (**Reader**) Fix each key press triggering a keybind (example: "n" -> next page, "ctrl+n" -> next chapter - previously "ctrl+n" would have triggered both keybinds) +- (**Reader**) Fix each key press triggering a keybind (example: "n" → next page, "ctrl+n" → next chapter - previously "ctrl+n" would have triggered both keybinds) - (**Reader**) Fix weird jumpiness while changing pages via progress bar dragging on iOS - (**Reader**) Fix resuming a chapter when selecting an already visible chapter (infinite scroll) from the chapter list - (**Reader**) Fix continuous reading mode tap zone click scrolling aborting sometimes diff --git a/src/base/hooks/useBackButton.ts b/src/base/hooks/useBackButton.ts index 19947732..bce5819c 100644 --- a/src/base/hooks/useBackButton.ts +++ b/src/base/hooks/useBackButton.ts @@ -11,7 +11,8 @@ import { useCallback } from 'react'; import { AppRoutes } from '@/base/AppRoute.constants.ts'; import { useAppPageHistoryContext } from '@/base/contexts/AppPageHistoryContext.tsx'; -const PAGES_TO_IGNORE: readonly RegExp[] = [/\/manga\/[0-9]+\/chapter\/[0-9]+/g]; +const READER_REGEX = /\/manga\/[0-9]+\/chapter\/[0-9]+/g; +const PAGES_TO_IGNORE: readonly RegExp[] = [READER_REGEX]; export const useBackButton = () => { const navigate = useNavigate(); @@ -19,16 +20,39 @@ export const useBackButton = () => { const history = useAppPageHistoryContext(); return useCallback(() => { - const isHistoryEmpty = !history.length; - const isLastPageInHistoryCurrentPage = history.length === 1 && history[0] === location.pathname; - const ignorePreviousPage = history.length && PAGES_TO_IGNORE.some((page) => !!history.slice(-2)[0].match(page)); + const getDelta = (historyToCheck: string[] = history, delta: number = 0) => { + const isHistoryEmpty = !historyToCheck.length; + if (isHistoryEmpty) { + return 0; + } - const canNavigateBack = !ignorePreviousPage && !isHistoryEmpty && !isLastPageInHistoryCurrentPage; - if (canNavigateBack) { - navigate(-1); + const isLastPageInHistoryCurrentPage = + historyToCheck.length === 1 && historyToCheck[0] === location.pathname; + if (isLastPageInHistoryCurrentPage) { + return 0; + } + + const previousPage = historyToCheck.slice(-2)[0]; + + const isPreviousPageCurrentPage = previousPage === location.pathname; + const ignorePreviousPage = PAGES_TO_IGNORE.some((page) => !!previousPage.match(page)); + + const skipPreviousPage = isPreviousPageCurrentPage || ignorePreviousPage; + if (!skipPreviousPage) { + return delta - 1; + } + + return getDelta(historyToCheck.slice(0, -1), delta - 1); + }; + + const backDelta = getDelta(); + + const canNavigateBack = backDelta < 0; + if (!canNavigateBack) { + navigate(AppRoutes.library.path()); return; } - navigate(AppRoutes.library.path()); + navigate(backDelta); }, [history, location.pathname]); };