first commit

This commit is contained in:
PC-202306242200\Administrator
2026-03-28 23:10:55 +08:00
commit 1c24452b6c
1735 changed files with 150474 additions and 0 deletions

502
pages/login/login.vue Normal file
View File

@@ -0,0 +1,502 @@
<template>
<view class="login-container">
<!-- 背景图 -->
<image class="bg-image" src="/static/image/login.png" mode="aspectFill"></image>
<!-- 返回按钮 -->
<wd-navbar left-arrow custom-style="background-color: transparent !important;" safeAreaInsetTop @click-left="back"></wd-navbar>
<view class="content">
<!-- Logo -->
<view class="logo-container">你好</view>
<!-- 欢迎文字 -->
<view class="welcome-text">
<view>欢迎来到</view>
<view class="welcome-tag">苗草古方</view>
</view>
<!-- Tab切换 -->
<view class="tabs" v-if="type == 'login'">
<view class="tab-item" :class="{ active: activeTab === 'password' }" @click="switchTabs('password')">
<text>密码登录</text>
<view class="underline" v-if="activeTab === 'password'"></view>
</view>
<view class="tab-item" :class="{ active: activeTab === 'code' }" @click="switchTabs('code')">
<text>验证码登录</text>
<view class="underline" v-if="activeTab === 'code'"></view>
</view>
</view>
<!-- 表单 -->
<view class="form-container">
<!-- 登录 -->
<view v-if="type == 'login'">
<view class="input-item">
<input
placeholder="请输入用户名"
style="font-weight: 600; font-size: 36rpx"
v-model="formData.mobile"
placeholder-style="color: #999999;font-size: 28rpx;font-weight: 400 !important;"
type="number"
/>
</view>
<view class="input-item" v-if="activeTab === 'password'">
<input placeholder="请输入密码" v-model="formData.password" password placeholder-style="color: #999999;;font-size: 28rpx;" />
</view>
<view class="input-item code-input" v-else>
<input placeholder="请输入验证码" v-model="formData.code" placeholder-style="color: #999999;;font-size: 28rpx;" />
<view class="get-code" @click="getCode(1)">{{ current.seconds || codeIngo }}</view>
</view>
</view>
<!-- 注册 -->
<view v-if="type == 'register'">
<view class="input-item">
<input
placeholder="请输入用户名"
type="number"
style="font-weight: 600; font-size: 36rpx"
v-model="registerInfo.mobile"
placeholder-style="color: #999999;font-size: 28rpx;font-weight: 400 !important;"
/>
</view>
<view class="input-item code-input">
<input placeholder="请输入验证码" v-model="registerInfo.code" placeholder-style="color: #999999;;font-size: 28rpx;" />
<view class="get-code" @click="getCode(2)">{{ current.seconds || codeIngo }}</view>
</view>
<view class="input-item">
<input placeholder="请输入您的密码" v-model="registerInfo.password" password placeholder-style="color: #999999;;font-size: 28rpx;" />
</view>
<view class="input-item">
<input placeholder="请再次输入您的密码" v-model="registerInfo.passwordNew" password placeholder-style="color: #999999;;font-size: 28rpx;" />
</view>
<view class="input-item">
<input placeholder="请输入邀请码(非必填)" v-model="registerInfo.inviteCode" placeholder-style="color: #999999;;font-size: 28rpx;" />
</view>
</view>
<!-- 注册链接 -->
<view class="register-text" @click="type = 'login'" v-if="type == 'register'">
<text>已有账号</text>
<text class="register-link">立即登录</text>
</view>
<!-- 登录链接 -->
<view class="register-text" @click="type = 'register'" v-if="type == 'login'">
<text>还没有账号</text>
<text class="register-link">立即注册</text>
</view>
<!-- 登录按钮 -->
<button class="login-btn" :loading="submitLoading" :disabled="submitLoading" @click="login">
{{ type == 'register' ? '注册' : '登录' }}
</button>
<!-- 底部声明 -->
<!-- <view class="agreement" v-if="type == 'login'">
<text>登录即表示接受</text>
<navigator url="/pages/protocol/protocol" class="agreement-link">版权声明</navigator>
<text></text>
<navigator url="/pages/protocol/protocol" class="agreement-link">隐私保护</navigator>
</view> -->
</view>
</view>
</view>
</template>
<script setup lang="ts">
import { ref } from 'vue';
import api from '@/api/index';
import { toast } from '@/utils/fun.js';
import { useCountDown } from '@/uni_modules/wot-design-uni';
import { Store } from '@/store';
import { onLoad } from '@dcloudio/uni-app';
const store = Store();
const { start, pause, reset, current } = useCountDown({
time: 60 * 1000,
onChange(current) {},
onFinish() {
codeIngo.value = '重新发送';
}
});
const initialRegisterInfo = {
mobile: '',
password: '',
code: '',
inviteCode: '',
passwordNew: ''
};
const registerInfo = ref({ ...initialRegisterInfo });
onLoad(() => {
if (uni.getStorageSync('inviteCode')) {
registerInfo.value.inviteCode = uni.getStorageSync('inviteCode');
console.log(registerInfo.value.inviteCode);
}else{
console.log('未取到邀请码');
}
});
const resetRegisterInfo = () => {
registerInfo.value = { ...initialRegisterInfo };
};
const type = ref('login');
const codeIngo = ref('点击获取验证码');
// 定义当前激活的tab
const activeTab = ref('password');
const formData = ref({
mobile: '',
password: '',
code: ''
});
const submitLoading = ref(false);
// 返回上一页
const back = () => {
uni.navigateBack();
};
const switchTabs = (v) => {
activeTab.value = v;
formData.value = {};
};
// 获取验证码方法
const getCode = (e) => {
if (!formData.value.mobile && e == 1) {
toast('请输入手机号');
return;
}
if (!registerInfo.value.mobile && e == 2) {
toast('请输入手机号');
return;
}
if (current.value.seconds) {
toast('请等待倒计时结束');
return;
}
api.smsCode({
mobile: e == 2 ? registerInfo.value.mobile : formData.value.mobile,
scene: 1
})
.then((res) => {
start();
toast('验证码发送成功');
})
.catch((err) => {
console.log(err);
toast('验证码发送失败');
});
};
// 登录方法
const login = () => {
// 注册
if (type.value == 'register') {
if (!registerInfo.value.mobile) return toast('请输入手机号码');
if (!registerInfo.value.code) return toast('请输入验证码');
if (!registerInfo.value.password) return toast('请输入密码');
if (!registerInfo.value.passwordNew) return toast('请再次输入密码');
if (registerInfo.value.password != registerInfo.value.passwordNew) return toast('两次密码输入不一致');
// if (!registerInfo.value.inviteCode) return toast('请输入邀请码');
api.registerApi(registerInfo.value).then((res) => {
uni.showModal({
title: '提示',
content: '注册成功',
showCancel: false,
success: (res) => {
type.value = 'login';
resetRegisterInfo();
}
});
});
} else {
if (!formData.value.mobile) return toast('请输入手机号码');
if (activeTab.value === 'password') {
if (!formData.value.password) return toast('请输入登录密码');
api.loginApi(formData.value).then((res: any) => {
uni.setStorageSync('Authorization', res.accessToken);
store.setUserId(res.userId);
store.usersGetInfo();
back();
});
} else {
if (!formData.value.code) return toast('请输入验证码');
api.smsLoginApi(formData.value).then((res: any) => {
uni.setStorageSync('Authorization', res.accessToken);
store.setUserId(res.userId);
store.usersGetInfo();
back();
});
}
}
// if (activeTab.value === 'code') {
// if (!formData.value?.phone) {
// uni.showToast({
// title: '请输入手机号',
// icon: 'none'
// });
// return;
// }
// if (!formData.value?.code) {
// uni.showToast({
// title: '请输入验证码',
// icon: 'none'
// });
// return;
// }
// } else {
// if (!formData.value?.mobile) {
// uni.showToast({
// title: '请输入用户名',
// icon: 'none'
// });
// return;
// }
// if (!formData.value?.password) {
// uni.showToast({
// title: '请输入密码',
// icon: 'none'
// });
// return;
// }
// }
// submitLoading.value = true;
// uni.showLoading({
// title: '登录中...'
// });
// wx.login({
// success(loginRes) {
// if (loginRes.code) {
// //发起网络请求
// formData.value.socialCode = loginRes.code;
// // formData.value.socialState = ""
// loginApi({ ...formData.value })
// .then((res) => {
// if (res?.accessToken) {
// uni.hideLoading();
// store.commit('setToken', res.accessToken);
// getUser()
// .then((resUser) => {
// uni.hideLoading();
// store.commit('setUserInfo', { id: res.userId, ...resUser });
// // uni.switchTab({ url: "/pages/mine/mine" })
// navigateBackOrUrl('/pages/mine/mine', true);
// submitLoading.value = false;
// uni.showToast({
// title: '登录成功',
// icon: 'success'
// });
// })
// .catch((err) => {
// uni.showToast({
// title: '获取用户信息失败',
// icon: 'none'
// });
// uni.hideLoading();
// submitLoading.value = false;
// });
// } else {
// uni.showToast({
// title: '登录失败',
// icon: 'none'
// });
// uni.hideLoading();
// submitLoading.value = false;
// }
// })
// .catch((err) => {
// uni.hideLoading();
// submitLoading.value = false;
// });
// } else {
// console.log('登录失败!' + loginRes.errMsg);
// }
// },
// fail(err) {
// console.log('wx.login err', err);
// }
// });
};
// 跳转到注册页
const toRegister = () => {
uni.navigateTo({
url: '/pages/login/register'
});
};
</script>
<style lang="scss" scoped>
.login-container {
position: relative;
width: 100%;
height: 100vh;
}
.bg-image {
position: fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
z-index: -1;
}
.back-btn {
position: absolute;
top: 100rpx;
left: 40rpx;
width: 40rpx;
height: 40rpx;
z-index: 10;
}
.content {
padding: 0 65rpx;
margin-top: 180rpx;
position: absolute;
}
.logo-container {
margin-bottom: 8rpx;
font-weight: bold;
font-size: 44rpx;
color: #232323;
}
.logo {
width: 180rpx;
height: 180rpx;
}
.welcome-text {
font-weight: bold;
font-size: 44rpx;
color: #232323;
text-align: center;
margin-bottom: 60rpx;
display: flex;
align-items: flex-end;
}
.welcome-tag {
color: #5d7a4e;
margin-left: 12rpx;
font-size: 44rpx;
}
.tabs {
display: flex;
margin-bottom: 40rpx;
}
.tab-item {
position: relative;
margin-right: 60rpx;
// padding-bottom: 20rpx;
}
.tab-item text {
font-weight: bold;
font-size: 28rpx;
}
.tab-item.active text {
color: #232323;
}
.tab-item:not(.active) text {
color: #999999;
}
.underline {
width: 104rpx;
height: 4rpx;
background: #5d7a4e;
border-radius: 170rpx;
}
.form-container {
width: 100%;
}
.input-item {
width: 620rpx;
height: 90rpx;
background: #ffffff;
border-radius: 14rpx;
border: 2rpx solid #f6f6f6;
margin-bottom: 30rpx;
padding: 0 30rpx;
display: flex;
align-items: center;
}
.input-item input {
width: 100%;
height: 100%;
font-size: 28rpx;
color: #333333;
}
.code-input {
input {
flex: 1;
}
.get-code {
font-size: 24rpx;
color: #8e8e8e;
margin-left: 20rpx;
}
}
.register-text {
display: flex;
margin-bottom: 210rpx;
font-size: 26rpx;
color: #232323;
}
.register-link {
color: #5d7a4e;
margin-left: 10rpx;
}
.login-btn {
width: 474rpx;
height: 78rpx;
line-height: 78rpx;
border-radius: 39rpx;
text-align: center;
color: #fff !important;
font-size: 28rpx;
margin: 0 auto;
margin-bottom: 40rpx;
background: #5d7a4e !important;
&::after {
border: none;
}
}
.agreement {
display: flex;
justify-content: center;
font-size: 24rpx;
color: #999999;
}
.agreement-link {
color: #5d7a4e;
margin: 0 10rpx;
}
</style>