373 lines
8.4 KiB
Vue
373 lines
8.4 KiB
Vue
<template>
|
|
<view class="change-password-page">
|
|
<PageHeader
|
|
title="修改密码"
|
|
:is-back="true"
|
|
:border-bottom="false"
|
|
:background="headerBackground"
|
|
/>
|
|
|
|
<view class="content-wrapper">
|
|
<view class="form-card single-row-card">
|
|
<view class="form-row">
|
|
<text class="label">手机号</text>
|
|
<input
|
|
class="input"
|
|
type="number"
|
|
v-model="form.phone"
|
|
placeholder="请输入手机号"
|
|
placeholder-style="color: #c0c0c0;"
|
|
/>
|
|
</view>
|
|
</view>
|
|
|
|
<view class="form-card single-row-card">
|
|
<view class="form-row captcha-row">
|
|
<text class="label">图形验证码</text>
|
|
<input
|
|
class="input"
|
|
v-model="form.captcha"
|
|
placeholder="请输入验证码"
|
|
placeholder-style="color: #c0c0c0;"
|
|
/>
|
|
<image
|
|
class="captcha-image"
|
|
:src="captchaUrl"
|
|
mode="aspectFill"
|
|
@click="refreshCaptcha"
|
|
/>
|
|
</view>
|
|
</view>
|
|
|
|
<view class="form-card single-row-card">
|
|
<view class="form-row">
|
|
<text class="label">验证码</text>
|
|
<input
|
|
class="input"
|
|
type="number"
|
|
v-model="form.code"
|
|
placeholder="请输入验证码"
|
|
placeholder-style="color: #c0c0c0;"
|
|
/>
|
|
<text
|
|
class="get-code"
|
|
:class="{ disabled: codeText !== '获取验证码' }"
|
|
@click="handleGetCode"
|
|
>
|
|
{{ codeText }}
|
|
</text>
|
|
</view>
|
|
</view>
|
|
|
|
<view class="form-card">
|
|
<view class="form-row">
|
|
<text class="label">新密码</text>
|
|
<input
|
|
class="input"
|
|
:password="!showPassword"
|
|
v-model="form.pwd"
|
|
placeholder="请输入新密码"
|
|
placeholder-style="color: #c0c0c0;"
|
|
/>
|
|
</view>
|
|
<view class="form-row">
|
|
<text class="label">确认新密码</text>
|
|
<input
|
|
class="input"
|
|
:password="!showPassword"
|
|
v-model="form.confirmPwd"
|
|
placeholder="请再次输入新密码"
|
|
placeholder-style="color: #c0c0c0;"
|
|
/>
|
|
</view>
|
|
</view>
|
|
|
|
<button class="submit-button" @click="handleSubmit">确定</button>
|
|
</view>
|
|
|
|
<u-toast ref="uToast" />
|
|
</view>
|
|
</template>
|
|
|
|
<script>
|
|
import PageHeader from "@/components/PageHeader.vue";
|
|
import { generateSign } from "@/utils/signUtil.js";
|
|
import md5 from "js-md5";
|
|
|
|
export default {
|
|
name: "ChangePassword",
|
|
components: {
|
|
PageHeader,
|
|
},
|
|
data() {
|
|
return {
|
|
headerBackground: {
|
|
background: "transparent",
|
|
},
|
|
form: {
|
|
phone: "",
|
|
code: "",
|
|
captcha: "",
|
|
pwd: "",
|
|
confirmPwd: "",
|
|
},
|
|
showPassword: false,
|
|
codeText: "获取验证码",
|
|
countdown: 60,
|
|
timer: null,
|
|
captchaId: "",
|
|
captchaUrl: "",
|
|
};
|
|
},
|
|
onLoad() {
|
|
const userInfo = this.vuex_user || {};
|
|
const phone = userInfo.phone || userInfo.Phone || "";
|
|
if (phone) {
|
|
this.form.phone = phone;
|
|
}
|
|
this.refreshCaptcha();
|
|
},
|
|
beforeDestroy() {
|
|
if (this.timer) {
|
|
clearInterval(this.timer);
|
|
}
|
|
},
|
|
methods: {
|
|
refreshCaptcha() {
|
|
this.$u.api.GetCaptcha().then((res) => {
|
|
this.captchaId = res.captchaId || "";
|
|
this.captchaUrl = res.imageBase64
|
|
? `data:image/png;base64,${res.imageBase64}`
|
|
: "";
|
|
});
|
|
},
|
|
handleGetCode() {
|
|
if (this.codeText !== "获取验证码") return;
|
|
if (!this.validatePhone()) return;
|
|
if (!this.validateCaptcha()) return;
|
|
this.requestSmsCode();
|
|
},
|
|
requestSmsCode() {
|
|
const sign = generateSign(this.form.phone);
|
|
const params = {
|
|
phone: this.form.phone,
|
|
sign,
|
|
captchaId: this.captchaId,
|
|
captchaCode: this.form.captcha,
|
|
ip: "",
|
|
};
|
|
|
|
this.$u.api.RequestForgotPasswordSMSCode(params).then((res) => {
|
|
if (res && res.succeed) {
|
|
this.$refs.uToast.show({
|
|
title: "发送成功",
|
|
type: "success",
|
|
});
|
|
this.startCountdown();
|
|
} else {
|
|
this.$refs.uToast.show({
|
|
title: res?.error || "发送失败",
|
|
type: "error",
|
|
});
|
|
this.refreshCaptcha();
|
|
}
|
|
});
|
|
},
|
|
startCountdown() {
|
|
this.countdown = 60;
|
|
this.codeText = `${this.countdown}秒后重试`;
|
|
if (this.timer) {
|
|
clearInterval(this.timer);
|
|
}
|
|
this.timer = setInterval(() => {
|
|
this.countdown -= 1;
|
|
this.codeText = `${this.countdown}秒后重试`;
|
|
if (this.countdown <= 0) {
|
|
clearInterval(this.timer);
|
|
this.codeText = "获取验证码";
|
|
}
|
|
}, 1000);
|
|
},
|
|
validatePhone() {
|
|
if (!this.form.phone) {
|
|
this.$refs.uToast.show({
|
|
title: "请输入手机号",
|
|
type: "warning",
|
|
});
|
|
return false;
|
|
}
|
|
if (!/^1[3-9]\d{9}$/.test(this.form.phone)) {
|
|
this.$refs.uToast.show({
|
|
title: "手机号格式不正确",
|
|
type: "warning",
|
|
});
|
|
return false;
|
|
}
|
|
return true;
|
|
},
|
|
validateCaptcha() {
|
|
if (!this.form.captcha) {
|
|
this.$refs.uToast.show({
|
|
title: "请输入图形验证码",
|
|
type: "warning",
|
|
});
|
|
return false;
|
|
}
|
|
return true;
|
|
},
|
|
validateForm() {
|
|
if (!this.validatePhone()) return false;
|
|
if (!this.validateCaptcha()) return false;
|
|
if (!this.form.code) {
|
|
this.$refs.uToast.show({
|
|
title: "请输入验证码",
|
|
type: "warning",
|
|
});
|
|
return false;
|
|
}
|
|
if (!this.form.pwd) {
|
|
this.$refs.uToast.show({
|
|
title: "请输入新密码",
|
|
type: "warning",
|
|
});
|
|
return false;
|
|
}
|
|
if (!this.form.confirmPwd) {
|
|
this.$refs.uToast.show({
|
|
title: "请再次输入新密码",
|
|
type: "warning",
|
|
});
|
|
return false;
|
|
}
|
|
if (this.form.pwd !== this.form.confirmPwd) {
|
|
this.$refs.uToast.show({
|
|
title: "两次密码输入不一致",
|
|
type: "warning",
|
|
});
|
|
return false;
|
|
}
|
|
return true;
|
|
},
|
|
handleSubmit() {
|
|
if (!this.validateForm()) return;
|
|
const params = {
|
|
phone: this.form.phone,
|
|
code: this.form.code,
|
|
pwd: md5(this.form.pwd),
|
|
};
|
|
this.$u.api.ForgotPasswordChangePassword(params).then((res) => {
|
|
if (res && res.succeed) {
|
|
this.$refs.uToast.show({
|
|
title: "修改成功",
|
|
type: "success",
|
|
});
|
|
setTimeout(() => {
|
|
uni.navigateBack();
|
|
}, 800);
|
|
} else {
|
|
this.$refs.uToast.show({
|
|
title: res?.error || "修改失败",
|
|
type: "error",
|
|
});
|
|
}
|
|
});
|
|
},
|
|
},
|
|
};
|
|
</script>
|
|
|
|
<style scoped>
|
|
.change-password-page {
|
|
min-height: 100vh;
|
|
background-image: url("@/static/notes/bg.png");
|
|
background-position: center top;
|
|
background-repeat: no-repeat;
|
|
background-size: 100% auto;
|
|
display: flex;
|
|
flex-direction: column;
|
|
}
|
|
|
|
.content-wrapper {
|
|
flex: 1;
|
|
padding: 30rpx;
|
|
padding-top: 40rpx;
|
|
box-sizing: border-box;
|
|
}
|
|
|
|
.form-card {
|
|
background-color: #ffffff;
|
|
border-radius: 20rpx;
|
|
padding: 0 30rpx;
|
|
margin-bottom: 24rpx;
|
|
}
|
|
|
|
.form-row {
|
|
display: flex;
|
|
align-items: center;
|
|
padding: 28rpx 0;
|
|
/* border-bottom: 1rpx solid #f1f1f1; */
|
|
}
|
|
|
|
.form-row:last-child {
|
|
border-bottom: none;
|
|
}
|
|
|
|
.form-row.captcha-row {
|
|
align-items: center;
|
|
}
|
|
|
|
.label {
|
|
width: 150rpx;
|
|
font-weight: 500;
|
|
font-size: 27rpx;
|
|
color: #333333;
|
|
}
|
|
|
|
.input {
|
|
flex: 1;
|
|
font-size: 28rpx;
|
|
color: #333333;
|
|
text-align: right;
|
|
}
|
|
|
|
.get-code {
|
|
font-size: 26rpx;
|
|
color: #4f6aff;
|
|
padding-left: 16rpx;
|
|
border-left: 1rpx solid #e5e5e5;
|
|
margin-left: 16rpx;
|
|
}
|
|
|
|
.get-code.disabled {
|
|
color: #b8b8b8;
|
|
}
|
|
|
|
.captcha-image {
|
|
width: 180rpx;
|
|
height: 72rpx;
|
|
border-radius: 10rpx;
|
|
background-color: #f5f5f5;
|
|
margin-left: 16rpx;
|
|
}
|
|
|
|
.submit-button {
|
|
margin-top: 30rpx;
|
|
width: 100%;
|
|
height: 88rpx;
|
|
line-height: 88rpx;
|
|
background-color: #4f6aff;
|
|
color: #ffffff;
|
|
border-radius: 16rpx;
|
|
font-size: 30rpx;
|
|
font-weight: 600;
|
|
}
|
|
|
|
.single-row-card .form-row {
|
|
border-bottom: none;
|
|
}
|
|
|
|
.captcha-row .input {
|
|
text-align: left;
|
|
}
|
|
</style>
|