Files
xiaozhi-esp32-server/main/manager-web/src/views/login.vue
T

153 lines
5.1 KiB
Vue
Raw Normal View History

2025-03-05 23:13:24 +08:00
<template>
<div class="welcome">
<el-container style="height: 100%;">
<el-header>
2025-04-05 20:19:28 +08:00
<div style="display: flex;align-items: center;margin-top: 15px;margin-left: 10px;gap: 10px;">
<img loading="lazy" alt="" src="@/assets/xiaozhi-logo.png" style="width: 45px;height: 45px;" />
<img loading="lazy" alt="" src="@/assets/xiaozhi-ai.png" style="height: 18px;" />
2025-03-05 23:13:24 +08:00
</div>
</el-header>
<div class="login-person">
2025-04-05 20:19:28 +08:00
<img loading="lazy" alt="" src="@/assets/login/login-person.png" style="width: 100%;" />
</div>
2025-03-05 23:13:24 +08:00
<el-main style="position: relative;">
2025-04-01 10:59:35 +08:00
<div class="login-box" @keyup.enter="login">
2025-04-05 20:19:28 +08:00
<div style="display: flex;align-items: center;gap: 20px;margin-bottom: 39px;padding: 0 30px;">
<img loading="lazy" alt="" src="@/assets/login/hi.png" style="width: 34px;height: 34px;" />
2025-03-05 23:13:24 +08:00
<div class="login-text">登录</div>
<div class="login-welcome">
2025-03-07 10:01:20 +08:00
WELCOME TO LOGIN
</div>
2025-03-05 23:13:24 +08:00
</div>
2025-03-07 10:01:20 +08:00
<div style="padding: 0 30px;">
<div class="input-box">
2025-04-05 20:19:28 +08:00
<img loading="lazy" alt="" class="input-icon" src="@/assets/login/username.png" />
<el-input v-model="form.username" placeholder="请输入用户名" />
2025-03-07 10:01:20 +08:00
</div>
<div class="input-box">
2025-04-05 20:19:28 +08:00
<img loading="lazy" alt="" class="input-icon" src="@/assets/login/password.png" />
<el-input v-model="form.password" placeholder="请输入密码" type="password" />
2025-03-07 10:01:20 +08:00
</div>
2025-03-12 13:38:44 +08:00
<div style="display: flex; align-items: center; margin-top: 20px; width: 100%; gap: 10px;">
<div class="input-box" style="width: calc(100% - 130px); margin-top: 0;">
2025-04-05 20:19:28 +08:00
<img loading="lazy" alt="" class="input-icon" src="@/assets/login/shield.png" />
<el-input v-model="form.captcha" placeholder="请输入验证码" style="flex: 1;" />
2025-03-12 13:38:44 +08:00
</div>
2025-04-05 20:19:28 +08:00
<img loading="lazy" v-if="captchaUrl" :src="captchaUrl" alt="验证码"
style="width: 150px; height: 40px; cursor: pointer;" @click="fetchCaptcha" />
2025-03-07 10:01:20 +08:00
</div>
<div
2025-04-05 20:19:28 +08:00
style="font-weight: 400;font-size: 14px;text-align: left;color: #5778ff;display: flex;justify-content: space-between;margin-top: 20px;">
2025-03-12 13:38:44 +08:00
<div style="cursor: pointer;" @click="goToRegister">新用户注册</div>
2025-03-07 10:01:20 +08:00
</div>
</div>
2025-04-09 09:11:25 +08:00
<div class="login-btn" @click="login">登录</div>
2025-03-05 23:13:24 +08:00
<div style="font-size: 14px;color: #979db1;">
2025-03-07 10:01:20 +08:00
登录即同意
<div style="display: inline-block;color: #5778FF;cursor: pointer;">用户协议</div>
2025-03-05 23:13:24 +08:00
<div style="display: inline-block;color: #5778FF;cursor: pointer;">隐私政策</div>
</div>
</div>
</el-main>
<el-footer>
<div class="copyright">
2025-03-07 10:01:20 +08:00
©2025 xiaozhi-esp32-server
</div>
2025-03-05 23:13:24 +08:00
</el-footer>
</el-container>
</div>
</template>
<script>
2025-03-12 13:38:44 +08:00
import Api from '@/apis/api';
2025-04-05 20:16:02 +08:00
import { getUUID, goToPage, showDanger, showSuccess } from '@/utils';
2025-03-12 13:38:44 +08:00
2025-03-05 23:13:24 +08:00
export default {
name: 'login',
data() {
return {
activeName: "username",
2025-03-07 10:01:20 +08:00
form: {
username: '',
password: '',
2025-03-12 23:31:59 +08:00
captcha: '',
captchaId: ''
2025-03-12 13:38:44 +08:00
},
captchaUuid: '',
captchaUrl: ''
2025-03-05 23:13:24 +08:00
}
},
2025-03-12 13:38:44 +08:00
mounted() {
this.fetchCaptcha();
},
2025-03-07 10:01:20 +08:00
methods: {
2025-03-12 13:38:44 +08:00
fetchCaptcha() {
2025-03-14 23:48:59 +08:00
if (this.$store.getters.getToken) {
2025-04-05 20:19:28 +08:00
if (this.$route.path !== '/home') {
2025-04-01 10:59:35 +08:00
this.$router.push('/home')
}
2025-03-14 23:48:59 +08:00
} else {
this.captchaUuid = getUUID();
2025-03-12 13:38:44 +08:00
2025-03-14 23:48:59 +08:00
Api.user.getCaptcha(this.captchaUuid, (res) => {
if (res.status === 200) {
2025-04-05 20:19:28 +08:00
const blob = new Blob([res.data], { type: res.data.type });
2025-03-14 23:48:59 +08:00
this.captchaUrl = URL.createObjectURL(blob);
} else {
2025-04-01 10:59:35 +08:00
showDanger('验证码加载失败,点击刷新');
2025-03-14 23:48:59 +08:00
}
});
}
2025-03-12 13:38:44 +08:00
},
// 封装输入验证逻辑
validateInput(input, message) {
if (!input.trim()) {
showDanger(message);
return false;
}
return true;
},
2025-03-12 13:38:44 +08:00
async login() {
// 验证用户名
if (!this.validateInput(this.form.username, '用户名不能为空')) {
return;
2025-03-07 10:01:20 +08:00
}
// 验证密码
if (!this.validateInput(this.form.password, '密码不能为空')) {
return;
2025-03-07 10:01:20 +08:00
}
// 验证验证码
if (!this.validateInput(this.form.captcha, '验证码不能为空')) {
return;
2025-03-07 10:01:20 +08:00
}
2025-03-12 13:38:44 +08:00
2025-03-12 23:31:59 +08:00
this.form.captchaId = this.captchaUuid
2025-04-05 20:19:28 +08:00
Api.user.login(this.form, ({ data }) => {
2025-04-01 10:59:35 +08:00
if (data.code === 0) {
showSuccess('登录成功!');
this.$store.commit('setToken', JSON.stringify(data.data));
goToPage('/home');
} else {
showDanger(data.msg || '登录失败');
}
2025-03-07 10:01:20 +08:00
})
2025-03-14 23:48:59 +08:00
// 重新获取验证码
2025-03-12 23:31:59 +08:00
setTimeout(() => {
this.fetchCaptcha();
}, 1000);
2025-03-12 13:38:44 +08:00
},
goToRegister() {
goToPage('/register')
2025-03-05 23:13:24 +08:00
}
}
}
</script>
<style lang="scss" scoped>
2025-04-05 20:19:28 +08:00
@import './auth.scss'; // 添加这行引用</style>