You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 

536 lines
19 KiB

//
// VideoChatViewController.m
// LekangGuard
//
// Created by ecell on 2023/1/12.
//
#import "VideoChatViewController.h"
#import "VideoMemberCollectionViewCell.h"
#import "CallViewController.h"
#import "JCManager.h"
#import "BRManager.h"
#import "TihuManager.h"
@interface VideoChatViewController ()<WSLWaterFlowLayoutDelegate,UICollectionViewDelegate,UICollectionViewDataSource>
@property (nonatomic, assign) WSLWaterFlowLayoutStyle flowLayoutStyle;
@property (nonatomic ,strong) UICollectionView *menuCollectionView;
@property (nonatomic ,strong) UIView *headerView;
@property (nonatomic ,strong) DeviceVideoConfigModel *configModel;
@property (assign, nonatomic) int callTimes;
@property (assign, nonatomic) BOOL isCancelTimer;
@end
@interface TestUILabel : UILabel
@end
@implementation TestUILabel
- (void)drawTextInRect:(CGRect)rect
{
//文字距离上下左右边框都有10单位的间隔
CGRect newRect = CGRectMake(rect.origin.x + 10, rect.origin.y + 10, rect.size.width - 20, rect.size.height -20);
[super drawTextInRect:newRect];
}
@end
@implementation VideoChatViewController
- (void)viewDidLoad {
[super viewDidLoad];
self.zx_navTitle = GJText(@"视频通话");
// Do any additional setup after loading the view.
[self.view addSubview:self.headerView];
[self.headerView mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.right.equalTo(self.view);
make.top.equalTo(self.view).offset(iPhoneX_NavHeight);
make.height.mas_equalTo(300);
}];
[self GetQueryVideo];
UIButton *callBtn = [UICommon ui_buttonSimple:CGRectZero font:FontADA_(14) normalColor:KKWhiteColorColor normalText:GJText(@"视频通话") click:^(id x) {
[self monitorDevice];
}];
callBtn.backgroundColor = KKMainColor;
callBtn.layer.cornerRadius = 5;
callBtn.layer.masksToBounds = YES;
[self.view addSubview:callBtn];
[callBtn mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.right.equalTo(self.view).inset(20);
make.bottom.equalTo(self.view.mas_bottom).inset(iPhoneX_TabbarSafeBottomMargin > 0 ? iPhoneX_TabbarSafeBottomMargin : 30);
make.height.mas_equalTo(Adapted(48));
}];
WSLWaterFlowLayout *FlowLayout = [[WSLWaterFlowLayout alloc] init];
FlowLayout.delegate = self;
FlowLayout.flowLayoutStyle = self.flowLayoutStyle;
_menuCollectionView = [[UICollectionView alloc] initWithFrame:CGRectMake(0, 0, SCREEN_WIDTH-20, SCREEN_HEIGHT) collectionViewLayout:FlowLayout];
_menuCollectionView.backgroundColor = KKClearColor;
_menuCollectionView.dataSource = self;
_menuCollectionView.delegate = self;
_menuCollectionView.showsVerticalScrollIndicator = NO;
_menuCollectionView.alwaysBounceVertical = NO;
_menuCollectionView.scrollEnabled = NO;
if (@available(iOS 11.0, *))
_menuCollectionView.contentInsetAdjustmentBehavior = UIScrollViewContentInsetAdjustmentNever;
[_menuCollectionView registerClass:VideoMemberCollectionViewCell.class forCellWithReuseIdentifier:NSStringFromClass(VideoMemberCollectionViewCell.class)];
[self.view addSubview:_menuCollectionView];
[_menuCollectionView mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.right.equalTo(self.view);
make.top.equalTo(self.headerView.mas_bottom);
make.bottom.equalTo(callBtn.mas_top);
}];
}
#pragma mark - WSLWaterFlowLayoutDelegate
//返回每个item大小
- (CGSize)waterFlowLayout:(WSLWaterFlowLayout *)waterFlowLayout sizeForItemAtIndexPath:(NSIndexPath *)indexPath
{
return CGSizeMake((SCREEN_WIDTH-65)/5, (SCREEN_WIDTH)/5);
}
/** 头视图Size */
-(CGSize )waterFlowLayout:(WSLWaterFlowLayout *)waterFlowLayout sizeForHeaderViewInSection:(NSInteger)section
{
return CGSizeMake(SCREEN_WIDTH, 0);
}
/** 列数*/
-(CGFloat)columnCountInWaterFlowLayout:(WSLWaterFlowLayout *)waterFlowLayout
{
return 5;
}
/** 列间距*/
-(CGFloat)columnMarginInWaterFlowLayout:(WSLWaterFlowLayout *)waterFlowLayout
{
return 10;
}
/** 行间距*/
-(CGFloat)rowMarginInWaterFlowLayout:(WSLWaterFlowLayout *)waterFlowLayout
{
return 10;
}
/** 边缘之间的间距*/
-(UIEdgeInsets)edgeInsetInWaterFlowLayout:(WSLWaterFlowLayout *)waterFlowLayout
{
return UIEdgeInsetsMake(5, 10, 5, 10);
}
#pragma mark - UICollectionView数据源
//组个数
- (NSInteger)numberOfSectionsInCollectionView:(UICollectionView *)collectionView
{
return 1;
}
//组内成员个数
- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section
{
return self.modelListArr.count;
}
//设置元素内容
- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
{
VideoMemberCollectionViewCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:NSStringFromClass(VideoMemberCollectionViewCell.class) forIndexPath:indexPath];
cell.model = self.modelListArr[indexPath.row];
return cell;
}
-(void)collectionView:(UICollectionView *)collectionView didSelectItemAtIndexPath:(NSIndexPath *)indexPath
{
}
- (UIView *)headerView
{
if (!_headerView)
{
_headerView = [UIView new];
_headerView.backgroundColor = KKClearColor;
UIImageView *iconView = [UIImageView new];
iconView.layer.cornerRadius = 8;
iconView.layer.masksToBounds = YES;
if (APIManager.sharedManager.deviceModel.image.length <= 0)
[iconView setImage:ImageName_(APIManager.sharedManager.deviceModel.sex == 0 ? @"icon_head_girl" : @"icon_head_boy")];
else
[iconView sd_setImageWithURL:[NSURL URLWithString:APIManager.sharedManager.deviceModel.image] placeholderImage:ImageName_(@"")];
[_headerView addSubview:iconView];
[iconView mas_makeConstraints:^(MASConstraintMaker *make) {
make.centerX.equalTo(_headerView);
make.top.equalTo(_headerView).offset(Adapted(50));
make.width.height.mas_equalTo(Adapted(70));
}];
UILabel *nameLabel = [UICommon ui_label:CGRectZero lines:0 align:NSTextAlignmentLeft font:FontADA_(17) textColor:KKTextBlackColor text:@"" Radius:0];
nameLabel.text = APIManager.sharedManager.deviceModel.name;
[_headerView addSubview:nameLabel];
[nameLabel mas_makeConstraints:^(MASConstraintMaker *make) {
make.centerX.equalTo(_headerView);
make.top.equalTo(iconView.mas_bottom).offset(5);
}];
NSString *Labelstr = GJText(@"设备视频通话联系人管理(注:每次只能和一个联系人视频)");
CGRect rect = [UICommon GetTextWidth:Labelstr ViewHeight:SCREEN_WIDTH fontSize:Font_(13) type:@"h"];
UIView *bgView = [UIView new];
bgView.backgroundColor = RGB(248, 248, 248);
[_headerView addSubview:bgView];
[bgView mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.right.equalTo(_headerView);
make.bottom.equalTo(_headerView.mas_bottom);
make.height.mas_equalTo(Adapted(rect.size.height+10));
}];
UILabel *titleLabel = [UICommon ui_label:CGRectZero lines:0 align:NSTextAlignmentLeft font:FontADA_(13) textColor:KKGrey121 text:Labelstr Radius:0];
[_headerView addSubview:titleLabel];
[titleLabel mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.right.equalTo(bgView).inset(15);
make.centerY.equalTo(bgView);
}];
}
return _headerView;
}
#pragma mark 根据imei查询可视频通话成员
/// 根据imei查询可视频通话成员
- (void)GetQueryVideo
{
[UICommon MessageUpload:@"加载中"];
NSMutableDictionary *parameters = [NSMutableDictionary dictionary];
[parameters setValue:APIManager.sharedManager.deviceModel.imei forKey:@"imei"];
[[[APIManager sharedManager] APGET:QueryVideo_URL parameters:parameters resultClass:nil] subscribeNext:^(NSArray *arr) {
[UICommon HidenLoading];
if (ARRAYHASVALUE(arr))
{
[arr enumerateObjectsUsingBlock:^(NSDictionary *obj, NSUInteger idx, BOOL * _Nonnull stop) {
MemberModel *model = [MemberModel yy_modelWithJSON:obj];
[self.modelListArr addObject:model];
}];
[self.menuCollectionView reloadData];
}
} error:^(NSError * _Nullable error) {
NSDictionary *dic = error.userInfo;
[UICommon MessageErrorText:dic[NSLocalizedDescriptionKey]];
}];
}
#pragma mark 视频通话方法
/// 视频通话方法
- (void)monitorDevice
{
kWeakSelf(self)
JLAuthorizationManager *jlManager = [JLAuthorizationManager defaultManager];
[jlManager JL_requestAuthorizationWithAuthorizationType:JLAuthorizationTypeMicrophone
authorizedHandler:^{
[weakself videoActionFunction];
}
unAuthorizedHandler:^{
EasyAlertView *alertV = [EasyAlertView alertViewWithTitle:GJText(@"请在iPhone的\"设置-隐私-麦克风\"选项中,允许守护星访问你的麦克风") subtitle:nil AlertViewType:AlertViewTypeSystemAlert config:nil];
[alertV addAlertItem:^EasyAlertItem *{
return [EasyAlertItem itemWithTitle:GJText(@"确定") type:AlertItemTypeSystemDefault callback:nil];
}];
[alertV showAlertView];
}];
[jlManager JL_requestAuthorizationWithAuthorizationType:JLAuthorizationTypeCamera
authorizedHandler:nil
unAuthorizedHandler:^{
EasyAlertView *alertV = [EasyAlertView alertViewWithTitle:GJText(@"请在iPhone的\"设置-隐私-相机\"选项中,允许守护星访问你的相机") subtitle:nil AlertViewType:AlertViewTypeSystemAlert config:nil];
[alertV addAlertItem:^EasyAlertItem *{
return [EasyAlertItem itemWithTitle:GJText(@"确定") type:AlertItemTypeSystemDefault callback:nil];
}];
[alertV showAlertView];
}];
}
#pragma mark 主动请求视频通话返回配置参数
/// 主动请求视频通话返回配置参数
- (void)videoActionFunction
{
kWeakSelf(self)
[UICommon MessageUpload:@"加载中"];
NSMutableDictionary *parameters = [NSMutableDictionary dictionary];
[parameters setValue:@(0) forKey:@"callType"];/// 视频通话类型(0:视频,1:语音)
[parameters setValue:APIManager.sharedManager.deviceModel.imei forKey:@"imei"];
[parameters setValue:@"APP" forKey:@"type"];/// 学生证发起传:device,APP发起传:APP
[[[APIManager sharedManager] APGET:UserQueryVideo_URL parameters:parameters resultClass:DeviceVideoConfigModel.class] subscribeNext:^(DeviceVideoConfigModel *model) {
[UICommon HidenLoading];
weakself.configModel = model;
[weakself callVideo:model];
} error:^(NSError * _Nullable error) {
NSDictionary *dic = error.userInfo;
[UICommon MessageErrorText:dic[NSLocalizedDescriptionKey]];
}];
}
#pragma mark 拨打拨打视频电话
- (void)callVideo:(DeviceVideoConfigModel *)model
{
kWeakSelf(self)
NSMutableDictionary *parameters = [NSMutableDictionary dictionary];
[parameters setValue:@(0) forKey:@"callType"];
[parameters setValue:APIManager.sharedManager.deviceModel.imei forKey:@"imei"];
[[[APIManager sharedManager] APGET:VideoCall_URL parameters:parameters resultClass:nil] subscribeNext:^(id _Nullable x) {
[UICommon HidenLoading];
if(model.videoType == 2)
{
//声网
[weakself SWJoinChannel];
}
else if (model.videoType == 3)
{
/// 佰瑞
[weakself BR_LoginAndCallVideo];
}
else if (model.videoType == 4)
{
/// 鹈鹕
[weakself TH_LoginAndCallVideo];
}
else if (model.videoType == 1)
{
//菊风 (默认)
[weakself JH_LoginAndCallVideo];
}
} error:^(NSError * _Nullable error) {
NSDictionary *dic = error.userInfo;
[UICommon MessageErrorText:dic[NSLocalizedDescriptionKey]];
}];
}
#pragma mark 声网
/// 调起声网
- (void)SWJoinChannel
{
UIStoryboard *sb = [UIStoryboard storyboardWithName:@"Main" bundle:[NSBundle mainBundle]];
CallViewController *callVC = [sb instantiateViewControllerWithIdentifier:@"CallViewController"];
callVC.appid = self.configModel.appKey;
// callVC.token = self.agoraModel.token;
callVC.video_id = self.configModel.videoId;
// callVC.channelID = self.agoraModel.channelID;
callVC.uid = self.configModel.userId;
// callVC.device_uid = self.configModel.device_uid;
callVC.videoSize = CGSizeMake(self.configModel.width, self.configModel.height) ; //AgoraVideoDimension640x360
callVC.limit_time = self.configModel.allCallTime;
callVC.wait_time = self.configModel.callInterval;
callVC.modalPresentationStyle = UIModalPresentationFullScreen;
[self presentViewController:callVC animated:NO completion:nil];
}
#pragma mark 菊风
/// 调起菊风
- (void)JH_LoginAndCallVideo
{
//需要去注册
if(![JCManager shared].client)
{
[[JCManager shared] initializeWithAPPKey:self.configModel.appKey];
[[JCManager shared].client setServerAddress:@"http:cn.router.justalkcloud.com:8080"];
[[JCManager shared].client login:APIManager.sharedManager.loginModel.openid password:@"test" loginParam:nil];
}
else
{
[[JCManager shared] _stopCallTimeoutTimer];
[[JCManager shared] _stopVideoLimitTimeoutTimer];
}
[JCManager shared].gMianVC = self;
//测试模拟
// self.jhModel.limit_time = DefineVideoLimitTime;
// self.jhModel.wait_time = DefineCallWaitTime;
[JCManager shared].model = self.configModel;
[[JCManager shared] callVideoWithUserName];
//调起页面
UIStoryboard *sb = [UIStoryboard storyboardWithName:@"Main" bundle:[NSBundle mainBundle]];
JuPhoonCallViewController *callVC = [sb instantiateViewControllerWithIdentifier:@"JuPhoonCallViewController"];
[JCManager shared].callViewController = callVC;
callVC.video_id = self.configModel.videoId;
callVC.distinguishability_width = self.configModel.width;
callVC.distinguishability_heiger = self.configModel.height;
callVC.device = APIManager.sharedManager.deviceModel;
callVC.isReceiveCall = NO; //主叫
callVC.statusLabel.text = GJText(@"正在发起通话请求...");
[callVC openLocationCarmeraViewWithFullSScreen:YES];
// //清除原本定时器配置
callVC.modalPresentationStyle = UIModalPresentationFullScreen;
[self.navigationController presentViewController:callVC animated:YES completion:nil];
}
#pragma mark 佰瑞
/// 调起佰瑞
- (void)BR_LoginAndCallVideo
{
if (![[BRManager shared] isUserLogin]) {
[[BRManager shared] initialize];
[BRManager shared].gMianVC = self;
[[BRManager shared] login:self.configModel.deviceUserName nick:APIManager.sharedManager.deviceModel.name];
}
[BRManager shared].brModel = self.configModel;
[BRManager shared].isReceiveCall = NO;
[BRManager shared].video_id = self.configModel.videoId;
[BRManager shared].callType = 0;
kWeakSelf(self)
[[BRManager shared] showCallDialog:APIManager.sharedManager.deviceModel userId:[self.configModel.deviceUserName intValue] callback:^{
[weakself cancelTimer];
}];
_callTimes = 0;
BOOL online = [[BRManager shared] queryRemoteUserOnline:[self.configModel.deviceUserName intValue]];
if (online) {
[AnyChatPlatform VideoCallControl:BRAC_VIDEOCALL_EVENT_REQUEST :[self.configModel.deviceUserName intValue] :0 :0 :0 :@"video"];
} else {
[self performSelector:@selector(reCall) withObject:nil afterDelay:3];
}
}
- (void)cancelTimer {
[NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(reCall) object:nil];
}
- (void)reCall {
_callTimes++;
if (_callTimes > 3) {
[AnyChatPlatform VideoCallControl:BRAC_VIDEOCALL_EVENT_REQUEST :[self.configModel.deviceUserName intValue] :0 :0 :0 :@"video"];
return;
}
BOOL online = [[BRManager shared] queryRemoteUserOnline:[self.configModel.deviceUserName intValue]];
if (online) {
[AnyChatPlatform VideoCallControl:BRAC_VIDEOCALL_EVENT_REQUEST :[self.configModel.deviceUserName intValue] :0 :0 :0 :@"video"];
} else {
[self performSelector:@selector(reCall) withObject:nil afterDelay:3];
}
NSLog(@"查询用户在线次数:%d", _callTimes);
}
#pragma mark 鹈鹕
/// 调起鹈鹕
- (void)TH_LoginAndCallVideo
{
if (![[TihuManager shared] isUserLogin]) {
[[TihuManager shared] login:APIManager.sharedManager.loginModel.openid pwd:@"123456"];
}
[TihuManager shared].thModel = self.configModel;
[TihuManager shared].isReceiveCall = NO;
[TihuManager shared].video_id = self.configModel.videoId;
[TihuManager shared].callType = 0;
kWeakSelf(self)
[[TihuManager shared] showCallDialog:APIManager.sharedManager.deviceModel userId:self.configModel.deviceUserName callback:^{
[weakself cancelTimer2];
}];
_callTimes = 0;
_isCancelTimer = NO;
[[TihuManager shared] queryRemoteUserOnline:self.configModel.imei callback:^(BOOL online) {
if (online) {
[MoonChatPlatform startCalling:self.configModel.imei phoneType:MoonChatVideo callBlock:^(CallStatus status) {
NSLog(@"========CallStatus=%zd", status);
}];
} else {
if (!self->_isCancelTimer) {
[weakself performSelector:@selector(reCall2) withObject:nil afterDelay:3];
}
}
NSLog(@"查询用户在线:%d", online);
}];
}
- (void)cancelTimer2 {
_isCancelTimer = YES;
[NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(reCall2) object:nil];
}
- (void)reCall2 {
_callTimes++;
if (_callTimes > 3) {
[MoonChatPlatform startCalling:self.configModel.imei phoneType:MoonChatVideo callBlock:^(CallStatus status) {
NSLog(@"=========CallStatus=%zd", status);
}];
return;
}
kWeakSelf(self)
[[TihuManager shared] queryRemoteUserOnline:self.configModel.imei callback:^(BOOL online) {
if (online) {
[MoonChatPlatform startCalling:self.configModel.imei phoneType:MoonChatVideo callBlock:^(CallStatus status) {
NSLog(@"========CallStatus=%zd", status);
}];
} else {
if (!self->_isCancelTimer) {
[weakself performSelector:@selector(reCall2) withObject:nil afterDelay:3];
}
}
NSLog(@"查询用户在线:%d", online);
}];
NSLog(@"查询用户在线次数:%d", _callTimes);
}
/*
#pragma mark - Navigation
// In a storyboard-based application, you will often w ant to do a little preparation before navigation
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
// Get the new view controller using [segue destinationViewController].
// Pass the selected object to the new view controller.
}
*/
@end