| | |
| | | <template> |
| | | <div class="login-page"> |
| | | <div class="login-page" :style="{ backgroundImage: `url(${backgroundImage})` }"> |
| | | <main class="page"> |
| | | <section class="factory"> |
| | | <div class="brand hero-brand"> |
| | | <div class="logo hero-logo"> |
| | | <img :src="brandLogoUrl" |
| | | :alt="`${companyName} logo`" |
| | | class="logo-image hero-logo-image" |
| | | @error="handleLogoError" /> |
| | | </div> |
| | | </div> |
| | | <div class="hero"> |
| | | <div class="chip">数字工厂 · 智能排产 · 设备互联 · 质量追溯</div> |
| | | <h1>数字工厂<br />MOM 智造平台</h1> |
| | | <p> |
| | | 以实时数据驱动生产现场,把工单、设备、物料、质量、能耗与仓储连接成一张透明的制造运营网络。 |
| | | </p> |
| | | </div> |
| | | <div class="scene" |
| | | aria-hidden="true"> |
| | | <div class="floor"></div> |
| | | <svg class="factory-svg" |
| | | viewBox="0 0 920 360" |
| | | preserveAspectRatio="xMidYMid meet"> |
| | | <defs> |
| | | <linearGradient id="g1" |
| | | x1="0" |
| | | y1="0" |
| | | x2="1" |
| | | y2="1"> |
| | | <stop offset="0" |
| | | stop-color="#40e4ff" |
| | | stop-opacity=".9" /> |
| | | <stop offset="1" |
| | | stop-color="#1f78ff" |
| | | stop-opacity=".68" /> |
| | | </linearGradient> |
| | | <linearGradient id="g2" |
| | | x1="0" |
| | | y1="0" |
| | | x2="1" |
| | | y2="1"> |
| | | <stop offset="0" |
| | | stop-color="#ffffff" |
| | | stop-opacity=".28" /> |
| | | <stop offset="1" |
| | | stop-color="#ffffff" |
| | | stop-opacity=".06" /> |
| | | </linearGradient> |
| | | </defs> |
| | | <path d="M45 255H830" |
| | | stroke="url(#g1)" |
| | | stroke-width="16" |
| | | stroke-linecap="round" |
| | | opacity=".55" /> |
| | | <path class="belt" |
| | | d="M45 255H830" |
| | | stroke="#fff" |
| | | stroke-width="3" |
| | | stroke-linecap="round" |
| | | opacity=".75" /> |
| | | <g class="box"> |
| | | <rect x="60" |
| | | y="212" |
| | | width="54" |
| | | height="42" |
| | | rx="8" |
| | | fill="#ffb15f" /> |
| | | <path d="M60 225h54" |
| | | stroke="#fff" |
| | | opacity=".45" /> |
| | | </g> |
| | | <g class="box two"> |
| | | <rect x="60" |
| | | y="212" |
| | | width="54" |
| | | height="42" |
| | | rx="8" |
| | | fill="#28d9cd" /> |
| | | <path d="M60 225h54" |
| | | stroke="#fff" |
| | | opacity=".45" /> |
| | | </g> |
| | | <g class="box three"> |
| | | <rect x="60" |
| | | y="212" |
| | | width="54" |
| | | height="42" |
| | | rx="8" |
| | | fill="#8b5cf6" /> |
| | | <path d="M60 225h54" |
| | | stroke="#fff" |
| | | opacity=".45" /> |
| | | </g> |
| | | <g> |
| | | <rect x="120" |
| | | y="112" |
| | | width="138" |
| | | height="128" |
| | | rx="10" |
| | | fill="url(#g2)" |
| | | stroke="rgba(255,255,255,.42)" /> |
| | | <path d="M145 185h88M145 210h58" |
| | | stroke="#40e4ff" |
| | | stroke-width="6" |
| | | stroke-linecap="round" /> |
| | | <path d="M145 140h88" |
| | | stroke="#fff" |
| | | stroke-opacity=".5" |
| | | stroke-width="4" |
| | | stroke-linecap="round" /> |
| | | </g> |
| | | <g> |
| | | <rect x="315" |
| | | y="76" |
| | | width="190" |
| | | height="164" |
| | | rx="12" |
| | | fill="url(#g2)" |
| | | stroke="rgba(255,255,255,.42)" /> |
| | | <path d="M350 126h120M350 158h90M350 190h112" |
| | | stroke="#fff" |
| | | stroke-opacity=".5" |
| | | stroke-width="6" |
| | | stroke-linecap="round" /> |
| | | <circle class="signal" |
| | | cx="472" |
| | | cy="104" |
| | | r="10" |
| | | fill="#20e0d2" /> |
| | | <circle class="signal two" |
| | | cx="448" |
| | | cy="104" |
| | | r="10" |
| | | fill="#1f78ff" /> |
| | | <circle class="signal three" |
| | | cx="424" |
| | | cy="104" |
| | | r="10" |
| | | fill="#ff8a3d" /> |
| | | </g> |
| | | <g class="arm"> |
| | | <path d="M612 124h92" |
| | | stroke="#40e4ff" |
| | | stroke-width="14" |
| | | stroke-linecap="round" /> |
| | | <path d="M704 124l42 56" |
| | | stroke="#40e4ff" |
| | | stroke-width="14" |
| | | stroke-linecap="round" /> |
| | | <circle cx="612" |
| | | cy="124" |
| | | r="25" |
| | | fill="#1f78ff" |
| | | stroke="#fff" |
| | | stroke-opacity=".45" /> |
| | | <circle cx="704" |
| | | cy="124" |
| | | r="18" |
| | | fill="#20e0d2" /> |
| | | <path d="M744 180v34M727 214h34" |
| | | stroke="#fff" |
| | | stroke-width="7" |
| | | stroke-linecap="round" /> |
| | | </g> |
| | | <g> |
| | | <rect x="690" |
| | | y="82" |
| | | width="148" |
| | | height="158" |
| | | rx="12" |
| | | fill="url(#g2)" |
| | | stroke="rgba(255,255,255,.42)" /> |
| | | <path d="M724 206V134M764 206V112M804 206V154" |
| | | stroke="#20e0d2" |
| | | stroke-width="12" |
| | | stroke-linecap="round" /> |
| | | <path d="M720 206h92" |
| | | stroke="#fff" |
| | | stroke-opacity=".44" |
| | | stroke-width="5" |
| | | stroke-linecap="round" /> |
| | | </g> |
| | | <path d="M190 112C265 42 348 48 410 76C502 118 568 76 612 124C654 170 700 74 764 82" |
| | | fill="none" |
| | | stroke="#20e0d2" |
| | | stroke-width="2" |
| | | stroke-dasharray="8 10" |
| | | opacity=".58"> |
| | | <animate attributeName="stroke-dashoffset" |
| | | from="80" |
| | | to="0" |
| | | dur="2s" |
| | | repeatCount="indefinite" /> |
| | | </path> |
| | | </svg> |
| | | </div> |
| | | </section> |
| | | <section class="login-wrap"> |
| | | <div class="time"> |
| | | <span>{{ todayLabel }}</span> |
| | |
| | | </div> |
| | | <div class="brand-copy card-brand-copy"> |
| | | <div class="brand-title">{{ companyName }}</div> |
| | | <small>数字工厂统一入口</small> |
| | | </div> |
| | | </div> |
| | | <h2>欢迎登录</h2> |
| | | <p class="sub">进入 MOM 数字工厂运营驾驶舱</p> |
| | | <div class="form-row"> |
| | | <label>账号</label> |
| | | <div class="input"> |
| | |
| | | import { encrypt, decrypt } from "@/utils/jsencrypt"; |
| | | import useUserStore from "@/store/modules/user"; |
| | | import defaultBrandLogo from "@/assets/logo/logo.png"; |
| | | import backgroundImage from "@/layout/components/Sidebar/KHLView.png"; |
| | | |
| | | const userStore = useUserStore(); |
| | | const route = useRoute(); |
| | |
| | | position: relative; |
| | | min-height: 100vh; |
| | | overflow: hidden; |
| | | background: radial-gradient( |
| | | circle at 12% 14%, |
| | | rgba(var(--accent-rgb), 0.14), |
| | | transparent 38% |
| | | ), |
| | | radial-gradient(circle at 92% 8%, rgba(2, 132, 199, 0.12), transparent 36%), |
| | | conic-gradient( |
| | | from 220deg at 24% 18%, |
| | | rgba(var(--accent-rgb), 0.1), |
| | | rgba(56, 189, 248, 0.08), |
| | | rgba(99, 102, 241, 0.08), |
| | | rgba(var(--accent-rgb), 0.1) |
| | | ), |
| | | linear-gradient(180deg, #f7f8fb 0%, #f3f5fa 100%); |
| | | background-position: center; |
| | | background-size: cover; |
| | | background-repeat: no-repeat; |
| | | } |
| | | |
| | | .login-page * { |
| | |
| | | .page { |
| | | position: relative; |
| | | z-index: 1; |
| | | max-width: 1200px; |
| | | margin: 48px auto; |
| | | width: calc(100% - 48px); |
| | | min-height: calc(100vh - 96px); |
| | | display: grid; |
| | | grid-template-columns: 3fr 2fr; |
| | | gap: 0; |
| | | align-items: stretch; |
| | | border-radius: var(--content-radius); |
| | | background: rgba(255, 255, 255, 0.72); |
| | | border: 1px solid rgba(255, 255, 255, 0.72); |
| | | box-shadow: var(--shadow); |
| | | backdrop-filter: blur(18px); |
| | | overflow: hidden; |
| | | } |
| | | |
| | | .page::before { |
| | | content: ""; |
| | | position: absolute; |
| | | inset: 0; |
| | | border-radius: inherit; |
| | | background: radial-gradient( |
| | | circle at 22% 22%, |
| | | rgba(var(--accent-rgb), 0.34), |
| | | transparent 58% |
| | | ) |
| | | left center / 60% 100% no-repeat, |
| | | radial-gradient( |
| | | circle at 76% 12%, |
| | | rgba(56, 189, 248, 0.22), |
| | | transparent 50% |
| | | ) |
| | | left center / 60% 100% no-repeat, |
| | | linear-gradient( |
| | | 135deg, |
| | | rgba(2, 6, 23, 0.96) 0%, |
| | | rgba(15, 35, 57, 0.94) 52%, |
| | | rgba(15, 35, 57, 0.88) 100% |
| | | ) |
| | | left center / 60% 100% no-repeat; |
| | | pointer-events: none; |
| | | z-index: 0; |
| | | } |
| | | |
| | | .page::after { |
| | | content: ""; |
| | | position: absolute; |
| | | top: 0; |
| | | bottom: 0; |
| | | left: 60%; |
| | | width: 1px; |
| | | background: linear-gradient( |
| | | 180deg, |
| | | transparent, |
| | | rgba(15, 23, 42, 0.16), |
| | | transparent |
| | | ); |
| | | pointer-events: none; |
| | | z-index: 0; |
| | | width: 100%; |
| | | min-height: 100vh; |
| | | padding: 48px 72px; |
| | | display: flex; |
| | | align-items: center; |
| | | justify-content: center; |
| | | } |
| | | |
| | | .factory { |
| | |
| | | display: flex; |
| | | align-items: center; |
| | | justify-content: center; |
| | | padding: 36px 44px; |
| | | padding: 0; |
| | | width: 100%; |
| | | max-width: 100%; |
| | | } |
| | | |
| | | .time { |
| | |
| | | } |
| | | |
| | | .login-card { |
| | | width: min(420px, 100%); |
| | | width: min(520px, 100%); |
| | | padding: 38px 34px 34px; |
| | | border-radius: var(--radius-lg); |
| | | border: 1px solid rgba(15, 23, 42, 0.12); |
| | |
| | | } |
| | | |
| | | :global(html.dark) .page { |
| | | background: rgba(2, 6, 23, 0.46); |
| | | border-color: rgba(226, 232, 240, 0.12); |
| | | box-shadow: 0 38px 96px rgba(0, 0, 0, 0.5); |
| | | background: transparent; |
| | | border-color: transparent; |
| | | box-shadow: none; |
| | | } |
| | | |
| | | :global(html.dark) .page::before { |
| | | background: linear-gradient( |
| | | 135deg, |
| | | rgba(var(--accent-rgb), 0.62) 0%, |
| | | rgba(var(--accent-rgb), 0.42) 52%, |
| | | rgba(56, 189, 248, 0.28) 100% |
| | | ); |
| | | box-shadow: 0 18px 60px rgba(0, 0, 0, 0.28); |
| | | } |
| | | |
| | | :global(html.dark) .page::after { |
| | | background-image: radial-gradient( |
| | | circle at 16% 22%, |
| | | rgba(255, 255, 255, 0.16), |
| | | transparent 56% |
| | | ), |
| | | radial-gradient( |
| | | circle at 76% 16%, |
| | | rgba(255, 255, 255, 0.1), |
| | | transparent 52% |
| | | ), |
| | | radial-gradient( |
| | | circle at 78% 72%, |
| | | rgba(255, 255, 255, 0.12), |
| | | transparent 58% |
| | | ), |
| | | radial-gradient(rgba(255, 255, 255, 0.2) 1px, transparent 1px), |
| | | repeating-linear-gradient( |
| | | 132deg, |
| | | rgba(255, 255, 255, 0.14) 0 1px, |
| | | transparent 1px 14px |
| | | ), |
| | | repeating-linear-gradient( |
| | | 42deg, |
| | | rgba(2, 6, 23, 0.26) 0 1px, |
| | | transparent 1px 18px |
| | | ); |
| | | opacity: 0.5; |
| | | } |
| | | |
| | | :global(html.dark) .page::after { |
| | |
| | | } |
| | | |
| | | .page { |
| | | grid-template-columns: 1fr; |
| | | gap: 18px; |
| | | margin: 18px auto; |
| | | width: calc(100% - 32px); |
| | | min-height: auto; |
| | | max-width: 560px; |
| | | padding: 18px 16px; |
| | | min-height: 100vh; |
| | | justify-content: center; |
| | | } |
| | | |
| | | .page::before, |
| | |
| | | |
| | | .login-wrap { |
| | | padding: 0; |
| | | width: 100%; |
| | | max-width: 100%; |
| | | margin-left: 0; |
| | | } |
| | | |
| | | .time { |