40 lines
1.1 KiB
Vue
40 lines
1.1 KiB
Vue
|
|
<script setup lang="ts">
|
|||
|
|
import { ref } from 'vue'
|
|||
|
|
import { api } from '../api'
|
|||
|
|
|
|||
|
|
const visible = ref(false)
|
|||
|
|
const qrCodeData = ref<{ url: string; qrCodeBase64: string } | null>(null)
|
|||
|
|
const error = ref('')
|
|||
|
|
|
|||
|
|
async function open() {
|
|||
|
|
try {
|
|||
|
|
error.value = ''
|
|||
|
|
qrCodeData.value = await api.qrCode()
|
|||
|
|
visible.value = true
|
|||
|
|
} catch (e) {
|
|||
|
|
error.value = e instanceof Error ? e.message : '加载失败'
|
|||
|
|
}
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
function close() {
|
|||
|
|
visible.value = false
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
defineExpose({ open })
|
|||
|
|
</script>
|
|||
|
|
|
|||
|
|
<template>
|
|||
|
|
<Teleport to="body">
|
|||
|
|
<div v-if="visible" class="qr-overlay" @click.self="close">
|
|||
|
|
<div class="qr-modal">
|
|||
|
|
<h2>扫码访问</h2>
|
|||
|
|
<p v-if="error" class="error-banner">{{ error }}</p>
|
|||
|
|
<img v-if="qrCodeData" :src="qrCodeData.qrCodeBase64" alt="QR Code" class="qr-image" />
|
|||
|
|
<p v-else-if="!error" class="qr-hint">加载中...</p>
|
|||
|
|
<p class="qr-hint">使用手机扫描二维码,即可在局域网中打开此网站</p>
|
|||
|
|
<button type="button" class="primary-button qr-close" @click="close">关闭</button>
|
|||
|
|
</div>
|
|||
|
|
</div>
|
|||
|
|
</Teleport>
|
|||
|
|
</template>
|