电话咨询
This commit is contained in:
@@ -16,7 +16,15 @@
|
|||||||
-->
|
-->
|
||||||
<template>
|
<template>
|
||||||
<view v-if="initializing || autoJoin" class="auto-join-page">
|
<view v-if="initializing || autoJoin" class="auto-join-page">
|
||||||
<text class="auto-join-title">正在进入会议…</text>
|
<template v-if="autoJoinError">
|
||||||
|
<text class="auto-join-error-title">进入会议失败</text>
|
||||||
|
<text class="auto-join-error-msg">{{ autoJoinError }}</text>
|
||||||
|
<view class="auto-join-actions">
|
||||||
|
<button class="aj-btn aj-btn-primary" @click="retryAutoJoin">重试</button>
|
||||||
|
<button class="aj-btn aj-btn-secondary" @click="exitAutoJoin">返回</button>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
|
<text v-else class="auto-join-title">正在进入会议…</text>
|
||||||
</view>
|
</view>
|
||||||
<view v-else class="page">
|
<view v-else class="page">
|
||||||
<view class="container">
|
<view class="container">
|
||||||
@@ -116,6 +124,9 @@ const joinCode = ref('')
|
|||||||
const joinPassword = ref('')
|
const joinPassword = ref('')
|
||||||
const autoJoin = ref(false)
|
const autoJoin = ref(false)
|
||||||
const initializing = ref(true)
|
const initializing = ref(true)
|
||||||
|
// autoJoin 失败/超时的可见错误(替代无限"正在进入会议…"转圈)
|
||||||
|
const autoJoinError = ref('')
|
||||||
|
let autoJoinWatchdog = null
|
||||||
|
|
||||||
const modeLabel = computed(() => mode.value === 'create' ? '即将创建新会议' : `即将加入会议 ${joinCode.value}`)
|
const modeLabel = computed(() => mode.value === 'create' ? '即将创建新会议' : `即将加入会议 ${joinCode.value}`)
|
||||||
|
|
||||||
@@ -363,6 +374,42 @@ const onCancel = () => {
|
|||||||
uni.navigateBack()
|
uni.navigateBack()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// autoJoin 看门狗:若 15s 内既没进房也没报错(多见于 WS 连不上 / mediasoup 传输 ICE 不通而无限等待),
|
||||||
|
// 主动把无限转圈切换成可见的超时错误,便于真机定位与重试。
|
||||||
|
const startAutoJoinWatchdog = () => {
|
||||||
|
clearAutoJoinWatchdog()
|
||||||
|
autoJoinWatchdog = setTimeout(() => {
|
||||||
|
if (joining.value && !autoJoinError.value) {
|
||||||
|
autoJoinError.value = '连接会议服务器超时(15s)。可能是网络受限或会议服务(WebSocket/媒体通道)暂不可达,请重试或检查网络。'
|
||||||
|
}
|
||||||
|
}, 15000)
|
||||||
|
}
|
||||||
|
const clearAutoJoinWatchdog = () => {
|
||||||
|
if (autoJoinWatchdog) { clearTimeout(autoJoinWatchdog); autoJoinWatchdog = null }
|
||||||
|
}
|
||||||
|
|
||||||
|
const retryAutoJoin = () => {
|
||||||
|
autoJoinError.value = ''
|
||||||
|
joining.value = false
|
||||||
|
startAutoJoinWatchdog()
|
||||||
|
onJoin({ skipMedia: true })
|
||||||
|
}
|
||||||
|
|
||||||
|
const exitAutoJoin = () => {
|
||||||
|
clearAutoJoinWatchdog()
|
||||||
|
// 云律小程序 web-view 内:返回到小程序;否则回上一步
|
||||||
|
try {
|
||||||
|
const embedded = typeof window !== 'undefined' && window.sessionStorage
|
||||||
|
&& window.sessionStorage.getItem('echo_cloud_law_meeting_embed') === '1'
|
||||||
|
const mp = typeof window !== 'undefined' && window.wx && window.wx.miniProgram ? window.wx.miniProgram : null
|
||||||
|
if (embedded && mp && typeof mp.navigateBack === 'function') {
|
||||||
|
mp.navigateBack({ delta: 1 })
|
||||||
|
return
|
||||||
|
}
|
||||||
|
} catch (e) {}
|
||||||
|
onCancel()
|
||||||
|
}
|
||||||
|
|
||||||
const onJoin = async (options = {}) => {
|
const onJoin = async (options = {}) => {
|
||||||
if (joining.value || !canJoin.value) return
|
if (joining.value || !canJoin.value) return
|
||||||
joining.value = true
|
joining.value = true
|
||||||
@@ -423,12 +470,17 @@ const onJoin = async (options = {}) => {
|
|||||||
uni.redirectTo({ url: `/pages/meeting/room${roomCode ? `?code=${roomCode}` : ''}` })
|
uni.redirectTo({ url: `/pages/meeting/room${roomCode ? `?code=${roomCode}` : ''}` })
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
const msg = err?.message || JSON.stringify(err)
|
const msg = err?.message || JSON.stringify(err)
|
||||||
|
// autoJoin 模式下把错误显式呈现在页面(toast 一闪而过,真机很难看清)
|
||||||
|
if (autoJoin.value) {
|
||||||
|
autoJoinError.value = `加入失败:${msg}`
|
||||||
|
}
|
||||||
uni.showToast({ title: `加入失败:${msg}`, icon: 'none', duration: 3500 })
|
uni.showToast({ title: `加入失败:${msg}`, icon: 'none', duration: 3500 })
|
||||||
console.error('[Preview] 加入会议失败', err)
|
console.error('[Preview] 加入会议失败', err)
|
||||||
// 入会失败:track 尚未转给 mediasoup 或刚拿到就失败,显式 stop 避免摄像头泄漏
|
// 入会失败:track 尚未转给 mediasoup 或刚拿到就失败,显式 stop 避免摄像头泄漏
|
||||||
try { audioTrack && audioTrack.stop && audioTrack.stop() } catch {}
|
try { audioTrack && audioTrack.stop && audioTrack.stop() } catch {}
|
||||||
try { videoTrack && videoTrack.stop && videoTrack.stop() } catch {}
|
try { videoTrack && videoTrack.stop && videoTrack.stop() } catch {}
|
||||||
} finally {
|
} finally {
|
||||||
|
clearAutoJoinWatchdog()
|
||||||
joining.value = false
|
joining.value = false
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -466,6 +518,7 @@ onLoad(async (query) => {
|
|||||||
hasPermission: hasPermission.value,
|
hasPermission: hasPermission.value,
|
||||||
permissionError: permissionError.value
|
permissionError: permissionError.value
|
||||||
})
|
})
|
||||||
|
startAutoJoinWatchdog()
|
||||||
onJoin({ skipMedia: true })
|
onJoin({ skipMedia: true })
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@@ -489,6 +542,7 @@ onBeforeUnmount(() => {
|
|||||||
clearTimeout(changeDebounceTimer)
|
clearTimeout(changeDebounceTimer)
|
||||||
changeDebounceTimer = null
|
changeDebounceTimer = null
|
||||||
}
|
}
|
||||||
|
clearAutoJoinWatchdog()
|
||||||
stopPreviewStream()
|
stopPreviewStream()
|
||||||
stopAudioMeter()
|
stopAudioMeter()
|
||||||
})
|
})
|
||||||
@@ -499,13 +553,50 @@ onBeforeUnmount(() => {
|
|||||||
min-height: 100vh;
|
min-height: 100vh;
|
||||||
background: #F8FAFC;
|
background: #F8FAFC;
|
||||||
display: flex;
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
justify-content: center;
|
justify-content: center;
|
||||||
|
padding: 0 48rpx;
|
||||||
}
|
}
|
||||||
.auto-join-title {
|
.auto-join-title {
|
||||||
font-size: 30rpx;
|
font-size: 30rpx;
|
||||||
color: #475569;
|
color: #475569;
|
||||||
}
|
}
|
||||||
|
.auto-join-error-title {
|
||||||
|
font-size: 34rpx;
|
||||||
|
font-weight: 600;
|
||||||
|
color: #DC2626;
|
||||||
|
margin-bottom: 20rpx;
|
||||||
|
}
|
||||||
|
.auto-join-error-msg {
|
||||||
|
font-size: 26rpx;
|
||||||
|
line-height: 40rpx;
|
||||||
|
color: #475569;
|
||||||
|
text-align: center;
|
||||||
|
margin-bottom: 40rpx;
|
||||||
|
word-break: break-all;
|
||||||
|
}
|
||||||
|
.auto-join-actions {
|
||||||
|
display: flex;
|
||||||
|
gap: 24rpx;
|
||||||
|
}
|
||||||
|
.aj-btn {
|
||||||
|
min-width: 200rpx;
|
||||||
|
height: 80rpx;
|
||||||
|
line-height: 80rpx;
|
||||||
|
border-radius: 16rpx;
|
||||||
|
font-size: 28rpx;
|
||||||
|
text-align: center;
|
||||||
|
border: none;
|
||||||
|
}
|
||||||
|
.aj-btn-primary {
|
||||||
|
background: #3B82F6;
|
||||||
|
color: #FFFFFF;
|
||||||
|
}
|
||||||
|
.aj-btn-secondary {
|
||||||
|
background: #E2E8F0;
|
||||||
|
color: #334155;
|
||||||
|
}
|
||||||
.page { min-height: 100vh; background: #F8FAFC; padding: 24rpx; }
|
.page { min-height: 100vh; background: #F8FAFC; padding: 24rpx; }
|
||||||
.container { max-width: 960rpx; margin: 0 auto; }
|
.container { max-width: 960rpx; margin: 0 auto; }
|
||||||
.title { font-size: 40rpx; font-weight: 600; color: #0F172A; display: block; margin: 24rpx 0 8rpx; }
|
.title { font-size: 40rpx; font-weight: 600; color: #0F172A; display: block; margin: 24rpx 0 8rpx; }
|
||||||
|
|||||||
Reference in New Issue
Block a user