From 8306091de489c107e2f5530326dc3c5aba3080eb Mon Sep 17 00:00:00 2001 From: mykh-hailo Date: Mon, 6 Apr 2026 00:29:51 -0400 Subject: [PATCH] fix: folder tree selection after any action in main content Signed-off-by: mykh-hailo --- .../components/FilesNavigationListItem.vue | 46 ++++++++++++++++++- 1 file changed, 45 insertions(+), 1 deletion(-) diff --git a/apps/files/src/components/FilesNavigationListItem.vue b/apps/files/src/components/FilesNavigationListItem.vue index a4bda51a19140..f854b21600dcb 100644 --- a/apps/files/src/components/FilesNavigationListItem.vue +++ b/apps/files/src/components/FilesNavigationListItem.vue @@ -8,12 +8,20 @@ import type { IView } from '@nextcloud/files' import { getCanonicalLocale, getLanguage } from '@nextcloud/l10n' import { computed, onMounted, ref } from 'vue' +import { useRoute } from 'vue-router/composables' import NcAppNavigationItem from '@nextcloud/vue/components/NcAppNavigationItem' import NcIconSvgWrapper from '@nextcloud/vue/components/NcIconSvgWrapper' import { useVisibleViews } from '../composables/useViews.ts' import { folderTreeId } from '../services/FolderTree.ts' import { useViewConfigStore } from '../store/viewConfig.ts' +/** + * Views whose main file list is driven by `dir`. The route often carries a `fileid` for the + * selected row; many actions switch `view` between `folders`, `files`, and `personal` while + * keeping the same directory — the folder tree should stay highlighted based on `dir` only. + */ +const PATH_BASED_LISTING_VIEW_IDS = new Set([folderTreeId, 'files', 'personal']) + const props = withDefaults(defineProps<{ view: IView level?: number @@ -24,9 +32,22 @@ const props = withDefaults(defineProps<{ const maxLevel = 6 // Limit nesting to not exceed max call stack size const viewConfigStore = useViewConfigStore() const viewConfig = computed(() => viewConfigStore.viewConfigs[props.view.id]) +const route = useRoute() const isExpanded = computed(() => viewConfig.value ? (viewConfig.value.expanded === true) : (props.view.expanded === true)) +const isFolderTreeNode = computed(() => props.view.id.startsWith(`${folderTreeId}::`)) +const isDirectoryActive = computed(() => { + if (!isFolderTreeNode.value) { + return false + } + + const currentView = String(route.params?.view ?? '') + const currentDir = normalizeDir(route.query?.dir) + const viewDir = normalizeDir(props.view.params?.dir) + + return PATH_BASED_LISTING_VIEW_IDS.has(currentView) && currentDir === viewDir +}) const views = useVisibleViews() const childViews = computed(() => { @@ -66,6 +87,16 @@ const hasChildViews = computed(() => childViews.value.length > 0) const navigationRoute = computed(() => { if (props.view.params) { const { dir } = props.view.params + // Folder tree: navigate by `dir` only (no `fileid` in the path). Matches how the list + // is located (`?dir=…`) even when a file row is selected (`/:fileid`). + if (isFolderTreeNode.value) { + const dirParam = typeof dir === 'string' ? dir : '/' + return { + name: 'filelist', + params: { view: folderTreeId }, + query: { dir: dirParam }, + } + } return { name: 'filelist', params: { ...props.view.params }, query: { dir } } } return { name: 'filelist', params: { view: props.view.id } } @@ -121,6 +152,18 @@ async function loadChildViews() { } } } + +/** + * Normalize directory paths for route comparisons. + * + * @param dir - the route directory to normalize + */ +function normalizeDir(dir: unknown): string { + if (typeof dir !== 'string' || dir.length === 0) { + return '/' + } + return dir.replace(/^(.+)\/$/, '$1') +}