iOS remote support: Share Screen -> Connect Screen over LiveKit (core)
Rebuild the iOS remote-support screen share the RIGHT way: keep the exact Share/Connect UX + session (consent + symmetric session-ended), swap only the media to LiveKit since WKWebView can't getDisplayMedia. (Replaces the earlier "route to a meeting" detour, which was reverted.) Flow: customer taps Share Screen -> gets a 6-digit code (unchanged UI) -> helper enters it in Connect Screen -> on the customer's "Allow", the app publishes the screen natively (ReplayKit -> LiveKit) into a per-session room and tells the agent it's a LiveKit session -> connect.html joins that room and shows the screen in its existing viewer (recording/controls intact). Chat runs over the session socket (no P2P data channel in this mode). Either side ending fires the existing session-ended -> both tear down (symmetric disconnect). - signaling.js: relay 'rs-livekit' + 'rs-chat' between the two ends. - home.html: parent bridge so the /share iframe can drive startMeetingScreenShare/ stop on the native plugin (+ a capability handshake). - share.html (iOS): publish via native LiveKit instead of getDisplayMedia; chat over WS; hide mic (voice = next iteration) + remote-control (impossible on iOS). - connect.html: LiveKit viewer for iOS-shared sessions, reusing the P2P viewer. Web-only, no new build (reuses the shipped startMeetingScreenShare). Desktop Share/Connect P2P unchanged. Two-way voice is the planned follow-up. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -6587,6 +6587,12 @@ async function doRegister(){
|
||||
window.addEventListener('message',(e)=>{
|
||||
if(e.origin!==location.origin) return; const d=e.data||{}; const n=window.bizConnectNative;
|
||||
if(d.type==='rc-ping'){ const desktop=!!(n&&n.rcAvailable&&n.rcAvailable()); try{ e.source&&e.source.postMessage({type:'rc-pong', desktop}, location.origin); }catch(_){} return; }
|
||||
// iOS remote-support: the /share iframe can't reach the native plugin, so it asks THIS top frame to
|
||||
// publish the screen over LiveKit (WKWebView can't getDisplayMedia). Answer the capability handshake and
|
||||
// drive startMeetingScreenShare/stopMeetingScreenShare (the same native method meetings use).
|
||||
if(d.type==='bzc-native-ping'){ const ok=bzIsIOS() && !!(nativeCallPlugin() && nativeCallPlugin().startMeetingScreenShare); try{ e.source&&e.source.postMessage({type:'bzc-native', ok}, location.origin); }catch(_){} return; }
|
||||
if(d.type==='rs-native-share'){ (async()=>{ try{ const NC=nativeCallPlugin(); if(!NC||!NC.startMeetingScreenShare||!d.room) return; const tk=await postJSON('/api/meetings/token',{ room:d.room, screen:true }); await NC.startMeetingScreenShare({ url:(tk.url||SFU.url), token:tk.token }); }catch(_){} })(); return; }
|
||||
if(d.type==='rs-native-stop'){ try{ const NC=nativeCallPlugin(); if(NC&&NC.stopMeetingScreenShare) NC.stopMeetingScreenShare(); }catch(_){} return; }
|
||||
if(!n) return;
|
||||
if(d.type==='rc-arm'){ try{ n.rcArm&&n.rcArm(!!d.on); }catch(_){} return; }
|
||||
if(d.type==='rc-input'){ try{ n.rcInput&&n.rcInput(d.evt); }catch(_){} return; }
|
||||
|
||||
Reference in New Issue
Block a user