Browse Source

feat: 更换迷你版企业登录界面

master
wangxiang 2 years ago
parent
commit
ea9bee9bbc
  1. BIN
      src/assets/images/login-ad-mini.jpg
  2. BIN
      src/assets/images/logo-tag.png
  3. BIN
      src/assets/loginmini/icon/icon-code.png
  4. BIN
      src/assets/loginmini/icon/icon-eye-g.png
  5. BIN
      src/assets/loginmini/icon/icon-eye-k.png
  6. BIN
      src/assets/loginmini/icon/icon-line-msg.png
  7. BIN
      src/assets/loginmini/icon/icon-line-pad.png
  8. BIN
      src/assets/loginmini/icon/icon-line-tel.png
  9. BIN
      src/assets/loginmini/icon/icon-line-user.png
  10. BIN
      src/assets/loginmini/icon/icon-password.png
  11. BIN
      src/assets/loginmini/icon/icon-success.png
  12. BIN
      src/assets/loginmini/icon/icon-user.png
  13. BIN
      src/assets/loginmini/icon/icon_dow.png
  14. BIN
      src/assets/loginmini/icon/jeecg_ad.png
  15. BIN
      src/assets/loginmini/icon/jeecg_bg.png
  16. BIN
      src/assets/loginmini/icon/jeecg_logo.png
  17. BIN
      src/assets/loginmini/icon/login-ad-text.png
  18. BIN
      src/assets/loginmini/icon/login-ad.png
  19. BIN
      src/assets/loginmini/icon/logo.png
  20. 365
      src/assets/loginmini/style/base.less
  21. 608
      src/assets/loginmini/style/home.less
  22. 4
      src/router/routes/index.ts
  23. 167
      src/views/core/loginmini/MiniCodelogin.vue
  24. 282
      src/views/core/loginmini/MiniForgotpad.vue
  25. 594
      src/views/core/loginmini/MiniLogin.vue
  26. 311
      src/views/core/loginmini/MiniRegister.vue
  27. 86
      src/views/core/loginmini/OAuth2Login.vue

BIN
src/assets/images/login-ad-mini.jpg

Binary file not shown.

Before

Width:  |  Height:  |  Size: 525 KiB

BIN
src/assets/images/logo-tag.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 61 KiB

BIN
src/assets/loginmini/icon/icon-code.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.0 KiB

BIN
src/assets/loginmini/icon/icon-eye-g.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.6 KiB

BIN
src/assets/loginmini/icon/icon-eye-k.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.5 KiB

BIN
src/assets/loginmini/icon/icon-line-msg.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.1 KiB

BIN
src/assets/loginmini/icon/icon-line-pad.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.0 KiB

BIN
src/assets/loginmini/icon/icon-line-tel.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.4 KiB

BIN
src/assets/loginmini/icon/icon-line-user.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.1 KiB

BIN
src/assets/loginmini/icon/icon-password.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

BIN
src/assets/loginmini/icon/icon-success.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

BIN
src/assets/loginmini/icon/icon-user.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.6 KiB

BIN
src/assets/loginmini/icon/icon_dow.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 536 B

BIN
src/assets/loginmini/icon/jeecg_ad.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 84 KiB

BIN
src/assets/loginmini/icon/jeecg_bg.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 23 KiB

BIN
src/assets/loginmini/icon/jeecg_logo.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 12 KiB

BIN
src/assets/loginmini/icon/login-ad-text.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 53 KiB

BIN
src/assets/loginmini/icon/login-ad.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.9 MiB

BIN
src/assets/loginmini/icon/logo.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.9 KiB

365
src/assets/loginmini/style/base.less

@ -0,0 +1,365 @@ @@ -0,0 +1,365 @@
::-webkit-input-placeholder {
/* WebKit browsers */
color: #868686;
font-size: 15px;
}
::-moz-placeholder {
/* Mozilla Firefox 19+ */
color: #868686;
font-size: 15px;
}
:-ms-input-placeholder {
/* Internet Explorer 10+ */
color: #868686;
font-size: 15px;
}
input:-webkit-autofill {
transition: background-color 5000s ease-in-out 0s;
}
html {
scroll-behavior: smooth;
}
html,
body {
color: #333;
margin: 0;
height: 100%;
font-family: 'Myriad Set Pro', 'Helvetica Neue', Helvetica, Arial, Verdana, sans-serif;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
font-weight: normal;
}
* {
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
}
a {
text-decoration: none;
color: #000;
}
a,
label,
button,
input,
select {
-webkit-tap-highlight-color: rgba(0, 0, 0, 0);
}
img {
max-width: 100%;
height: auto;
display: block;
border: 0;
}
body {
background: #e3f0ff;
color: #666;
}
html,
body,
div,
dl,
dt,
dd,
ol,
ul,
li,
h1,
h2,
h3,
h4,
h5,
h6,
p,
blockquote,
pre,
button,
fieldset,
form,
input,
legend,
textarea,
th,
td {
margin: 0;
padding: 0;
}
a {
text-decoration: none;
color: #08acee;
}
button {
outline: 0;
}
button,
input,
optgroup,
select,
textarea {
margin: 0;
font: inherit;
color: inherit;
outline: none;
}
li {
list-style: none;
}
a {
color: #666;
}
.clearfix::after {
clear: both;
content: '.';
display: block;
height: 0;
visibility: hidden;
}
.clearfix {
}
.divHeight {
width: 100%;
height: 10px;
background: #f5f5f5;
position: relative;
overflow: hidden;
}
.r-line {
position: relative;
}
.r-line:after {
content: '';
position: absolute;
z-index: 0;
top: 0;
right: 0;
height: 100%;
border-right: 1px solid #d9d9d9;
-webkit-transform: scaleX(0.5);
transform: scaleX(0.5);
-webkit-transform-origin: 100% 0;
transform-origin: 100% 0;
}
.b-line {
position: relative;
}
.b-line:after {
content: '';
position: absolute;
z-index: 2;
bottom: 0;
left: 0;
width: 100%;
height: 1px;
border-bottom: 1px solid #dedede;
-webkit-transform: scaleY(0.5);
transform: scaleY(0.5);
-webkit-transform-origin: 0 100%;
transform-origin: 0 100%;
}
.aui-arrow {
position: relative;
padding-right: 0.8rem;
}
.aui-arrow span {
font-size: 0.8rem;
color: #9b9b9b;
}
.aui-arrow:after {
content: ' ';
display: inline-block;
height: 6px;
width: 6px;
border-width: 2px 2px 0 0;
border-color: #848484;
border-style: solid;
-webkit-transform: matrix(0.71, 0.71, -0.71, 0.71, 0, 0);
transform: matrix(0.71, 0.71, -0.71, 0.71, 0, 0);
position: relative;
position: absolute;
top: 50%;
margin-top: -4px;
right: 2px;
border-radius: 1px;
}
.aui-flex {
display: -webkit-box;
display: -webkit-flex;
display: flex;
-webkit-box-align: center;
-webkit-align-items: center;
align-items: center;
position: relative;
}
.aui-flex-box {
-webkit-box-flex: 1;
-webkit-flex: 1;
flex: 1;
min-width: 0;
font-size: 14px;
color: #333;
}
/* 必要布局样式css */
.aui-flexView {
width: 100%;
height: 100%;
margin: 0 auto;
display: -webkit-box;
display: -webkit-flex;
display: -ms-flexbox;
display: flex;
-webkit-box-orient: vertical;
-webkit-box-direction: normal;
-webkit-flex-direction: column;
-ms-flex-direction: column;
flex-direction: column;
}
.aui-scrollView {
width: 100%;
height: 100%;
-webkit-box-flex: 1;
-webkit-flex: 1;
-ms-flex: 1;
flex: 1;
overflow-y: auto;
overflow-x: hidden;
-webkit-overflow-scrolling: touch;
position: relative;
padding-bottom: 53px;
}
.aui-navBar {
height: 44px;
position: relative;
display: -webkit-box;
display: -webkit-flex;
display: -ms-flexbox;
display: flex;
z-index: 102;
background-color: #5064eb;
}
.aui-navBar-item {
height: 44px;
min-width: 15%;
-webkit-box-flex: 0;
-webkit-flex: 0 0 15%;
-ms-flex: 0 0 15%;
flex: 0 0 15%;
padding: 0 0.9rem;
display: -webkit-box;
display: -webkit-flex;
display: -ms-flexbox;
display: flex;
-webkit-box-align: center;
-webkit-align-items: center;
-ms-flex-align: center;
align-items: center;
font-size: 0.7rem;
white-space: nowrap;
overflow: hidden;
color: #808080;
position: relative;
}
.aui-navBar-item:first-child {
-webkit-box-ordinal-group: 2;
-webkit-order: 1;
-ms-flex-order: 1;
order: 1;
margin-right: -25%;
font-size: 0.9rem;
font-weight: bold;
}
.aui-navBar-item:last-child {
-webkit-box-ordinal-group: 4;
-webkit-order: 3;
-ms-flex-order: 3;
order: 3;
-webkit-box-pack: end;
-webkit-justify-content: flex-end;
-ms-flex-pack: end;
justify-content: flex-end;
}
.aui-center {
-webkit-box-ordinal-group: 3;
-webkit-order: 2;
-ms-flex-order: 2;
order: 2;
display: -webkit-box;
display: -webkit-flex;
display: -ms-flexbox;
display: flex;
-webkit-box-pack: center;
-webkit-justify-content: center;
-ms-flex-pack: center;
justify-content: center;
-webkit-box-align: center;
-webkit-align-items: center;
-ms-flex-align: center;
align-items: center;
height: 44px;
width: 80%;
margin-left: 22%;
}
.aui-center-title {
text-align: center;
width: 100%;
white-space: nowrap;
overflow: hidden;
display: block;
text-overflow: ellipsis;
font-size: 0.95rem;
color: #fff;
font-weight: 500;
}
.icon {
width: 20px;
height: 20px;
display: block;
border: none;
float: left;
background-size: 20px;
background-repeat: no-repeat;
position: relative;
}
.login-background-img {
background-image: url(../icon/jeecg_bg.png);
background-size: cover;
background-position: top center;
background-repeat: no-repeat;
}

608
src/assets/loginmini/style/home.less

@ -0,0 +1,608 @@ @@ -0,0 +1,608 @@
.aui-content {
padding: 40px 60px;
min-height: 97vh;
}
.aui-container {
max-width: 1000px;
margin: 0 auto;
box-shadow: 0 4px 8px 1px rgba(0, 0, 0, 0.2);
position: fixed;
top: 50%;
left: 50%;
width: 92%;
height: auto;
-webkit-transform: translateX(-50%) translateY(-50%);
-moz-transform: translateX(-50%) translateY(-50%);
-ms-transform: translateX(-50%) translateY(-50%);
transform: translateX(-50%) translateY(-50%);
-webkit-transform: translateX(-50%) translateY(-50%);
}
.aui-form {
width: 100%;
background: #eee;
display: -webkit-box;
display: -moz-box;
display: -ms-flexbox;
display: -webkit-flex;
display: flex;
}
.aui-image {
flex-basis: 60%;
-webkit-flex-basis: 60%;
background-image: url(../icon/login-ad.png);
background-size: cover;
}
.aui-image-text{
width: 100%;
}
.aui-formBox {
flex-basis: 40%;
-webkit-flex-basis: 40%;
box-sizing: border-box;
padding: 30px 20px;
background: #fff;
box-shadow: 2px 9px 49px -17px rgba(0, 0, 0, 0.1);
}
.aui-logo {
width: 180px;
height: 80px;
position: absolute;
top: 2%;
left: 8%;
z-index: 4;
}
.aui-account-line {
padding-top: 20px;
padding-bottom: 40px;
}
.aui-code-line {
position: absolute;
right: 0;
top: 0;
border-left: 3px solid #fff;
height: 42px;
padding: 0 15px;
line-height: 40px;
font-size: 14px;
cursor: pointer;
}
.aui-eye {
position: absolute;
right: 20px;
top: 10px;
width: 20px;
cursor: pointer;
}
.aui-input-line {
background: #f5f5f9;
border-radius: 2px;
position: relative;
margin: 12px 0;
}
.aui-input-line input {
width: 100%;
padding: 12px 10px;
border: none;
color: #333333;
font-size: 14px;
background: unset;
padding-left: 40px;
}
.aui-input-line .icon {
position: absolute;
top: 10px;
left: 10px;
}
.icon-line-user {
background-image: url(../icon/icon-line-user.png);
}
.icon-line-tel {
background-image: url(../icon/icon-line-tel.png);
}
.icon-line-msg {
background-image: url(../icon/icon-line-msg.png);
}
.icon-line-pad {
background-image: url(../icon/icon-line-pad.png);
}
.aui-forgot .aui-input-line input {
padding-left: 20px;
}
.aui-forgot .aui-input-line {
background: none;
border: 1px solid #dbdbdb;
border-radius: 2px;
}
.aui-forgot .aui-input-line:focus {
border-color: #1b90ff;
}
.aui-forgot .aui-input-line:hover {
border-color: #1b90ff;
}
.aui-forgot .aui-input-line .aui-code-line {
border-left: 1px solid #dbdbdb;
height: 40px;
color: #1b90ff;
}
.aui-step-box {
width: 100%;
height: auto;
position: relative;
overflow: hidden;
margin-top: 50px;
margin-bottom: 20px;
}
.aui-step-box::after {
position: absolute;
top: 20px;
left: 50%;
width: 76%;
margin-left: -38%;
height: 1px;
background: #bcbcbc;
content: '';
}
.aui-step-item {
width: 33.333%;
float: left;
text-align: center;
position: relative;
z-index: 2;
}
.aui-step-tags em {
width: 40px;
height: 40px;
border: 8px solid #fff;
line-height: 1.3;
border-radius: 100px;
background: #bcbcbc;
display: block;
margin: 0 auto;
font-style: normal;
color: #fff;
font-size: 19px;
font-weight: 500;
}
.aui-step-tags p {
font-size: 14px;
color: #bcbcbc;
}
.activeStep .aui-step-tags em {
background: #1b90ff;
}
.activeStep .aui-step-tags p {
color: #1b90ff;
}
.aui-success {
position: absolute;
top: 50%;
left: 50%;
height: 80px;
width: 100%;
margin-top: -40px;
margin-left: -50%;
}
.aui-success-icon {
width: 40px;
margin: 0 auto;
}
.aui-success h3 {
width: 100%;
text-align: center;
color: #515151;
font-size: 18px;
padding-top: 20px;
}
.aui-form-nav {
text-align: center;
padding-bottom: 20px;
}
.aui-form-nav .aui-flex-box {
color: #040404;
font-size: 18px;
font-weight: 500;
cursor: pointer;
}
.aui-clear-left {
text-align: left;
}
.aui-clear-left .activeNav::after {
left: 18px;
}
.activeNav {
position: relative;
}
.activeNav::after {
content: '';
position: absolute;
z-index: 0;
bottom: -10px;
left: 50%;
margin-left: -15px;
width: 30px;
height: 4px;
background: #1b90ff;
border-radius: 100px;
}
.phone .aui-inputClear {
padding-left: 0;
}
.phone .aui-inputClear input {
//padding-left: 1px;
}
.phone .aui-inputClear .aui-code {
text-align: right;
width: auto;
bottom: 10px;
}
.phone .aui-inputClear .aui-code a {
color: #1b90ff;
font-size: 14px;
}
.phoneChina {
position: absolute;
bottom: 10px;
left: 0;
font-size: 14px;
color: #040404;
}
.phoneChina::after {
position: absolute;
right: -25px;
bottom: 0;
content: '';
background-image: url(../icon/icon_dow.png);
background-size: 18px;
width: 18px;
height: 18px;
}
.phoneChina:before {
position: absolute;
right: -42px;
bottom: -15px;
content: ' ';
background: #fff;
width: 18px;
height: 18px;
}
.aui-ewm {
width: 280px;
margin: 0 auto;
}
.aui-formEwm {
padding: 50px 40px 55px 40px;
}
.aui-inputClear {
width: 100%;
border-bottom: 1px solid #cccccc;
position: relative;
padding-left: 20px;
background: #fff;
margin-bottom: 8px;
margin-top: 20px;
}
.aui-inputClear .icon {
position: absolute;
top: 10px;
left: 0;
}
.aui-inputClear input {
width: 100%;
padding: 10px;
border: none;
color: #333333;
font-size: 14px;
background: none;
}
.aui-code {
position: absolute;
right: 8px;
bottom: 0;
width: 115px;
cursor: pointer;
}
.icon-code {
background-image: url(../icon/icon-user.png);
}
.icon-password {
background-image: url(../icon/icon-password.png);
}
.icon-code {
background-image: url(../icon/icon-code.png);
}
.aui-inputClear:focus {
border-bottom: 1px solid #1b90ff;
}
.aui-inputClear:hover {
border-bottom: 1px solid #1b90ff;
}
.aui-choice {
position: relative;
font-size: 12px;
display: -webkit-box;
display: -webkit-flex;
display: flex;
-webkit-box-align: center;
-webkit-align-items: center;
align-items: center;
position: relative;
color: #040404;
}
.aui-choice input {
width: 14px;
height: 14px;
cursor: pointer;
}
.aui-forget a {
color: #1b90ff;
font-size: 12px;
}
.aui-forget a:hover {
text-decoration: underline;
}
.aui-formButton {
padding-top: 10px;
}
.aui-formButton a {
height: 42px;
padding: 10px 15px;
font-size: 14px;
border-radius: 8px;
border-color: #67b5ff;
background: #1b90ff;
width: 100%;
cursor: pointer;
border: none;
color: #fff;
margin: 8px 0;
display: block;
text-align: center;
}
.aui-formButton a:focus {
opacity: 0.9;
}
.aui-formButton a:hover {
opacity: 0.9;
}
.aui-formButton .aui-linek-code {
background: #fff;
color: #3c3c3c;
border: 1px solid #dbdbdb;
}
.aui-formButton .aui-linek-code:hover {
color: #1b90ff;
border: 1px solid #1b90ff;
}
.aui-third-text {
font-size: 12px;
color: #3c3c3c;
margin-top: 25px;
margin-bottom: 25px;
}
.aui-third-text span {
color: #afafaf;
display: block;
width: 38%;
margin: 0 auto;
text-align: center;
position: relative;
background: #fff;
z-index: 100;
font-size: 12px;
}
.aui-third-border {
position: relative;
}
.aui-third-border::after {
content: '';
position: absolute;
z-index: 0;
top: 8px;
left: 0;
width: 100%;
height: 1px;
border-top: 1px solid #d9d9d9;
-webkit-transform: scaleY(0.5);
transform: scaleY(0.5);
-webkit-transform-origin: 0 100%;
transform-origin: 0 100%;
}
.aui-third-login {
width: 30px;
height: 30px;
margin: 0 auto;
border-radius: 100px;
}
.aui-third-login a {
font-size: 22px;
margin: 0 auto;
border-radius: 100px;
display: inline-block;
color: #888;
}
.aui-third-login a:hover {
color: #1b90ff;
cursor: pointer;
}
.aui-third-login:hover {
cursor: pointer;
}
@media (max-width: 320px) {
.aui-form {
flex-direction: column;
}
.aui-image {
order: 2;
display: none;
}
.aui-container {
width: 100%;
max-width: 550px;
margin-top: 10px;
}
.aui-content {
justify-content: initial;
width: 100%;
padding: 20px;
}
}
@media (min-width: 321px) and (max-width: 375px) {
.aui-form {
flex-direction: column;
}
.aui-image {
order: 2;
display: none;
}
.aui-container {
width: 90%;
max-width: 550px;
}
.aui-content {
justify-content: initial;
width: 100%;
padding: 20px;
}
}
@media (min-width: 375px) and (max-width: 425px) {
.aui-form {
flex-direction: column;
}
.aui-image {
order: 2;
display: none;
}
.aui-container {
width: 90%;
max-width: 550px;
}
.aui-content {
justify-content: initial;
width: 100%;
padding: 40px;
}
}
@media (min-width: 425px) and (max-width: 768px) {
.aui-form {
flex-direction: column;
}
.aui-image {
order: 2;
display: none;
}
.aui-container {
width: 90%;
max-width: 550px;
}
.aui-content {
justify-content: initial;
width: 100%;
padding: 40px;
}
.aui-step-box::after {
width: 70%;
margin-left: -35%;
}
}
@media only screen and (max-width: 767px) {
.aui-logo {
top: 3%;
}
}
@media screen and (max-width: 300px) {
.aui-logo {
top: 3%;
}
}

4
src/router/routes/index.ts

@ -35,7 +35,9 @@ export const RootRoute: AppRouteRecordRaw = { @@ -35,7 +35,9 @@ export const RootRoute: AppRouteRecordRaw = {
export const LoginRoute: AppRouteRecordRaw = {
path: '/login',
name: 'Login',
component: () => import('/@/views/core/login/Login.vue'),
//新版后台登录,如果想要使用旧版登录放开即可
// component: () => import('/@/views/core/login/Login.vue'),
component: () => import('/@/views/core/loginmini/MiniLogin.vue'),
meta: {
title: t('routes.basic.login'),
},

167
src/views/core/loginmini/MiniCodelogin.vue

@ -0,0 +1,167 @@ @@ -0,0 +1,167 @@
<template>
<div class="aui-content">
<div class="aui-container">
<div class="aui-form">
<div class="aui-image">
<div class="aui-image-text">
<img :src="adTextImg" alt="">
</div>
</div>
<div class="aui-formBox aui-formEwm">
<div class="aui-formWell">
<form>
<div class="aui-flex aui-form-nav investment_title" style="padding-bottom: 19px">
<div class="aui-flex-box activeNav">{{ t('sys.login.qrSignInFormTitle') }}</div>
</div>
<div class="aui-form-box">
<div class="aui-account" style="padding: 30px 0">
<div class="aui-ewm">
<QrCode :value="qrCodeUrl" class="enter-x flex justify-center xl:justify-start" :width="280"/>
</div>
</div>
</div>
<div class="aui-formButton">
<a class="aui-linek-code aui-link-register" @click="goBackHandleClick">{{ t('sys.login.backSignIn') }}</a>
</div>
</form>
</div>
<div class="aui-flex aui-third-text">
<div class="aui-flex-box aui-third-border">
<span>{{ t('sys.login.otherSignIn') }}</span>
</div>
</div>
<div class="aui-flex" :class="`${prefixCls}-sign-in-way`">
<div class="aui-flex-box">
<div class="aui-third-login">
<a href="" title="github" @click="onThirdLogin('github')"><GithubFilled/></a>
</div>
</div>
<div class="aui-flex-box">
<div class="aui-third-login">
<a href="" title="企业微信" @click="onThirdLogin('wechat_enterprise')"><icon-font class="item-icon" type="icon-qiyeweixin3"/></a>
</div>
</div>
<div class="aui-flex-box">
<div class="aui-third-login">
<a href="" title="钉钉" @click="onThirdLogin('dingtalk')"><DingtalkCircleFilled/></a>
</div>
</div>
<div class="aui-flex-box">
<div class="aui-third-login">
<a href="" title="微信" @click="onThirdLogin('wechat_open')"><WechatFilled/></a>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- 第三方登录相关弹框 -->
<!--<ThirdModal ref="thirdModalRef"/>-->
</template>
<script lang="ts" setup name="mini-code-login">
import { ref, onUnmounted } from 'vue';
import { getCaptcha } from '/@/api/platform/core/controller/user';
import { useUserStore } from '/@/store/modules/user';
import { QrCode } from '/@/components/Qrcode/index';
//import ThirdModal from '/@/views/sys/login/ThirdModal.vue';
import logoImg from '/@/assets/images/logo-tag.png';
import adTextImg from '/@/assets/loginmini/icon/login-ad-text.png';
import { useI18n } from '/@/hooks/web/useI18n';
import { useDesign } from '/@/hooks/web/useDesign';
import { GithubFilled, WechatFilled, DingtalkCircleFilled, createFromIconfontCN } from '@ant-design/icons-vue';
const IconFont = createFromIconfontCN({
scriptUrl: '//at.alicdn.com/t/font_2316098_umqusozousr.js',
});
const { prefixCls } = useDesign('minilogin');
const { t } = useI18n();
const qrCodeUrl = ref<string>('');
let timer: IntervalHandle;
const state = ref('0');
const thirdModalRef = ref();
const userStore = useUserStore();
const emit = defineEmits(['go-back', 'success', 'register']);
//
function loadQrCode() {
state.value = '0';
qrCodeUrl.value = 'https://github.com/wangxiang4';
/*getLoginQrcode().then((res) => {
qrCodeUrl.value = res.qrcodeId;
if (res.qrcodeId) {
openTimer(res.qrcodeId);
}
});*/
}
//
function watchQrcodeToken(qrcodeId) {
/*getQrcodeToken({ qrcodeId: qrcodeId }).then((res) => {
let token = res.token;
if (token == '-2') {
//
loadQrCode();
clearInterval(timer);
}
//
if (res.success) {
state.value = '2';
clearInterval(timer);
setTimeout(() => {
userStore.qrCodeLogin(token);
}, 500);
}
});*/
}
/** 开启定时器 */
function openTimer(qrcodeId) {
watchQrcodeToken(qrcodeId);
closeTimer();
timer = setInterval(() => {
watchQrcodeToken(qrcodeId);
}, 1500);
}
/** 关闭定时器 */
function closeTimer() {
if (timer) clearInterval(timer);
}
/**
* 第三方登录
* @param type
*/
function onThirdLogin(type) {
thirdModalRef.value.onThirdLogin(type);
}
/**
* 初始化表单
*/
function initFrom() {
loadQrCode();
}
/**
* 返回
*/
function goBackHandleClick() {
emit('go-back');
closeTimer();
}
onUnmounted(() => {
closeTimer();
});
defineExpose({
initFrom,
});
</script>
<style lang="less" scoped>
@import '/@/assets/loginmini/style/home.less';
@import '/@/assets/loginmini/style/base.less';
</style>

282
src/views/core/loginmini/MiniForgotpad.vue

@ -0,0 +1,282 @@ @@ -0,0 +1,282 @@
<template>
<div class="aui-content">
<div class="aui-container">
<div class="aui-form">
<div class="aui-image">
<div class="aui-image-text">
<img :src="adTextImg" alt="">
</div>
</div>
<div class="aui-formBox">
<div class="aui-formWell">
<div class="aui-step-box">
<div class="aui-step-item" :class="activeKey === 1 ? 'activeStep' : ''">
<div class="aui-step-tags">
<em>1</em>
<p>{{ t('sys.login.authentication') }}</p>
</div>
</div>
<div class="aui-step-item" :class="activeKey === 2 ? 'activeStep' : ''">
<div class="aui-step-tags">
<em>2</em>
<p>{{ t('sys.login.resetLoginPassword') }}</p>
</div>
</div>
<div class="aui-step-item" :class="activeKey === 3 ? 'activeStep' : ''">
<div class="aui-step-tags">
<em>3</em>
<p>{{ t('sys.login.resetSuccess') }}</p>
</div>
</div>
</div>
<div class="" style="height: 230px; position: relative">
<a-form v-if="activeKey === 1" ref="formRef" :model="formData">
<!-- 身份验证 begin -->
<div class="aui-account aui-account-line aui-forgot">
<a-form-item>
<div class="aui-input-line">
<a-input v-model:value="formData.mobile" type="text" :placeholder="t('sys.login.mobile')"/>
</div>
</a-form-item>
<div class="aui-input-line">
<a-form-item>
<a-input v-model:value="formData.smscode" type="text" :placeholder="t('sys.login.smsCode')"/>
</a-form-item>
<div v-if="showInterval" class="aui-code-line" @click="getLoginCode">{{ t('component.countdown.normalText') }}</div>
<div v-else class="aui-code-line">{{ t('component.countdown.sendText',[unref(timeRuning)]) }}</div>
</div>
</div>
<!-- 身份验证 end -->
</a-form>
<a-form v-else-if="activeKey === 2" ref="pwdFormRef" :model="pwdFormData">
<!-- 重置密码 begin -->
<div class="aui-account aui-account-line aui-forgot">
<a-form-item>
<div class="aui-input-line">
<a-input v-model:value="pwdFormData.password" type="password" :placeholder="t('sys.login.passwordPlaceholder')"/>
</div>
</a-form-item>
<a-form-item>
<div class="aui-input-line">
<a-input v-model:value="pwdFormData.confirmPassword" type="password" :placeholder="t('sys.login.confirmPassword')"/>
</div>
</a-form-item>
</div>
<!-- 重置密码 end -->
</a-form>
<!-- 重置成功 begin -->
<div v-else class="aui-success">
<div class="aui-success-icon">
<img :src="successImg">
</div>
<h3>恭喜您重置密码成功</h3>
</div>
<!-- 重置成功 end -->
</div>
<div class="aui-formButton" style="padding-bottom: 40px">
<div v-if="activeKey === 1 || activeKey === 2" class="aui-flex">
<a class="aui-link-login aui-flex-box" @click="nextStepClick">{{ t('sys.login.nextStep') }}</a>
</div>
<div v-else class="aui-flex">
<a class="aui-linek-code aui-flex-box" @click="toLogin">{{ t('sys.login.goToLogin') }}</a>
</div>
<div class="aui-flex">
<a class="aui-linek-code aui-flex-box" @click="goBack"> {{ t('sys.login.backSignIn') }}</a>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</template>
<script lang="ts" name="mini-forgotpad" setup>
import { reactive, ref, toRaw, unref } from 'vue';
import { useI18n } from '/@/hooks/web/useI18n';
import { LoginStateEnum, useFormRules, useFormValid, useLoginState } from '/@/views/core/login/useLogin';
import { useMessage } from '/@/hooks/web/useMessage';
import { getCaptcha } from '/@/api/platform/core/controller/user';
import logoImg from '/@/assets/images/logo-tag.png';
import adTextImg from '/@/assets/loginmini/icon/login-ad-text.png';
import successImg from '/@/assets/loginmini/icon/icon-success.png';
//
const activeKey = ref<number>(1);
const { t } = useI18n();
const { handleBackLogin } = useLoginState();
const { notification, createMessage, createErrorModal } = useMessage();
//
const showInterval = ref<boolean>(true);
//60s
const timeRuning = ref<number>(60);
//
const timer = ref<any>(null);
const formRef = ref();
const pwdFormRef = ref();
//
const accountInfo = reactive<any>({});
//
const formData = reactive({
mobile: '',
smscode: '',
});
//
const pwdFormData = reactive<any>({
password: '',
confirmPassword: '',
});
const emit = defineEmits(['go-back', 'success', 'register']);
/**
* 下一步
*/
async function handleNext() {
if (!formData.mobile) {
createMessage.warn(t('sys.login.mobilePlaceholder'));
return;
}
if (!formData.smscode) {
createMessage.warn(t('sys.login.smsPlaceholder'));
return;
}
/*const resultInfo = await phoneVerify(
toRaw({
phone: formData.mobile,
smscode: formData.smscode,
})
);
if (resultInfo.success) {
Object.assign(accountInfo, {
username: resultInfo.result.username,
phone: formData.mobile,
smscode: formData.smscode,
});
activeKey.value = 2;
setTimeout(()=>{
pwdFormRef.value.resetFields();
},300);
} else {
notification.error({
message: '错误提示',
description: resultInfo.message || t('sys.api.networkExceptionMsg'),
duration: 3,
});
}*/
}
/**
* 完成修改密码
*/
async function finishedPwd() {
if (!pwdFormData.password) {
createMessage.warn(t('sys.login.passwordPlaceholder'));
return;
}
if (!pwdFormData.confirmPassword) {
createMessage.warn(t('sys.login.confirmPassword'));
return;
}
if (pwdFormData.password !== pwdFormData.confirmPassword) {
createMessage.warn(t('sys.login.diffPwd'));
return;
}
/* const resultInfo = await passwordChange(
toRaw({
username: accountInfo.username,
password: pwdFormData.password,
smscode: accountInfo.smscode,
phone: accountInfo.phone,
})
);
if (resultInfo.success) {
accountInfo.password = pwdFormData.password;
//
activeKey.value = 3;
} else {
//
createErrorModal({
title: t('sys.api.errorTip'),
content: resultInfo.message || t('sys.api.networkExceptionMsg'),
});
}*/
}
/**
* 下一步
*/
function nextStepClick() {
if (unref(activeKey) == 1) {
handleNext();
} else if (unref(activeKey) == 2) {
finishedPwd();
}
}
/**
* 去登录
*/
function toLogin() {
emit('success', { username: accountInfo.username, password: accountInfo.password });
initForm();
}
/**
* 返回
*/
function goBack() {
emit('go-back');
initForm();
}
/**
* 获取手机验证码
*/
async function getLoginCode() {
if (!formData.mobile) {
createMessage.warn(t('sys.login.mobilePlaceholder'));
return;
}
/*const result = await getCaptcha({ mobile: formData.mobile, smsmode: SmsEnum.FORGET_PASSWORD });
if (result) {
const TIME_COUNT = 60;
if (!unref(timer)) {
timeRuning.value = TIME_COUNT;
showInterval.value = false;
timer.value = setInterval(() => {
if (unref(timeRuning) > 0 && unref(timeRuning) <= TIME_COUNT) {
timeRuning.value = timeRuning.value - 1;
} else {
showInterval.value = true;
clearInterval(unref(timer));
timer.value = null;
}
}, 1000);
}
}*/
}
/**
* 初始化表单
*/
function initForm() {
activeKey.value = 1;
Object.assign(formData, { phone: '', smscode: '' });
Object.assign(pwdFormData, { password: '', confirmPassword: '' });
Object.assign(accountInfo, {});
if(unref(timer)){
clearInterval(unref(timer));
timer.value = null;
showInterval.value = true;
}
setTimeout(()=>{
formRef.value.resetFields();
},300);
}
defineExpose({
initForm,
});
</script>
<style lang="less" scoped>
@import '/@/assets/loginmini/style/home.less';
@import '/@/assets/loginmini/style/base.less';
</style>

594
src/views/core/loginmini/MiniLogin.vue

@ -0,0 +1,594 @@ @@ -0,0 +1,594 @@
<template>
<div :class="prefixCls" class="login-background-img">
<AppLocalePicker class="absolute top-4 right-4 enter-x xl:text-gray-600" :showText="false"/>
<AppDarkModeToggle class="absolute top-3 right-10 enter-x"/>
<div v-if="!getIsMobile" class="aui-logo">
<div>
<h3>
<img :src="logoImg">
</h3>
</div>
</div>
<div v-else class="aui-phone-logo">
<img :src="logoImg">
</div>
<div v-show="type === 'login'">
<div class="aui-content">
<div class="aui-container">
<div class="aui-form">
<div class="aui-image">
<div class="aui-image-text">
<img :src="adTextImg" alt="">
</div>
</div>
<div class="aui-formBox">
<div class="aui-formWell">
<div class="aui-flex aui-form-nav investment_title">
<div
class="aui-flex-box"
:class="activeIndex === 'accountLogin' ? 'activeNav on' : ''"
@click="loginClick('accountLogin')"
>{{ t('sys.login.signInFormTitle') }}
</div>
<div
class="aui-flex-box"
:class="activeIndex === 'phoneLogin' ? 'activeNav on' : ''"
@click="loginClick('phoneLogin')"
>{{ t('sys.login.mobileSignInFormTitle') }}
</div>
</div>
<div class="aui-form-box" style="height: 180px">
<a-form
v-if="activeIndex === 'accountLogin'"
ref="loginRef"
:model="formData"
@keyup.enter="loginHandleClick"
>
<div class="aui-account">
<div class="aui-inputClear">
<i class="icon icon-code"/>
<a-form-item>
<a-input v-model:value="formData.username" class="fix-auto-fill" :placeholder="t('sys.login.userName')"/>
</a-form-item>
</div>
<div class="aui-inputClear">
<i class="icon icon-password"/>
<a-form-item>
<a-input
v-model:value="formData.password"
class="fix-auto-fill"
type="password"
:placeholder="t('sys.login.password')"
/>
</a-form-item>
</div>
<div class="aui-inputClear">
<i class="icon icon-code"/>
<a-form-item>
<a-input
v-model:value="formData.inputCode"
class="fix-auto-fill"
type="text"
:placeholder="t('sys.login.captcha')"
/>
</a-form-item>
<div class="aui-code">
<img v-if="randCodeData.requestCodeSuccess" :src="randCodeData.randCodeImage" @click="handleChangeCheckCode">
<img
v-else
style="margin-top: 2px; max-width: initial"
:src="codeImg"
@click="handleChangeCheckCode"
>
</div>
</div>
<div class="aui-flex">
<div class="aui-flex-box">
<div class="aui-choice">
<a-input v-model:value="rememberMe" class="fix-auto-fill" type="checkbox"/>
<span style="margin-left: 5px">{{ t('sys.login.rememberMe') }}</span>
</div>
</div>
<div class="aui-forget">
<a @click="forgetHandelClick"> {{ t('sys.login.forgetPassword') }}</a>
</div>
</div>
</div>
</a-form>
<a-form
v-else
ref="phoneFormRef"
:model="phoneFormData"
@keyup.enter="loginHandleClick"
>
<div class="aui-account phone">
<div class="aui-inputClear phoneClear">
<a-input v-model:value="phoneFormData.mobile" class="fix-auto-fill" :placeholder="t('sys.login.mobile')"/>
</div>
<div class="aui-inputClear">
<a-input
v-model:value="phoneFormData.smscode"
class="fix-auto-fill"
:maxlength="6"
:placeholder="t('sys.login.smsCode')"
/>
<div v-if="showInterval" class="aui-code" @click="getLoginCode">
<a>{{ t('component.countdown.normalText') }}</a>
</div>
<div v-else class="aui-code">
<span class="aui-get-code code-shape">{{ t('component.countdown.sendText', [unref(timeRuning)]) }}</span>
</div>
</div>
</div>
</a-form>
</div>
<div class="aui-formButton">
<div class="aui-flex">
<a-button
:loading="loginLoading"
class="aui-link-login aui-flex-box"
type="primary"
@click="loginHandleClick"
>
{{ t('sys.login.loginButton') }}</a-button>
</div>
<div class="aui-flex">
<a class="aui-linek-code aui-flex-box" @click="codeHandleClick">{{ t('sys.login.qrSignInFormTitle') }}</a>
</div>
<!--<div class="aui-flex">
<a class="aui-linek-code aui-flex-box" @click="registerHandleClick">{{ t('sys.login.registerButton') }}</a>
</div>-->
</div>
</div>
<a-form @keyup.enter="loginHandleClick">
<div class="aui-flex aui-third-text">
<div class="aui-flex-box aui-third-border">
<span>{{ t('sys.login.otherSignIn') }}</span>
</div>
</div>
<div class="aui-flex" :class="`${prefixCls}-sign-in-way`">
<div class="aui-flex-box">
<div class="aui-third-login">
<a title="github" @click="onThirdLogin('github')"><GithubFilled/></a>
</div>
</div>
<div class="aui-flex-box">
<div class="aui-third-login">
<a title="企业微信" @click="onThirdLogin('wechat_enterprise')"><icon-font class="item-icon" type="icon-qiyeweixin3"/></a>
</div>
</div>
<div class="aui-flex-box">
<div class="aui-third-login">
<a title="钉钉" @click="onThirdLogin('dingtalk')"><DingtalkCircleFilled/></a>
</div>
</div>
<div class="aui-flex-box">
<div class="aui-third-login">
<a title="微信" @click="onThirdLogin('wechat_open')"><WechatFilled/></a>
</div>
</div>
</div>
</a-form>
</div>
</div>
</div>
</div>
</div>
<div v-show="type === 'forgot'" :class="`${prefixCls}-form`">
<MiniForgotpad ref="forgotRef" @go-back="goBack" @success="handleSuccess"/>
</div>
<div v-show="type === 'register'" :class="`${prefixCls}-form`">
<MiniRegister ref="registerRef" @go-back="goBack" @success="handleSuccess"/>
</div>
<div v-show="type === 'codeLogin'" :class="`${prefixCls}-form`">
<MiniCodelogin ref="codeRef" @go-back="goBack" @success="handleSuccess"/>
</div>
</div>
</template>
<script lang="ts" setup name="login-mini">
import { getCaptcha } from '/@/api/platform/core/controller/user';
import { computed, onMounted, reactive, ref, toRaw, unref } from 'vue';
import codeImg from '/@/assets/images/checkcode.png';
import { Rule } from '/@/components/Form';
import { useUserStore } from '/@/store/modules/user';
import { useMessage } from '/@/hooks/web/useMessage';
import { useI18n } from '/@/hooks/web/useI18n';
import { LoginStateEnum } from '/@/views/core/login/useLogin';
//import ThirdModal from '/@/views/sys/login/ThirdModal.vue';
import MiniForgotpad from './MiniForgotpad.vue';
import MiniRegister from './MiniRegister.vue';
import MiniCodelogin from './MiniCodelogin.vue';
import adTextImg from '/@/assets/loginmini/icon/login-ad-text.png';
import logoImg from '/@/assets/images/logo-tag.png';
import { AppLocalePicker, AppDarkModeToggle } from '/@/components/Application';
import { useLocaleStore } from '/@/store/modules/locale';
import { useDesign } from '/@/hooks/web/useDesign';
import { useAppInject } from '/@/hooks/web/useAppInject';
import { GithubFilled, WechatFilled, DingtalkCircleFilled, createFromIconfontCN } from '@ant-design/icons-vue';
const IconFont = createFromIconfontCN({
scriptUrl: '//at.alicdn.com/t/font_2316098_umqusozousr.js',
});
const { prefixCls } = useDesign('mini-login');
const { notification, createMessage } = useMessage();
const userStore = useUserStore();
const { t } = useI18n();
const localeStore = useLocaleStore();
const showLocale = localeStore.getShowPicker;
const randCodeData = reactive<any>({
randCodeImage: '',
requestCodeSuccess: false,
checkKey: null,
});
const rememberMe = ref<string>('0');
//
const activeIndex = ref<string>('accountLogin');
const type = ref<string>('login');
//
const formData = reactive<any>({
realKey: '',
inputCode: '',
username: 'admin',
password: '123456',
});
//
const phoneFormData = reactive<any>({
mobile: '',
smscode: '',
});
const loginRef = ref();
//
const thirdModalRef = ref();
//
const codeRef = ref();
//
const showInterval = ref<boolean>(true);
//60s
const timeRuning = ref<number>(60);
//
const timer = ref<any>(null);
//
const forgotRef = ref();
//
const registerRef = ref();
const loginLoading = ref<boolean>(false);
const { getIsMobile } = useAppInject();
defineProps({
sessionTimeout: {
type: Boolean,
},
});
/**
* 获取验证码
*/
async function handleChangeCheckCode() {
formData.inputCode = '';
try {
const codeModel = await getCaptcha();
randCodeData.randCodeImage = codeModel.img ?? codeImg;
randCodeData.requestCodeSuccess = true;
formData.realKey = codeModel.realKey;
} catch(error) {
randCodeData.requestCodeSuccess = false;
}
}
/**
* 切换登录方式
*/
function loginClick(type) {
activeIndex.value = type;
}
/**
* 账号或者手机登录
*/
async function loginHandleClick() {
if (unref(activeIndex) === 'accountLogin') {
accountLogin();
} else {
//
phoneLogin();
}
}
async function accountLogin() {
if (!formData.username) {
createMessage.warn(t('sys.login.accountPlaceholder'));
return;
}
if (!formData.password) {
createMessage.warn(t('sys.login.passwordPlaceholder'));
return;
}
try {
loginLoading.value = true;
const userInfo = await userStore.login(toRaw({
password: formData.password,
username: formData.username,
realKey: formData.realKey,
code: formData.inputCode,
}));
if (userInfo) {
notification.success({
message: t('sys.login.loginSuccessTitle'),
description: `${t('sys.login.loginSuccessDesc')}: ${userInfo.nickName}`,
duration: 3,
});
}
} catch (error){
formData.code='';
formData.realKey='';
handleChangeCheckCode();
} finally {
loginLoading.value = false;
}
}
/**
* 手机号登录
*/
async function phoneLogin() {
/*if (!phoneFormData.mobile) {
createMessage.warn(t('sys.login.mobilePlaceholder'));
return;
}
if (!phoneFormData.smscode) {
createMessage.warn(t('sys.login.smsPlaceholder'));
return;
}
try {
loginLoading.value = true;
const { userInfo }: any = await userStore.phoneLogin({
mobile: phoneFormData.mobile,
captcha: phoneFormData.smscode,
mode: 'none', //
});
if (userInfo) {
notification.success({
message: t('sys.login.loginSuccessTitle'),
description: `${t('sys.login.loginSuccessDesc')}: ${userInfo.realname}`,
duration: 3,
});
}
} catch (error) {
notification.error({
message: t('sys.api.errorTip'),
description: error.message || t('sys.login.networkExceptionMsg'),
duration: 3,
});
} finally {
loginLoading.value = false;
}*/
}
/**
* 获取手机验证码
*/
async function getLoginCode() {
/*if (!phoneFormData.mobile) {
createMessage.warn(t('sys.login.mobilePlaceholder'));
return;
}
const result = await getCaptcha({ mobile: phoneFormData.mobile, smsmode: SmsEnum.FORGET_PASSWORD });
if (result) {
const TIME_COUNT = 60;
if (!unref(timer)) {
timeRuning.value = TIME_COUNT;
showInterval.value = false;
timer.value = setInterval(() => {
if (unref(timeRuning) > 0 && unref(timeRuning) <= TIME_COUNT) {
timeRuning.value = timeRuning.value - 1;
} else {
showInterval.value = true;
clearInterval(unref(timer));
timer.value = null;
}
}, 1000);
}
}*/
}
/**
* 第三方登录
* @param type
*/
function onThirdLogin(type) {
thirdModalRef.value.onThirdLogin(type);
}
/**
* 忘记密码
*/
function forgetHandelClick() {
type.value = 'forgot';
setTimeout(() => {
forgotRef.value.initForm();
}, 300);
}
/**
* 返回登录页面
*/
function goBack() {
activeIndex.value = 'accountLogin';
type.value = 'login';
}
/**
* 忘记密码/注册账号回调事件
* @param value
*/
function handleSuccess(value) {
Object.assign(formData, value);
Object.assign(phoneFormData, { mobile: '', smscode: '' });
type.value = 'login';
activeIndex.value = 'accountLogin';
handleChangeCheckCode();
}
/**
* 注册
*/
function registerHandleClick() {
type.value = 'register';
setTimeout(() => {
registerRef.value.initForm();
}, 300);
}
/**
* 注册
*/
function codeHandleClick() {
type.value = 'codeLogin';
setTimeout(() => {
codeRef.value.initFrom();
}, 300);
}
onMounted(() => {
//
handleChangeCheckCode();
});
</script>
<style lang="less" scoped>
@import '/@/assets/loginmini/style/home.less';
@import '/@/assets/loginmini/style/base.less';
:deep(.ant-input:focus) {
box-shadow: none;
}
.aui-get-code {
float: right;
position: relative;
z-index: 3;
background: #ffffff;
color: #1573e9;
border-radius: 100px;
padding: 5px 16px;
margin: 7px;
border: 1px solid #1573e9;
top: 12px;
}
.aui-get-code:hover {
color: #1573e9;
}
.code-shape {
border-color: #dadada !important;
color: #aaa !important;
}
:deep(.jeecg-dark-switch){
position:absolute;
margin-right: 10px;
}
.aui-link-login{
height: 42px;
padding: 10px 15px;
font-size: 14px;
border-radius: 8px;
margin-top: 15px;
margin-bottom: 8px;
}
.aui-phone-logo{
position: absolute;
margin-left: 10px;
width: 60px;
top:2px;
z-index: 4;
}
.top-3{
top: 0.45rem;
}
</style>
<style lang="less">
@prefix-cls: ~'@{namespace}-mini-login';
@dark-bg: #293146;
html[data-theme='dark'] {
.@{prefix-cls} {
background-color: @dark-bg !important;
background-image: none;
&::before {
background-image: url(/@/assets/images/login-bg-dark.svg);
}
.aui-inputClear{
background-color: #232a3b !important;
}
.ant-input,
.ant-input-password {
background-color: #232a3b !important;
}
.ant-btn:not(.ant-btn-link):not(.ant-btn-primary) {
border: 1px solid #4a5569 !important;
}
&-form {
background: @dark-bg !important;
}
.app-iconify {
color: #fff !important;
}
.aui-inputClear input,.aui-input-line input,.aui-choice{
color: #c9d1d9 !important;
}
.aui-formBox{
background-color: @dark-bg !important;
}
.aui-third-text span{
background-color: @dark-bg !important;
}
.aui-form-nav .aui-flex-box{
color: #c9d1d9 !important;
}
.aui-formButton .aui-linek-code{
background: @dark-bg !important;
color: white !important;
}
.aui-code-line{
border-left: none !important;
}
.ant-checkbox-inner,.aui-success h3{
border-color: #c9d1d9;
}
}
input.fix-auto-fill,
.fix-auto-fill input {
-webkit-text-fill-color: #c9d1d9 !important;
box-shadow: inherit !important;
}
&-sign-in-way {
.anticon {
font-size: 22px !important;
color: #888 !important;
cursor: pointer !important;
&:hover {
color: @primary-color !important;
}
}
}
.ant-divider-inner-text {
font-size: 12px !important;
color: @text-color-secondary !important;
}
.aui-third-login a{
background: transparent;
}
}
</style>

311
src/views/core/loginmini/MiniRegister.vue

@ -0,0 +1,311 @@ @@ -0,0 +1,311 @@
<template>
<div class="aui-content">
<div class="aui-container">
<div class="aui-form">
<div class="aui-image">
<div class="aui-image-text">
<img :src="jeecgAdTextImg" alt="">
</div>
</div>
<div class="aui-formBox">
<div class="aui-formWell">
<a-form ref="formRef" :model="formData">
<div class="aui-flex aui-form-nav aui-clear-left" style="padding-bottom: 21px">
<div class="aui-flex-box activeNav on">{{ t('sys.login.signUpFormTitle') }}</div>
</div>
<div class="aui-form-box">
<div class="aui-account aui-account-line">
<a-form-item>
<div class="aui-input-line">
<Icon class="aui-icon" icon="ant-design:user-outlined"/>
<a-input
v-model:value="formData.username"
class="fix-auto-fill"
type="text"
:placeholder="t('sys.login.userName')"
/>
</div>
</a-form-item>
<a-form-item>
<div class="aui-input-line">
<Icon class="aui-icon" icon="ant-design:mobile-outlined"/>
<a-input
v-model:value="formData.mobile"
class="fix-auto-fill"
type="text"
:placeholder="t('sys.login.mobile')"
/>
</div>
</a-form-item>
<a-form-item>
<div class="aui-input-line">
<Icon class="aui-icon" icon="ant-design:mail-outlined"/>
<a-input
v-model:value="formData.smscode"
class="fix-auto-fill"
type="text"
:placeholder="t('sys.login.smsCode')"
/>
<div v-if="showInterval" class="aui-code-line" @click="getLoginCode">{{ t('component.countdown.normalText') }}</div>
<div v-else class="aui-code-line">{{ t('component.countdown.sendText',[unref(timeRuning)]) }}</div>
</div>
</a-form-item>
<a-form-item>
<div class="aui-input-line">
<Icon class="aui-icon" icon="ant-design:lock-outlined"/>
<a-input
v-model:value="formData.password"
class="fix-auto-fill"
:type="pwdIndex==='close'?'password':'text'"
:placeholder="t('sys.login.password')"
/>
<div class="aui-eye">
<img
v-if="pwdIndex==='open'"
:src="eyeKImg"
alt="开启"
@click="pwdClick('close')"
>
<img
v-else-if="pwdIndex==='close'"
:src="eyeGImg"
alt="关闭"
@click="pwdClick('open')"
>
</div>
</div>
</a-form-item>
<a-form-item>
<div class="aui-input-line">
<Icon class="aui-icon" icon="ant-design:lock-outlined"/>
<a-input
v-model:value="formData.confirmPassword"
class="fix-auto-fill"
:type="confirmPwdIndex==='close'?'password':'text'"
:placeholder="t('sys.login.confirmPassword')"
/>
<div class="aui-eye">
<img
v-if="confirmPwdIndex==='open'"
:src="eyeKImg"
alt="开启"
@click="confirmPwdClick('close')"
>
<img
v-else-if="confirmPwdIndex==='close'"
:src="eyeGImg"
alt="关闭"
@click="confirmPwdClick('open')"
>
</div>
</div>
</a-form-item>
<a-form-item name="policy">
<div class="aui-flex">
<div class="aui-flex-box">
<div class="aui-choice">
<a-checkbox v-model:checked="formData.policy"/>
<span style="color: #1b90ff;margin-left: 4px">{{ t('sys.login.policy') }}</span>
</div>
</div>
</div>
</a-form-item>
</div>
</div>
<div class="aui-formButton">
<div class="aui-flex">
<a class="aui-link-login aui-flex-box" @click="registerHandleClick"> {{ t('sys.login.registerButton') }}</a>
</div>
<div class="aui-flex">
<a class="aui-linek-code aui-flex-box" @click="goBackHandleClick">{{ t('sys.login.backSignIn') }}</a>
</div>
</div>
</a-form>
</div>
</div>
</div>
</div>
</div>
</template>
<script lang="ts" setup name="mini-register">
import { ref, reactive, unref, toRaw } from 'vue';
import { getCaptcha } from '/@/api/platform/core/controller/user';
import { LoginStateEnum } from '/@/views/core/login/useLogin';
import { useMessage } from '/@/hooks/web/useMessage';
import logoImg from '/@/assets/images/logo-tag.png';
import jeecgAdTextImg from '/@/assets/loginmini/icon/login-ad-text.png';
import eyeKImg from '/@/assets/loginmini/icon/icon-eye-k.png';
import eyeGImg from '/@/assets/loginmini/icon/icon-eye-g.png';
import { useI18n } from '/@/hooks/web/useI18n';
const { t } = useI18n();
const { notification, createErrorModal, createMessage } = useMessage();
const emit = defineEmits(['go-back', 'success', 'register']);
const formRef = ref();
const formData = reactive<any>({
username: '',
mobile: '',
smscode: '',
password: '',
confirmPassword: '',
policy: false,
});
//
const showInterval = ref<boolean>(true);
//60s
const timeRuning = ref<number>(60);
//
const timer = ref<any>(null);
//
const pwdIndex = ref<string>('close');
//
const confirmPwdIndex = ref<string>('close');
/**
* 返回
*/
function goBackHandleClick() {
emit('go-back');
initForm();
}
/**
* 获取手机验证码
*/
async function getLoginCode() {
/*if (!formData.mobile) {
createMessage.warn(t('sys.login.mobilePlaceholder'));
return;
}
const result = await getCaptcha({ mobile: formData.mobile, smsmode: LoginStateEnum.REGISTER });
if (result) {
const TIME_COUNT = 60;
if (!unref(timer)) {
timeRuning.value = TIME_COUNT;
showInterval.value = false;
timer.value = setInterval(() => {
if (unref(timeRuning) > 0 && unref(timeRuning) <= TIME_COUNT) {
timeRuning.value = timeRuning.value - 1;
} else {
showInterval.value = true;
clearInterval(unref(timer));
timer.value = null;
}
}, 1000);
}
}*/
}
function registerHandleClick() {
if (!formData.username) {
createMessage.warn(t('sys.login.accountPlaceholder'));
return;
}
if (!formData.mobile) {
createMessage.warn(t('sys.login.mobilePlaceholder'));
return;
}
if (!formData.smscode) {
createMessage.warn(t('sys.login.smsPlaceholder'));
return;
}
if (!formData.password) {
createMessage.warn(t('sys.login.passwordPlaceholder'));
return;
}
if (!formData.confirmPassword) {
createMessage.warn(t('sys.login.confirmPassword'));
return;
}
if (formData.password !== formData.confirmPassword) {
createMessage.warn(t('sys.login.diffPwd'));
return;
}
if(!formData.policy){
createMessage.warn(t('sys.login.policyPlaceholder'));
return;
}
registerAccount();
}
/**
* 注册账号
*/
async function registerAccount() {
/*try {
const resultInfo = await register(
toRaw({
username: formData.username,
password: formData.password,
phone: formData.mobile,
smscode: formData.smscode,
})
);
if (resultInfo && resultInfo.data.success) {
notification.success({
description: resultInfo.data.message || t('sys.api.registerMsg'),
duration: 3,
});
emit('success', { username: formData.username, password: formData.password });
initForm();
} else {
notification.warning({
message: t('sys.api.errorTip'),
description: resultInfo.data.message || t('sys.api.networkExceptionMsg'),
duration: 3,
});
}
} catch (error) {
notification.error({
message: t('sys.api.errorTip'),
description: error.message || t('sys.api.networkExceptionMsg'),
duration: 3,
});
}*/
}
/**
* 初始化表单
*/
function initForm() {
Object.assign(formData,{username:'',mobile: '', smscode: '', password: '', confirmPassword: '', policy: false});
if(!unref(timer)){
showInterval.value = true;
clearInterval(unref(timer));
timer.value = null;
}
formRef.value.resetFields();
}
/**
* 密码打开或关闭
* @param value
*/
function pwdClick(value) {
pwdIndex.value = value;
}
/**
* 确认密码打开或关闭
* @param value
*/
function confirmPwdClick(value) {
confirmPwdIndex.value = value;
}
defineExpose({
initForm
});
</script>
<style lang="less" scoped>
@import '/@/assets/loginmini/style/home.less';
@import '/@/assets/loginmini/style/base.less';
.aui-input-line .aui-icon{
position: absolute;
z-index: 2;
top: 10px;
left: 10px;
font-size: 20px !important;
}
</style>

86
src/views/core/loginmini/OAuth2Login.vue

@ -0,0 +1,86 @@ @@ -0,0 +1,86 @@
<template>
<div/>
</template>
<script setup lang="ts">
/*import { ref } from 'vue';
import { isOAuth2AppEnv, sysOAuth2Login } from '/@/views/sys/login/useLogin';
import { useRouter } from 'vue-router';
import { PageEnum } from '/@/enums/pageEnum';
import { router } from '/@/router';
import { useUserStore } from '/@/store/modules/user';
import { useMessage } from '/@/hooks/web/useMessage';
import { useI18n } from '/@/hooks/web/useI18n';
const isOAuth = ref<boolean>(isOAuth2AppEnv());
const env = ref<any>({ thirdApp: false, wxWork: false, dingtalk: false });
const { currentRoute } = useRouter();
const route = currentRoute.value;
if (!isOAuth2AppEnv()) {
router.replace({ path: PageEnum.BASE_LOGIN, query: route.query });
}
if (isOAuth.value) {
checkEnv();
}
/!**
* 检测当前的环境
*!/
function checkEnv() {
//
if (/wxwork/i.test(navigator.userAgent)) {
env.value.thirdApp = true;
env.value.wxWork = true;
}
//
if (/dingtalk/i.test(navigator.userAgent)) {
env.value.thirdApp = true;
env.value.dingtalk = true;
}
doOAuth2Login();
}
/!**
* 进行OAuth2登录操作
*!/
function doOAuth2Login() {
if (env.value.thirdApp) {
// Token
if (route.query.oauth2LoginToken) {
let token = route.query.oauth2LoginToken;
//
thirdLogin({ token, thirdType: route.query.thirdType });
} else if (env.value.wxWork) {
sysOAuth2Login('wechat_enterprise');
} else if (env.value.dingtalk) {
sysOAuth2Login('dingtalk');
}
}
}
/!**
* 第三方登录
* @param params
*!/
function thirdLogin(params) {
const userStore = useUserStore();
const { notification } = useMessage();
const { t } = useI18n();
userStore.ThirdLogin(params).then((res) => {
if (res && res.userInfo) {
notification.success({
message: t('sys.login.loginSuccessTitle'),
description: `${t('sys.login.loginSuccessDesc')}: ${res.userInfo.realname}`,
duration: 3,
});
} else {
notification.error({
message: t('sys.login.errorTip'),
description: ((res.response || {}).data || {}).message || res.message || t('sys.login.networkExceptionMsg'),
duration: 4,
});
}
});
}*/
</script>
Loading…
Cancel
Save