优化首页筛选功能

This commit is contained in:
yml2213
2026-05-29 10:06:47 +08:00
parent 72f7d504d1
commit 2966b59c90
4 changed files with 1176 additions and 405 deletions
+225 -127
View File
@@ -2,12 +2,12 @@
import { ref } from "vue";
import { useRouter } from "vue-router";
import {
Bell,
ArrowDown,
ChatDotRound,
CirclePlus,
House,
Search,
Shop,
Service,
SwitchButton,
Tickets,
UserFilled,
@@ -38,8 +38,11 @@ function handleLogout() {
<div class="pc-app-shell">
<header class="pc-topbar">
<RouterLink class="pc-brand" to="/">
<span class="pc-brand-mark">HFB</span>
<span class="pc-brand-text">哈夫币租号</span>
<span class="pc-brand-mark"></span>
<div class="pc-brand-info">
<span class="pc-brand-text">大锤商行</span>
<small class="pc-brand-sub">哈夫币租号</small>
</div>
</RouterLink>
<nav class="pc-nav">
@@ -56,15 +59,22 @@ function handleLogout() {
<div class="pc-search">
<el-icon><Search /></el-icon>
<input placeholder="搜索区服 / 段位 / 哈夫币数量" />
<input placeholder="搜索区服 / 段位 / 哈夫币数量 / 皮肤" />
</div>
<div class="pc-user-actions">
<RouterLink class="pc-icon-link service-link" to="/notifications" title="联系客服">
<el-icon><Service /></el-icon>
<span>客服</span>
</RouterLink>
<RouterLink class="pc-post-link" :to="session.isLoggedIn ? '/seller/listings/create' : '/login'">
<el-icon><CirclePlus /></el-icon>
<span>发布账号</span>
</RouterLink>
<!-- 未登录显示登录/注册按钮 -->
<template v-if="!session.isLoggedIn">
<RouterLink class="pc-icon-link" to="/notifications" aria-label="通知">
<el-icon><Bell /></el-icon>
</RouterLink>
<RouterLink class="pc-login-link" to="/login">
<el-icon><UserFilled /></el-icon>
<span>登录/注册</span>
@@ -73,15 +83,12 @@ function handleLogout() {
<!-- 已登录显示用户头像+昵称 + 下拉菜单 -->
<template v-else>
<RouterLink class="pc-icon-link" to="/notifications" aria-label="通知">
<el-icon><Bell /></el-icon>
</RouterLink>
<div class="pc-user-block" @mouseleave="showUserDropdown = false">
<button
class="pc-user-trigger"
@mouseenter="showUserDropdown = true"
@click="showUserDropdown = !showUserDropdown"
:class="{ active: showUserDropdown }"
>
<span class="pc-avatar-chip">
<img
@@ -93,49 +100,46 @@ function handleLogout() {
<span v-else class="pc-avatar-text">{{ session.avatarText }}</span>
</span>
<span class="pc-user-name">{{ session.displayName }}</span>
<el-icon class="arrow-icon" :class="{ rotated: showUserDropdown }"><ArrowDown /></el-icon>
</button>
<Transition name="dropdown">
<div v-if="showUserDropdown" class="pc-user-dropdown">
<RouterLink
class="dropdown-item"
to="/orders"
@click="showUserDropdown = false"
>
<el-icon><Tickets /></el-icon>
<span>我的订单</span>
</RouterLink>
<RouterLink
class="dropdown-item"
to="/wallet"
@click="showUserDropdown = false"
>
<el-icon><Wallet /></el-icon>
<span>钱包</span>
</RouterLink>
<RouterLink
class="dropdown-item"
to="/seller/listings/create"
@click="showUserDropdown = false"
>
<el-icon><CirclePlus /></el-icon>
<span>发布账号</span>
</RouterLink>
<div class="dropdown-divider"></div>
<button class="dropdown-item logout" @click="handleLogout">
<el-icon><SwitchButton /></el-icon>
<span>退出登录</span>
</button>
<div v-if="showUserDropdown" class="pc-user-dropdown-container">
<div class="pc-user-dropdown">
<RouterLink
class="dropdown-item"
to="/orders"
@click="showUserDropdown = false"
>
<el-icon><Tickets /></el-icon>
<span>我的订单</span>
</RouterLink>
<RouterLink
class="dropdown-item"
to="/wallet"
@click="showUserDropdown = false"
>
<el-icon><Wallet /></el-icon>
<span>我的钱包</span>
</RouterLink>
<RouterLink
class="dropdown-item"
to="/seller/listings/create"
@click="showUserDropdown = false"
>
<el-icon><CirclePlus /></el-icon>
<span>发布账号</span>
</RouterLink>
<div class="dropdown-divider"></div>
<button class="dropdown-item logout" @click="handleLogout">
<el-icon><SwitchButton /></el-icon>
<span>退出登录</span>
</button>
</div>
</div>
</Transition>
</div>
</template>
<!-- 未登录时发布按钮放在外面 -->
<RouterLink v-if="!session.isLoggedIn" class="pc-post-link" to="/login">
<el-icon><CirclePlus /></el-icon>
<span>发布账号</span>
</RouterLink>
</div>
</header>
@@ -151,6 +155,8 @@ function handleLogout() {
display: flex;
flex-direction: column;
min-height: 100vh;
max-width: 100vw;
overflow-x: clip;
background: #f5f6f8;
}
@@ -160,8 +166,10 @@ function handleLogout() {
z-index: 100;
display: flex;
align-items: center;
gap: 16px;
height: 56px;
gap: 20px;
min-width: 0;
max-width: 100%;
height: 64px;
padding: 0 24px;
background: #fff;
border-bottom: 1px solid #eef1f5;
@@ -172,28 +180,39 @@ function handleLogout() {
.pc-brand {
display: flex;
align-items: center;
gap: 8px;
gap: 10px;
text-decoration: none;
flex-shrink: 0;
}
.pc-brand-mark {
display: grid;
width: 32px;
height: 32px;
width: 38px;
height: 38px;
place-items: center;
border-radius: 8px;
background: #1477ff;
color: #fff;
font-size: 14px;
border-radius: 12px;
background: linear-gradient(135deg, #fff3e8 0%, #ffe4cc 100%);
color: #ff6a00;
font-size: 20px;
font-weight: 900;
}
.pc-brand-info {
display: flex;
flex-direction: column;
line-height: 1.2;
}
.pc-brand-text {
font-size: 16px;
font-weight: 800;
color: #17233d;
white-space: nowrap;
}
.pc-brand-sub {
font-size: 11px;
color: #8b9cb5;
font-weight: 600;
}
/* ========== 导航 ========== */
@@ -201,40 +220,51 @@ function handleLogout() {
display: flex;
align-items: center;
gap: 4px;
margin-left: 16px;
margin-left: 10px;
min-width: 0;
height: 100%;
}
.pc-nav-link {
display: flex;
align-items: center;
gap: 5px;
padding: 6px 12px;
border-radius: 8px;
padding: 8px 14px;
border-radius: 10px;
color: #5a6577;
font-size: 14px;
font-weight: 600;
font-weight: 700;
text-decoration: none;
transition: background 0.15s, color 0.15s;
transition: all 0.2s;
}
.pc-nav-link:hover,
.pc-nav-link.router-link-active {
background: #f0f5ff;
color: #1477ff;
background: #fff3e8;
color: #ff6a00;
}
/* ========== 搜索 ========== */
.pc-search {
display: flex;
align-items: center;
gap: 6px;
gap: 8px;
margin-left: auto;
padding: 0 12px;
height: 36px;
border-radius: 10px;
padding: 0 14px;
height: 40px;
border-radius: 12px;
background: #f4f6f8;
max-width: 280px;
flex: 0 1 280px;
border: 1px solid transparent;
max-width: 320px;
min-width: 180px;
flex: 1;
transition: all 0.2s;
}
.pc-search:focus-within {
background: #fff;
border-color: #ff6a00;
box-shadow: 0 0 0 4px rgba(255, 106, 0, 0.08);
}
.pc-search input {
@@ -252,6 +282,7 @@ function handleLogout() {
.pc-search .el-icon {
color: #a0aab6;
font-size: 16px;
flex-shrink: 0;
}
@@ -259,66 +290,110 @@ function handleLogout() {
.pc-user-actions {
display: flex;
align-items: center;
gap: 8px;
gap: 12px;
margin-left: 12px;
min-width: 0;
flex-shrink: 0;
height: 100%;
}
.pc-icon-link {
display: grid;
width: 36px;
height: 36px;
place-items: center;
border-radius: 10px;
color: #6b7a90;
display: flex;
align-items: center;
gap: 10px;
padding: 0 22px;
height: 40px;
border-radius: 12px;
border: 1px solid #eef1f5;
background: #ffffff;
color: #5a6577;
font-size: 14px;
font-weight: 700;
text-decoration: none;
transition: background 0.15s;
transition: all 0.2s;
white-space: nowrap;
}
.pc-icon-link:hover {
background: #f0f5ff;
color: #1477ff;
background: #fff3e8;
border-color: #ff6a00;
color: #ff6a00;
box-shadow: 0 4px 12px rgba(255, 106, 0, 0.05);
}
.service-link {
gap: 7px;
min-width: 92px;
justify-content: center;
padding: 0 18px;
border-color: rgba(255, 106, 0, 0.32);
border-radius: 10px;
background: #fff8f2;
color: #ff6a00;
font-size: 14px;
font-weight: 800;
}
.service-link .el-icon {
width: 18px;
height: 18px;
font-size: 18px;
stroke-width: 2.2;
}
.service-link:hover {
background: #fff3e8;
border-color: #ff6a00;
box-shadow: 0 6px 16px rgba(255, 106, 0, 0.1);
transform: translateY(-1px);
}
.pc-login-link {
display: flex;
align-items: center;
gap: 5px;
padding: 6px 14px;
gap: 6px;
padding: 0 16px;
height: 40px;
border-radius: 10px;
background: #1477ff;
color: #fff;
background: #f4f6f8;
color: #17233d;
font-size: 13px;
font-weight: 700;
text-decoration: none;
transition: background 0.15s;
transition: all 0.2s;
}
.pc-login-link:hover {
background: #0d5fd4;
background: #eaeff5;
}
.pc-post-link {
display: flex;
align-items: center;
gap: 5px;
padding: 6px 14px;
gap: 6px;
padding: 0 18px;
height: 40px;
border-radius: 10px;
background: #ff6a00;
color: #fff;
font-size: 13px;
font-weight: 700;
font-size: 14px;
font-weight: 800;
text-decoration: none;
transition: background 0.15s;
box-shadow: 0 6px 16px rgba(255, 106, 0, 0.2);
transition: all 0.2s;
}
.pc-post-link:hover {
background: #e55d00;
transform: translateY(-1px);
}
/* ========== 已登录 - 用户块 ========== */
.pc-user-block {
position: relative;
height: 40px;
display: flex;
align-items: center;
}
.pc-user-trigger {
@@ -326,27 +401,29 @@ function handleLogout() {
align-items: center;
gap: 8px;
padding: 4px 10px 4px 4px;
height: 36px;
border: none;
border-radius: 10px;
border-radius: 999px;
background: #f4f6f8;
cursor: pointer;
transition: background 0.15s;
transition: all 0.2s;
}
.pc-user-trigger:hover {
.pc-user-trigger:hover,
.pc-user-trigger.active {
background: #eaeff5;
}
.pc-avatar-chip {
display: grid;
width: 30px;
height: 30px;
width: 28px;
height: 28px;
place-items: center;
border-radius: 8px;
border-radius: 50%;
overflow: hidden;
background: #1477ff;
background: linear-gradient(135deg, #ff6a00 0%, #e55d00 100%);
color: #fff;
font-size: 14px;
font-size: 13px;
font-weight: 800;
flex-shrink: 0;
}
@@ -365,89 +442,110 @@ function handleLogout() {
max-width: 100px;
overflow: hidden;
color: #17233d;
font-size: 13px;
font-size: 14px;
font-weight: 700;
text-overflow: ellipsis;
white-space: nowrap;
}
/* ========== 下拉菜单 ========== */
.pc-user-dropdown {
.arrow-icon {
font-size: 12px;
color: #8b9cb5;
transition: transform 0.3s;
}
.arrow-icon.rotated {
transform: rotate(180deg);
}
/* ========== 下拉菜单容器 (Hover Bridge) ========== */
.pc-user-dropdown-container {
position: absolute;
top: calc(100% + 6px);
top: 100%;
right: 0;
z-index: 200;
min-width: 180px;
padding: 6px;
border-radius: 12px;
padding-top: 12px;
}
.pc-user-dropdown {
min-width: 200px;
padding: 8px;
border-radius: 14px;
background: #fff;
border: 1px solid #eef1f5;
box-shadow: 0 8px 24px rgba(23, 35, 61, 0.12);
box-shadow: 0 10px 30px rgba(23, 35, 61, 0.15);
}
.dropdown-item {
display: flex;
align-items: center;
gap: 8px;
gap: 10px;
width: 100%;
padding: 9px 12px;
padding: 10px 14px;
border: none;
border-radius: 8px;
border-radius: 10px;
background: none;
color: #3d4e63;
color: #475569;
font-size: 14px;
font-weight: 500;
font-weight: 600;
text-decoration: none;
cursor: pointer;
transition: background 0.12s;
transition: all 0.2s;
}
.dropdown-item:hover {
background: #f0f5ff;
color: #1477ff;
background: #fff3e8;
color: #ff6a00;
transform: translateX(4px);
}
.dropdown-item .el-icon {
color: #8b9cb5;
flex-shrink: 0;
font-size: 16px;
color: #94a3b8;
transition: color 0.2s;
}
.dropdown-item:hover .el-icon {
color: #1477ff;
color: #ff6a00;
}
.dropdown-item.logout {
color: #e74c3c;
color: #ef4444;
}
.dropdown-item.logout .el-icon {
color: #e74c3c;
color: #ef4444;
}
.dropdown-item.logout:hover {
background: #fef0ef;
background: #fff1f0;
}
.dropdown-divider {
height: 1px;
margin: 4px 8px;
background: #eef1f5;
margin: 6px 10px;
background: #f1f5f9;
}
/* 下拉动画 */
.dropdown-enter-active,
.dropdown-leave-active {
transition: opacity 0.15s ease, transform 0.15s ease;
transition: opacity 0.2s ease, transform 0.2s ease;
}
.dropdown-enter-from {
opacity: 0;
transform: translateY(10px);
}
.dropdown-enter-from,
.dropdown-leave-to {
opacity: 0;
transform: translateY(-4px);
transform: translateY(5px);
}
/* ========== 主体 ---------- */
.pc-main {
flex: 1;
min-width: 0;
padding: 20px 24px;
overflow-x: clip;
}
</style>
+8
View File
@@ -11,10 +11,18 @@
box-sizing: border-box;
}
html,
body {
margin: 0;
min-width: 320px;
min-height: 100vh;
max-width: 100%;
overflow-x: hidden;
}
#app {
max-width: 100%;
overflow-x: hidden;
}
a {
File diff suppressed because it is too large Load Diff