Files
lanecarford_front/src/views/login/components/GoogleLogin.vue
2025-11-05 10:39:35 +08:00

157 lines
3.5 KiB
Vue

<template>
<div class="Container">
<div class="g_id_signin" id="g_id_signin"></div>
<div class="icon">
<img :src="google" class="google-icon" />
<span>{{ text }}</span>
</div>
</div>
</template>
<script setup lang="ts">
import { reactive, onMounted, onBeforeUnmount } from 'vue'
import { google } from '@/assets/base64'
// 定义 props
defineProps({
text: {
type: String,
default: 'Sign in with Google'
}
})
// 定义 emits
const emit = defineEmits<{
(e: 'googelLogin', code: string): void
}>()
// 处理 Google 登录回调
const handleCredentialResponse = async (response: { credential: string }) => {
const code = response.credential
emit('googelLogin', code)
window.isAddGmail = false
}
// 配置数据
const data = reactive({
// scriptSrc:'https://apis.google.com/js/platform.js',
scriptSrc: 'https://accounts.google.com/gsi/client',
script: null
})
// 根据环境设置 Google Client ID
const GOOGLE_CLIENT_ID = '216037134725-7q8vqp0ohtmohlosltkfg7bd2v29rm5a.apps.googleusercontent.com'
// 创建 Gmail 登录
const createGmailLogin = async () => {
const existingScript = document.querySelector(`script[src="${data.scriptSrc}"]`)
if (!window.isAddGmail) {
if (!existingScript) {
window.isAddGmail = true
await new Promise<void>((resolve) => {
const script = document.createElement('script')
script.onload = () => {
resolve()
}
document.body.appendChild(script)
script.src = data.scriptSrc
})
}
window.google.accounts.id.initialize({
// 主要就是填写client_id
client_id: GOOGLE_CLIENT_ID,
auto_select: false,
callback: handleCredentialResponse,
// context:"signin",
ux_mode: 'popup',
itp_support: true
})
console.log('创建谷歌登录按钮:', document.querySelector('.Container #g_id_signin'))
window.google.accounts.id.renderButton(document.querySelector('.Container #g_id_signin'), {
type: 'standard', //icon为只有一个icon
shape: 'circle',
theme: 'outline',
size: 'large',
logo_alignment: 'center'
})
}
}
onBeforeUnmount(() => {
const existingScript = document.querySelector(`script[src="${data.scriptSrc}"]`)
if (existingScript) {
existingScript.remove()
window.isAddGmail = false
}
})
onMounted(() => {
createGmailLogin()
})
</script>
<style scoped lang="less">
.Container {
width: 100%;
height: 10.6rem;
padding: 1.6rem;
border: 0.2rem solid #fff;
border-radius: 7rem;
font-size: 3.83rem;
cursor: pointer;
display: flex;
align-items: center;
justify-content: center;
column-gap: 3.1rem;
margin-bottom: 1.67rem;
:deep(.nsm7Bb-HzV7m-LgbsSe-bN97Pc-sM5MNb) {
justify-content: center;
.nsm7Bb-HzV7m-LgbsSe-Bz112c {
padding: 0;
}
}
:deep(.nsm7Bb-HzV7m-LgbsSe.JGcpL-RbRzK) {
width: 100%;
height: 10.6rem;
}
.icon {
width: auto;
display: flex;
align-items: center;
justify-content: center;
border-radius: 4rem;
padding: 1.3rem 4.6rem;
cursor: pointer;
box-sizing: border-box;
position: relative;
background: transparent;
pointer-events: none;
column-gap: 3.1rem;
}
.g_id_signin {
position: absolute;
width: 100%;
height: 100%;
top: 0;
left: 0;
opacity: 0;
:deep(.S9gUrf-YoZ4jf) {
&,
& > div {
width: 100%;
height: 100%;
}
iframe {
zoom: 3;
}
}
}
}
.google-icon {
width: 4.8rem;
height: 4.8rem;
}
</style>