fix(desktop): lock appbar to edge

This commit is contained in:
2026-07-25 20:14:58 +08:00
parent 1e1718caee
commit 81ffe64446
5 changed files with 13 additions and 118 deletions

View File

@@ -1,7 +1,7 @@
import { useEffect, useRef, useState } from 'react'
import { Alert, Avatar, Button, Empty, Input, Message, Modal, Select, Spin, Tag, Typography } from '@arco-design/web-react'
import {
IconApps, IconArrowLeft, IconArrowRight, IconCheckCircle, IconClockCircle,
IconApps, IconCheckCircle, IconClockCircle,
IconFile, IconFolder, IconPlus, IconRefresh, IconRobot, IconSearch, IconSettings,
} from '@arco-design/web-react/icon'
import {
@@ -12,7 +12,6 @@ import {
const { Text, Title } = Typography
type View = 'home' | 'tasks' | 'notes' | 'ai' | 'more'
type DockSide = 'left' | 'right'
type Action = 'project' | 'task' | 'cron' | null
type ConnectionStatus = 'checking' | 'online' | 'offline'
@@ -32,21 +31,11 @@ export function App() {
const [experts, setExperts] = useState<Expert[]>([])
const [aiSessions, setAISessions] = useState<AISession[]>([])
const [view, setView] = useState<View>('home')
const [dockSide, setDockSide] = useState<DockSide>(() => {
if ('__TAURI_INTERNALS__' in window) return 'right'
return localStorage.getItem('senlin-mini-dock') === 'left' ? 'left' : 'right'
})
const [loading, setLoading] = useState(Boolean(session))
const [error, setError] = useState('')
const [action, setAction] = useState<Action>(null)
const refreshGeneration = useRef(0)
useEffect(() => {
document.documentElement.dataset.dock = dockSide
localStorage.setItem('senlin-mini-dock', dockSide)
void moveDesktopWindow(dockSide)
}, [dockSide])
useEffect(() => {
if (!session) return
let cancelled = false
@@ -89,10 +78,6 @@ export function App() {
}
}
async function dock(side: DockSide) {
setDockSide(side)
}
if (!session) return <Login onLogin={(next) => { localStorage.setItem('senlin-mini-session', JSON.stringify(next)); setSession(next) }} />
const activeProject = projects.find((project) => project.id === projectId) ?? projects[0]
@@ -112,10 +97,6 @@ export function App() {
<span>AI</span>
<Tag size="small" color="arcoblue">App 1.0</Tag>
</div>
<div className="window-actions">
<Button aria-label="停靠左侧" className={dockSide === 'left' ? 'active' : ''} type="text" size="mini" icon={<IconArrowLeft />} onClick={() => void dock('left')} />
<Button aria-label="停靠右侧" className={dockSide === 'right' ? 'active' : ''} type="text" size="mini" icon={<IconArrowRight />} onClick={() => void dock('right')} />
</div>
</header>
<div className="project-switcher">
@@ -415,13 +396,3 @@ function errorMessage(error: unknown) {
if (error instanceof ApiError || error instanceof Error) return error.message
return '操作失败,请稍后重试'
}
async function moveDesktopWindow(side: DockSide) {
if (!('__TAURI_INTERNALS__' in window)) return
try {
const { invoke } = await import('@tauri-apps/api/core')
await invoke('dock_window', { side })
} catch (requestError) {
Message.warning(errorMessage(requestError))
}
}

View File

@@ -17,19 +17,16 @@ button, input, textarea { font: inherit; }
button { color: inherit; }
.mini-shell {
width: min(100%, 440px);
width: 100%;
height: 100vh;
display: grid;
grid-template-rows: 44px 50px 58px minmax(0, 1fr) 28px;
overflow: hidden;
background: var(--canvas);
border: 1px solid rgba(78, 89, 105, 0.18);
box-shadow: 0 20px 60px rgba(29, 33, 41, 0.18);
border: 0;
box-shadow: none;
}
html[data-dock="right"] .mini-shell { margin-left: auto; }
html[data-dock="left"] .mini-shell { margin-right: auto; }
.mini-header,
.project-switcher,
.mini-nav,
@@ -47,7 +44,6 @@ html[data-dock="left"] .mini-shell { margin-right: auto; }
}
.mini-brand,
.window-actions,
.project-trigger,
.mini-footer,
.section-title,
@@ -63,9 +59,6 @@ html[data-dock="left"] .mini-shell { margin-right: auto; }
.mini-brand { gap: 7px; font-weight: 800; }
.mini-brand img { width: 25px; height: 25px; }
.mini-brand .arco-tag { margin-left: 2px; }
.window-actions { gap: 2px; }
.window-actions .arco-btn { color: #6b778c; }
.window-actions .active { color: var(--blue); background: #edf3ff; }
.project-switcher {
display: grid;
@@ -236,14 +229,7 @@ html[data-dock="left"] .mini-shell { margin-right: auto; }
.mini-form { display: grid; gap: 13px; }
.mini-form .arco-select { width: 100%; }
@media (min-width: 700px) {
body { display: flex; }
html[data-dock="right"] body { justify-content: flex-end; }
html[data-dock="left"] body { justify-content: flex-start; }
}
@media (max-width: 359px) {
.mini-shell { border: 0; }
.mini-brand .arco-tag { display: none; }
.note-grid, .expert-strip { grid-template-columns: 1fr; }
}