前端: 浅色模式 + 系统自动主题
- 引入语义化 CSS 变量令牌(bg/surface/edge/ink/muted/accent 等), data-theme 三态切换 - theme store(localStorage + 系统偏好跟随), 首屏内联脚本防主题闪烁 - ThemeToggle 组件(浅色/深色/跟随系统) 置于导航与控制台顶栏 - 全量替换硬编码 zinc/emerald/red 类为令牌, 图表基线/状态色随主题适配 - 浅色对比度校准(accent/err/warn 深浅各一套) Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@@ -93,13 +93,13 @@ onMounted(load)
|
||||
<div class="mb-6 flex items-center justify-between">
|
||||
<div>
|
||||
<h1 class="text-lg font-semibold">用户</h1>
|
||||
<p class="text-sm text-zinc-500">管理角色、状态与余额</p>
|
||||
<p class="text-sm text-muted">管理角色、状态与余额</p>
|
||||
</div>
|
||||
<div class="flex gap-2">
|
||||
<input
|
||||
v-model="q"
|
||||
placeholder="搜索用户名 / 邮箱"
|
||||
class="h-10 w-56 rounded-md border border-zinc-700 bg-zinc-900 px-3 text-sm outline-none focus:border-accent"
|
||||
class="h-10 w-56 rounded-md border border-edge2 bg-surface px-3 text-sm outline-none focus:border-accent"
|
||||
@keyup.enter="search"
|
||||
/>
|
||||
<Button variant="ghost" @click="search">搜索</Button>
|
||||
@@ -110,7 +110,7 @@ onMounted(load)
|
||||
<div class="overflow-x-auto">
|
||||
<table class="w-full text-sm">
|
||||
<thead>
|
||||
<tr class="border-b border-zinc-800 text-left text-xs text-zinc-500">
|
||||
<tr class="border-b border-edge text-left text-xs text-muted">
|
||||
<th scope="col" class="px-4 py-2.5 font-medium">ID</th>
|
||||
<th scope="col" class="px-4 py-2.5 font-medium">用户名</th>
|
||||
<th scope="col" class="px-4 py-2.5 font-medium">邮箱</th>
|
||||
@@ -123,35 +123,35 @@ onMounted(load)
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr v-for="u in users" :key="u.id" class="table-row">
|
||||
<td class="px-4 py-2.5 font-mono text-xs text-zinc-500">{{ u.id }}</td>
|
||||
<td class="px-4 py-2.5 text-zinc-200">
|
||||
<td class="px-4 py-2.5 font-mono text-xs text-muted">{{ u.id }}</td>
|
||||
<td class="px-4 py-2.5 text-ink">
|
||||
{{ u.username }}
|
||||
<span v-if="u.id === auth.user?.id" class="text-[11px] text-zinc-600">(我)</span>
|
||||
<span v-if="u.id === auth.user?.id" class="text-[11px] text-muted">(我)</span>
|
||||
</td>
|
||||
<td class="px-4 py-2.5 text-xs text-zinc-400">{{ u.email }}</td>
|
||||
<td class="px-4 py-2.5 text-xs text-muted">{{ u.email }}</td>
|
||||
<td class="px-4 py-2.5">
|
||||
<Badge :variant="u.role === 'admin' ? 'accent' : 'neutral'">{{ u.role }}</Badge>
|
||||
</td>
|
||||
<td class="px-4 py-2.5 mono-num text-xs text-emerald-300/90">{{ fmtMoney(u.balance) }}</td>
|
||||
<td class="px-4 py-2.5 mono-num text-xs text-accent">{{ fmtMoney(u.balance) }}</td>
|
||||
<td class="px-4 py-2.5">
|
||||
<Badge :variant="u.status === 'active' ? 'ok' : 'warn'">{{ u.status }}</Badge>
|
||||
</td>
|
||||
<td class="px-4 py-2.5 font-mono text-xs text-zinc-500">{{ fmtTime(u.created_at) }}</td>
|
||||
<td class="px-4 py-2.5 font-mono text-xs text-muted">{{ fmtTime(u.created_at) }}</td>
|
||||
<td class="px-4 py-2.5 text-right">
|
||||
<div class="flex justify-end gap-2">
|
||||
<button class="text-xs text-zinc-500 hover:text-zinc-200" @click="openEdit(u)">编辑</button>
|
||||
<button class="text-xs text-zinc-500 hover:text-accent" @click="openBalance(u)">调余额</button>
|
||||
<button class="text-xs text-muted hover:text-ink" @click="openEdit(u)">编辑</button>
|
||||
<button class="text-xs text-muted hover:text-accent" @click="openBalance(u)">调余额</button>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr v-if="users.length === 0">
|
||||
<td colspan="8" class="px-4 py-10 text-center text-sm text-zinc-600">无用户</td>
|
||||
<td colspan="8" class="px-4 py-10 text-center text-sm text-muted">无用户</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div class="flex items-center justify-between border-t border-zinc-800 px-4 py-3">
|
||||
<span class="font-mono text-xs text-zinc-600">共 {{ total }} 人</span>
|
||||
<div class="flex items-center justify-between border-t border-edge px-4 py-3">
|
||||
<span class="font-mono text-xs text-muted">共 {{ total }} 人</span>
|
||||
<div class="flex gap-2">
|
||||
<Button size="sm" variant="ghost" :disabled="page <= 1" @click="goPage(page - 1)">上一页</Button>
|
||||
<Button size="sm" variant="ghost" :disabled="page * pageSize >= total" @click="goPage(page + 1)">下一页</Button>
|
||||
@@ -163,15 +163,15 @@ onMounted(load)
|
||||
<Modal :open="editOpen" title="编辑用户" @close="editOpen = false">
|
||||
<div class="space-y-4">
|
||||
<label class="block">
|
||||
<span class="mb-1.5 block text-xs font-medium text-zinc-400">角色</span>
|
||||
<select v-model="editForm.role" class="h-10 w-full rounded-md border border-zinc-700 bg-zinc-900 px-3 text-sm outline-none focus:border-accent">
|
||||
<span class="mb-1.5 block text-xs font-medium text-muted">角色</span>
|
||||
<select v-model="editForm.role" class="h-10 w-full rounded-md border border-edge2 bg-surface px-3 text-sm outline-none focus:border-accent">
|
||||
<option value="user">user</option>
|
||||
<option value="admin">admin</option>
|
||||
</select>
|
||||
</label>
|
||||
<label class="block">
|
||||
<span class="mb-1.5 block text-xs font-medium text-zinc-400">状态</span>
|
||||
<select v-model="editForm.status" class="h-10 w-full rounded-md border border-zinc-700 bg-zinc-900 px-3 text-sm outline-none focus:border-accent">
|
||||
<span class="mb-1.5 block text-xs font-medium text-muted">状态</span>
|
||||
<select v-model="editForm.status" class="h-10 w-full rounded-md border border-edge2 bg-surface px-3 text-sm outline-none focus:border-accent">
|
||||
<option value="active">active</option>
|
||||
<option value="disabled">disabled</option>
|
||||
</select>
|
||||
@@ -186,7 +186,7 @@ onMounted(load)
|
||||
<!-- 调整余额 -->
|
||||
<Modal :open="balanceOpen" :title="`调整余额 · ${balanceUser?.username}`" @close="balanceOpen = false">
|
||||
<div class="space-y-4">
|
||||
<p class="text-xs text-zinc-500">当前余额 {{ fmtMoney(balanceUser?.balance ?? 0) }}</p>
|
||||
<p class="text-xs text-muted">当前余额 {{ fmtMoney(balanceUser?.balance ?? 0) }}</p>
|
||||
<Input v-model="balanceForm.amount" label="调整金额" type="number" hint="正数增加,负数扣减" />
|
||||
<Input v-model="balanceForm.remark" label="备注" placeholder="可选" />
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user