fix(layout): close tools panel on outside click

This commit is contained in:
digua committed 2026-06-10 22:18:20 +08:00
1 parent b831c4ead8
commit bbcc350d97
3 files changed
+25 -1

No files matched your search

+23 -1
View File
@@ -1,5 +1,5 @@
<script setup lang="ts">
import { computed, watch } from 'vue'
import { computed, onBeforeUnmount, onMounted, ref, watch } from 'vue'
import { useI18n } from 'vue-i18n'
import { storeToRefs } from 'pinia'
import { useLayoutStore } from '@/stores/layout'
@@ -10,6 +10,7 @@ const { isToolsPanelMini, toolsPanelPosition, isToolsPanelOpen } = storeToRefs(l
const isHeaderMode = computed(() => toolsPanelPosition.value === 'header')
const isPanelVisible = computed(() => !isHeaderMode.value || isToolsPanelOpen.value)
const panelRef = ref<HTMLElement | null>(null)
type ToolEvent =
| 'openIncrementalImport'
@@ -29,6 +30,18 @@ function handleToolClick(event: ToolEvent) {
}
}
function handleDocumentMouseDown(event: MouseEvent) {
if (!isHeaderMode.value || !isToolsPanelOpen.value) return
const target = event.target
if (!(target instanceof Element)) return
// header 模式下,“更多”按钮在面板外部,需要排除它,否则点按钮关闭时会被外部点击监听反向打开。
if (panelRef.value?.contains(target) || target.closest('[data-tools-panel-trigger]')) return
isToolsPanelOpen.value = false
}
const tools = [
{
event: 'openIncrementalImport' as const,
@@ -89,6 +102,14 @@ const visibleTools = computed(() => (isHeaderMode.value ? headerTools : tools))
watch(toolsPanelPosition, () => {
isToolsPanelOpen.value = false
})
onMounted(() => {
document.addEventListener('mousedown', handleDocumentMouseDown)
})
onBeforeUnmount(() => {
document.removeEventListener('mousedown', handleDocumentMouseDown)
})
</script>
<template>
@@ -129,6 +150,7 @@ watch(toolsPanelPosition, () => {
:class="isPanelVisible ? 'translate-x-0 opacity-100' : 'pointer-events-none translate-x-full opacity-0'"
>
<div
ref="panelRef"
class="no-capture flex w-40 flex-col rounded-l-xl border border-r-0 border-gray-200/60 bg-white p-3 shadow-lg dark:border-white/5 dark:bg-gray-900"
>
<div class="mb-2 flex items-center justify-between">
+1
View File
@@ -163,6 +163,7 @@ const filteredMemberCount = computed(() => {
<CaptureButton color="gray" />
<UTooltip :text="t('analysis.tooltip.more')">
<UButton
data-tools-panel-trigger
icon="i-heroicons-ellipsis-horizontal"
variant="ghost"
color="gray"
+1
View File
@@ -176,6 +176,7 @@ const otherMemberAvatar = computed(() => {
<CaptureButton color="gray" />
<UTooltip :text="t('analysis.tooltip.more')">
<UButton
data-tools-panel-trigger
icon="i-heroicons-ellipsis-horizontal"
variant="ghost"
color="gray"