LoginForm.vue 4.88 KB
<template lang="pug">
  div(class="login-main login-form-bg")
    div(class="title")
    .main-content
      el-form(:model="loginForm" ref="form" :rules="rules" @keydown.enter.native="login")
        el-form-item(prop="username")
          el-input(
            ref="username"
            size="medium"
            class="login-input"
            placeholder="请输入工号"
            v-model.trim="loginForm.username"
            :maxlength="inputMaxLength"
          )
            i(slot="prefix" class="icon username-icon")
        el-form-item(prop="password")
          el-input(
            ref="password"
            type="password"
            size="medium"
            placeholder="请输入密码"
            class="login-input"
            :maxlength="inputMaxLength"
            v-model.trim="loginForm.password"
          )
            i(slot="prefix" class="icon password-icon")
        el-form-item(prop="verificationCode")
          .captcha
            el-input(
              size="medium"
              placeholder="请输入验证码"
              class="captcha-input"
              v-model.trim="loginForm.verificationCode"
            )
              i(slot="prefix" class="icon validate-icon")
            <canvas width="93" height="36" id="captcha1"></canvas>
        el-form-item
          .buton-warp
            el-button(class="login-btn" type="primary" @click="login" :loading="loading")
              span(class="login-btn-text") 登&nbsp;&nbsp;&nbsp;&nbsp;录
</template>

<script>
import Captcha from 'captcha-mini'
import { maxSizeValidate } from '@/views/validate'
import { inputMaxLength } from '@/utils/mappingData'

export default {
  name: 'LoginForm',
  props: {
    usernameRules: {
      type: Array,
      default: () => {
        return [
          { required: true, message: '账号不能为空', trigger: 'blur' },
          maxSizeValidate
        ]
      }
    },
    passwordRules: {
      type: Array,
      default: () => {
        return [
          { required: true, message: '密码不能为空', trigger: 'blur' },
          maxSizeValidate
        ]
      }
    },
    loading: {
      type: Boolean,
      default: false
    }
  },
  data() {
    return {
      inputMaxLength,
      verCode: '',
      captcha1: null,
      loginForm: {
        username: '',
        password: '',
        verificationCode: ''
      }
    }
  },
  computed: {
    rules() {
      return {
        username: this.usernameRules,
        password: this.passwordRules,
        verificationCode: [
          {
            validator: (rule, value, callback) => {
              if (value === '') {
                return callback(new Error('验证码不能为空'))
              }
              if (value.toLowerCase() !== this.verCode.toLowerCase()) {
                return callback(new Error('请输入正确的验证码'))
              } else {
                callback()
              }
            },
            trigger: 'blur'
          },
          maxSizeValidate
        ]
      }
    }
  },
  mounted() {
    if (this.loginForm.username === '') {
      this.$refs.username.focus()
    }
    this.captcha1 = new Captcha()
    this.updateCaptcha()
  },
  methods: {
    login() {
      this.$refs.form.validate(valid => {
        if (valid) {
          this.$emit('on-success-valid', {
            username: this.loginForm.username,
            password: this.loginForm.password
          })
        } else {
          this.updateCaptcha()
        }
      })
    },
    updateCaptcha() {
      this.captcha1.draw(document.querySelector('#captcha1'), r => {
        this.verCode = r
      })
    }
  }
}
</script>

<style lang="scss">
.login-main {
  height: 420px;
  width: 420px;
  display: flex;
  flex-flow: column nowrap;
  align-items: center;
  padding: 0 48px;
  box-sizing: border-box;
  .title {
    width: 292px;
    height: 36px;
    margin: 32px 0 36px 0;
  }
  .main-content {
    .captcha {
      display: flex;
    }
    .login-btn {
      width: 100%;
      height: 48px;
      .login-btn-text {
        font-size: 18px;
      }
    }
  }
}
// 重置输入框 图标
.login-input {
  .el-input__prefix {
    display: inline-flex;
    align-items: center;
  }
  .el-input__inner {
    height: 44px;
    width: 324px;
  }
}
.captcha-input {
  margin-right: 7px;
  .el-input__prefix {
    display: inline-flex;
    align-items: center;
  }
  .el-input__inner {
    height: 44px;
  }
}
.login-input,
.captcha-input {
  .el-input__inner {
    background: #0f1f3b;
    padding-left: 46px;
    color: rgba(255, 255, 255, 1);
    background: rgba(193, 225, 253, 0.03);
    border-radius: 4px;
    border: 1px solid rgba(24, 144, 255, 0.2);
  }
  .el-input__inner:active,
  .el-input__inner:focus {
    background: rgba(193, 225, 253, 0.03);
    border-radius: 4px;
    border: 1px solid rgba(94, 178, 255, 0.8);
  }
  .el-input__prefix {
    left: 14px;
  }
}
.icon {
  width: 20px;
  height: 20px;
  display: inline-block;
}
</style>