Overview
Sharing in a meeting comes in two types, distinguished byShareType:
Only one member in a meeting can share at a time. To find out who is sharing, read
RoomInfo.shareUid; for the current sharing type, read RoomInfo.shareState.
On iOS, screen sharing has two capture paths that capture completely different scopes. Decide which one you need before integrating:
macOS has only one path:
requestShare() captures the whole screen / a specified window.
Start sharing
Default capture
requestShare(shareType: .screen, preset: .h1080p), and on macOS it captures the main display. preset takes values from SRTC’s ScreenPreset: .h720p, .h1080p (default).
macOS: let the user choose a display or window
macOS 12.3 and later support specifying the capture source. Your app enumerates the sources first, shows a selection UI, and then passes in the source the user chose:source accepts a DisplaySource (display) or a WindowSource (app window).
The SDK handles “discovering shareable sources” and “starting capture”; how to present the source list to the user is up to you, so the SDK isn’t tied to any particular UI.
macOS: exclude in-meeting windows when sharing the whole screen
When sharing an entire display, the video includes your app’s own windows by default (consistent with Zoom / Tencent Meeting). But the main in-meeting window is usually rendering remote video, and if it happens to be rendering your own shared stream (testing with two instances on the same machine, or a sharing preview in your UI), you get an infinite mirror. Pass the IDs of these windows to cut them out one by one:- The values are
UInt32(NSWindow.windowNumber); they only matter when sharing an entire display and are ignored when capturing a single window - The list is snapshotted once when capture starts; windows opened afterward always appear in the video
- If you really want the old behavior of “not sharing the app at all,” set
excludesCurrentApplicationtotrue;excludedWindowIdsis then ignored
Local preview
If you need a local preview of the shared content in UIKit / AppKit, passview; in SwiftUI, don’t pass it and use SRTCVideoView(track: meeting.screenTrack) instead.
iOS: full-screen sharing
On iOS,requestShare() uses in-app capture and can capture only your own app’s content. To share the entire system screen, you must use a ReplayKit Broadcast Upload Extension—this is an iOS system constraint that no SDK can get around.
1. Integrate the extension target
Create a Broadcast Upload Extension target that links onlySRTCBroadcastKit, with its principal class inheriting from SRTCBroadcastSampleHandler:
SRTCBroadcastKit is a product of the audio and video layer’s srtc-swift-sdk, and SwiftPM doesn’t allow using products of transitive dependencies, so you must add one more dependency to your project, with a version matching the SRTC version pinned inside SMeeting (see Integration):
2. Configure the App Group
Configure the same App Group for the app and the extension, and setSRTCAppGroupIdentifier in the extension’s Info.plist. These three places must match exactly: the app’s entitlement, the extension’s entitlement, and the extension’s Info.plist.
The App Group must also be registered in the developer portal, and both provisioning profiles must include that capability; otherwise signing fails with Provisioning profile doesn't include the App Groups capability.
3. Set up the listener after entering the meeting, and let the user start from the system UI
Full-screen capture can only be started by the user from the system UI, so the flow is “set up the listener first → the user taps the system pill → announce sharing to the meeting only once frames actually arrive”:publishBroadcastShare(byAdmin: true, adminUid:); the semantics are the same as for requestShare.
Because the share button itself is the system SRTCBroadcastPicker, your UI doesn’t need an intermediate prompt page such as “waiting for the user to start sharing.”
4. State and cleanup
When the user stops broadcasting from the system pill, the SDK cleans up automatically (unpublishes + notifies the meeting backend) and sets up the listener again. Your app doesn’t need to call
stopShare() or prepare again; just refresh the UI. The user can share again right away.
Call stopBroadcastListening() when you no longer need the sharing capability; exitRoom() tears down the listener automatically, so you don’t need to handle it manually.
Full-screen capture doesn’t work in the simulator; you must use a real device (it depends on real signing and the App Group). Logs from the extension process don’t appear in the Xcode console; use Console.app and filter by the subsystem
com.srtc.broadcast.iOS full-screen sharing doesn’t capture system audio—the extension side can get audio frames, but the current iOS audio path on the host side isn’t connected, and the protocol only reserves a slot for it. Shared content is video only.Stop sharing
stopShare() notifies the meeting, unpublishes, and stops capture; it doesn’t throw.
The host can also force the current sharing to end:
roomShareDidStop (with byAdmin set to true).
Whiteboard sharing
A whiteboard doesn’t produce a media stream;requestShare(shareType: .whiteBoard) only broadcasts the sharing status:
WKWebView. You host the whiteboard’s actual interaction in your own container; the SDK only synchronizes the state of “who is currently sharing the whiteboard.”
Members who enter mid-meeting don’t receive roomShareDidStart, so they need to check once themselves: RoomInfo.shareState == 2 means someone in the meeting is already sharing the whiteboard.
For the whiteboard page’s URL parameters, host JS APIs, lifecycle, and when it’s destroyed, see SRTC · Whiteboard.
Sharing events
roomShareDidStart is driven by the RTC media track: it’s reported as soon as the remote screen track arrives, so when you receive this event you can render the shared video immediately without extra delays or retries. The sharing broadcast message and the media track are two independent paths with no guaranteed arrival order; the SDK deduplicates and adds fallbacks across three paths, so each sharing session is reported only once.
shareBroadcastDidStart / shareBroadcastDidFinish fire only for iOS full-screen sharing, and only on the sharer’s own side, to distinguish “the listener is set up” from “there’s actually video.” Other members only need to care about roomShareDidStart / roomShareDidStop; they don’t need to tell which capture path the sharer is using.