Render user video
The code on this page only works with the custom UI.
In custom UI mode, the SDK provides multiple options to render user video after a user subscribes to another user's video. After following the steps to render a user's video, each option contains a different type of video stream.
- Single attendee - A single user's video.
- Active speaker - A single user's video that automatically updates when the active speaker changes.
- Preview - A preview of the local user's video.
- Share - The content being shared by another user.
Regardless of which render option you are using, the SDK utilizes four main components.
ZoomSDKNormalVideoElement,ZoomSDKActiveVideoElement, orZoomSDKPreViewVideoElement- Interface for video element rendering in custom UI.ZoomSDKVideoContainer- An object that sets up the video view.ZoomSDKVideoContainerDelegate- A delegate that indicates if a video's subscription fails and more.
Subscribe to error data
Before subscribing to the video, conform your class to the ZoomSDKVideoContainerDelegate protocol to know when a video subscription fails. To pass it into the SDK, you'll need a reference to the ZoomSDKVideoContainer instance being set up.
// Add delegate first.
if let videoContainer = ZoomSDK.shared().getMeetingService()?.getVideoContainer() {
videoContainer.delegate = self
}
// Also, conform your class to the ZoomSDKVideoContainerDelegate
extension ViewController: ZoomSDKVideoContainerDelegate
func onSubscribeUserFail(_ error: ZoomSDKVideoSubscribeFailReason, videoElement element: ZoomSDKVideoElement) {
}
}
// In your .h file, conform to the ZoomSDKVideoContainerDelegate protocol
@interface ZMSDKWindow : NSWindowController <ZoomSDKVideoContainerDelegate> {
}
// In your .m file, add delegate and add onSubscribeUserFail callback
ZoomSDKVideoContainer *videoContainer = [[[ZoomSDK sharedSDK] getMeetingService] getVideoContainer];
if (videoContainer) {
videoContainer.delegate = self;
}
- (void)onSubscribeUserFail:(ZoomSDKVideoSubscribeFailReason)error videoElement:(ZoomSDKVideoElement *)element {
}
When you've finished using the video view, remove the listener to avoid leaks.
videoContainer.delegate = nil
videoContainer.delegate = nil;
Define a video element
The primary user-facing video element is ZoomSDKVideoElement and is inherited by the components
ZoomSDKActiveVideoElement - for active speaker video,
ZoomSDKPreViewVideoElement - for local user preview video, and
ZoomSDKNormalVideoElement - for local and remote participant video.
Create a new ZoomSDKVideoElement instance based on which video element you need and give it the frame of the NSView that you will be using to add the video view to.
// To create the video element for a local/remote participant video
let yourVideoView:NSView = NSView() // Get your NSView to show a user's video
var normalVideoElement = ZoomSDKNormalVideoElement(frame: yourVideoView.frame)
var videoElement: ZoomSDKVideoElement? = normalVideoElement
// To create the video element for active speaker video
let yourVideoView:NSView = NSView() // Get your NSView to show a user's video
var activeVideoElement = ZoomSDKActiveVideoElement(frame: yourVideoView.frame)
var videoElement: ZoomSDKVideoElement? = normalVideoElement
// To create the video element for local user's preview video
let yourVideoView:NSView = NSView() // Get your NSView to show a user's video
previewVideoElement = ZoomSDKPreViewVideoElement(frame: yourVideoView.frame)
var videoElement: ZoomSDKVideoElement? = normalVideoElement
// To create the video element for a local/remote participant video
NSView *yourVideoView = [NSView alloc];
ZoomSDKNormalVideoElement* normalVideoElement = [[ZoomSDKNormalVideoElement alloc] initWithFrame:yourVideoView.frame];
// To create the video element for active speaker video
NSView *yourVideoView = [NSView alloc];
ZoomSDKActiveVideoElement* activeVideoElement = [[ZoomSDKActiveVideoElement alloc] initWithFrame:yourVideoView.frame];
// To create the video element for local user's preview video
NSView *yourVideoView = [NSView alloc];
ZoomSDKPreViewVideoElement* previewVideoElement = [[ZoomSDKPreViewVideoElement alloc] initWithFrame:yourVideoView.frame];
Subscribe to video streams
Each of the ZoomSDKVideoElement instance created by the SDK is managed by the ZoomSDKVideoContainer. Use these to manage the lifecycle of the video subscription rendered on each video view.
To subscribe to a single attendee's video, you must provide the userId of the user whose video is being subscribed to. Access this in ZoomSDKUserInfo.userID.
Learn how to retrieve a userID on Access in-meeting user info.
videoContainer.createVideoElement(&videoElement)
// To subscribe a participant view
yourVideoView.addSubview(normalVideoElement.getVideoView())
normalVideoElement.userid = 123456789 // userID of the participant you will like to subscribe to
normalVideoElement.subscribeVideo(true) // or false
// To subscribe to the active speaker view
yourVideoView.addSubview(activeVideoElement.getVideoView())
activeVideoElement.startActiveView(true) // or false
// To subscribe to the local user preview view
yourVideoView.addSubview(previewVideoElement.getVideoView())
previewVideoElement.startPreview(true) // or false
// To subscribe a participant view
[videoContainer createVideoElement:&normalVideoElement];
[yourVideoView addSubview:[normalVideoElement getVideoView]];66
normalVideoElement.userid = 123456789 // userID of the participant you will like to subscribe to
[normalVideoElement subscribeVideo:YES]; // or NO
// To subscribe to the active speaker view
[videoContainer createVideoElement:&activeVideoElement];
[yourVideoView addSubview:[activeVideoElement getVideoView]];
[activeVideoElement startActiveView:YES]; // or NO
// To subscribe to the local user preview view
[videoContainer createVideoElement:&previewVideoElement];
[yourVideoView addSubview:[previewVideoElement getVideoView]];
[previewVideoElement startPreview:YES]; // or NO
Manage existing video streams
To resize or set resolution to any of the video element, use the resize or setResolution method respectively.
videoElement?.resize(yourNewVideoView.frame)
videoElement?.setResolution(ZoomSDKVideoRenderResolution_360p) // Check out ZoomSDKVideoRenderResolution for all resolution available.
[normalVideoElement resize:yourVideoView.frame];
[normalVideoElement setResolution:ZoomSDKVideoRenderResolution_360p];
Finally, when a video unit is no longer being used, end the subscription with the cleanVideoElement method and remove the video view from its superview.
videoContainer.clean(normalVideoElement)
normalVideoElement.getVideoView().removeFromSuperview()
[videoContainer cleanVideoElement:normalVideoElement];
[[normalVideoElement getVideoView] removeFromSuperview];