feat: 添加微信扫码登录功能

This commit is contained in:
wangqiao
2025-10-13 23:03:55 +08:00
parent 3f3ea878b9
commit 5baae7652f
5 changed files with 229 additions and 2 deletions

View File

@ -0,0 +1,156 @@
<template>
<div class="auth-success-container">
<!-- 顶部成功图标 -->
<div class="success-icon">
<svg width="80" height="80" viewBox="0 0 80 80" fill="none" xmlns="http://www.w3.org/2000/svg">
<circle cx="40" cy="40" r="40" fill="#4CD964" />
<path d="M25 40L35 50L55 30" stroke="white" stroke-width="4" stroke-linecap="round" stroke-linejoin="round" />
</svg>
</div>
<!-- 标题和描述 -->
<div class="text-content">
<h1 class="title">授权成功</h1>
<p class="desc">
您已完成微信授权<br />
请返回电脑端继续操作
</p>
</div>
<!-- 倒计时提示 -->
<!-- <div class="countdown" v-if="countdown > 0">
<p>页面将在 {{ countdown }} 秒后自动关闭</p>
</div> -->
<!-- 底部按钮 -->
<!-- <div class="btn-group">
<button class="close-btn" @click="closePage">立即关闭</button>
</div> -->
</div>
</template>
<script setup lang="ts">
definePageMeta({
layout: 'success',
})
import { ref, onMounted } from 'vue'
// 倒计时秒数
const countdown = ref(5)
onMounted(() => {
// 启动倒计时
const timer = setInterval(() => {
countdown.value--
if (countdown.value <= 0) {
clearInterval(timer)
// 倒计时结束后尝试关闭页面(微信环境可能限制,仅作尝试)
closePage()
}
}, 1000)
})
// 关闭页面方法(微信环境中可能无法直接关闭,仅作提示)
const closePage = () => {
// 尝试关闭当前页面(部分浏览器支持)
if (window.close) {
window.close()
} else {
// 微信环境中提示用户手动关闭
alert('请手动关闭此页面,返回电脑端继续操作')
}
}
</script>
<style scoped>
.auth-success-container {
min-height: 100vh;
box-sizing: border-box;
padding: 20px;
background-color: #f5f7fa;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
}
.success-icon {
margin-bottom: 30px;
animation: pop 0.5s ease-out;
}
@keyframes pop {
0% {
transform: scale(0.8);
opacity: 0;
}
70% {
transform: scale(1.1);
}
100% {
transform: scale(1);
opacity: 1;
}
}
.text-content {
text-align: center;
margin-bottom: 40px;
}
.title {
font-size: 24px;
font-weight: 600;
color: #333;
margin: 0 0 15px 0;
}
.desc {
font-size: 16px;
color: #666;
line-height: 1.6;
margin: 0;
}
.countdown {
margin-bottom: 50px;
color: #999;
font-size: 14px;
}
.btn-group {
width: 100%;
max-width: 300px;
}
.close-btn {
width: 100%;
height: 48px;
background-color: #07c160;
color: white;
border: none;
border-radius: 24px;
font-size: 16px;
font-weight: 500;
cursor: pointer;
transition: background-color 0.3s;
}
.close-btn:hover {
background-color: #06b355;
}
/* 适配小屏手机 */
@media (max-width: 320px) {
.title {
font-size: 22px;
}
.desc {
font-size: 15px;
}
.close-btn {
height: 44px;
font-size: 15px;
}
}
</style>

View File

@ -64,7 +64,7 @@
</div>
<div v-if="!isLogin" class="mt-[30px] flex justify-between px-[20px]">
<img src="~/assets/images/qq-v2.png" alt="QQ登录" class="social-icon" @click="handleLoginQQ" />
<img src="~/assets/images/weixin-v2.png" alt="微信登录" class="social-icon" @click="handleLoginWechat" />
<img src="~/assets/images/weixin-v2.png" alt="微信登录" class="social-icon" @click="handleLoginWechatV2" />
<img src="~/assets/images/email-v2.png" alt="邮箱登录" class="social-icon" @click="handleLoginEmail" />
<img src="~/assets/images/phone-v2.png" alt="手机登录" class="social-icon" @click="handleLoginPhone" />
</div>
@ -73,6 +73,9 @@
<img src="~/assets/images/sign.png" alt="签到奖励" class="bonus-image" />
</div>
</div>
<!-- wx二维码弹窗 -->
<wx v-model:visible="visible" v-model:qrcode="qrcode" />
</template>
<script setup lang="ts">
@ -80,7 +83,7 @@
import { getCurrentInstance, computed, watchEffect, ref } from 'vue'
import { handleLoginQQ, handleLoginWechat } from '~/utils/login'
import type { UserStatisticsCountRespVO } from '~/api/personal-center/types'
import { getUserStatistics } from '~/api/personal-center/index'
import { getUserStatistics, getLoginQrcode } from '~/api/personal-center/index'
import useUserStore from '~/stores/user'
const userStore = useUserStore()
const app = useNuxtApp()
@ -90,6 +93,18 @@
return !!userStore.token
})
// 打开微信二维码
const qrcode = ref<string>()
const visible = ref<boolean>(false)
const handleLoginWechatV2 = () => {
getLoginQrcode().then((res) => {
if (res.code === 0) {
visible.value = true
qrcode.value = res.data
}
})
}
// 获取用户统计信息
const userStaticInfo = ref<UserStatisticsCountRespVO>()
const fetchUserStatistics = async () => {