webRtcPlayerViewController.m 42 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151
  1. //
  2. // webRtcPlayerViewController.m
  3. // 双子星云手机
  4. //
  5. // Created by xd h on 2024/9/2.
  6. //
  7. #import "webRtcPlayerViewController.h"
  8. #import "webRtcPlayerViewController+AdjustBtnFrame.h"
  9. #import "webRtcPlayerViewController+AdjustPlayerViewFrame.h"
  10. #import "webRtcPlayerViewController+AppDelegate.h"
  11. #import "UIInterface+HXRotation.h"
  12. #import "playerSetView.h"
  13. @interface webRtcPlayerViewController ()<MediaStreamClientEventsDelegate>
  14. {
  15. BOOL outputVolumeKVO;/*标记声音监听通知*/
  16. double lastTimestamp;/*最后一帧时间戳*/
  17. NSNumber *lastBytesReceived;/*最后一帧数据量*/
  18. UILabel* netWorkInfoLabel;//网络延时等信息 正式环境屏蔽
  19. //记录上次 线性增长接收包数
  20. long lasPacketsReceived;
  21. //记录上次 总丢包数据
  22. long lastAlllostData;
  23. }
  24. @property (nonatomic, copy) NSTimer *playerSecondTimer; // 定时器-控制按钮
  25. @property (nonatomic, assign) RTCIceConnectionState linkState;
  26. @property (nonatomic, assign) BOOL didHandleRotation;//第一次处理旋转
  27. @property (nonatomic, assign) BOOL needToReportWebRtcType;//上报打洞是否成功
  28. @end
  29. @implementation webRtcPlayerViewController
  30. @synthesize controlBtn;
  31. - (void)viewDidLoad {
  32. [super viewDidLoad];
  33. // Do any additional setup after loading the view.
  34. [self.toolBar setHidden:YES];
  35. [self.navigationBar setHidden:YES];
  36. [self.navBarBGView setHidden:YES];
  37. [self.view setBackgroundColor:[UIColor blackColor]];
  38. if([DFPlayer sharedPlayer].state == DFPlayerStateBuffering
  39. ||[DFPlayer sharedPlayer].state == DFPlayerStatePlaying){
  40. _isCodeSuspendAudioType = YES;
  41. [[DFPlayer sharedPlayer] df_pause];
  42. }
  43. }
  44. - (void)viewWillAppear:(BOOL)animated {
  45. [super viewWillAppear:animated];
  46. // 屏幕常亮
  47. [UIApplication sharedApplication].idleTimerDisabled = YES;
  48. [[UIApplication sharedApplication] setStatusBarHidden:YES];
  49. }
  50. - (void)viewDidAppear:(BOOL)animated
  51. {
  52. [super viewDidAppear:animated];
  53. [self noEnablePanRightBack];
  54. [self addKVOObserverFun];
  55. ksharedAppDelegate.supportScreenRotateType = YES;
  56. }
  57. - (void)viewDidDisappear:(BOOL)animated{
  58. [super viewDidDisappear:animated];
  59. [UIApplication sharedApplication].idleTimerDisabled = NO;
  60. [[UIApplication sharedApplication] setStatusBarHidden:NO];
  61. [_mediaStream disconnect];
  62. _mediaStream = nil;
  63. [self enablePanRightBack];
  64. [self removeKVOObserverFun];
  65. ksharedAppDelegate.supportScreenRotateType = NO;
  66. [self removeNewIndicator];
  67. [_playerSecondTimer invalidate];
  68. _webRtcMsgMod = nil;
  69. }
  70. - (void)setWebRtcMsgMod:(webRtcMsgModel *)webRtcMsgMod
  71. {
  72. _webRtcMsgMod = webRtcMsgMod;
  73. [self beginWebRtcPlayFun];
  74. }
  75. #pragma mark 开始拉流
  76. - (void)beginWebRtcPlayFun
  77. {
  78. if(_mediaStream){
  79. //[_mediaStream disconnect];
  80. //[_mediaStream removeFromSuperview];
  81. //_mediaStream = nil;
  82. }
  83. _mediaStream = [[RTC_OBJC_TYPE(AMediaStream) alloc] initWithFrame:CGRectZero];
  84. [_mediaStream setEventDelegate:self];
  85. [self.view addSubview:_mediaStream];
  86. HLog(@"_mediaStream:%@",_mediaStream)
  87. [_mediaStream mas_makeConstraints:^(MASConstraintMaker *make) {
  88. make.left.mas_equalTo(0.f);
  89. make.bottom.mas_equalTo(0.f);
  90. make.right.mas_equalTo(0.f);
  91. make.top.mas_equalTo(0.f);
  92. }];
  93. //判断是否是全屏
  94. BOOL fullscreenType = [HWDataManager getBoolWithKey:Consn_player_full_screen_show];
  95. CGSize phoneSize = CGSizeMake(1080.0, 1920.0);
  96. if(fullscreenType){
  97. phoneSize = [RCCommandHelp commondToSetFullScreenPhoneSizeBySize];
  98. }
  99. [self linkWebRtcFunWithSize:phoneSize];
  100. [self initBaseUIFun];
  101. [self setTimerCountDown];
  102. //CGFloat curRate = 1080.0/1920.0;
  103. //CGFloat curRate = phoneSize.width/phoneSize.height;
  104. [self showNewIndicatorWithCanBack:YES canTouch:NO];
  105. }
  106. #pragma mark 链接webrtc
  107. - (void)linkWebRtcFunWithSize:(CGSize)phoneSize
  108. {
  109. //链接用
  110. NSString *signallingUrl = [[NSString alloc] initWithFormat:@"%@:%@",_webRtcMsgMod.data.signalling.domainName,_webRtcMsgMod.data.signalling.port];
  111. NSURL *url = [NSURL URLWithString:signallingUrl];
  112. //ice用
  113. NSString *iceUrl = [[NSString alloc] initWithFormat:@"%@:%@",_webRtcMsgMod.data.turn.domainName,_webRtcMsgMod.data.turn.port];
  114. NSMutableDictionary *ice = [NSMutableDictionary new];
  115. if(iceUrl){
  116. [ice setValue:iceUrl forKey:@"CHINANET"];
  117. [ice setValue:iceUrl forKey:@"CMNET"];
  118. [ice setValue:iceUrl forKey:@"UNICOM"];
  119. }
  120. NSString *roomName = _webRtcMsgMod.data.uniqueIdentifier;
  121. NSInteger result = [_mediaStream start:url
  122. ice:ice
  123. sn:roomName
  124. direct:0
  125. fmt:1//1(h264) 5(h265)
  126. videoWidth:(NSInteger)phoneSize.width
  127. videoHeight:(NSInteger)phoneSize.height
  128. fps:30
  129. bitrate:3000
  130. cardWidth:0//1080//0
  131. cardHeight:0//1920//0
  132. cardDensity:0
  133. token:@"vclusters"];
  134. HLog(@"result:%ld",result)
  135. [_mediaStream setShouldGetStats:YES];
  136. }
  137. #pragma mark 重连
  138. - (void)relinkWebRtcFun
  139. {
  140. if(_linkState == RTCIceConnectionStateConnected
  141. || _linkState == RTCIceConnectionStateCompleted)
  142. {//链接中 不处理重连事件
  143. HLog(@"链接中 不处理重连事件")
  144. return;
  145. }
  146. HLog(@"发起重连 ......")
  147. KWeakSelf
  148. mainBlock(^{
  149. [weakSelf showNewIndicatorWithCanBack:YES canTouch:NO];
  150. //判断是否是全屏
  151. // BOOL fullscreenType = [HWDataManager getBoolWithKey:Consn_player_full_screen_show];
  152. // CGSize phoneSize = CGSizeMake(1080.0, 1920.0);
  153. // if(fullscreenType){
  154. // phoneSize = [RCCommandHelp commondToSetFullScreenPhoneSizeBySize];
  155. // }
  156. //
  157. // [weakSelf linkWebRtcFunWithSize:phoneSize];
  158. [weakSelf beginWebRtcPlayFun];
  159. });
  160. }
  161. #pragma mark 初始化其他UI
  162. - (void)initBaseUIFun
  163. {
  164. if(netWorkInfoLabel){
  165. [netWorkInfoLabel removeFromSuperview];
  166. netWorkInfoLabel = nil;
  167. }
  168. netWorkInfoLabel = [[UILabel alloc] init];
  169. [netWorkInfoLabel setTextColor:[UIColor greenColor]];
  170. [netWorkInfoLabel setBackgroundColor:HW000000Color60];
  171. [netWorkInfoLabel setFont:[UIFont systemFontOfSize:17]];
  172. [netWorkInfoLabel setNumberOfLines:0];
  173. [self.view addSubview:netWorkInfoLabel];
  174. [netWorkInfoLabel mas_makeConstraints:^(MASConstraintMaker *make) {
  175. make.top.mas_equalTo(80);
  176. make.left.mas_equalTo(20);
  177. }];
  178. if(_bottomContrView){
  179. [_bottomContrView removeFromSuperview];
  180. _bottomContrView = nil;
  181. }
  182. _bottomContrView = [[webRtcPlayerBottomContrView alloc] init];
  183. [self.view addSubview:_bottomContrView];
  184. [self getPlayerBottomNavShowOrHidefun];
  185. KWeakSelf
  186. _bottomContrView.didClickButtonFun = ^(NSInteger tag) {
  187. [weakSelf didClickBottomFunBy:tag];
  188. };
  189. /*控制按钮*/
  190. if(controlBtn){
  191. [controlBtn removeFromSuperview];
  192. controlBtn = nil;
  193. }
  194. UIImage *driftBtnImage = [UIImage imageNamed:@"you_icon"];
  195. controlBtn = [[UIButton alloc] init];
  196. [controlBtn setBackgroundColor:[UIColor clearColor]];
  197. [controlBtn setBackgroundImage:driftBtnImage forState:(UIControlStateNormal)];
  198. [controlBtn addTarget:self
  199. action:@selector(controlBtnPressed:)
  200. forControlEvents:(UIControlEventTouchUpInside)];
  201. [self.view addSubview:controlBtn];
  202. //拖拽事件等
  203. UIPanGestureRecognizer *gester = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(controlBtnPanGestureCallback:)];
  204. [controlBtn addGestureRecognizer:gester];
  205. //gester.delegate = self;
  206. [self initPointForControlBtnFun];
  207. }
  208. #pragma mark 设置 controlBtn 的初始位置
  209. - (void)initPointForControlBtnFun
  210. {
  211. CGFloat h_w_controlBtn = 60.f;
  212. /*区分横竖屏*/
  213. if (_mediaStream.hw_w > _mediaStream.hw_h){
  214. [controlBtn setFrame:CGRectMake((_mediaStream.hw_w - h_w_controlBtn)/2.f, _mediaStream.hw_h - h_w_controlBtn - 20.f, h_w_controlBtn, h_w_controlBtn)];
  215. }else{
  216. //默认居右
  217. //[mPlayerView.controlBtn setFrame:CGRectMake(mPlayerView.width - h_w_controlBtn - 20.f, (SCREEN_H - h_w_controlBtn)/2.f, h_w_controlBtn, h_w_controlBtn)];
  218. //默认居左
  219. [controlBtn setFrame:CGRectMake( h_w_controlBtn + 10.f, (SCREEN_H - h_w_controlBtn)/2.f, h_w_controlBtn, h_w_controlBtn)];
  220. }
  221. }
  222. #pragma mark 定时器
  223. - (void)setTimerCountDown {
  224. HLog(@"开启一个");
  225. if (_playerSecondTimer) {
  226. // 取消定时器
  227. [_playerSecondTimer invalidate];
  228. _playerSecondTimer = nil;
  229. }
  230. // 初始化值计时数据
  231. //self.adjustTime = 1;
  232. //self.concentTime = [iTools getNowTimeStamp];
  233. _playerSecondTimer = [NSTimer scheduledTimerWithTimeInterval:3.0 target:self selector:@selector(timerChange) userInfo:nil repeats:YES];
  234. [[NSRunLoop currentRunLoop] addTimer:_playerSecondTimer forMode:NSRunLoopCommonModes];
  235. }
  236. #pragma mark 定时器响应事件
  237. - (void)timerChange {
  238. [self extensionAdjustBtnFrameCheckAdjustTime];// 1、悬浮球3s后 自动靠边隐藏
  239. //[self checkConcentTime];// 3、30s之后 没有收到拉流数据 自动断开链接
  240. }
  241. #pragma mark 控制按钮点击事件
  242. - (void)controlBtnPressed:(UIButton*)but
  243. {
  244. playerSetView *nextVC = [[playerSetView alloc] init];
  245. [ksharedAppDelegate.window addSubview:nextVC];
  246. [nextVC mas_makeConstraints:^(MASConstraintMaker *make) {
  247. make.left.mas_equalTo(0);
  248. make.right.mas_equalTo(0);
  249. make.top.mas_equalTo(0.f);
  250. make.bottom.mas_equalTo(0.f);
  251. }];
  252. KWeakSelf
  253. nextVC.didClickButtonFun = ^(NSInteger tag) {
  254. switch (tag) {
  255. case 10:
  256. {//截图
  257. //self->needScreenShotType = YES;
  258. }
  259. break;
  260. #pragma mark 重启盒子
  261. case 11:
  262. {
  263. [weakSelf didClickRestartFun];
  264. }
  265. break;
  266. case 12:
  267. {//退出云机
  268. [weakSelf exitCloudPhoneFun];
  269. }
  270. break;
  271. case 100:
  272. {
  273. BOOL fullscreenType = [HWDataManager getBoolWithKey:Consn_player_full_screen_show];
  274. if(fullscreenType){
  275. [weakSelf showOpenTVP2PFun];
  276. }
  277. else{
  278. [weakSelf openTvShowFun];
  279. }
  280. }
  281. break;
  282. case 101:
  283. {
  284. weakSelf.controlBtn.userInteractionEnabled = NO;
  285. dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
  286. self->controlBtn.userInteractionEnabled = YES;
  287. });
  288. [weakSelf showCloseTVP2PFun];
  289. }
  290. break;
  291. default:
  292. break;
  293. }
  294. };
  295. }
  296. #pragma mark 点击了重启云机
  297. - (void)didClickRestartFun
  298. {
  299. KWeakSelf
  300. /*弹窗提示重启*/
  301. ComontAlretViewController *nextVC = [[ComontAlretViewController alloc] initWithTiTle:NSLocalizedString(@"my_set_no_restart_phone_tips",nil)
  302. msg:@""
  303. imageStr:@""
  304. cancelTitle:NSLocalizedString(@"other_cancel",nil)
  305. okTitle:NSLocalizedString(@"my_set_no_restart_phone_btn_ok",nil) isOkBtnHighlight:NO
  306. didClickOk:^{
  307. [weakSelf needToRebootFun];
  308. //提示语
  309. [[iToast makeText:NSLocalizedString(@"player_link_rebooting_Tips",nil)] show];
  310. } didClickCancel:^{
  311. }];
  312. nextVC.modalPresentationStyle = UIModalPresentationCustom;
  313. [self presentViewController:nextVC animated:YES completion:^{
  314. nextVC.view.superview.backgroundColor = [UIColor clearColor];
  315. }];
  316. }
  317. #pragma mark p2p通道 重启云机
  318. - (void)needToRebootFun
  319. {
  320. [[webRtcManager shareManager] needToRebootFun];
  321. [self startForceStartTimerFun];
  322. [self pauseStream];
  323. [webRtcManager shareManager].isRebootIngType = YES;
  324. [self showNewIndicatorWithCanBack:YES canTouch:NO];
  325. }
  326. #pragma mark X 秒后检查是否软件重启成功
  327. - (void)startForceStartTimerFun
  328. {
  329. KWeakSelf
  330. //1. 5秒后跟硬件发起硬重启
  331. dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
  332. [weakSelf updateForceStartFun];
  333. });
  334. //2. 20秒后尝试重连
  335. dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(20 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
  336. [weakSelf relinkWebRtcFun];
  337. [[webRtcManager shareManager] relinkWebRtcFun];
  338. });
  339. }
  340. #pragma mark 需要强制重启
  341. - (void)updateForceStartFun{
  342. NSString* curSn = ksharedAppDelegate.DeviceThirdIdMod.data.changeSn;
  343. NSMutableDictionary *paraDict = [NSMutableDictionary dictionary];
  344. [paraDict setValue:curSn forKey:@"sn"];
  345. [paraDict setValue:[NSNumber numberWithBool:YES] forKey:@"isForceStart"];
  346. [[netWorkManager shareInstance] CommonPostCallBackCode:updateForceStart Parameters:paraDict success:^(id _Nonnull responseObject) {
  347. SuperModel *model = [[SuperModel alloc] initWithDictionary:responseObject error:nil];
  348. if (model.status == 0) {
  349. }
  350. else
  351. {
  352. }
  353. } failure:^(NSError * _Nonnull error) {
  354. HLog(@"%@", error);
  355. }];
  356. }
  357. #pragma mark 退出云机
  358. - (void)exitCloudPhoneFun
  359. {
  360. //[self setShowImgAndVoiceTypeFun:NO];
  361. if(_isCodeSuspendAudioType){
  362. [[DFPlayer sharedPlayer] df_play];
  363. }
  364. [self.navigationController popViewControllerAnimated:YES];
  365. }
  366. #pragma mark 显示关闭投屏提示语
  367. - (void)showOpenTVP2PFun{
  368. /*弹窗提示TV投屏*/
  369. ComontAlretViewController *nextVC = [[ComontAlretViewController alloc] initWithTiTle:NSLocalizedString(@"File_upload_Record_clear_Tip_title",nil)
  370. msg:NSLocalizedString(@"cloudPhone_fullscreen_tvshow_tip",nil)
  371. imageStr:@""
  372. cancelTitle:NSLocalizedString(@"other_cancel",nil)
  373. okTitle:NSLocalizedString(@"my_set_TVP2P_Open_sure",nil) isOkBtnHighlight:YES
  374. didClickOk:^{
  375. [self openTvShowFun];
  376. //关闭全屏屏
  377. [HWDataManager setBoolWithKey:Consn_player_full_screen_show value:NO];
  378. [self setPlayerFullScreenNotFun];
  379. } didClickCancel:^{
  380. }];
  381. nextVC.modalPresentationStyle = UIModalPresentationCustom;
  382. [self presentViewController:nextVC animated:YES completion:^{
  383. nextVC.view.superview.backgroundColor = [UIColor clearColor];
  384. }];
  385. }
  386. #pragma mark 开始投屏
  387. - (void)openTvShowFun
  388. {
  389. self.controlBtn.userInteractionEnabled = NO;
  390. dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
  391. self->controlBtn.userInteractionEnabled = YES;
  392. });
  393. [[webRtcManager shareManager] onTvFun];
  394. [[iToast makeText:NSLocalizedString(@"cloudPhone_TV_show_tip",nil)] show];
  395. //数据埋点
  396. [[netWorkManager shareInstance] DataEmbeddingPointBy:3 withEventValue:@"Cloud_tv"];
  397. }
  398. #pragma mark 显示关闭投屏提示语
  399. - (void)showCloseTVP2PFun{
  400. /*弹窗提示TV投屏*/
  401. ComontAlretViewController *nextVC = [[ComontAlretViewController alloc] initWithTiTle:NSLocalizedString(@"my_set_no_close_TV_p2p_tip",nil)
  402. msg:@""
  403. imageStr:@""
  404. cancelTitle:NSLocalizedString(@"other_cancel",nil)
  405. okTitle:NSLocalizedString(@"my_set_TVP2P_Open_sure",nil) isOkBtnHighlight:YES
  406. didClickOk:^{
  407. [self gotoCloseTVP2PFun];
  408. } didClickCancel:^{
  409. //HLog(@"2222");
  410. }];
  411. nextVC.modalPresentationStyle = UIModalPresentationCustom;
  412. [self presentViewController:nextVC animated:YES completion:^{
  413. nextVC.view.superview.backgroundColor = [UIColor clearColor];
  414. }];
  415. }
  416. #pragma mark 确认开始TV投屏
  417. -(void)gotoCloseTVP2PFun
  418. {
  419. [[webRtcManager shareManager] offTvFun];
  420. }
  421. #pragma mark 挤下线功能
  422. -(void)offlineOtherPhoneFun
  423. {
  424. NSString *curOaidStr = [RcGameWQKeyChain getOaidStringFun];
  425. if(!curOaidStr){
  426. curOaidStr = @"";
  427. }
  428. NSString *commondStr = [[NSString alloc] initWithFormat:@"{\"type\":\"login\",\"value\":\"%@\"}",curOaidStr];
  429. [self send_dataInPlayer:commondStr];
  430. }
  431. #pragma mark 单点登录被挤下线弹框
  432. - (void)LogoutByOtherFun:(NSString*)oaid
  433. {
  434. if(logoutAlertVC){
  435. return;
  436. }
  437. NSString *curOaidStr = [RcGameWQKeyChain getOaidStringFun];
  438. if(oaid
  439. && oaid.length >0
  440. && [oaid isEqualToString:curOaidStr]){
  441. return;
  442. }
  443. //[self didReceiveLogoutMsgFun];
  444. //yyyy-MM-dd HH:mm:ss
  445. NSString*dateStr = [iTools getNowTimeString2];
  446. if(dateStr && dateStr.length == 19){
  447. dateStr = [dateStr substringWithRange:NSMakeRange(11, 5)];
  448. }
  449. NSString *LogoutTimerStr = [[NSString alloc] initWithFormat:@"%@%@%@",NSLocalizedString(@"single_sign_on_Tips_one",nil),dateStr,NSLocalizedString(@"single_sign_on_Tips_two",nil)];
  450. NSString * loginAgainStr = NSLocalizedString(@"single_sign_on_login_again",nil);
  451. BOOL isOkBtnHighlight = YES;
  452. if(!ksharedAppDelegate.DeviceThirdIdMod.data.isPrivacyMode){
  453. loginAgainStr = @"";
  454. isOkBtnHighlight = NO;
  455. }
  456. KWeakSelf
  457. if(ksharedAppDelegate.isDidShowPwdType){
  458. dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(3 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
  459. [weakSelf LogoutByOtherFun:oaid];
  460. HLog(@"weakSelf LogoutByOtherFun")
  461. });
  462. return;
  463. }
  464. //被挤下线 停止拉流
  465. [self pauseStream];
  466. /*弹窗提示重启*/
  467. //KWeakSelf
  468. logoutAlertVC = [[ComontAlretViewController alloc] initWithTiTle:NSLocalizedString(@"single_sign_on_Tips_logout",nil)
  469. msg:LogoutTimerStr
  470. imageStr:@""
  471. cancelTitle:NSLocalizedString(@"single_sign_on_exit",nil)
  472. okTitle:loginAgainStr isOkBtnHighlight:isOkBtnHighlight
  473. didClickOk:^{
  474. self->logoutAlertVC = nil;
  475. [[NSNotificationCenter defaultCenter] postNotificationName:lockBypwdNotification object:nil];
  476. } didClickCancel:^{
  477. exit(0);/*强制退出app*/
  478. }];
  479. logoutAlertVC.modalPresentationStyle = UIModalPresentationCustom;
  480. [[iTools appRootViewController] presentViewController:logoutAlertVC animated:YES completion:^{
  481. self->logoutAlertVC.view.superview.backgroundColor = [UIColor clearColor];
  482. }];
  483. }
  484. #pragma mark 底部按钮事件
  485. - (void)didClickBottomFunBy:(NSInteger)tag
  486. {
  487. int keyType = 0;
  488. if(tag == 1){//task
  489. keyType = 187;
  490. }
  491. else if(tag == 2){//home
  492. keyType = 3;
  493. }
  494. else if(tag == 3){//back
  495. keyType = 4;
  496. }
  497. if(keyType > 0){
  498. [self didClickKeyEventFunBy:keyType];
  499. }
  500. }
  501. #pragma mark 按键事件
  502. // home 3 back 4 task 187 volumeUp 24 volumeDown 25
  503. - (void)didClickKeyEventFunBy:(int)keyType
  504. {
  505. [_mediaStream sendKey:keyType];
  506. }
  507. #pragma mark 云机交互的消息发送 走P2P通道
  508. -(void)send_data:(NSString*)commandStr
  509. {
  510. [[webRtcManager shareManager] send_data:commandStr];
  511. }
  512. #pragma mark 云机交互的消息发送 走音视频推拉流通道
  513. -(void)send_dataInPlayer:(NSString*)commandStr
  514. {
  515. [_mediaStream sendData:commandStr];
  516. }
  517. #pragma mark -- /*底部导航栏开关通知*/
  518. - (void)getPlayerBottomNavShowOrHidefun
  519. {
  520. BOOL haveShowBottonNavType = ![HWDataManager getBoolWithKey:Consn_player_Nav_hide];
  521. if(haveShowBottonNavType){
  522. _bottomContrView.hidden = NO;
  523. }
  524. else{
  525. _bottomContrView.hidden = YES;
  526. }
  527. }
  528. #pragma mark -- /*全面屏开关通知*/
  529. - (void)setPlayerFullScreenNotFun
  530. {
  531. BOOL fullscreenType = [HWDataManager getBoolWithKey:Consn_player_full_screen_show];
  532. CGFloat tempRate = 0.0;
  533. //重新设置分辨率
  534. if(fullscreenType){
  535. NSInteger cardDensity = 380;//480;//422;//380;//460;
  536. CGSize size = [RCCommandHelp commondToSetFullScreenPhoneSizeBySize];
  537. if(isLan){
  538. if(size.width < size.height){
  539. size = CGSizeMake(size.height,size.width);
  540. }
  541. }
  542. [self setCardSize:size.width cardHeight:size.height cardDensity:cardDensity];
  543. tempRate = (size.width *1.0)/(size.height *1.0);
  544. }
  545. else{
  546. CGSize size = CGSizeMake(1080.0, 1920.0);
  547. if(isLan){
  548. size = CGSizeMake(1920.0, 1080.0);
  549. }
  550. [self setCardSize:(NSInteger)size.width cardHeight:(NSInteger)size.height cardDensity:480];
  551. tempRate = size.width/size.height;
  552. }
  553. //dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.1 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
  554. if (tempRate > 1) {/*横屏*/
  555. [self setLanMas_makeWithImageRate:tempRate];
  556. }else{/*竖屏*/
  557. [self setPoMas_makeWithImageRate:tempRate];
  558. }
  559. // });
  560. }
  561. #pragma mark -- /*推流中修改卡的分辨率*/
  562. - (void)setCardSize:(NSInteger)cardWidth
  563. cardHeight:(NSInteger)cardHeight
  564. cardDensity:(NSInteger)cardDensit
  565. {
  566. if(isLan){
  567. HLog(@"云机屏幕 设置 宽:%ld 高:%ld",cardHeight,cardWidth);
  568. [_mediaStream setCardSize:cardHeight cardHeight:cardWidth cardDensity:cardDensit];
  569. [_mediaStream setVideoSize:cardHeight videoHeight:cardWidth];
  570. }
  571. else{
  572. HLog(@"云机屏幕 设置 宽:%ld 高:%ld",cardWidth,cardHeight);
  573. [_mediaStream setCardSize:cardWidth cardHeight:cardHeight cardDensity:cardDensit];
  574. [_mediaStream setVideoSize:cardWidth videoHeight:cardHeight];
  575. }
  576. }
  577. #pragma mark -- /*通知添加与移除*/
  578. - (void)addKVOObserverFun
  579. {
  580. outputVolumeKVO = YES;
  581. [[AVAudioSession sharedInstance] addObserver:self forKeyPath:@"outputVolume" options:NSKeyValueObservingOptionNew | NSKeyValueObservingOptionOld context:(void *)[AVAudioSession sharedInstance]];
  582. [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(getPlayerBottomNavShowOrHidefun) name:getPlayerBottomNavNotification object:nil];
  583. [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(setPlayerFullScreenNotFun) name:setPlayerFullScreenNotification object:nil];
  584. //监听系统 前后台事件
  585. [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(applicationWillTerminate:) name:UIApplicationWillTerminateNotification object:nil];
  586. [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(applicationDidBecomeActive:) name:UIApplicationDidBecomeActiveNotification object:nil];
  587. [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(applicationWillResignActive:) name:UIApplicationWillResignActiveNotification object:nil];
  588. [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(applicationDidEnterBackground:) name:UIApplicationDidEnterBackgroundNotification object:nil];
  589. //输入密码完成
  590. [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(didInpuPwdOkFun) name:didInputPWDNotification object:nil];
  591. }
  592. - (void)removeKVOObserverFun
  593. {
  594. if (outputVolumeKVO)
  595. {
  596. [[AVAudioSession sharedInstance] removeObserver:self forKeyPath:@"outputVolume" context:(void *)[AVAudioSession sharedInstance]];
  597. outputVolumeKVO = NO;
  598. }
  599. [[NSNotificationCenter defaultCenter] removeObserver:self];
  600. }
  601. #pragma mark 系统音量键监听
  602. - (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context{
  603. if(context == (__bridge void *)[AVAudioSession sharedInstance])
  604. {
  605. /*音量开关打开时 允许发送指令 否则直接返回*/
  606. float newValue = [[change objectForKey:@"new"] floatValue];
  607. float oldValue = [[change objectForKey:@"old"] floatValue];
  608. //HLog(@"音量 --old: %f ---new: %f",oldValue,newValue)
  609. if (newValue > oldValue)
  610. {
  611. HLog(@"\n-----音量增加");
  612. [self didClickKeyEventFunBy:24];
  613. }
  614. else
  615. {
  616. HLog(@"\n-----音量降低");
  617. [self didClickKeyEventFunBy:25];
  618. }
  619. }
  620. }
  621. #pragma mark 监听到云机的宽高以及屏幕方向
  622. - (void)handlUIAfterGetCloudPhoneVideoWidth:(int)videoWidth videoHeight:(int)videoHeight rotation:(int)rotation
  623. {
  624. HLog(@"云机屏幕 回调 宽:%d 高:%d 横竖屏:%d",videoWidth,videoHeight,rotation);
  625. CGFloat curRate = (CGFloat)videoWidth/(CGFloat)videoHeight;
  626. if(lastVideoWHRate == curRate){
  627. return;
  628. }
  629. didAdjusBtnType = NO;
  630. if(rotation == 0){//竖屏
  631. //切换到竖屏
  632. isLan = NO;
  633. [self hx_rotateToInterfaceOrientation:UIInterfaceOrientationPortrait];
  634. [self setPoMas_makeWithImageRate:curRate];
  635. }
  636. else if(rotation == 1){//横屏
  637. //切换到横屏屏
  638. isLan = YES;
  639. [self hx_rotateToInterfaceOrientation:UIInterfaceOrientationLandscapeRight];
  640. [self setLanMas_makeWithImageRate:curRate];
  641. }
  642. _didHandleRotation = YES;
  643. dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
  644. [self extensionAdjustBtnFrameCheckAdjustTime];
  645. });
  646. }
  647. #pragma mark WebRTC 回调 MediaStreamClientEventsDelegate
  648. #pragma mark - 宽高变化
  649. -(void)onFrameResolutionChangedFromPeerName:(NSString*)peerName videoWidth:(int)videoWidth videoHeight:(int)videoHeight rotation:(int)rotation {
  650. HLog(@"推拉流 onFrameResolutionChangedFromPeerName:%@---%d---%d--%d",peerName,videoWidth,videoHeight,rotation)
  651. HLog(@"ok _mediaStream:%@",_mediaStream)
  652. mainBlock(^{
  653. [self handlUIAfterGetCloudPhoneVideoWidth:videoWidth videoHeight:videoHeight rotation:rotation];
  654. });
  655. }
  656. //code 0 成功 1失败
  657. -(void)onAuthResultFromPeerName:(NSString*)peerName code:(int)code descriptions:(NSString*)descriptions
  658. {
  659. HLog(@"onAuthResultFromPeerName:%@---%d---%@",peerName,code,descriptions)
  660. }
  661. #pragma mark 链接发生变化
  662. -(void)onChangeConnectionStateFromPeerName:(NSString*)peerName didChangeIceConnectionState:(RTCIceConnectionState)state
  663. {
  664. HLog(@"推拉流 onChangeConnectionStateFromPeerName: state:%ld",state)
  665. _linkState = state;
  666. switch (state) {
  667. case RTCIceConnectionStateConnected:{
  668. //链接成功
  669. mainBlock(^{
  670. [self removeNewIndicator];
  671. });
  672. }
  673. break;
  674. case RTCIceConnectionStateCompleted:
  675. //链接完成
  676. break;
  677. case RTCIceConnectionStateFailed:
  678. //链接失败
  679. [self relinkWebRtcFun];
  680. break;
  681. case RTCIceConnectionStateDisconnected:
  682. //链接断开
  683. [self relinkWebRtcFun];
  684. break;
  685. case RTCIceConnectionStateClosed:
  686. //链接关闭
  687. if([webRtcManager shareManager].isRebootIngType){
  688. [self relinkWebRtcFun];
  689. }
  690. break;
  691. default:
  692. break;
  693. }
  694. }
  695. - (void)dataChannelDidChangeFromPeerName:(NSString*)peerName State:(RTCDataChannelState)state;
  696. {
  697. HLog(@"推拉流 dataChannelDidChangeFromPeerName: state:%ld",state)
  698. switch (state) {
  699. case RTCDataChannelStateConnecting:
  700. {
  701. }
  702. break;
  703. case RTCDataChannelStateOpen:
  704. {
  705. //链接成功
  706. [self offlineOtherPhoneFun];
  707. }
  708. break;
  709. case RTCDataChannelStateClosing:
  710. {
  711. }
  712. break;
  713. case RTCDataChannelStateClosed:
  714. {
  715. //链接断开
  716. [self relinkWebRtcFun];
  717. }
  718. break;
  719. default:
  720. break;
  721. }
  722. }
  723. -(void)onChannelDataFromPeerName:(NSString*)peerName buffer:(RTC_OBJC_TYPE(RTCDataBuffer) *)buffer
  724. {
  725. //HLog(@"onIceConnectedFromPeerName:%@",buffer.data);
  726. if(buffer && buffer.data){
  727. KWeakSelf
  728. mainBlock(^{
  729. [weakSelf handleWebRtcMsgResponseBy:buffer.data];
  730. });
  731. }
  732. }
  733. -(void)didGetStats:(NSString*)peerName stats:(RTC_OBJC_TYPE(RTCStatisticsReport) *)stats {
  734. if(!_needToReportWebRtcType){
  735. [[webRtcManager shareManager] reportWebRtcRePoportTypeIsChannel:NO withStats:stats];
  736. _needToReportWebRtcType = YES;
  737. }
  738. NSString *selectedCandidatePairId = nil;
  739. NSString *localCandidateId = nil;
  740. NSString *remoteCandidateId = nil;
  741. /*延时数据*/
  742. NSNumber *currentRoundTripTime = nil;
  743. //线性增长接收包数
  744. long packetsReceived = 0;
  745. //视频丢包数据
  746. long videolostData = 0;
  747. //音频丢包数据
  748. long audiolostData = 0;
  749. //总丢包数据
  750. long alllostData = 0;
  751. //每秒帧数 ----界面展示的帧率
  752. NSInteger framesPerSecond = 0;
  753. //计算传输速度
  754. long preReceive = 0;
  755. KWeakSelf
  756. for (NSString *key in [stats.statistics allKeys]) {
  757. RTCStatistics *rtcStatistics = [stats.statistics objectForKey:key];
  758. //HLog(@"hxd11111---->%@",rtcStatistics.type);
  759. if ([rtcStatistics.type isEqualToString:@"transport"]) {
  760. //HLog(@"传输数据---->%@",rtcStatistics.values);
  761. double timestamp = rtcStatistics.timestamp_us;
  762. NSNumber *bytesReceived = [rtcStatistics.values objectForKey:@"bytesReceived"];
  763. NSNumber *packetsReceivedNumber = [rtcStatistics.values objectForKey:@"packetsReceived"];
  764. packetsReceived = [packetsReceivedNumber longValue];
  765. if (lastTimestamp > 0) {
  766. long diffReceive = [bytesReceived longValue] - [lastBytesReceived longValue];
  767. double diffTime = timestamp - lastTimestamp;
  768. preReceive = (diffReceive / diffTime) * 1000000;
  769. HLog(@"传输数据速度---->%ld",preReceive);
  770. // mainBlock((^{
  771. // if (self->mPlayerView.upControlView.hidden == NO){
  772. // NSString *str = [NSString stringWithFormat:@"清晰度 %ldk/s",preReceive/1024];
  773. // NSMutableAttributedString *underAttr = [[NSMutableAttributedString alloc] initWithString:str attributes:@{NSForegroundColorAttributeName:[UIColor hwColor:@"#FFFFFF"]}];
  774. // [underAttr addAttributes:@{NSFontAttributeName:[UIFont systemFontOfSize:12]} range:NSMakeRange(0, str.length - 2)];
  775. // [underAttr addAttributes:@{NSFontAttributeName:[UIFont systemFontOfSize:10]} range:NSMakeRange(str.length - 2,2)];
  776. // [self->mPlayerView.upControlView.articulationBtn setAttributedTitle:underAttr forState:(UIControlStateNormal)];
  777. // }else{
  778. // NSString *str = [NSString stringWithFormat:@"%ldk/s",preReceive/1024];
  779. // NSMutableAttributedString *underAttr = [[NSMutableAttributedString alloc] initWithString:str attributes:@{NSForegroundColorAttributeName:[UIColor hwColor:@"#FFFFFF"]}];
  780. // [underAttr addAttributes:@{NSFontAttributeName:[UIFont systemFontOfSize:12]} range:NSMakeRange(0, str.length - 2)];
  781. // [underAttr addAttributes:@{NSFontAttributeName:[UIFont systemFontOfSize:10]} range:NSMakeRange(str.length - 2,2)];
  782. // [self->mPlayerView.controlBtn setAttributedTitle:underAttr forState:(UIControlStateNormal)];
  783. // }
  784. // }));
  785. }else{
  786. lastTimestamp = timestamp;
  787. lastBytesReceived = bytesReceived;
  788. }
  789. selectedCandidatePairId = [rtcStatistics.values objectForKey:@"selectedCandidatePairId"];
  790. //HLog(@"三网数据--selectedCandidatePairId-->%@",selectedCandidatePairId);
  791. }
  792. /*丢包数据*/
  793. if ([rtcStatistics.type isEqualToString:@"inbound-rtp"]) {
  794. NSString *kind = [rtcStatistics.values objectForKey:@"kind"];
  795. if([kind isEqualToString:@"video"]){
  796. NSNumber*videolostDataNumber = [rtcStatistics.values objectForKey:@"packetsLost"];
  797. videolostData = [videolostDataNumber longValue];
  798. NSNumber*framesPerSecondNumber = [rtcStatistics.values objectForKey:@"framesPerSecond"];
  799. framesPerSecond = [framesPerSecondNumber integerValue];
  800. }
  801. else if([kind isEqualToString:@"audio"]){
  802. NSNumber*audiolostDataNumber = [rtcStatistics.values objectForKey:@"packetsLost"];
  803. audiolostData = [audiolostDataNumber longValue];
  804. }
  805. }
  806. for (NSString *keyin in [rtcStatistics.values allKeys]) {
  807. if ([keyin isEqualToString:@"currentRoundTripTime"]){
  808. /*延时数据*/
  809. currentRoundTripTime = [rtcStatistics.values objectForKey:@"currentRoundTripTime"];
  810. //[self updateAutoRateAndNetWorkStatesWithDelatyMS:(NSInteger)currentRoundTripTime.floatValue*1000];
  811. break;
  812. }
  813. }
  814. }
  815. //netWorkInfoLabel 网络信息 测试用
  816. if (selectedCandidatePairId) {
  817. for (NSString *key in [stats.statistics allKeys]) {
  818. RTCStatistics *rtcStatistics = [stats.statistics objectForKey:key];
  819. if ([rtcStatistics.type isEqualToString:@"candidate-pair"]){
  820. NSString *tempselectedCandidatePairId = rtcStatistics.id;
  821. if ([tempselectedCandidatePairId isEqualToString:selectedCandidatePairId]) {
  822. localCandidateId = [rtcStatistics.values objectForKey:@"localCandidateId"];
  823. remoteCandidateId = [rtcStatistics.values objectForKey:@"remoteCandidateId"];
  824. HLog(@"三网数据--localCandidateId-->%@",localCandidateId);
  825. HLog(@"三网数据--remoteCandidateId-->%@",remoteCandidateId);
  826. }
  827. }
  828. }
  829. }
  830. NSString *remoteCandidateStr = nil;
  831. NSString *localCandidateStr = nil;
  832. if (localCandidateId && remoteCandidateId) {
  833. for (NSString *key in [stats.statistics allKeys]) {
  834. RTCStatistics *rtcStatistics = [stats.statistics objectForKey:key];
  835. if ([rtcStatistics.type isEqualToString:@"local-candidate"]){
  836. NSString *templocalCandidateId = rtcStatistics.id;
  837. if ([templocalCandidateId isEqualToString:localCandidateId]) {
  838. HLog(@"三网数据--localCandidateIdInfo-->%@",rtcStatistics.values);
  839. localCandidateStr = @"本地\n";
  840. NSString *candidateType = [rtcStatistics.values objectForKey:@"candidateType"];
  841. if (candidateType) {
  842. localCandidateStr = [localCandidateStr stringByAppendingString:[NSString stringWithFormat:@"candidateType:%@",candidateType]];
  843. localCandidateStr = [localCandidateStr stringByAppendingString:@"\n"];
  844. }
  845. NSString *address = [rtcStatistics.values objectForKey:@"address"];
  846. if (address) {
  847. localCandidateStr = [localCandidateStr stringByAppendingString:[NSString stringWithFormat:@"address:%@",address]];
  848. localCandidateStr = [localCandidateStr stringByAppendingString:@"\n"];
  849. }
  850. NSString *ip = [rtcStatistics.values objectForKey:@"ip"];
  851. if (ip) {
  852. localCandidateStr = [localCandidateStr stringByAppendingString:[NSString stringWithFormat:@"ip:%@",ip]];
  853. localCandidateStr = [localCandidateStr stringByAppendingString:@"\n"];
  854. }
  855. NSString *relatedAddress = [rtcStatistics.values objectForKey:@"relatedAddress"];
  856. if (relatedAddress) {
  857. localCandidateStr = [localCandidateStr stringByAppendingString:[NSString stringWithFormat:@"relatedAddress:%@",relatedAddress]];
  858. localCandidateStr = [localCandidateStr stringByAppendingString:@"\n"];
  859. }
  860. }
  861. }else if ([rtcStatistics.type isEqualToString:@"remote-candidate"]){
  862. NSString *tempRemoteCandidateId = rtcStatistics.id;
  863. if ([tempRemoteCandidateId isEqualToString:remoteCandidateId]) {
  864. HLog(@"三网数据--remoteCandidateIdInfo-->%@",rtcStatistics.values);
  865. remoteCandidateStr = @"远端\n";
  866. NSString *candidateType = [rtcStatistics.values objectForKey:@"candidateType"];
  867. if (candidateType) {
  868. remoteCandidateStr = [remoteCandidateStr stringByAppendingString:[NSString stringWithFormat:@"candidateType:%@",candidateType]];
  869. remoteCandidateStr = [remoteCandidateStr stringByAppendingString:@"\n"];
  870. }
  871. NSString *address = [rtcStatistics.values objectForKey:@"address"];
  872. if (address) {
  873. remoteCandidateStr = [remoteCandidateStr stringByAppendingString:[NSString stringWithFormat:@"address:%@",address]];
  874. remoteCandidateStr = [remoteCandidateStr stringByAppendingString:@"\n"];
  875. }
  876. NSString *ip = [rtcStatistics.values objectForKey:@"ip"];
  877. if (ip) {
  878. remoteCandidateStr = [remoteCandidateStr stringByAppendingString:[NSString stringWithFormat:@"ip:%@",ip]];
  879. remoteCandidateStr = [remoteCandidateStr stringByAppendingString:@"\n"];
  880. }
  881. NSString *relatedAddress = [rtcStatistics.values objectForKey:@"relatedAddress"];
  882. if (relatedAddress) {
  883. remoteCandidateStr = [remoteCandidateStr stringByAppendingString:[NSString stringWithFormat:@"relatedAddress:%@",relatedAddress]];
  884. remoteCandidateStr = [remoteCandidateStr stringByAppendingString:@"\n"];
  885. }
  886. }
  887. }
  888. }
  889. }
  890. NSString *showStr = @"";
  891. if (localCandidateStr) {
  892. showStr = [showStr stringByAppendingString:localCandidateStr];
  893. }
  894. if (remoteCandidateStr) {
  895. showStr = [showStr stringByAppendingString:remoteCandidateStr];
  896. }
  897. //网络延迟, 丢包率,FPS,网速 分辨率 流量
  898. //延时数据
  899. NSString*currentRoundTripTimeStr = [[NSString alloc] initWithFormat:@"延时:%ldms\n",(NSInteger)(currentRoundTripTime.floatValue*1000)];
  900. showStr = [showStr stringByAppendingString:currentRoundTripTimeStr];
  901. //计算上次报道到这一次的丢包率---------界面展示百分比丢包率
  902. long allPacketsReceived = packetsReceived - lasPacketsReceived;
  903. alllostData = audiolostData + videolostData;
  904. NSInteger lostRate = ((alllostData - lastAlllostData) *1.0 / (allPacketsReceived + (alllostData - lastAlllostData))) *100;
  905. //记录上一次丢包数
  906. lastAlllostData = alllostData;
  907. //记录上一次接收包数
  908. lasPacketsReceived = packetsReceived;
  909. NSString*lostDataStr = [[NSString alloc] initWithFormat:@"丢包率:(%ld/%ld) %ld%%\n",alllostData - lastAlllostData,allPacketsReceived + alllostData - lastAlllostData,lostRate];
  910. showStr = [showStr stringByAppendingString:lostDataStr];
  911. //FPS
  912. NSString*FPSStr = [[NSString alloc] initWithFormat:@"FPS:%ld\n",framesPerSecond];
  913. showStr = [showStr stringByAppendingString:FPSStr];
  914. //网速 传输数据速度
  915. NSString *netDataSpeedStr = [NSString stringWithFormat:@"传输数据速度:%ldk/s\n",preReceive/1024];
  916. showStr = [showStr stringByAppendingString:netDataSpeedStr];
  917. mainBlock(^{
  918. [self->netWorkInfoLabel setText:showStr];
  919. });
  920. }
  921. #pragma mark 收到的webrtc消息处理
  922. - (void)handleWebRtcMsgResponseBy:(NSData*)message
  923. {
  924. if([message isKindOfClass:[NSMutableString class]] || [message isKindOfClass:[NSString class]])
  925. {
  926. message = [(NSString *)message dataUsingEncoding:(NSUTF8StringEncoding)];
  927. }
  928. NSError *error = nil;
  929. NSDictionary *dataDict = [NSJSONSerialization JSONObjectWithData:message options:NSJSONReadingMutableContainers error:&error];
  930. HLog(@"webRtc 音视频推拉流 通道接收消息:------------------%@",dataDict);
  931. if(!dataDict){
  932. //[weakSelf handleDownloadResponseFunBy:message];
  933. return;
  934. }
  935. if(![dataDict isKindOfClass:[NSDictionary class]]){
  936. //[__NSCFString allKeys] unrecognized selector sent to ins
  937. return;
  938. }
  939. if(![[dataDict allKeys] containsObject:@"type"]){
  940. return;
  941. }
  942. NSString *messageType = dataDict[@"type"];
  943. if ([messageType isEqualToString:@"login"]) {
  944. if([[dataDict allKeys] containsObject:@"value"]){
  945. NSString *value = dataDict[@"value"];
  946. [self LogoutByOtherFun:value];
  947. }
  948. }
  949. }
  950. @end