新增同城便民生活服务平台标识,重构看板为业务总览与运营看板 新增待办督办中心、营收构成分析、热门分类与区域排行等模块 新增近7/14/30天多时段趋势切换,支持发布量/订单额/用户/曝光量指标切换 新增平台商业与生态资产统计模块,新增待办预警与空状态提示 新增趋势数据汇总与明细表联动,优化响应式布局与交互样式 新增商家管理、举报投诉等语言翻译项,新增登录推荐图
1228 行
44 KiB
HTML
可执行文件
1228 行
44 KiB
HTML
可执行文件
<!DOCTYPE html>
|
|
<html lang="zh-cn">
|
|
<head>
|
|
{include file="common/meta" /}
|
|
<title>山间小仓 · 同城农品供求信息发布与管理后台</title>
|
|
<style type="text/css">
|
|
:root {
|
|
--primary: #006948;
|
|
--primary-hover: #00855d;
|
|
--primary-active: #00563a;
|
|
--primary-light: #e6f7f0;
|
|
--primary-fixed: #85f8c4;
|
|
--on-primary: #ffffff;
|
|
--secondary-container: #c4f5de;
|
|
--on-secondary-container: #00533a;
|
|
--amber-start: #ffddb8;
|
|
--amber-mid: #ffc885;
|
|
--amber-end: #ffb95f;
|
|
--amber-text: #2a1700;
|
|
--amber-sub: #653e00;
|
|
--bg-canvas: #ffffff;
|
|
--bg-input: #f8fafc;
|
|
--bg-input-hover: #f1f5f9;
|
|
--border-line: #e2e8f0;
|
|
--border-line-hover: #cbd5e1;
|
|
--text-heading: #0b1c30;
|
|
--text-body: #334155;
|
|
--text-muted: #64748b;
|
|
--text-placeholder: #94a3b8;
|
|
--radius-sm: 8px;
|
|
--radius-md: 12px;
|
|
--radius-lg: 16px;
|
|
--radius-xl: 20px;
|
|
--radius-full: 9999px;
|
|
--shadow-card: 0 20px 45px -15px rgba(0, 30, 20, 0.25);
|
|
--shadow-btn: 0 10px 22px -5px rgba(0, 105, 72, 0.38);
|
|
}
|
|
|
|
/* 基础层样式重置与抗锯齿优化 */
|
|
*, *::before, *::after {
|
|
box-sizing: border-box;
|
|
margin: 0;
|
|
padding: 0;
|
|
}
|
|
|
|
html, body {
|
|
height: 100%;
|
|
min-height: 100%;
|
|
font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", Arial, sans-serif;
|
|
background: var(--bg-canvas);
|
|
color: var(--text-body);
|
|
-webkit-font-smoothing: antialiased;
|
|
-moz-osx-font-smoothing: grayscale;
|
|
overflow-x: hidden;
|
|
}
|
|
|
|
/* 主视口双栏布局 */
|
|
.login-wrap {
|
|
display: flex;
|
|
min-height: 100vh;
|
|
width: 100%;
|
|
}
|
|
|
|
/* ================= 左侧沉浸式农业生态展屏 ================= */
|
|
.hero-panel {
|
|
position: relative;
|
|
flex: 0 0 54%;
|
|
width: 54%;
|
|
min-height: 100vh;
|
|
background: var(--primary);
|
|
padding: 48px 56px 40px;
|
|
display: flex;
|
|
flex-direction: column;
|
|
justify-content: space-between;
|
|
overflow: hidden;
|
|
color: #ffffff;
|
|
user-select: none;
|
|
}
|
|
|
|
/* 柔和环境光晕 */
|
|
.ambient-glow-top {
|
|
position: absolute;
|
|
top: -120px;
|
|
right: -120px;
|
|
width: 480px;
|
|
height: 480px;
|
|
border-radius: 50%;
|
|
background: rgba(0, 133, 93, 0.45);
|
|
filter: blur(80px);
|
|
pointer-events: none;
|
|
}
|
|
.ambient-glow-bottom {
|
|
position: absolute;
|
|
bottom: 20px;
|
|
left: -80px;
|
|
width: 380px;
|
|
height: 380px;
|
|
border-radius: 50%;
|
|
background: rgba(133, 248, 196, 0.16);
|
|
filter: blur(70px);
|
|
pointer-events: none;
|
|
}
|
|
|
|
/* 中部 Bento 堆叠展区 */
|
|
.bento-stage {
|
|
position: relative;
|
|
z-index: 2;
|
|
max-width: 580px;
|
|
width: 100%;
|
|
margin: auto;
|
|
padding: 10px 0;
|
|
}
|
|
|
|
/* 装饰手绘涂鸦星线 */
|
|
.accent-sparkle {
|
|
position: absolute;
|
|
top: -10px;
|
|
left: -12px;
|
|
width: 42px;
|
|
height: 42px;
|
|
color: rgba(133, 248, 196, 0.85);
|
|
pointer-events: none;
|
|
}
|
|
|
|
.bento-stack {
|
|
position: relative;
|
|
}
|
|
|
|
/* Card 1: 核心数据走势看板 */
|
|
.card-analytics {
|
|
position: relative;
|
|
z-index: 1;
|
|
width: 82%;
|
|
background: #ffffff;
|
|
color: var(--text-heading);
|
|
border-radius: var(--radius-xl);
|
|
padding: 24px 24px 28px;
|
|
box-shadow: var(--shadow-card);
|
|
transition: transform 0.3s ease, box-shadow 0.3s ease;
|
|
}
|
|
.card-analytics:hover {
|
|
transform: translateY(-2px);
|
|
box-shadow: 0 25px 50px -15px rgba(0, 30, 20, 0.35);
|
|
}
|
|
|
|
.analytics-head {
|
|
display: flex;
|
|
align-items: flex-start;
|
|
justify-content: space-between;
|
|
margin-bottom: 12px;
|
|
}
|
|
.analytics-meta-title {
|
|
font-size: 13px;
|
|
color: var(--text-muted);
|
|
font-weight: 500;
|
|
}
|
|
.analytics-num-row {
|
|
display: flex;
|
|
align-items: baseline;
|
|
gap: 10px;
|
|
margin-top: 4px;
|
|
}
|
|
.analytics-main-val {
|
|
font-size: 32px;
|
|
font-weight: 700;
|
|
color: var(--text-heading);
|
|
line-height: 1.1;
|
|
letter-spacing: -0.02em;
|
|
}
|
|
.analytics-badge-inc {
|
|
display: inline-flex;
|
|
align-items: center;
|
|
gap: 3px;
|
|
padding: 2px 8px;
|
|
border-radius: var(--radius-full);
|
|
background: var(--primary-fixed);
|
|
color: #002114;
|
|
font-size: 11.5px;
|
|
font-weight: 700;
|
|
}
|
|
.analytics-date-filter {
|
|
display: inline-flex;
|
|
align-items: center;
|
|
gap: 5px;
|
|
padding: 5px 10px;
|
|
border-radius: var(--radius-sm);
|
|
background: #f1f5f9;
|
|
color: var(--text-heading);
|
|
font-size: 11.5px;
|
|
font-weight: 600;
|
|
}
|
|
.analytics-date-filter svg {
|
|
width: 13px;
|
|
height: 13px;
|
|
color: var(--primary);
|
|
}
|
|
|
|
/* SVG 走势图表容器 */
|
|
.chart-box {
|
|
position: relative;
|
|
width: 100%;
|
|
height: 105px;
|
|
margin-top: 6px;
|
|
}
|
|
.chart-box svg {
|
|
width: 100%;
|
|
height: 100%;
|
|
overflow: visible;
|
|
}
|
|
.chart-tooltip-floating {
|
|
position: absolute;
|
|
top: 0;
|
|
left: 58%;
|
|
transform: translateX(-50%);
|
|
background: #ffffff;
|
|
border-radius: var(--radius-sm);
|
|
padding: 4px 10px;
|
|
box-shadow: 0 4px 16px rgba(0, 0, 0, 0.12);
|
|
text-align: center;
|
|
white-space: nowrap;
|
|
pointer-events: none;
|
|
border: 1px solid rgba(0, 105, 72, 0.08);
|
|
}
|
|
.tooltip-title {
|
|
display: block;
|
|
font-size: 11.5px;
|
|
font-weight: 700;
|
|
color: var(--primary);
|
|
line-height: 1.3;
|
|
}
|
|
.tooltip-sub {
|
|
display: block;
|
|
font-size: 10px;
|
|
color: var(--text-muted);
|
|
line-height: 1.2;
|
|
}
|
|
|
|
.chart-axis-months {
|
|
display: flex;
|
|
justify-content: space-between;
|
|
align-items: center;
|
|
padding-top: 8px;
|
|
font-size: 11px;
|
|
color: var(--text-muted);
|
|
}
|
|
.chart-axis-months span.active {
|
|
font-weight: 700;
|
|
color: var(--primary);
|
|
}
|
|
|
|
/* Card 2: 黄金推荐农品展示卡片 */
|
|
.card-showcase {
|
|
position: absolute;
|
|
z-index: 3;
|
|
top: 12px;
|
|
right: -10px;
|
|
width: 47%;
|
|
background: linear-gradient(135deg, var(--amber-start) 0%, var(--amber-mid) 50%, var(--amber-end) 100%);
|
|
border-radius: var(--radius-xl);
|
|
padding: 16px;
|
|
box-shadow: 0 25px 45px -10px rgba(0, 0, 0, 0.3);
|
|
color: var(--amber-text);
|
|
transform: rotate(2.5deg);
|
|
transition: transform 0.3s cubic-bezier(0.34, 1.56, 0.64, 1), box-shadow 0.3s ease;
|
|
}
|
|
.card-showcase:hover {
|
|
transform: rotate(0deg) scale(1.02);
|
|
box-shadow: 0 30px 50px -10px rgba(0, 0, 0, 0.36);
|
|
}
|
|
.showcase-header {
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: space-between;
|
|
margin-bottom: 8px;
|
|
}
|
|
.showcase-tag {
|
|
font-size: 11px;
|
|
font-weight: 800;
|
|
letter-spacing: 0.05em;
|
|
color: var(--amber-sub);
|
|
}
|
|
.showcase-badge-pill {
|
|
padding: 2px 7px;
|
|
border-radius: var(--radius-full);
|
|
background: var(--amber-text);
|
|
color: var(--amber-start);
|
|
font-size: 9.5px;
|
|
font-weight: 700;
|
|
}
|
|
.showcase-img-wrap {
|
|
position: relative;
|
|
width: 100%;
|
|
height: 130px;
|
|
border-radius: var(--radius-md);
|
|
overflow: hidden;
|
|
margin-bottom: 10px;
|
|
background: #e2e8f0;
|
|
}
|
|
.showcase-img-wrap img {
|
|
width: 100%;
|
|
height: 100%;
|
|
object-fit: cover;
|
|
display: block;
|
|
}
|
|
.showcase-img-cover {
|
|
position: absolute;
|
|
inset: 0;
|
|
background: linear-gradient(180deg, transparent 40%, rgba(0, 0, 0, 0.75) 100%);
|
|
display: flex;
|
|
flex-direction: column;
|
|
justify-content: flex-end;
|
|
padding: 8px 10px;
|
|
color: #ffffff;
|
|
}
|
|
.cover-title {
|
|
font-size: 13px;
|
|
font-weight: 700;
|
|
line-height: 1.3;
|
|
text-shadow: 0 1px 3px rgba(0, 0, 0, 0.6);
|
|
}
|
|
.cover-desc {
|
|
font-size: 10px;
|
|
color: rgba(255, 255, 255, 0.85);
|
|
line-height: 1.2;
|
|
margin-top: 2px;
|
|
}
|
|
.showcase-foot {
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: space-between;
|
|
gap: 6px;
|
|
}
|
|
.trace-badge {
|
|
display: flex;
|
|
align-items: center;
|
|
gap: 4px;
|
|
font-size: 10.5px;
|
|
font-weight: 700;
|
|
color: var(--amber-text);
|
|
}
|
|
.trace-badge svg {
|
|
width: 14px;
|
|
height: 14px;
|
|
color: var(--amber-sub);
|
|
}
|
|
.spec-pill {
|
|
padding: 3px 7px;
|
|
border-radius: var(--radius-sm);
|
|
background: rgba(101, 62, 0, 0.12);
|
|
color: var(--amber-sub);
|
|
font-size: 10px;
|
|
font-weight: 700;
|
|
white-space: nowrap;
|
|
}
|
|
|
|
/* Card 3: 分类分布小卡片 */
|
|
.card-distribution {
|
|
position: relative;
|
|
z-index: 2;
|
|
width: 63%;
|
|
margin-top: -12px;
|
|
margin-left: 18px;
|
|
background: #ffffff;
|
|
color: var(--text-heading);
|
|
border-radius: var(--radius-xl);
|
|
padding: 16px 20px;
|
|
box-shadow: 0 16px 36px -10px rgba(0, 30, 20, 0.22);
|
|
transition: transform 0.25s ease;
|
|
}
|
|
.card-distribution:hover {
|
|
transform: translateY(-2px);
|
|
}
|
|
.dist-head {
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: space-between;
|
|
margin-bottom: 12px;
|
|
}
|
|
.dist-title {
|
|
display: flex;
|
|
align-items: center;
|
|
gap: 6px;
|
|
font-size: 13px;
|
|
font-weight: 700;
|
|
color: var(--text-heading);
|
|
}
|
|
.dist-dot {
|
|
width: 8px;
|
|
height: 8px;
|
|
border-radius: 50%;
|
|
background: var(--primary);
|
|
}
|
|
.dist-tab-group {
|
|
display: flex;
|
|
gap: 4px;
|
|
font-size: 10.5px;
|
|
}
|
|
.dist-tab {
|
|
padding: 2px 7px;
|
|
border-radius: 4px;
|
|
color: var(--text-muted);
|
|
cursor: pointer;
|
|
transition: background 0.15s, color 0.15s;
|
|
}
|
|
.dist-tab.active {
|
|
background: var(--primary-fixed);
|
|
color: #002114;
|
|
font-weight: 700;
|
|
}
|
|
|
|
.dist-item {
|
|
margin-bottom: 9px;
|
|
}
|
|
.dist-item:last-child {
|
|
margin-bottom: 0;
|
|
}
|
|
.dist-item-label {
|
|
display: flex;
|
|
justify-content: space-between;
|
|
align-items: center;
|
|
font-size: 11px;
|
|
margin-bottom: 4px;
|
|
}
|
|
.dist-name {
|
|
color: var(--text-muted);
|
|
}
|
|
.dist-val {
|
|
font-weight: 700;
|
|
color: var(--text-heading);
|
|
}
|
|
.progress-track {
|
|
width: 100%;
|
|
height: 6px;
|
|
border-radius: 999px;
|
|
background: #edf2f7;
|
|
overflow: hidden;
|
|
}
|
|
.progress-bar {
|
|
height: 100%;
|
|
border-radius: 999px;
|
|
transition: width 0.6s ease;
|
|
}
|
|
|
|
/* 手绘粉笔线条 */
|
|
.chalk-wave {
|
|
position: absolute;
|
|
right: 20px;
|
|
bottom: -20px;
|
|
width: 120px;
|
|
height: 20px;
|
|
color: rgba(255, 255, 255, 0.45);
|
|
pointer-events: none;
|
|
}
|
|
|
|
/* 底部大标语与轮播指示器 */
|
|
.hero-foot {
|
|
position: relative;
|
|
z-index: 2;
|
|
text-align: center;
|
|
max-width: 520px;
|
|
margin: 0 auto;
|
|
padding-top: 14px;
|
|
}
|
|
.hero-main-title {
|
|
font-size: 28px;
|
|
line-height: 1.35;
|
|
font-weight: 800;
|
|
letter-spacing: -0.01em;
|
|
color: #ffffff;
|
|
text-shadow: 0 2px 10px rgba(0, 0, 0, 0.15);
|
|
}
|
|
.hero-sub-title {
|
|
font-size: 14px;
|
|
line-height: 1.7;
|
|
color: rgba(255, 255, 255, 0.86);
|
|
margin-top: 8px;
|
|
max-width: 450px;
|
|
margin-left: auto;
|
|
margin-right: auto;
|
|
}
|
|
.hero-dots {
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: center;
|
|
gap: 7px;
|
|
margin-top: 18px;
|
|
}
|
|
.hero-dot {
|
|
height: 7px;
|
|
border-radius: 999px;
|
|
background: rgba(255, 255, 255, 0.35);
|
|
transition: all 0.25s ease;
|
|
cursor: pointer;
|
|
border: none;
|
|
padding: 0;
|
|
}
|
|
.hero-dot.active {
|
|
width: 26px;
|
|
background: #ffffff;
|
|
}
|
|
.hero-dot:not(.active) {
|
|
width: 7px;
|
|
}
|
|
.hero-dot:hover:not(.active) {
|
|
background: rgba(255, 255, 255, 0.65);
|
|
}
|
|
|
|
/* ================= 右侧登录交互表单区 ================= */
|
|
.auth-panel {
|
|
position: relative;
|
|
flex: 0 0 46%;
|
|
width: 46%;
|
|
min-height: 100vh;
|
|
background: #ffffff;
|
|
padding: 44px 64px 32px;
|
|
display: flex;
|
|
flex-direction: column;
|
|
justify-content: space-between;
|
|
z-index: 10;
|
|
}
|
|
|
|
/* 顶部品牌 Logo Header */
|
|
.auth-brand-head {
|
|
display: flex;
|
|
align-items: center;
|
|
gap: 12px;
|
|
user-select: none;
|
|
}
|
|
.brand-icon-box {
|
|
width: 40px;
|
|
height: 40px;
|
|
border-radius: var(--radius-md);
|
|
background: var(--primary);
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: center;
|
|
color: #ffffff;
|
|
box-shadow: 0 4px 12px rgba(0, 105, 72, 0.25);
|
|
}
|
|
.brand-icon-box svg {
|
|
width: 23px;
|
|
height: 23px;
|
|
}
|
|
.brand-title-wrap {
|
|
display: flex;
|
|
align-items: center;
|
|
gap: 8px;
|
|
}
|
|
.brand-name {
|
|
font-size: 22px;
|
|
font-weight: 700;
|
|
color: var(--text-heading);
|
|
letter-spacing: -0.01em;
|
|
}
|
|
.brand-badge {
|
|
font-size: 11.5px;
|
|
font-weight: 600;
|
|
padding: 3px 9px;
|
|
border-radius: var(--radius-full);
|
|
background: var(--secondary-container);
|
|
color: var(--on-secondary-container);
|
|
}
|
|
|
|
/* 表单居中容器 */
|
|
.auth-center-box {
|
|
width: 100%;
|
|
max-width: 420px;
|
|
margin: 40px auto;
|
|
}
|
|
|
|
/* 表单引导语 */
|
|
.auth-heading-wrap {
|
|
margin-bottom: 26px;
|
|
}
|
|
.auth-main-title {
|
|
font-size: 26px;
|
|
font-weight: 800;
|
|
color: var(--text-heading);
|
|
letter-spacing: -0.01em;
|
|
line-height: 1.25;
|
|
}
|
|
.auth-sub-desc {
|
|
font-size: 13.5px;
|
|
color: var(--text-muted);
|
|
margin-top: 6px;
|
|
line-height: 1.5;
|
|
}
|
|
|
|
/* 错误提示框 */
|
|
#errtips {
|
|
margin-bottom: 18px;
|
|
padding: 10px 14px;
|
|
border-radius: var(--radius-sm);
|
|
background: #fff1f0;
|
|
border: 1px solid #ffccc7;
|
|
color: #cf1322;
|
|
font-size: 13px;
|
|
display: none;
|
|
align-items: center;
|
|
gap: 8px;
|
|
animation: shake 0.3s ease-in-out;
|
|
}
|
|
#errtips:not(:empty) {
|
|
display: flex;
|
|
}
|
|
@keyframes shake {
|
|
0%, 100% { transform: translateX(0); }
|
|
20%, 60% { transform: translateX(-4px); }
|
|
40%, 80% { transform: translateX(4px); }
|
|
}
|
|
|
|
/* 表单控件项 */
|
|
.form-row {
|
|
margin-bottom: 16px;
|
|
position: relative;
|
|
}
|
|
.input-group-modern {
|
|
position: relative;
|
|
display: flex;
|
|
align-items: center;
|
|
width: 100%;
|
|
}
|
|
.input-left-icon {
|
|
position: absolute;
|
|
left: 15px;
|
|
top: 50%;
|
|
transform: translateY(-50%);
|
|
width: 20px;
|
|
height: 20px;
|
|
color: var(--text-placeholder);
|
|
pointer-events: none;
|
|
z-index: 2;
|
|
transition: color 0.2s ease;
|
|
}
|
|
.form-input-modern {
|
|
width: 100%;
|
|
height: 50px;
|
|
padding: 0 16px 0 46px;
|
|
background: var(--bg-input) !important;
|
|
border: 1.5px solid transparent !important;
|
|
border-radius: var(--radius-md) !important;
|
|
font-size: 14px !important;
|
|
color: var(--text-heading) !important;
|
|
outline: none !important;
|
|
box-shadow: none !important;
|
|
transition: all 0.2s ease !important;
|
|
}
|
|
.form-input-modern::placeholder {
|
|
color: var(--text-placeholder);
|
|
font-size: 13.5px;
|
|
}
|
|
.form-input-modern:hover {
|
|
background: var(--bg-input-hover) !important;
|
|
}
|
|
.form-input-modern:focus {
|
|
background: #ffffff !important;
|
|
border-color: var(--primary) !important;
|
|
box-shadow: 0 0 0 3.5px rgba(0, 105, 72, 0.12) !important;
|
|
}
|
|
.input-group-modern:focus-within .input-left-icon {
|
|
color: var(--primary);
|
|
}
|
|
|
|
/* 校验失败红色警示态 */
|
|
.form-input-modern.n-invalid,
|
|
.has-error .form-input-modern {
|
|
border-color: #e05b52 !important;
|
|
box-shadow: 0 0 0 3.5px rgba(224, 91, 82, 0.12) !important;
|
|
}
|
|
|
|
/* 密码切换小眼睛按钮 */
|
|
.pwd-eye-btn {
|
|
position: absolute;
|
|
right: 14px;
|
|
top: 50%;
|
|
transform: translateY(-50%);
|
|
background: transparent;
|
|
border: none;
|
|
padding: 4px;
|
|
color: var(--text-placeholder);
|
|
cursor: pointer;
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: center;
|
|
border-radius: 4px;
|
|
transition: color 0.15s;
|
|
}
|
|
.pwd-eye-btn:hover {
|
|
color: var(--primary);
|
|
}
|
|
.pwd-eye-btn svg {
|
|
width: 20px;
|
|
height: 20px;
|
|
}
|
|
|
|
/* 验证码行 */
|
|
.captcha-flex-row {
|
|
display: flex;
|
|
align-items: center;
|
|
gap: 12px;
|
|
}
|
|
.captcha-flex-row .input-group-modern {
|
|
flex: 1;
|
|
}
|
|
.captcha-img-box {
|
|
position: relative;
|
|
height: 50px;
|
|
min-width: 135px;
|
|
padding: 0 10px;
|
|
background: var(--bg-input);
|
|
border: 1.5px solid var(--border-line);
|
|
border-radius: var(--radius-md);
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: center;
|
|
gap: 6px;
|
|
cursor: pointer;
|
|
overflow: hidden;
|
|
transition: all 0.2s ease;
|
|
user-select: none;
|
|
}
|
|
.captcha-img-box:hover {
|
|
background: #f1f5f9;
|
|
border-color: var(--primary);
|
|
}
|
|
.captcha-img-box img {
|
|
height: 38px;
|
|
width: auto;
|
|
display: block;
|
|
}
|
|
.captcha-refresh-icon {
|
|
width: 15px;
|
|
height: 15px;
|
|
color: var(--text-placeholder);
|
|
transition: transform 0.3s ease, color 0.2s ease;
|
|
flex-shrink: 0;
|
|
}
|
|
.captcha-img-box:hover .captcha-refresh-icon {
|
|
color: var(--primary);
|
|
transform: rotate(180deg);
|
|
}
|
|
|
|
/* 记住我与忘记密码 */
|
|
.auth-actions-row {
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: space-between;
|
|
margin: 4px 0 22px;
|
|
}
|
|
.checkbox-label {
|
|
display: inline-flex;
|
|
align-items: center;
|
|
gap: 8px;
|
|
font-size: 13.5px;
|
|
color: var(--text-body);
|
|
cursor: pointer;
|
|
user-select: none;
|
|
margin: 0;
|
|
font-weight: 400;
|
|
}
|
|
.checkbox-label input[type="checkbox"] {
|
|
width: 17px;
|
|
height: 17px;
|
|
border-radius: 4px;
|
|
accent-color: var(--primary);
|
|
cursor: pointer;
|
|
}
|
|
.forgot-link {
|
|
font-size: 13px;
|
|
font-weight: 600;
|
|
color: var(--primary);
|
|
text-decoration: none;
|
|
transition: color 0.15s;
|
|
}
|
|
.forgot-link:hover {
|
|
color: var(--primary-hover);
|
|
text-decoration: underline;
|
|
}
|
|
|
|
/* 登录提交大按钮 */
|
|
.btn-submit-login {
|
|
width: 100%;
|
|
height: 50px;
|
|
border: none;
|
|
border-radius: var(--radius-md);
|
|
background: var(--primary);
|
|
color: #ffffff !important;
|
|
font-size: 15px;
|
|
font-weight: 700;
|
|
letter-spacing: 0.02em;
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: center;
|
|
gap: 8px;
|
|
box-shadow: var(--shadow-btn);
|
|
cursor: pointer;
|
|
transition: all 0.2s ease;
|
|
}
|
|
.btn-submit-login:hover {
|
|
background: var(--primary-hover);
|
|
box-shadow: 0 14px 26px -5px rgba(0, 105, 72, 0.45);
|
|
transform: translateY(-1px);
|
|
}
|
|
.btn-submit-login:active {
|
|
transform: scale(0.99);
|
|
background: var(--primary-active);
|
|
}
|
|
.btn-submit-login svg {
|
|
width: 18px;
|
|
height: 18px;
|
|
transition: transform 0.2s ease;
|
|
}
|
|
.btn-submit-login:hover svg {
|
|
transform: translateX(3px);
|
|
}
|
|
|
|
/* 页脚版权 */
|
|
.auth-footer {
|
|
font-size: 12.5px;
|
|
color: var(--text-placeholder);
|
|
line-height: 1.6;
|
|
user-select: none;
|
|
}
|
|
|
|
/* ================= 移动与平板端响应式适配 ================= */
|
|
@media (max-width: 1080px) {
|
|
.hero-panel {
|
|
display: none;
|
|
}
|
|
.auth-panel {
|
|
flex: 0 0 100%;
|
|
width: 100%;
|
|
padding: 40px 24px 28px;
|
|
}
|
|
.auth-center-box {
|
|
max-width: 440px;
|
|
margin: 32px auto;
|
|
}
|
|
}
|
|
@media (max-width: 480px) {
|
|
.auth-panel {
|
|
padding: 24px 16px 20px;
|
|
}
|
|
.auth-main-title {
|
|
font-size: 22px;
|
|
}
|
|
.captcha-flex-row {
|
|
flex-direction: column;
|
|
align-items: stretch;
|
|
}
|
|
.captcha-img-box {
|
|
height: 46px;
|
|
}
|
|
}
|
|
</style>
|
|
</head>
|
|
<body>
|
|
<div class="login-wrap">
|
|
<!-- ===== 左侧沉浸式农业生态展屏 ===== -->
|
|
<aside class="hero-panel">
|
|
<!-- 环形背景柔光 -->
|
|
<div class="ambient-glow-top"></div>
|
|
<div class="ambient-glow-bottom"></div>
|
|
|
|
<!-- 中部 Bento 堆叠展区 -->
|
|
<div class="bento-stage">
|
|
<!-- 矢量手绘突起装饰线 -->
|
|
<svg class="accent-sparkle" viewBox="0 0 40 40" fill="none">
|
|
<path d="M6 10L14 16M2 24H12M8 34L15 27" stroke="currentColor" stroke-width="2.5" stroke-linecap="round"/>
|
|
</svg>
|
|
|
|
<div class="bento-stack">
|
|
<!-- Card 1: 核心数据走势看板 -->
|
|
<div class="card-analytics">
|
|
<div class="analytics-head">
|
|
<div>
|
|
<div class="analytics-meta-title">今日有效供求发布量 (条)</div>
|
|
<div class="analytics-num-row">
|
|
<span class="analytics-main-val">56,345.98</span>
|
|
<span class="analytics-badge-inc">
|
|
<svg viewBox="0 0 24 24" width="13" height="13" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round">
|
|
<polyline points="23 6 13.5 15.5 8.5 10.5 1 18"></polyline>
|
|
<polyline points="17 6 23 6 23 12"></polyline>
|
|
</svg>
|
|
+23.5%
|
|
</span>
|
|
</div>
|
|
</div>
|
|
<div class="analytics-date-filter">
|
|
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
|
<rect x="3" y="4" width="18" height="18" rx="2" ry="2"></rect>
|
|
<line x1="16" y1="2" x2="16" y2="6"></line>
|
|
<line x1="8" y1="2" x2="8" y2="6"></line>
|
|
<line x1="3" y1="10" x2="21" y2="10"></line>
|
|
</svg>
|
|
<span>最近7个月</span>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- SVG 走势图表 -->
|
|
<div class="chart-box">
|
|
<svg viewBox="0 0 380 90" fill="none">
|
|
<line x1="0" y1="20" x2="380" y2="20" stroke="#f1f5f9" stroke-width="1"></line>
|
|
<line x1="0" y1="50" x2="380" y2="50" stroke="#f1f5f9" stroke-width="1"></line>
|
|
<line x1="0" y1="80" x2="380" y2="80" stroke="#f1f5f9" stroke-width="1"></line>
|
|
<!-- 黄色平滑走势曲线 -->
|
|
<path d="M10 70 C 60 70, 90 35, 150 45 C 210 55, 270 20, 320 40 C 350 50, 370 25, 375 22" fill="none" stroke="#ffb95f" stroke-width="2.5" stroke-linecap="round"></path>
|
|
<!-- 翡翠绿主峰曲线 -->
|
|
<path d="M10 55 C 70 55, 110 68, 160 50 C 210 32, 260 62, 300 28 C 340 -2, 365 30, 375 18" fill="none" stroke="#006948" stroke-width="3" stroke-linecap="round"></path>
|
|
<!-- 4月高亮区块与圆点 -->
|
|
<rect x="258" y="15" width="28" height="65" rx="6" fill="#85f8c4" fill-opacity="0.38"></rect>
|
|
<circle cx="272" cy="38" r="4.5" fill="#006948"></circle>
|
|
</svg>
|
|
<!-- 悬浮数据气泡 -->
|
|
<div class="chart-tooltip-floating">
|
|
<span class="tooltip-title">四月 (供求峰值)</span>
|
|
<span class="tooltip-sub">产销对接意向</span>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 月份横轴刻度 -->
|
|
<div class="chart-axis-months">
|
|
<span>一月</span>
|
|
<span>二月</span>
|
|
<span>三月</span>
|
|
<span class="active">四月 (供求峰值)</span>
|
|
<span>五月</span>
|
|
<span>六月</span>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Card 2: 黄金推荐农品展示卡片 -->
|
|
<div class="card-showcase">
|
|
<div class="showcase-header">
|
|
<span class="showcase-tag">2025 推荐农品</span>
|
|
<span class="showcase-badge-pill">最新供应发布</span>
|
|
</div>
|
|
<div class="showcase-img-wrap">
|
|
<img src="__CDN__/assets/img/login-recommend.jpg" alt="径山高山富硒草莓">
|
|
<div class="showcase-img-cover">
|
|
<div class="cover-title">径山高山富硒草莓</div>
|
|
<div class="cover-desc">余杭农科直供基地 · 晨采现发</div>
|
|
</div>
|
|
</div>
|
|
<div class="showcase-foot">
|
|
<div class="trace-badge">
|
|
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.2" stroke-linecap="round" stroke-linejoin="round">
|
|
<path d="M12 22s8-4 8-10V5l-8-3-8 3v7c0 6 8 10 8 10z"></path>
|
|
</svg>
|
|
<span>产地溯源凭证已核实</span>
|
|
</div>
|
|
<span class="spec-pill">余杭现货 · 支持看样</span>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Card 3: 分类分布小卡片 -->
|
|
<div class="card-distribution">
|
|
<div class="dist-head">
|
|
<div class="dist-title">
|
|
<span class="dist-dot"></span>
|
|
<span>发布分类分布</span>
|
|
</div>
|
|
<div class="dist-tab-group">
|
|
<span class="dist-tab active">本月</span>
|
|
<span class="dist-tab">本周</span>
|
|
</div>
|
|
</div>
|
|
<div class="dist-item">
|
|
<div class="dist-item-label">
|
|
<span class="dist-name">时令果蔬供给信息 (65%)</span>
|
|
<span class="dist-val">48,345 条</span>
|
|
</div>
|
|
<div class="progress-track">
|
|
<div class="progress-bar" style="width: 65%; background: var(--primary);"></div>
|
|
</div>
|
|
</div>
|
|
<div class="dist-item">
|
|
<div class="dist-item-label">
|
|
<span class="dist-name">生鲜采购寻源需求 (25%)</span>
|
|
<span class="dist-val">18,200 条</span>
|
|
</div>
|
|
<div class="progress-track">
|
|
<div class="progress-bar" style="width: 25%; background: var(--amber-end);"></div>
|
|
</div>
|
|
</div>
|
|
<div class="dist-item">
|
|
<div class="dist-item-label">
|
|
<span class="dist-name">农技与设施农品发布 (10%)</span>
|
|
<span class="dist-val">6,840 条</span>
|
|
</div>
|
|
<div class="progress-track">
|
|
<div class="progress-bar" style="width: 10%; background: #7bd8b1;"></div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 手绘粉笔线条 -->
|
|
<svg class="chalk-wave" viewBox="0 0 140 20" fill="none">
|
|
<path d="M4 14C35 4 80 18 136 6M10 18C45 10 95 14 128 12" stroke="currentColor" stroke-width="2.5" stroke-linecap="round"/>
|
|
</svg>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 底部大标题与指示器 -->
|
|
<div class="hero-foot">
|
|
<h1 class="hero-main-title">汇聚源头农品信息<br>赋能同城产销撮合对接</h1>
|
|
<p class="hero-sub-title">一站式同城涉农信息发布中台,连通种植基地与采购需求,让优质农品供应与求购信息精准透明触达。</p>
|
|
<div class="hero-dots">
|
|
<button type="button" class="hero-dot active" aria-label="第1屏"></button>
|
|
<button type="button" class="hero-dot" aria-label="第2屏"></button>
|
|
<button type="button" class="hero-dot" aria-label="第3屏"></button>
|
|
</div>
|
|
</div>
|
|
</aside>
|
|
|
|
<!-- ===== 右侧登录表单区 ===== -->
|
|
<main class="auth-panel">
|
|
<!-- 品牌 LOGO 顶栏 -->
|
|
<header class="auth-brand-head">
|
|
<div class="brand-icon-box">
|
|
<!-- 生态叶片矢量图标 -->
|
|
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.2" stroke-linecap="round" stroke-linejoin="round">
|
|
<path d="M11 20A7 7 0 0 1 9.8 6.1C15.5 5 17 4.48 19 2c1 2 2 4.18 2 8 0 5.5-4.78 10-10 10Z"></path>
|
|
<path d="M2 21c0-3 1.85-5.36 5.08-6C9.5 14.52 12 13 13 12"></path>
|
|
</svg>
|
|
</div>
|
|
<div class="brand-title-wrap">
|
|
<span class="brand-name">山间小仓</span>
|
|
<span class="brand-badge">发布中心</span>
|
|
</div>
|
|
</header>
|
|
|
|
<!-- 表单垂直居中主体 -->
|
|
<div class="auth-center-box">
|
|
<!-- 标题引导语 -->
|
|
<div class="auth-heading-wrap">
|
|
<h2 class="auth-main-title">登录您的账号</h2>
|
|
<p class="auth-sub-desc">山间小仓 · 同城农品供求信息发布与管理后台</p>
|
|
</div>
|
|
|
|
<!-- FastAdmin 表单开始 -->
|
|
<form action="" method="post" id="login-form">
|
|
<!--@AdminLoginFormBegin-->
|
|
<div id="errtips"></div>
|
|
{:token()}
|
|
|
|
<!-- 账号输入 -->
|
|
<div class="form-row">
|
|
<div class="input-group-modern">
|
|
<!-- 工牌/用户矢量图标 -->
|
|
<svg class="input-left-icon" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
|
<path d="M16 21v-2a4 4 0 0 0-4-4H6a4 4 0 0 0-4 4v2"></path>
|
|
<circle cx="9" cy="7" r="4"></circle>
|
|
<path d="M22 21v-2a4 4 0 0 0-3-3.87"></path>
|
|
<path d="M16 3.13a4 4 0 0 1 0 7.75"></path>
|
|
</svg>
|
|
<input type="text"
|
|
class="form-control form-input-modern"
|
|
id="pd-form-username"
|
|
name="username"
|
|
placeholder="请输入管理员账号"
|
|
autocomplete="off"
|
|
value=""
|
|
data-rule="{:__('Username')}:required;username"/>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 密码输入 -->
|
|
<div class="form-row">
|
|
<div class="input-group-modern">
|
|
<!-- 锁矢量图标 -->
|
|
<svg class="input-left-icon" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
|
<rect x="3" y="11" width="18" height="11" rx="2" ry="2"></rect>
|
|
<path d="M7 11V7a5 5 0 0 1 10 0v4"></path>
|
|
</svg>
|
|
<input type="password"
|
|
class="form-control form-input-modern"
|
|
id="pd-form-password"
|
|
name="password"
|
|
placeholder="请输入登录密码"
|
|
autocomplete="off"
|
|
value=""
|
|
data-rule="{:__('Password')}:required;password"/>
|
|
<!-- 切换密码明文/密文小眼睛 -->
|
|
<button type="button" class="pwd-eye-btn" id="toggle-pwd-btn" aria-label="切换密码可见性" title="切换密码可见性">
|
|
<svg id="eye-icon-off" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
|
<path d="M17.94 17.94A10.07 10.07 0 0 1 12 20c-7 0-11-8-11-8a18.45 18.45 0 0 1 5.06-5.94M9.9 4.24A9.12 9.12 0 0 1 12 4c7 0 11 8 11 8a18.5 18.5 0 0 1-2.16 3.19m-6.72-1.07a3 3 0 1 1-4.24-4.24"></path>
|
|
<line x1="1" y1="1" x2="23" y2="23"></line>
|
|
</svg>
|
|
<svg id="eye-icon-on" style="display: none;" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
|
<path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z"></path>
|
|
<circle cx="12" cy="12" r="3"></circle>
|
|
</svg>
|
|
</button>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- 验证码输入 -->
|
|
<!--@CaptchaBegin-->
|
|
{if $Think.config.fastadmin.login_captcha}
|
|
<div class="form-row">
|
|
<div class="captcha-flex-row">
|
|
<div class="input-group-modern">
|
|
<!-- 盾牌安全图标 -->
|
|
<svg class="input-left-icon" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
|
<path d="M12 22s8-4 8-10V5l-8-3-8 3v7c0 6 8 10 8 10z"></path>
|
|
</svg>
|
|
<input type="text"
|
|
name="captcha"
|
|
id="pd-form-captcha"
|
|
class="form-control form-input-modern"
|
|
placeholder="请输入4位验证码"
|
|
maxlength="4"
|
|
data-rule="{:__('Captcha')}:required;length({$Think.config.captcha.length|htmlentities})"
|
|
autocomplete="off"/>
|
|
</div>
|
|
<div class="captcha-img-box input-group-addon" id="captcha-box" title="点击刷新验证码">
|
|
<img src="{:rtrim('__PUBLIC__', '/')}/index.php?s=/captcha"
|
|
alt="验证码"
|
|
id="captcha-img"
|
|
onclick="this.src = '{:rtrim('__PUBLIC__', '/')}/index.php?s=/captcha&r=' + Math.random();"/>
|
|
<svg class="captcha-refresh-icon" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round">
|
|
<polyline points="23 4 23 10 17 10"></polyline>
|
|
<polyline points="1 20 1 14 7 14"></polyline>
|
|
<path d="M3.51 9a9 9 0 0 1 14.85-3.36L23 10M1 14l4.64 4.36A9 9 0 0 0 20.49 15"></path>
|
|
</svg>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
{/if}
|
|
<!--@CaptchaEnd-->
|
|
|
|
<!-- 记住我与忘记密码 -->
|
|
<div class="auth-actions-row">
|
|
{if $keeyloginhours>0}
|
|
<label class="checkbox-label" for="keeplogin" title="{:__('The duration of the session is %s hours', $keeyloginhours)}">
|
|
<input type="checkbox" name="keeplogin" id="keeplogin" value="1" checked/>
|
|
<span>记住我</span>
|
|
</label>
|
|
{else}
|
|
<div></div>
|
|
{/if}
|
|
<a href="javascript:void(0);" class="forgot-link" id="btn-forgot-pwd">忘记密码?</a>
|
|
</div>
|
|
|
|
<!-- 提交登录按钮 -->
|
|
<button type="submit" class="btn btn-submit-login">
|
|
<span>立即安全登录</span>
|
|
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round">
|
|
<line x1="5" y1="12" x2="19" y2="12"></line>
|
|
<polyline points="12 5 19 12 12 19"></polyline>
|
|
</svg>
|
|
</button>
|
|
<!--@AdminLoginFormEnd-->
|
|
</form>
|
|
</div>
|
|
|
|
<!-- 页脚版权 -->
|
|
<footer class="auth-footer">
|
|
<div>© {:date('Y')} 山间小仓数字农品信息发布网 · 同城分类管理中台</div>
|
|
</footer>
|
|
</main>
|
|
</div>
|
|
|
|
{include file="common/script" /}
|
|
|
|
<script>
|
|
/**
|
|
* 绑定登录页前端交互行为
|
|
* 包括密码可见性切换、验证码刷新与管理员联系提示
|
|
*/
|
|
(function initLoginInteractions() {
|
|
// 密码明密文切换逻辑
|
|
var pwdInput = document.getElementById('pd-form-password');
|
|
var toggleBtn = document.getElementById('toggle-pwd-btn');
|
|
var eyeOff = document.getElementById('eye-icon-off');
|
|
var eyeOn = document.getElementById('eye-icon-on');
|
|
|
|
if (toggleBtn && pwdInput) {
|
|
toggleBtn.addEventListener('click', function (e) {
|
|
e.preventDefault();
|
|
var isPassword = pwdInput.type === 'password';
|
|
pwdInput.type = isPassword ? 'text' : 'password';
|
|
if (eyeOff && eyeOn) {
|
|
eyeOff.style.display = isPassword ? 'none' : 'block';
|
|
eyeOn.style.display = isPassword ? 'block' : 'none';
|
|
}
|
|
});
|
|
}
|
|
|
|
// 验证码容器点击刷新逻辑
|
|
var captchaBox = document.getElementById('captcha-box');
|
|
var captchaImg = document.getElementById('captcha-img');
|
|
if (captchaBox && captchaImg) {
|
|
captchaBox.addEventListener('click', function () {
|
|
captchaImg.src = '{:rtrim("__PUBLIC__", "/")}/index.php?s=/captcha&r=' + Math.random();
|
|
});
|
|
}
|
|
|
|
// 忘记密码弹窗指引
|
|
var forgotBtn = document.getElementById('btn-forgot-pwd');
|
|
if (forgotBtn) {
|
|
forgotBtn.addEventListener('click', function () {
|
|
if (window.Layer) {
|
|
Layer.alert('如需找回或重置管理后台登录密码,请联系系统超级管理员进行身份核验与重置。', {
|
|
title: '找回密码指引',
|
|
icon: 0,
|
|
btn: ['我知道了']
|
|
});
|
|
} else {
|
|
alert('如需找回或重置管理后台登录密码,请联系系统超级管理员进行身份核验与重置。');
|
|
}
|
|
});
|
|
}
|
|
|
|
// 轮播圆点高亮切换
|
|
var dots = document.querySelectorAll('.hero-dot');
|
|
dots.forEach(function (dot) {
|
|
dot.addEventListener('click', function () {
|
|
dots.forEach(function (d) { d.classList.remove('active'); });
|
|
dot.classList.add('active');
|
|
});
|
|
});
|
|
})();
|
|
</script>
|
|
</body>
|
|
</html>
|