屏幕共享功能主要运用于远程指导,远程协助,远程教育等场景,我利用声网的SDK进行了实现,详细过程做如下分享,希望能给有需要的人带来一定的帮助和启发,也欢迎同仁进行优化和讨论!
1.接入实时通话进行过程控制
屏幕共享的过程是需要一定的流程,所以我也利用声网的pod 'AgoraRtm_iOS','1.5.0',这个SDK就行过程串联和通信。之所以用到此版本,是因为没有接入推送功能,在交互的过程中需要被请求共享屏幕的一方同意即使响应。挂断过程也需要告知另一方!因为不是重点所以不做详细说明。
注意点有以下几个方面:
a:pod 'AgoraRtm_iOS','1.5.0',这个版本才包含对方是否在线的判断方法。
b:因为要同事接入 pod 'AgoraRtcEngine_iOS', :subspecs => ['RtcBasic', 'ReplayKit'] 屏幕共享用到的SDK,所以有冲突,解决办法如下如何处理同时集成 RTM SDK 和 RTC SDK 遇到的问题?
2.屏幕共享的实现
由于 Apple 不支持在 App 主进程采集屏幕,因此你需要为屏幕共享流单独创建一个 Extension,并在 Extension 中使用 iOS 原生的 ReplayKit 框架实现录制屏幕,然后将屏幕共享流发送给主进程、实现屏幕共享。
注意:受系统限制,屏幕共享只支持 iOS 12.0 及以上版本。该功能对设备性能要求较高,声网推荐你使用 iPhone X 及以上设备。
前提条件
在实现屏幕共享前,请确保已在你的项目中实现基本的实时音视频功能。详见实现音视频互动
项目设置
按照以下步骤修改你的项目文件。
前往你的项目文件夹,用 Xcode 打开 .xcodeproj 文件。
点击 File > New > Target..., 在弹出的窗口中选择 Broadcast Upload Extension, 点击 Next。
在弹出的窗口中填写 Product Name 等信息,取消勾选 Include UI Extension,点击 Finish。Xcode 会自动创建该 Extension 的文件夹,其中包含 SampleHandler文件。
修改项目设置以实现屏幕共享的代码逻辑,根据实际业务需求选择以下三种方式其中之一即可:
如果你只需使用声网提供的 YBRExtension.xcframework 动态库中的功能,则:选中 Target 为刚刚创建的 Extension,在 Info 中将 NSExtension > NSExtensionPrincipalClass 所对应的 Value 从 SampleHandler 改为 AgoraReplayKitHandler。
你的pod 需要这么写
target 'YBR*****istant' do
# Comment the next line if you don't want to use dynamic frameworks
# use_frameworks!
# Pods for YBR*****istan
#屏幕共享
pod'AgoraRtcEngine_iOS', :subspecs => ['RtcBasic', 'ReplayKit']
#即时通讯
pod'AgoraRtm_iOS','1.5.0'
end
target 'YBRExtension' do
pod'AgoraRtcEngine_iOS', :subspecs => ['RtcBasic', 'ReplayKit']
end
实现屏幕共享
- (void)startRemote {
// // 视频默认禁用,你需要调用 enableVideo 启用视频流。
[self.mRtcEngine enableVideo];
[self.mRtcEngine enableLocalAudio:NO];
AgoraRtcChannelMediaOptions *options = [AgoraRtcChannelMediaOptions new];
//// 视频通话场景下,设置频道场景为 BROADCASTING。
options.channelProfile = AgoraChannelProfileLiveBroadcasting;
// 将用户角色设置为 BROADCASTER。
options.clientRoleType = AgoraClientRoleBroadcaster;
//加入频道
[self.mRtcEngine joinChannelByToken:[RtmMessageManager shared].currentSession.rtcToken.token channelId:[RtmMessageManager shared].currentSession.rtcToken.channelName uid:YBRuserModel.ybrid.integerValue mediaOptions:options joinSuccess:^(NSString * _Nonnull channel, NSUInteger uid, NSInteger elapsed) {
if ([[RtmMessageManager shared].currentSession.mineRoler isEqualToString:RemoteRolerPARTICIPANT]) {
self.screenParams = [AgoraScreenCaptureParameters2 new];
AgoraScreenVideoParameters *videoParams = [AgoraScreenVideoParameters new];
//设置屏幕录制的分辨率
videoParams.dimensions=CGSizeMake(SCREEN_WIDTH*[UIScreen mainScreen].scale,SCREEN_HEIGHT*[UIScreen mainScreen].scale);
videoParams.frameRate = AgoraVideoFrameRateFps15;
videoParams.bitrate = AgoraVideoBitrateStandard;
self.screenParams.videoParams= videoParams;
//// 开启屏幕采集
[self.mRtcEngine startScreenCapture:self.screenParams];
AgoraRtcChannelMediaOptions *options = [AgoraRtcChannelMediaOptions new];
//// 视频通话场景下,设置频道场景为 BROADCASTING。
options.channelProfile = AgoraChannelProfileLiveBroadcasting;
// 将用户角色设置为 BROADCASTER。
options.clientRoleType = AgoraClientRoleBroadcaster;
//发布屏幕录制
options.publishScreenCaptureVideo = YES;
options.publishCameraTrack=NO;
[self.mRtcEngine updateChannelWithMediaOptions:options];
}
}];
}
使用 Apple 在 iOS 12.0 中新增的 RPSystemBroadcastPickerView,使 App 界面弹出 “开启屏幕共享” 的按钮,提示用户通过点击该按钮开启录制,示例代码如下:
RPSystemBroadcastPickerView *systemBroadcastPicker = [[RPSystemBroadcastPickerView alloc] initWithFrame:CGRectMake(0, 0, 60, 60)];
systemBroadcastPicker.showsMicrophoneButton=false;
systemBroadcastPicker.autoresizingMask =UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleRightMargin;
NSString*bundleId = [NSBundlemainBundle].bundleIdentifier;
systemBroadcastPicker.preferredExtension= [NSStringstringWithFormat:@"%@.Agora-ScreenShare-Extension",bundleId];
self.systemBroadcastPicker= systemBroadcastPicker;
for (UIView *view in self.systemBroadcastPicker.subviews) {
if([viewisKindOfClass:[UIButtonclass]]) {
[((UIButton *)view) sendActionsForControlEvents:(UIControlEventAllEvents)];
break;
}
}