//
//  GMVideoTelephoneLoginManager.m
//  Gengmei
//
//  Created by 卢悦明 on 2020/2/18.
//  Copyright © 2020 更美互动信息科技有限公司. All rights reserved.
//处理用户，医生登录的

#import "GMUserVideoTelephoneLogin.h"
#import "GMRtcManager.h"
#import "GMUserVideoTelephoneWindow.h"
#import "GMVideoTelephoneRequestTool.h"
#import "GMTelephoneAudioPlay.h"
#import "GMAppCameraAndMicrophone.h"
#import "GMVideoPhobos.h"
#import "GMSureOrderPopView.h"
#import "GMToFaceOrderInfoModel.h"
#import "GMNimChannelManager.h"
#import "NSDictionary+json.h"
#import "GMToFaceNetworking.h"
#import <GMBase/GMBaseTool.h>



static GMUserVideoTelephoneLogin *loginManager = nil;

@interface GMUserVideoTelephoneLogin ()<TTTRtcEngineDelegate, GMVideoTelephoneWindowDelegate>
/// 用户id(更美的userId)
@property (nonatomic, assign) int64_t uid;
/// 聊天室房间id
@property (nonatomic, strong) NSString *channelId;
/// 角色
@property (nonatomic, assign) TTTRtcClientRole clientRole;
/// 推流地址
@property (nonatomic, strong) NSString *pushURL;
/// 扩展字段
@property (nonatomic, strong) NSDictionary *extensionDict;

@property (nonatomic, strong) GMPublicNomalHUD *logoHud;
/// 正式发起1v1视频面诊的参数
@property (nonatomic, strong) NSDictionary *messageDict;

/// 网易云信
@property (nonatomic, strong) GMNeteaseIMModel *neteaseModel;
@end

@implementation GMUserVideoTelephoneLogin {
    GMRtcManager *TTManager;
    GMTelephoneAudioPlay *_audioPlay;
    GMVideoTelephoneWindow *_window;
    /// 加入房间重试次数，大于等于0，0代表不重试
    NSInteger _joinChannelRetryCount;

    /// 重试间隔，毫秒，大于等于0
    NSInteger _joinChannelRetryMs;
}

+ (GMUserVideoTelephoneLogin *)sharedVideoTelephoneLogin {
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        loginManager = [[GMUserVideoTelephoneLogin alloc] init];
    });
    return loginManager;
}

- (instancetype)init
{
    self = [super init];
    if (self) {
        self.logoHud = [[GMPublicNomalHUD alloc] init];
        self.logoHud.frame = CGRectMake(0, 0, 100, 100);
        self.logoHud.hidden = YES;
        self.logoHud.center = [GMBaseTool getCurrentViewController].view.center;
    }
    return self;
}

#pragma mark - 主播
- (void)userCreateVideoRoom:(NSDictionary*)messageDict extension:(NSDictionary *)extentsionDict {
    self.messageDict = messageDict;
    if ([GMAppCameraAndMicrophone getAppCameraAction] == NO ||  [GMAppCameraAndMicrophone getAppMicrophoneAction] == NO) {
        //如果相机或是麦克风权限必须获取才能视频通话
        return;
    }
    
    [[GMBaseTool getCurrentViewController].view addSubview:self.logoHud];
    self.logoHud.hidden = NO;
    _clientRole = TTTRtc_ClientRole_Anchor;
    _extensionDict = extentsionDict;
    TTManager = [GMRtcManager sharedRtcManager];
    __weak typeof(self) weakSelf = self;
    [GMVideoTelephoneRequestTool userVideoTelephoneMessage:messageDict finishBlock:^(BOOL success, NSDictionary *modelDict, NSString *errorMessage) {
        weakSelf.logoHud.hidden = YES;
        if (success) {
            GMVideoTelephoneModel *model = modelDict[@"model"];
            
            [GMVideoPhobos consultation_traceWithActionStep:@"Consultation.One2One.Launch" status:@"success" extraParam:@{@"order_no": SafeString(messageDict[@"order_no"]), @"consultation_record_id": SafeString(model.consultationRecordId)}];
            
            [self userLoginVideoRoomModel:model];
        } else {
            [GMVideoPhobos consultation_traceWithActionStep:@"Consultation.One2One.Launch" status:@"failed" extraParam:@{@"order_no": SafeString(messageDict[@"order_no"]), @"consultation_record_id": SafeString(messageDict[@"consultation_record_id"])}];
            [GMHudModule showWarning:errorMessage];
        }
        
    }]; 
}

#pragma mark- 副播
- (void)userEnterVideoRoom:(NSDictionary*)messageDict extension:(NSDictionary *)extentsionDict {
    self.messageDict = messageDict;
    if ([GMAppCameraAndMicrophone getAppCameraAction] == NO ||  [GMAppCameraAndMicrophone getAppMicrophoneAction] == NO) {
           //如果相机或是麦克风权限必须获取才能视频通话
           return;
    }
    [[GMBaseTool getCurrentViewController].view addSubview:self.logoHud];
    _clientRole = TTTRtc_ClientRole_Broadcaster;
    _extensionDict = extentsionDict;
    TTManager = [GMRtcManager sharedRtcManager];
    GMVideoTelephoneModel *model = [[GMVideoTelephoneModel alloc] initWithDictionary:messageDict error:nil];
      // 重试数据
      _joinChannelRetryMs = model.joinChannelRetryMs;
      _joinChannelRetryCount = model.joinChannelRetryCount;
    [self userLoginVideoRoomModel:model];
}

#pragma mark - 初始化直播间
- (void)userLoginVideoRoomModel:(GMVideoTelephoneModel *)model  {
    _uid = [[[GMRouter sharedInstance] pushScheme:@"gengmei://gm_userId"] longLongValue];
    _channelId = model.channelId;
    _pushURL = model.streamUrl;
    _neteaseModel = model.neteaseIm;
    if (_channelId.integerValue == 0 || _channelId.length >= 19) {
        TTManager.telephoneStatus = TelephoneVideoStatus_rest;
        //三体SDK的要求，channelId长度必须在0~19的范围内
        return;
    }
    [GMVideoPhobos video_monitoringWithActionStep:@"进入直播间" consultId:model.consultationRecordId traceId:nil];
    TTTRtcClientRole clientRole = _clientRole; //角色设置
    TTManager.me.clientRole = clientRole;
    TTManager.me.uid = _uid;
    TTManager.consultationRecordId = model.consultationRecordId;
    TTManager.vidoeTelephoneModel = model;
    TTManager.pushURL = _pushURL;
    TTManager.roomID = _channelId.longLongValue;
    TTManager.me.mutedSelf = false;
    TTTRtcEngineKit *rtcEngine = TTManager.rtcEngine;
    [TTManager beautyStatus:NO];//关闭美颜
    rtcEngine.delegate = self;
    [rtcEngine setChannelProfile:TTTRtc_ChannelProfile_LiveBroadcasting];
    [rtcEngine setClientRole:clientRole];
    [rtcEngine enableAudioVolumeIndication:200 smooth:3];
    
    if (_clientRole == TTTRtc_ClientRole_Anchor) {//主播推流
        TTTPublisherConfigurationBuilder *builder = [[TTTPublisherConfigurationBuilder alloc] init];
        //推流地址
        [builder setPublisherUrl:_pushURL];
        [rtcEngine configPublisher:builder.build];
    }
    [rtcEngine enableVideo];
    [rtcEngine muteLocalAudioStream:NO];
    BOOL swapWH = UIInterfaceOrientationIsPortrait(UIApplication.sharedApplication.statusBarOrientation);
    [rtcEngine setVideoProfile:TTTRtc_VideoProfile_720P swapWidthAndHeight:swapWH];
    [rtcEngine joinChannelByKey:nil channelName:_channelId uid:_uid joinSuccess:nil];
    [GMVideoPhobos consultation_traceWithActionStep:@"Consultation.Santi.Join" status:@"success" extraParam:@{@"order_no": SafeString(_messageDict[@"order_no"]), @"consultation_record_id": SafeString(model.consultationRecordId), @"channel_id": SafeString(_channelId)}];

}


#pragma mark - TTTRtcEngineDelegate初始化成功
-(void)rtcEngine:(TTTRtcEngineKit *)engine didJoinChannel:(NSString *)channel withUid:(int64_t)uid elapsed:(NSInteger)elapsed {

    [[NSNotificationCenter defaultCenter] postNotificationName:@"gm_push_remove_waiting_success" object:nil];
    // 加入房间并邀请
    if (_neteaseModel && [_neteaseModel.toAccountId isNonEmpty] && [_neteaseModel.channelId isNonEmpty]) {
        [[GMNimChannelManager shareInstance] doJoinAndInviteJoinChannelWithChannelId:_neteaseModel.channelId accountId:_neteaseModel.toAccountId customInfo:_neteaseModel.inviteExt resultBlock:^(BOOL isSuccess) {
            if (!isSuccess) {
#ifdef DEBUG
                [[GMBaseTool getCurrentViewController] toast:@"doJoinAndInviteJoinChannelWithChannelId失败"];
#endif
            }
        }];
    }
    
    [GMVideoTelephoneRequestTool telephoneMessageEventType:GMEventType_addSuccess consultationRecordId:TTManager.consultationRecordId finishBlock:nil];
    [self showWindow:_clientRole];
}

#pragma mark -初始化错误
-(void)rtcEngine:(TTTRtcEngineKit *)engine didOccurError:(TTTRtcErrorCode)errorCode {
    NSString *errorInfo = @"";
    switch (errorCode) {
        case TTTRtc_Error_Enter_TimeOut:
            errorInfo = @"超时,10秒未收到服务器返回结果";
            break;
        case TTTRtc_Error_Enter_Failed:
            errorInfo = @"该直播间不存在";
            break;
        case TTTRtc_Error_Enter_BadVersion:
            errorInfo = @"版本错误";
            break;
        case TTTRtc_Error_InvalidChannelName:
            errorInfo = @"无效的房间";
            break;
        case TTTRtc_Error_Enter_NoAnchor:
            errorInfo = @"接入失败，视频面诊将关闭，本次视频面诊订单金额将原路退还至您的账户";
            break;
        default:
            errorInfo = @"未知错误";
            break;
    }
    // 增加失败重试功能(当我是复播的时候)
    [self tryAgainIfFailedWithErrorInfo:errorInfo errorCode:errorCode];
}

/// 初始化失败重试
/// @param errorInfo 错误toast
/// @param errorCode 错误代码
- (void)tryAgainIfFailedWithErrorInfo:(NSString *)errorInfo errorCode:(TTTRtcErrorCode)errorCode {
    if (_clientRole == TTTRtc_ClientRole_Broadcaster && _joinChannelRetryCount > 0) {
        dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(_joinChannelRetryMs / 1000.0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
            [self userLoginVideoRoomModel:[[GMVideoTelephoneModel alloc] initWithDictionary:_messageDict error:nil]];
            _joinChannelRetryCount--;
        });
    } else {
        [GMVideoPhobos consultation_traceWithActionStep:@"Consultation.Santi.OnJoinError" status:@"failed" extraParam:@{@"order_no": SafeString(_messageDict[@"order_no"]), @"consultation_record_id": SafeString(TTManager.consultationRecordId), @"channel_id": SafeString(_channelId), @"error_code": @(errorCode)}];
        [self uploadFailedRecordWithErrorInfo:errorInfo];
    }
}

/// 上传状态到服务器
/// @param errorInfo 错误信息
- (void)uploadFailedRecordWithErrorInfo:(NSString *)errorInfo {
    TTManager.telephoneStatus = TelephoneVideoStatus_rest;
    [[NSNotificationCenter defaultCenter] postNotificationName:@"gm_push_remove_waiting_success" object:nil];
    [GMVideoTelephoneRequestTool telephoneMessageEventType:GMEventType_addFail consultationRecordId:TTManager.consultationRecordId finishBlock:nil];
    if (TTManager.totalTime <= 0) {
        [GMHudModule showWarning:errorInfo];
    }
}

#pragma mark - 展示直播页面
- (void)showWindow:(TTTRtcClientRole)userType {
    TTManager.telephoneStatus = TelephoneVideoStatus_wating;
    //禁止自动休眠
    [[UIApplication sharedApplication] setIdleTimerDisabled:YES];
    _window =  [[GMUserVideoTelephoneWindow alloc] initWithFrame:CGRectMake(0, 0, MAINSCREEN_WIDTH, MAINSCREEN_HEIGHT)];
    _window.delgate = self;
    [[UIApplication sharedApplication].keyWindow addSubview:_window];
}

#pragma mark - 直播中
- (void)videoLiveIn {}

#pragma mark - 关闭直播间的回调
- (void)nomalExitRoom {
    //取消禁止自动休眠
    [[UIApplication sharedApplication] setIdleTimerDisabled:NO];
    if (TTManager.telephoneStatus == TelephoneVideoStatus_rest) { //防止结束方法重复调用，导致套框
        return;
    }
    TTManager.telephoneStatus = TelephoneVideoStatus_rest;
    //如果接通时间为0，下面就不用走了
    if (TTManager.totalTime <= 0) {
        return;
    }
    NSInteger counsellorType = [self.messageDict[@"counsellor_type"] integerValue];
    NSInteger consultationType = [self.messageDict[@"consultation_type"] integerValue];
    //counsellorType = 1 医生 2 面诊师
    NSString *doctorId = counsellorType == 1 ? TTManager.vidoeTelephoneModel.counsellorInfo.doctorId:TTManager.vidoeTelephoneModel.counsellorInfo.id;
    [self clickConfireBtnPhobo:counsellorType consultationType:consultationType doctorId:doctorId];
    //确认订单
    [[GMToFaceNetworking shareInstance] excuteToFaceInfoSureOrder:self.messageDict[@"order_no"] SuccessBlock:^(id response) {
        GMToFaceOrderInfoModel *infoModel = [[GMToFaceOrderInfoModel alloc] initWithDictionary:response error:nil];
        infoModel.consultationRecordId = TTManager.consultationRecordId;
        GMSureOrderPopView *popView = [[GMSureOrderPopView alloc] init];
        popView.isCloseBtnHidden = YES;
        popView.infoModel = infoModel;
        [popView clickConfireBtnPhobo:counsellorType consultationType:consultationType doctorId:doctorId];
        [[GMBaseTool mainWindow]  addSubview:popView];
    } failureBlock:^(NSInteger errorCode, NSString *message) {
        [[GMBaseTool getCurrentViewController] toast:message];
    }];

}
- (void)clickConfireBtnPhobo:(NSInteger)counsellorType consultationType:(NSInteger)consultationType doctorId:(NSString *)doctorId{
    NSDictionary *dict = @{@"page_name":@"video_face_consultation",
                           @"order_id":self.messageDict[@"order_no"],
                           @"popup_name":@"confirm_order",
                           @"counsellor_type":@(counsellorType),
                           @"consultation_type":@(consultationType),
                           @"doctor_id":doctorId
    };
    [Phobos track:@"popup_view" attributes:dict];
}

@end
