4c682e873f79d56632de723aebf81efdf90df38d..450dc8a1e4e0d643817ffd0eee04b938cc84af74
2025-11-07 张含笑
feat:修改密码成功清除记住密码
450dc8 diff | tree
2025-11-07 张含笑
feat:记住密码
01ebf3 diff | tree
2 files modified
240 ■■■■■ changed files
src/pages/login/index.vue 64 ●●●● patch | view | raw | blame | history
src/subPackages/userDetail/password/index.vue 176 ●●●● patch | view | raw | blame | history
src/pages/login/index.vue
@@ -6,17 +6,24 @@
        <div class="user-name">
            <image :src="usernameSvg" />
            <input v-model="loginForm.username" placeholder="请输入用户名" />
        </div>
        <div class="pass-word">
            <image :src="passwordSvg" />
            <input v-model="loginForm.password" type="password" placeholder="请输入密码" />
        </div>
        <div class="remember-password">
            <label>
                <checkbox-group @change="toggleRemember">
                    <checkbox :checked="rememberPassword" color="#1D6FE9" style="transform:scale(0.7)" />
                </checkbox-group>
                记住密码
            </label>
        </div>
        <button class="login-btn" :style="[inputStyle]" @tap="submit">
            登录
        </button>
        <image class="lowerRightCorner" :src="droneSvg" />
    </view>
</template>
@@ -38,12 +45,14 @@
        LOGIN_PATH,
        removeQueryString
    } from "@/router";
    import { onMounted } from 'vue';
    const userStore = useUserStore();
    const loginForm = ref({
        username: "",
        password: "",
    });
    const rememberPassword = ref(false);
    const inputStyle = computed(() => {
        const style = {};
        if (loginForm.value.username && loginForm.value.password) {
@@ -53,6 +62,9 @@
        return style;
    });
    let redirect = HOME_PATH;
    function toggleRemember(e) {
        rememberPassword.value = e.detail.value.length > 0;
    }
    async function submit() {
        let userInfo = {
@@ -65,6 +77,16 @@
            code: "",
            key: "",
        };
        if (rememberPassword.value) {
            uni.setStorageSync('rememberedUser', {
                username: loginForm.value.username,
                password: loginForm.value.password
            });
        } else {
            uni.removeStorageSync('rememberedUser');
        }
        try {
            const res = await loginByUsername(
                userInfo.tenantId,
@@ -87,15 +109,24 @@
                icon: "none",
                duration: 2000
            });
        }
    }
    // 从本地存储加载记住的密码
    onMounted(() => {
        const savedUserInfo = uni.getStorageSync('rememberedUser');
        console.log('记住密码',savedUserInfo)
        if (savedUserInfo) {
            loginForm.value.username = savedUserInfo.username;
            loginForm.value.password = savedUserInfo.password;
            rememberPassword.value = true;
        }
    });
    onLoad((options) => {
        if (options.redirect && removeQueryString(options.redirect) !== LOGIN_PATH) {
            redirect = decodeURIComponent(options.redirect);
        }
    });
</script>
<style lang="scss" scoped>
@@ -164,13 +195,24 @@
                color: #E3E3E3;
                font-weight: 500;
            }
            //:deep(.uni-input-input) {
            //  top: 10px !important;
            //}
        }
        .pass-word {}
        .remember-password {
            display: flex;
            justify-content: flex-end;
            align-items: center;
            margin-left: 62rpx;
            margin-right: 58rpx;
            margin-top: 20rpx;
            color: #666;
            font-size: 28rpx;
            label {
                display: flex;
                align-items: center;
            }
        }
        input {
            @apply pb-6rpx mb-10rpx text-left;
@@ -178,7 +220,6 @@
        .tips {
            @apply mt-8rpx mb-60rpx;
            color: $u-info;
        }
@@ -199,7 +240,6 @@
        .alternative {
            @apply flex justify-between mt-30rpx;
            color: $u-tips-color;
        }
    }
@@ -209,14 +249,12 @@
        .item {
            @apply flex items-center flex-col text-28rpx;
            color: $u-content-color;
        }
    }
    .hint {
        @apply px-40rpx py-20rpx text-24rpx;
        color: $u-tips-color;
        .link {
src/subPackages/userDetail/password/index.vue
@@ -6,19 +6,16 @@
                <div class="orderRow">
                    <!-- type="password" :password-icon="passwordIcon" -->
                    <div class="rowTitle">原始密码</div>
                    <u-input input-align="right" v-model="passwordForm.oldPassword"   placeholder="请输入"
                        class="input-item" />
                    <input type="password" v-model="passwordForm.oldPassword" placeholder="请输入" class="input-item" />
                </div>
                <div class="orderRow">
                    <div class="rowTitle">新密码</div>
                    <u-input input-align="right" v-model="passwordForm.newPassword" placeholder="请输入"
                        class="input-item" />
                    <input type="password" v-model="passwordForm.newPassword" placeholder="请输入" class="input-item" />
                </div>
                <div class="orderRow">
                    <div class="rowTitle">确认密码</div>
                    <u-input input-align="right" v-model="passwordForm.newPassword1"  placeholder="请输入"
                        class="input-item" />
                    <input type="password" v-model="passwordForm.newPassword1" placeholder="请输入" class="input-item" />
                </div>
            </div>
        </view>
@@ -39,10 +36,10 @@
        updateInfo,
        updatePassword
    } from '@/api/user/index.js';
 const passwordIcon={
      show: 'fas fa-eye',     // 显示密码时的图标
      hide: 'fas fa-eye-slash' // 隐藏密码时的图标
    }
    const passwordIcon = {
        show: 'fas fa-eye', // 显示密码时的图标
        hide: 'fas fa-eye-slash' // 隐藏密码时的图标
    }
    const userStore = useUserStore();
    const passwordForm = ref({
        oldPassword: '',
@@ -51,36 +48,36 @@
    });
    // 校验密码不能包含中文
    const validatePasswordNoChinese = (password) => {
      const chineseRegex = /[\u4e00-\u9fa5]/;
      if (chineseRegex.test(password)) {
        const chineseRegex = /[\u4e00-\u9fa5]/;
        if (chineseRegex.test(password)) {
        uni.showToast({
            title: '密码不能包含中文字符',
            icon: 'none',
            duration: 2000
        });
        return false;
      }
      return true;
            uni.showToast({
                title: '密码不能包含中文字符',
                icon: 'none',
                duration: 2000
            });
            return false;
        }
        return true;
    };
    // 校验密码复杂度(长度≥6位,包含字母和数字)
    const validatePasswordStrength = (password) => {
      if (password.length < 6) {
        if (password.length < 6) {
        uni.showToast({
            title: '密码长度不能少于6位',
            icon: 'none',
            duration: 2000
        });
        return false;
      }
      // const hasLetter = /[a-zA-Z]/.test(password);
      // const hasNumber = /\d/.test(password);
      // if (!hasLetter || !hasNumber) {
      //   ElMessage.error('密码需同时包含字母和数字');
      //   return false;
      // }
      return true;
            uni.showToast({
                title: '密码长度不能少于6位',
                icon: 'none',
                duration: 2000
            });
            return false;
        }
        // const hasLetter = /[a-zA-Z]/.test(password);
        // const hasNumber = /\d/.test(password);
        // if (!hasLetter || !hasNumber) {
        //   ElMessage.error('密码需同时包含字母和数字');
        //   return false;
        // }
        return true;
    };
    const clearForm = () => {
        passwordForm.value = {
@@ -93,41 +90,41 @@
        clearForm();
    };
    const submit = () => {
// 原始密码校验
    if (!passwordForm.value.oldPassword) {
        // 原始密码校验
        if (!passwordForm.value.oldPassword) {
      uni.showToast({
          title: '请输入原始密码',
          icon: 'none',
          duration: 2000
      });
      return;
    }
     // 中文校验
    if (!validatePasswordNoChinese(passwordForm.value.newPassword)) return;
    // 新密码校验
    if (!passwordForm.value.newPassword) {
            uni.showToast({
                title: '请输入原始密码',
                icon: 'none',
                duration: 2000
            });
            return;
        }
        // 中文校验
        if (!validatePasswordNoChinese(passwordForm.value.newPassword)) return;
        // 新密码校验
        if (!passwordForm.value.newPassword) {
      uni.showToast({
          title: '请输入新密码',
          icon: 'none',
          duration: 2000
      });
      return;
    }
    // 确认密码校验
    if (passwordForm.value.newPassword !== passwordForm.value.newPassword1) {
            uni.showToast({
                title: '请输入新密码',
                icon: 'none',
                duration: 2000
            });
            return;
        }
        // 确认密码校验
        if (passwordForm.value.newPassword !== passwordForm.value.newPassword1) {
      uni.showToast({
          title: '两次输入的新密码不一致',
          icon: 'none',
          duration: 2000
      });
      return;
    }
            uni.showToast({
                title: '两次输入的新密码不一致',
                icon: 'none',
                duration: 2000
            });
            return;
        }
    // 复杂度校验
    if (!validatePasswordStrength(passwordForm.value.newPassword)) return;
        // 复杂度校验
        if (!validatePasswordStrength(passwordForm.value.newPassword)) return;
        updatePassword(md5(passwordForm.value.oldPassword),
            md5(passwordForm.value.newPassword),
            md5(passwordForm.value.newPassword1)).then(res => {
@@ -139,6 +136,7 @@
                });
                clearForm();
                userStore.setUserInfo(null)
                uni.removeStorageSync('rememberedUser');
                uni.reLaunch({
                    url: '/pages/login/index'
                })
@@ -170,22 +168,24 @@
    .detailBox {
        margin-top: 40rpx;
    width: 702rpx;
        width: 702rpx;
        min-height: 326rpx;
        background: #FFFFFF;
        border-radius: 12rpx;
        box-shadow: 0 4rpx 20rpx rgba(0, 0, 0, 0.05);
.detailCon {
        .detailCon {
            padding: 0 24rpx;
        }
        .orderRow {
        display: flex;
        justify-content: space-between;
        align-items: center;
        height: 96rpx;
        border-bottom: 2rpx solid #f5f5f5;
        color: #7b7b7b;
            display: flex;
            justify-content: space-between;
            align-items: center;
            height: 96rpx;
            border-bottom: 2rpx solid #f5f5f5;
            color: #7b7b7b;
            .rowTitle {
@@ -195,28 +195,36 @@
                color: #222324;
                white-space: nowrap;
            }
            ::v-deep .u-input {
                border: none !important;
                background: transparent !important;
            }
            ::v-deep .u-input__input {
            input.input-item {
                text-align: right;
                border: none !important;
                box-shadow: none !important;
                background: transparent !important;
                box-shadow: none !important;
                padding: 0 !important;
                margin: 0 !important;
                height: auto !important;
                outline: none;
                font-size: 30rpx;
                color: #222324;
                font-family: Source Han Sans CN, Source Han Sans CN;
            }
            input.input-item::placeholder {
                color: #c9c9c9;
                font-size: 30rpx;
            }
        }
    }
.btngroup {
    .btngroup {
        display: flex;
        position: absolute;
        bottom:150rpx;
        bottom: 150rpx;
    }
    .u-button:first-child{
    .u-button:first-child {
        margin-right: 30rpx;
    }
@@ -224,4 +232,4 @@
        width: 276rpx;
        height: 76rpx;
    }
</style>
</style>