初始化

This commit is contained in:
2026-07-01 16:27:02 +08:00
parent fe0d4304f8
commit accd62a2f3
31 changed files with 6448 additions and 1136 deletions

203
src/views/login/index.vue Normal file
View File

@@ -0,0 +1,203 @@
<script lang="ts" setup>
import { computed, reactive, ref } from "vue";
import { useRoute, useRouter } from "vue-router";
import { useUserStore } from "@/store/modules/user.js";
import { encryptPasswordPayload } from '@/utils/passwordEncrypt.js'
const route = useRoute();
const router = useRouter();
const userStore = useUserStore();
const form = reactive({
username: "",
password: "",
});
const loading = ref(false);
const errorMessage = ref("");
const redirectPath = computed(() => {
const redirect = route.query.redirect;
if (
typeof redirect === "string" &&
redirect.startsWith("/") &&
!redirect.startsWith("//")
) {
return redirect;
}
return "/dashboard/integrated-center";
});
// 校验登录表单,避免空账号或空密码提交到后端。
function validateLoginForm() {
if (!form.username.trim()) {
errorMessage.value = "请输入账号";
return false;
}
if (!form.password) {
errorMessage.value = "请输入密码";
return false;
}
return true;
}
// 提交登录信息,成功后回到登录前访问的页面。
async function handleLogin() {
if (!validateLoginForm() || loading.value) {
return;
}
loading.value = true;
errorMessage.value = "";
try {
const encryptedForm = await encryptPasswordPayload(form, ['password'])
await userStore.login(encryptedForm)
router.replace(redirectPath.value);
} catch (error) {
errorMessage.value =
error instanceof Error ? error.message : "登录失败,请检查账号或密码";
} finally {
loading.value = false;
}
}
</script>
<template>
<div class="login-page">
<form class="login-card" @submit.prevent="handleLogin">
<div class="login-card__eyebrow">Robot Manager</div>
<h1>系统登录</h1>
<p>请输入账号和密码进入巡检管理大屏</p>
<label class="login-field">
<span>账号</span>
<input v-model="form.username" autocomplete="username" placeholder="请输入账号" type="text" />
</label>
<label class="login-field">
<span>密码</span>
<input v-model="form.password" autocomplete="current-password" placeholder="请输入密码" type="password" />
</label>
<div v-if="errorMessage" class="login-error">{{ errorMessage }}</div>
<button class="login-button" :disabled="loading" type="submit">
{{ loading ? "登录中..." : "登录" }}
</button>
</form>
</div>
</template>
<style scoped>
.login-page {
display: flex;
align-items: center;
justify-content: center;
width: 100%;
height: 100%;
color: #dff7ff;
background:
radial-gradient(circle at 50% 42%,
rgba(31, 126, 202, 0.32),
transparent 34%),
radial-gradient(circle at center, #15385d 0%, #061426 60%, #02070f 100%);
}
.login-card {
box-sizing: border-box;
width: 440px;
padding: 44px 48px 48px;
text-align: left;
border: 1px solid rgba(116, 236, 255, 0.28);
border-radius: 18px;
background: linear-gradient(180deg,
rgba(7, 31, 61, 0.9),
rgba(4, 15, 31, 0.86));
box-shadow:
0 0 40px rgba(69, 188, 255, 0.18),
inset 0 0 26px rgba(116, 236, 255, 0.08);
}
.login-card__eyebrow {
margin-bottom: 12px;
color: #74ecff;
font-size: 13px;
letter-spacing: 0.22em;
text-transform: uppercase;
}
.login-card h1 {
margin: 0 0 12px;
font-size: 34px;
font-weight: 600;
letter-spacing: 0.08em;
}
.login-card p {
margin: 0 0 34px;
color: rgba(223, 247, 255, 0.72);
font-size: 15px;
}
.login-field {
display: block;
margin-bottom: 20px;
}
.login-field span {
display: block;
margin-bottom: 8px;
color: rgba(223, 247, 255, 0.78);
font-size: 14px;
}
.login-field input {
box-sizing: border-box;
width: 100%;
height: 46px;
padding: 0 16px;
color: #e8fbff;
border: 1px solid rgba(116, 236, 255, 0.26);
border-radius: 8px;
outline: none;
background: rgba(3, 15, 32, 0.74);
transition:
border-color 0.2s,
box-shadow 0.2s;
}
.login-field input:focus {
border-color: rgba(116, 236, 255, 0.78);
box-shadow: 0 0 18px rgba(116, 236, 255, 0.16);
}
.login-field input::placeholder {
color: rgba(223, 247, 255, 0.34);
}
.login-error {
min-height: 20px;
margin: -4px 0 16px;
color: #ff9c9c;
font-size: 14px;
}
.login-button {
width: 100%;
height: 48px;
color: #062239;
font-size: 17px;
font-weight: 600;
letter-spacing: 0.12em;
cursor: pointer;
border: 0;
border-radius: 8px;
background: linear-gradient(90deg, #74ecff, #46a7ff);
box-shadow: 0 0 24px rgba(70, 167, 255, 0.32);
}
.login-button:disabled {
cursor: not-allowed;
opacity: 0.68;
}
</style>