2025-03-23 09:18:42 +08:00
|
|
|
<template>
|
|
|
|
<div class="login-container">
|
|
|
|
<div class="top_item">
|
2025-10-22 14:07:54 +08:00
|
|
|
<div class="title_no">全球一体化系统管理平台({{ systemTypes }})</div>
|
2025-03-23 09:18:42 +08:00
|
|
|
<dv-decoration-5
|
|
|
|
:color="['#4278a3', '#4278a3']"
|
|
|
|
style="width: 100%; height: 100px"
|
|
|
|
/>
|
|
|
|
</div>
|
|
|
|
<!-- <div class="qiu">
|
|
|
|
<img src="@/assets/images/globel.gif"
|
|
|
|
alt="">
|
|
|
|
</div> -->
|
|
|
|
<div class="contain">
|
2025-04-08 09:12:42 +08:00
|
|
|
<dv-border-box-7 :color="['#0f2e66', '#139efa']" />
|
2025-03-23 09:18:42 +08:00
|
|
|
</div>
|
|
|
|
<div class="login_contain">
|
|
|
|
<el-form
|
|
|
|
ref="loginForm"
|
|
|
|
:model="loginForm"
|
|
|
|
:rules="loginRules"
|
|
|
|
class="login-form"
|
|
|
|
auto-complete="on"
|
|
|
|
label-position="left"
|
|
|
|
>
|
|
|
|
<!-- <div class="title-container">
|
|
|
|
<h3 class="title">Login Form</h3>
|
|
|
|
</div> -->
|
|
|
|
<div class="tit1">
|
|
|
|
<div class="act">密码登录</div>
|
|
|
|
<!-- <div>短信登录</div> -->
|
|
|
|
</div>
|
|
|
|
<el-form-item prop="username">
|
|
|
|
<span class="svg-container">
|
|
|
|
<svg-icon icon-class="user" />
|
|
|
|
</span>
|
|
|
|
<el-input
|
|
|
|
ref="username"
|
|
|
|
v-model="loginForm.username"
|
2025-04-08 09:12:42 +08:00
|
|
|
clearable
|
2025-03-23 09:18:42 +08:00
|
|
|
placeholder="Username"
|
|
|
|
name="username"
|
|
|
|
type="text"
|
|
|
|
tabindex="1"
|
|
|
|
auto-complete="on"
|
2025-04-08 09:12:42 +08:00
|
|
|
@blur="getCheck"
|
2025-03-23 09:18:42 +08:00
|
|
|
/>
|
|
|
|
</el-form-item>
|
|
|
|
|
|
|
|
<el-form-item prop="password">
|
|
|
|
<span class="svg-container">
|
|
|
|
<svg-icon icon-class="password" />
|
|
|
|
</span>
|
|
|
|
<el-input
|
|
|
|
:key="passwordType"
|
|
|
|
ref="password"
|
|
|
|
v-model="loginForm.password"
|
2025-04-08 09:12:42 +08:00
|
|
|
clearable
|
2025-03-23 09:18:42 +08:00
|
|
|
:type="passwordType"
|
|
|
|
placeholder="Password"
|
|
|
|
name="password"
|
|
|
|
tabindex="2"
|
|
|
|
auto-complete="on"
|
|
|
|
@keyup.enter.native="handleLogin"
|
|
|
|
/>
|
|
|
|
<span class="show-pwd" @click="showPwd">
|
|
|
|
<svg-icon
|
|
|
|
:icon-class="passwordType === 'password' ? 'eye' : 'eye-open'"
|
|
|
|
/>
|
|
|
|
</span>
|
|
|
|
</el-form-item>
|
|
|
|
<div class="yzm">
|
|
|
|
<el-form-item prop="code" style="flex: 1">
|
|
|
|
<span class="svg-container">
|
|
|
|
<svg-icon icon-class="password" />
|
|
|
|
</span>
|
|
|
|
<el-input
|
2025-04-08 09:12:42 +08:00
|
|
|
v-model.trim="loginForm.code"
|
2025-03-23 09:18:42 +08:00
|
|
|
clearable
|
|
|
|
placeholder="请输入验证码"
|
|
|
|
@keyup.enter.native="handleLogin"
|
2025-04-08 09:12:42 +08:00
|
|
|
/>
|
2025-03-23 09:18:42 +08:00
|
|
|
</el-form-item>
|
|
|
|
<div class="img">
|
2025-04-08 09:12:42 +08:00
|
|
|
<img :src="codeUrl" @click="getVerifyCode">
|
2025-03-23 09:18:42 +08:00
|
|
|
</div>
|
|
|
|
</div>
|
2025-04-08 09:12:42 +08:00
|
|
|
<div v-if="ismsgCode" class="yzm">
|
2025-03-23 09:18:42 +08:00
|
|
|
<el-form-item prop="smsCode" style="flex: 1">
|
|
|
|
<span class="svg-container">
|
|
|
|
<svg-icon icon-class="password" />
|
|
|
|
</span>
|
|
|
|
<el-input
|
2025-04-08 09:12:42 +08:00
|
|
|
v-model.trim="loginForm.smsCode"
|
2025-03-23 09:18:42 +08:00
|
|
|
clearable
|
|
|
|
placeholder="请输入短信验证码"
|
|
|
|
@keyup.enter.native="handleLogin"
|
2025-04-08 09:12:42 +08:00
|
|
|
/>
|
2025-03-23 09:18:42 +08:00
|
|
|
</el-form-item>
|
|
|
|
<div class="img">
|
|
|
|
<div class="hqyzm1" :class="isSend ? 'hui' : ''" @click="submitForm">{{ getCode }}</div>
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
<el-button
|
|
|
|
:loading="loading"
|
|
|
|
type="primary"
|
|
|
|
class="toLogin"
|
|
|
|
@click.native.prevent="handleLogin"
|
2025-04-08 09:12:42 +08:00
|
|
|
>登录</el-button>
|
2025-03-23 09:18:42 +08:00
|
|
|
|
|
|
|
<!-- <div class="tips">
|
|
|
|
<span style="margin-right:20px;">username: admin</span>
|
|
|
|
<span> password: any</span>
|
|
|
|
</div> -->
|
|
|
|
</el-form>
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
</template>
|
|
|
|
|
|
|
|
<script>
|
2025-04-08 09:12:42 +08:00
|
|
|
import { validUsername } from '@/utils/validate'
|
|
|
|
import { getCodeImg, userCheck, userSend } from '@/api/user'
|
2025-03-23 09:18:42 +08:00
|
|
|
export default {
|
2025-04-08 09:12:42 +08:00
|
|
|
name: 'Login',
|
2025-03-23 09:18:42 +08:00
|
|
|
data() {
|
|
|
|
const validateUsername = (rule, value, callback) => {
|
|
|
|
if (!validUsername(value)) {
|
2025-04-08 09:12:42 +08:00
|
|
|
callback(new Error('Please enter the correct user name'))
|
2025-03-23 09:18:42 +08:00
|
|
|
} else {
|
2025-04-08 09:12:42 +08:00
|
|
|
callback()
|
2025-03-23 09:18:42 +08:00
|
|
|
}
|
2025-04-08 09:12:42 +08:00
|
|
|
}
|
2025-03-23 09:18:42 +08:00
|
|
|
const validatePassword = (rule, value, callback) => {
|
|
|
|
if (value.length < 6) {
|
2025-04-08 09:12:42 +08:00
|
|
|
callback(new Error('The password can not be less than 6 digits'))
|
2025-03-23 09:18:42 +08:00
|
|
|
} else {
|
2025-04-08 09:12:42 +08:00
|
|
|
callback()
|
2025-03-23 09:18:42 +08:00
|
|
|
}
|
2025-04-08 09:12:42 +08:00
|
|
|
}
|
2025-03-23 09:18:42 +08:00
|
|
|
return {
|
|
|
|
loginForm: {
|
|
|
|
// username: 'admin',
|
|
|
|
// password: 'admin123',
|
2025-04-08 09:12:42 +08:00
|
|
|
username: '',
|
|
|
|
password: ''
|
2025-03-23 09:18:42 +08:00
|
|
|
},
|
|
|
|
loginRules: {
|
|
|
|
username: [
|
2025-04-08 09:12:42 +08:00
|
|
|
{ required: true, trigger: 'blur', message: '请输入用户名' }
|
2025-03-23 09:18:42 +08:00
|
|
|
],
|
|
|
|
password: [
|
2025-04-08 09:12:42 +08:00
|
|
|
{ required: true, trigger: 'blur', message: '请输入密码' }
|
2025-03-23 09:18:42 +08:00
|
|
|
],
|
|
|
|
code: [
|
2025-04-08 09:12:42 +08:00
|
|
|
{ required: true, trigger: 'blur', message: '请输入验证码' }
|
2025-03-23 09:18:42 +08:00
|
|
|
],
|
|
|
|
smsCode: [
|
2025-04-08 09:12:42 +08:00
|
|
|
{ required: true, trigger: 'blur', message: '请输入短信验证码' }
|
|
|
|
]
|
2025-03-23 09:18:42 +08:00
|
|
|
},
|
|
|
|
loading: false,
|
2025-04-08 09:12:42 +08:00
|
|
|
passwordType: 'password',
|
2025-03-23 09:18:42 +08:00
|
|
|
redirect: undefined,
|
2025-04-08 09:12:42 +08:00
|
|
|
codeUrl: '',
|
|
|
|
ismsgCode: false,
|
2025-03-23 09:18:42 +08:00
|
|
|
isSend: false,
|
|
|
|
beginTime: 60,
|
2025-04-01 23:46:26 +08:00
|
|
|
getCode: '获取验证码',
|
2025-10-22 14:07:54 +08:00
|
|
|
timer: '',
|
|
|
|
systemTypes: process.env.VUE_APP_SYSTEM_TYPE
|
2025-04-08 09:12:42 +08:00
|
|
|
}
|
2025-03-23 09:18:42 +08:00
|
|
|
},
|
|
|
|
watch: {
|
|
|
|
$route: {
|
2025-04-08 09:12:42 +08:00
|
|
|
handler: function(route) {
|
|
|
|
this.redirect = route.query && route.query.redirect
|
2025-03-23 09:18:42 +08:00
|
|
|
},
|
2025-04-08 09:12:42 +08:00
|
|
|
immediate: true
|
|
|
|
}
|
2025-03-23 09:18:42 +08:00
|
|
|
},
|
|
|
|
created() {
|
|
|
|
// 获取验证码
|
2025-04-08 09:12:42 +08:00
|
|
|
this.getVerifyCode()
|
2025-03-23 09:18:42 +08:00
|
|
|
},
|
|
|
|
methods: {
|
|
|
|
startTime() {
|
|
|
|
if (this.isSend) return
|
|
|
|
this.isSend = true
|
|
|
|
this.getCode = this.beginTime + 's后重新发送'
|
2025-04-08 09:12:42 +08:00
|
|
|
const that = this
|
2025-03-23 09:18:42 +08:00
|
|
|
this.timer = setInterval(() => {
|
|
|
|
this.beginTime--
|
|
|
|
this.getCode = this.beginTime + 's后重新发送'
|
|
|
|
if (this.beginTime < 0) {
|
|
|
|
clearInterval(this.timer)
|
2025-04-01 23:46:26 +08:00
|
|
|
this.getCode = '获取验证码'
|
2025-03-23 09:18:42 +08:00
|
|
|
this.beginTime = 60
|
|
|
|
this.isSend = false
|
|
|
|
}
|
|
|
|
}, 1000)
|
|
|
|
},
|
2025-04-08 09:12:42 +08:00
|
|
|
submitForm() {
|
|
|
|
if (!this.isSend) {
|
|
|
|
userSend({
|
|
|
|
userName: this.loginForm.username
|
|
|
|
}).then(res => {
|
|
|
|
this.startTime()
|
|
|
|
if (res.code === 200) {
|
|
|
|
this.$message({
|
|
|
|
message: res.msg,
|
|
|
|
type: 'success'
|
|
|
|
})
|
|
|
|
}
|
|
|
|
})
|
2025-03-23 09:18:42 +08:00
|
|
|
}
|
|
|
|
},
|
|
|
|
getCheck() {
|
2025-04-08 09:12:42 +08:00
|
|
|
return
|
|
|
|
// 短信验证码暂时注释
|
|
|
|
// userCheck({
|
|
|
|
// userName: this.loginForm.username
|
|
|
|
// }).then(res => {
|
|
|
|
// if (res.data === 0) {
|
|
|
|
// this.ismsgCode = true
|
|
|
|
// } else {
|
|
|
|
// this.ismsgCode = false
|
|
|
|
// }
|
|
|
|
// })
|
2025-03-23 09:18:42 +08:00
|
|
|
},
|
|
|
|
getVerifyCode() {
|
|
|
|
getCodeImg().then((res) => {
|
2025-04-08 09:12:42 +08:00
|
|
|
this.codeUrl = 'data:image/gif;base64,' + res.img
|
|
|
|
this.loginForm.uuid = res.uuid
|
|
|
|
})
|
2025-03-23 09:18:42 +08:00
|
|
|
},
|
|
|
|
showPwd() {
|
2025-04-08 09:12:42 +08:00
|
|
|
if (this.passwordType === 'password') {
|
|
|
|
this.passwordType = ''
|
2025-03-23 09:18:42 +08:00
|
|
|
} else {
|
2025-04-08 09:12:42 +08:00
|
|
|
this.passwordType = 'password'
|
2025-03-23 09:18:42 +08:00
|
|
|
}
|
|
|
|
this.$nextTick(() => {
|
2025-04-08 09:12:42 +08:00
|
|
|
this.$refs.password.focus()
|
|
|
|
})
|
2025-03-23 09:18:42 +08:00
|
|
|
},
|
|
|
|
handleLogin() {
|
|
|
|
this.$refs.loginForm.validate((valid) => {
|
|
|
|
if (valid) {
|
2025-04-08 09:12:42 +08:00
|
|
|
this.loading = true
|
2025-03-23 09:18:42 +08:00
|
|
|
this.$store
|
2025-04-08 09:12:42 +08:00
|
|
|
.dispatch('user/login', this.loginForm)
|
2025-03-23 09:18:42 +08:00
|
|
|
.then(() => {
|
2025-04-08 09:12:42 +08:00
|
|
|
this.$router.push({ path: this.redirect || '/' })
|
|
|
|
this.loading = false
|
2025-03-23 09:18:42 +08:00
|
|
|
})
|
|
|
|
.catch(() => {
|
2025-04-08 09:12:42 +08:00
|
|
|
this.getVerifyCode()
|
|
|
|
this.loginForm.code = ''
|
|
|
|
this.loading = false
|
|
|
|
})
|
2025-03-23 09:18:42 +08:00
|
|
|
} else {
|
2025-04-08 09:12:42 +08:00
|
|
|
console.log('error submit!!')
|
|
|
|
return false
|
2025-03-23 09:18:42 +08:00
|
|
|
}
|
2025-04-08 09:12:42 +08:00
|
|
|
})
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2025-03-23 09:18:42 +08:00
|
|
|
</script>
|
|
|
|
|
|
|
|
<style lang="scss">
|
|
|
|
/* 修复input 背景不协调 和光标变色 */
|
|
|
|
/* Detail see https://github.com/PanJiaChen/vue-element-admin/pull/927 */
|
|
|
|
|
|
|
|
$bg: #283443;
|
|
|
|
$light_gray: #fff;
|
|
|
|
$cursor: #fff;
|
|
|
|
|
|
|
|
@supports (-webkit-mask: none) and (not (cater-color: $cursor)) {
|
|
|
|
.login-container .el-input input {
|
|
|
|
color: $cursor;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* reset element-ui css */
|
|
|
|
.login-container {
|
|
|
|
.el-input {
|
|
|
|
display: inline-block;
|
|
|
|
height: 47px;
|
|
|
|
width: 85%;
|
|
|
|
|
|
|
|
input {
|
|
|
|
background: transparent;
|
|
|
|
border: 0px;
|
|
|
|
-webkit-appearance: none;
|
|
|
|
border-radius: 0px;
|
|
|
|
padding: 12px 5px 12px 15px;
|
|
|
|
color: $light_gray;
|
|
|
|
height: 47px;
|
|
|
|
caret-color: $cursor;
|
|
|
|
|
|
|
|
&:-webkit-autofill {
|
|
|
|
box-shadow: 0 0 0px 1000px $bg inset !important;
|
|
|
|
-webkit-text-fill-color: $cursor !important;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
.el-form-item {
|
|
|
|
border: 1px solid rgba(255, 255, 255, 0.1);
|
|
|
|
background: rgba(0, 0, 0, 0.1);
|
|
|
|
border-radius: 5px;
|
|
|
|
color: #454545;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
</style>
|
|
|
|
|
|
|
|
<style lang="scss" scoped>
|
|
|
|
$bg: #10224c;
|
|
|
|
$dark_gray: #889aa4;
|
|
|
|
$light_gray: #eee;
|
|
|
|
|
|
|
|
.login-container {
|
|
|
|
height: 100vh;
|
|
|
|
// width: 100%;
|
|
|
|
background-color: $bg;
|
|
|
|
overflow: hidden;
|
|
|
|
background: url("~@/assets/images/loginBgd1.gif") no-repeat 0 0;
|
|
|
|
background-size: 100% 100%;
|
|
|
|
.login-form {
|
|
|
|
position: relative;
|
|
|
|
width: 426px;
|
|
|
|
max-width: 100%;
|
|
|
|
// padding: 160px 35px 0;
|
|
|
|
margin: 0px auto;
|
|
|
|
margin-top: 25px;
|
|
|
|
overflow: hidden;
|
|
|
|
}
|
|
|
|
|
|
|
|
.tips {
|
|
|
|
font-size: 14px;
|
|
|
|
color: #fff;
|
|
|
|
margin-bottom: 10px;
|
|
|
|
|
|
|
|
span {
|
|
|
|
&:first-of-type {
|
|
|
|
margin-right: 16px;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
.svg-container {
|
|
|
|
padding: 6px 5px 6px 15px;
|
|
|
|
color: $dark_gray;
|
|
|
|
vertical-align: middle;
|
|
|
|
width: 30px;
|
|
|
|
display: inline-block;
|
|
|
|
}
|
|
|
|
|
|
|
|
.title-container {
|
|
|
|
position: relative;
|
|
|
|
|
|
|
|
.title {
|
|
|
|
font-size: 26px;
|
|
|
|
color: $light_gray;
|
|
|
|
margin: 0px auto 40px auto;
|
|
|
|
text-align: center;
|
|
|
|
font-weight: bold;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
.show-pwd {
|
|
|
|
position: absolute;
|
|
|
|
right: 10px;
|
|
|
|
top: 7px;
|
|
|
|
font-size: 16px;
|
|
|
|
color: $dark_gray;
|
|
|
|
cursor: pointer;
|
|
|
|
user-select: none;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
.yzm {
|
|
|
|
display: flex;
|
|
|
|
align-items: center;
|
|
|
|
justify-content: space-between;
|
|
|
|
}
|
|
|
|
.img {
|
|
|
|
margin-bottom: 18px;
|
|
|
|
margin-left: 20px;
|
|
|
|
img {
|
|
|
|
width: 100px;
|
|
|
|
height: 50px;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
.top_item {
|
|
|
|
text-align: center;
|
|
|
|
height: 100px;
|
|
|
|
position: relative;
|
|
|
|
}
|
|
|
|
.title_no {
|
|
|
|
font-size: 26px;
|
|
|
|
margin-top: 10px;
|
|
|
|
margin-bottom: -30px;
|
|
|
|
background: -webkit-linear-gradient(
|
|
|
|
left,
|
|
|
|
#4278a3,
|
|
|
|
#fff 25%,
|
|
|
|
#4278a3 50%,
|
|
|
|
#fff 75%,
|
|
|
|
#4278a3
|
|
|
|
);
|
|
|
|
color: transparent;
|
|
|
|
-webkit-background-clip: text;
|
|
|
|
background-size: 200% 100%;
|
|
|
|
animation: masked-animation 1.5s infinite linear;
|
|
|
|
}
|
|
|
|
@-webkit-keyframes masked-animation {
|
|
|
|
0% {
|
|
|
|
background-position: 0 0;
|
|
|
|
}
|
|
|
|
100% {
|
|
|
|
background-position: -100% 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
.qiu {
|
|
|
|
position: absolute;
|
|
|
|
top: 18%;
|
|
|
|
img {
|
|
|
|
width: 600px;
|
|
|
|
height: 600px;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
.contain {
|
|
|
|
height: 450px;
|
|
|
|
width: 600px;
|
|
|
|
box-sizing: border-box;
|
|
|
|
display: flex;
|
|
|
|
flex-direction: column;
|
|
|
|
position: absolute;
|
|
|
|
right: 5%;
|
|
|
|
top: 30%;
|
|
|
|
// background: url("~@/assets/images/loginBox.gif") no-repeat 0 0;
|
|
|
|
// background-size: 100% 100%;
|
|
|
|
// opacity: 0.55;
|
|
|
|
border-radius: 50px;
|
|
|
|
}
|
|
|
|
.login_contain {
|
|
|
|
height: 450px;
|
|
|
|
width: 600px;
|
|
|
|
// height: 640px;
|
|
|
|
// width: 854px;
|
|
|
|
position: absolute;
|
|
|
|
right: 5%;
|
|
|
|
top: 30%;
|
|
|
|
}
|
|
|
|
.toLogin {
|
|
|
|
background: #0f2e66;
|
|
|
|
border: 1px solid #5febfb;
|
|
|
|
box-shadow: 0px 6px 243px 8px rgba(82, 126, 201, 0.17);
|
|
|
|
border-radius: 5px;
|
|
|
|
color: #fff;
|
|
|
|
width: 100%;
|
|
|
|
border-color: #183467;
|
|
|
|
padding: 15px;
|
|
|
|
}
|
|
|
|
::v-deep .el-form-item__content {
|
|
|
|
background: #183467;
|
|
|
|
}
|
|
|
|
.tit1 {
|
|
|
|
display: flex;
|
|
|
|
align-items: center;
|
|
|
|
color: #fff;
|
|
|
|
font-size: 24px;
|
|
|
|
font-weight: 500;
|
|
|
|
margin-bottom: 10px;
|
|
|
|
div {
|
|
|
|
margin-right: 20px;
|
|
|
|
padding-bottom: 10px;
|
|
|
|
}
|
|
|
|
.act {
|
|
|
|
border-bottom: 2px solid #fff;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
::v-deep .el-form-item {
|
|
|
|
margin-bottom: 20px !important;
|
|
|
|
}
|
|
|
|
::v-deep .el-input__suffix {
|
|
|
|
line-height: 52px;
|
|
|
|
}
|
|
|
|
.hqyzm1 {
|
|
|
|
width: 100px;
|
|
|
|
height: 50px;
|
|
|
|
background: #0f2e66;
|
|
|
|
border: 1px solid #5febfb;
|
|
|
|
box-shadow: 0px 6px 243px 8px rgba(82, 126, 201, 0.17);
|
|
|
|
border-radius: 5px;
|
|
|
|
color: #fff;
|
|
|
|
border-color: #183467;
|
|
|
|
padding: 15px 0px;
|
|
|
|
color: #fff;
|
|
|
|
font-size: 10px;
|
|
|
|
text-align: center;
|
|
|
|
cursor: pointer;
|
|
|
|
}
|
|
|
|
.hui {
|
|
|
|
opacity: 0.5;
|
|
|
|
}
|
|
|
|
|
|
|
|
</style>
|