Files
yinmeng-ios/xplan-ios/Main/Room/View/XPMiniRoomView.m

479 lines
16 KiB
Mathematica
Raw Normal View History

2021-12-03 17:07:21 +08:00
//
// XPMiniRoomView.m
// xplan-ios
//
// Created by on 2021/12/3.
//
#import "XPMiniRoomView.h"
///Third
#import <Masonry/Masonry.h>
2021-12-03 19:10:35 +08:00
#import <NIMSDK/NIMSDK.h>
2021-12-03 17:07:21 +08:00
///Tool
#import "XPMacro.h"
#import "ThemeColor.h"
#import "NetImageView.h"
#import "RtcManager.h"
#import "UIButton+EnlargeTouchArea.h"
#import "TTPopup.h"
#import "XCHudTool.h"
#import "XPRoomMiniManager.h"
#import "AccountInfoStorage.h"
2021-12-03 17:07:21 +08:00
///Model
#import "RoomInfoModel.h"
#import "MicroQueueModel.h"
#import "MicroStateModel.h"
#import "UserInfoModel.h"
#import "AttachmentModel.h"
2021-12-03 17:07:21 +08:00
///View
#import "XPRoomViewController.h"
#import "XPNoteView.h"
2021-12-03 17:07:21 +08:00
@interface XPMiniRoomView ()<NIMChatroomManagerDelegate, NIMChatManagerDelegate, NIMLoginManagerDelegate>
2021-12-03 17:07:21 +08:00
///
@property (nonatomic,strong) UIImageView *backImageView;
///
@property (nonatomic,strong) NetImageView *avatarImageView;
///
@property (nonatomic,strong) UILabel *nickLabel;
///id
@property (nonatomic,strong) UILabel *idLabel;
///
@property (nonatomic,strong) UIButton *closeButton;
///
@property (nonatomic,strong) XPNoteView *noteView;
///
@property (nonatomic,strong) RoomInfoModel *roomInfo;
///
@property (nonatomic,strong) UserInfoModel *userInfo;
///uid nil
@property (nonatomic,strong) NSString *currentRoomUid;
2021-12-03 19:10:35 +08:00
///id
@property (nonatomic,strong) NSString *currentRoomId;
///
@property (nonatomic, strong) NSMutableDictionary<NSString *, MicroQueueModel *> *micQueue;
2021-12-03 17:07:21 +08:00
@end
@implementation XPMiniRoomView
- (instancetype)initWithFrame:(CGRect)frame {
self = [super initWithFrame:frame];
if (self) {
[[NIMSDK sharedSDK].chatroomManager addDelegate:self];
[[NIMSDK sharedSDK].chatManager addDelegate:self];
[[NIMSDK sharedSDK].loginManager addDelegate:self];
2021-12-03 17:07:21 +08:00
[self initEvents];
[self initSubViews];
[self initSubViewConstraints];
}
return self;
}
#pragma mark - Public Method
- (void)configRoomMiniView:(RoomInfoModel *)roomInfo userInfo:(UserInfoModel *)userInfo micQueue:(NSMutableDictionary *)micQueue {
self.hidden = NO;
self.currentRoomUid = [NSString stringWithFormat:@"%ld", roomInfo.uid];
2021-12-03 19:10:35 +08:00
self.currentRoomId = [NSString stringWithFormat:@"%ld", roomInfo.roomId];
2021-12-03 17:07:21 +08:00
self.roomInfo = roomInfo;
self.userInfo = userInfo;
self.micQueue = micQueue;
2021-12-03 17:07:21 +08:00
[self startAvatarAnimation];
[self.noteView startAnimation];
2021-12-03 17:07:21 +08:00
}
- (void)hiddenRoomMiniView {
[self.avatarImageView.layer removeAllAnimations];
[self.noteView stopAnimation];
self.currentRoomUid = nil;
2021-12-03 19:10:35 +08:00
self.currentRoomId = nil;
self.roomInfo = nil;
self.userInfo = nil;
self.micQueue = nil;
self.hidden = YES;
}
2021-12-03 17:07:21 +08:00
#pragma mark - Private Method
- (void)initSubViews {
self.frame = CGRectMake(KScreenWidth - 140 * 1.2, KScreenHeight - kSafeAreaBottomHeight - 150, 140 * 1.2, 34 * 1.2);
2021-12-03 17:07:21 +08:00
[self addSubview:self.backImageView];
[self.backImageView addSubview:self.avatarImageView];
[self.backImageView addSubview:self.noteView];
[self.backImageView addSubview:self.nickLabel];
[self.backImageView addSubview:self.idLabel];
[self.backImageView addSubview:self.closeButton];
}
- (void)initSubViewConstraints {
[self.backImageView mas_makeConstraints:^(MASConstraintMaker *make) {
make.edges.mas_equalTo(self);
}];
[self.avatarImageView mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.mas_equalTo(self.backImageView).offset(5);
make.top.bottom.mas_equalTo(self.backImageView).inset(5);
make.height.mas_equalTo(self.avatarImageView.mas_width);
}];
[self.nickLabel mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.mas_equalTo(self.avatarImageView.mas_right).offset(5);
make.bottom.mas_equalTo(self.avatarImageView.mas_centerY).offset(-1.5);
}];
[self.idLabel mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.mas_equalTo(self.nickLabel);
make.top.mas_equalTo(self.avatarImageView.mas_centerY).offset(1.5);
}];
[self.closeButton mas_makeConstraints:^(MASConstraintMaker *make) {
make.size.mas_equalTo(CGSizeMake(15, 15));
make.centerY.mas_equalTo(self.backImageView);
make.right.mas_equalTo(self.backImageView).offset(-11);
}];
[self.noteView mas_makeConstraints:^(MASConstraintMaker *make) {
make.center.mas_equalTo(self.avatarImageView);
make.height.mas_equalTo(12);
make.width.mas_equalTo(12);
}];
}
- (void)initEvents {
UIPanGestureRecognizer *pan = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(roomMiniTag:)];
pan.delaysTouchesBegan = YES;
2021-12-03 17:07:21 +08:00
[self addGestureRecognizer:pan];
UITapGestureRecognizer *enterRoomTag = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(enterRomRecognizer:)];
[self addGestureRecognizer:enterRoomTag];
2021-12-03 17:07:21 +08:00
}
- (void)startAvatarAnimation {
CABasicAnimation *rotationAnimation = [CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
rotationAnimation.toValue = [NSNumber numberWithFloat: M_PI * 2.0 ];
rotationAnimation.duration = 3;
rotationAnimation.cumulative = YES;
rotationAnimation.repeatCount = MAXFLOAT;
rotationAnimation.removedOnCompletion = NO;
[self.avatarImageView.layer addAnimation:rotationAnimation forKey:@"rotationAnimation"];
}
#pragma mark - NIMChatroomManagerDelegate
- (void)chatroomBeKicked:(NIMChatroomBeKickedResult *)result {
///
if ([XPRoomMiniManager shareManager].getRoomInfo == nil) return;
if (result.reason == 2) {
[XCHUDTool showErrorWithMessage:@"您被管理员踢出直播间"];
} else if (result.reason == 5) {
[XCHUDTool showErrorWithMessage:@"您已被管理员拉黑"];
}
[[XPRoomMiniManager shareManager] configRoomInfo:nil];
[[RtcManager instance] exitRoom];
[self hiddenRoomMiniView];
}
#pragma mark - NIMLoginManagerDelegate
- (void)onKickout:(NIMLoginKickoutResult *)result {
///
if ([XPRoomMiniManager shareManager].getRoomInfo == nil) return;
[[XPRoomMiniManager shareManager] configRoomInfo:nil];
[[RtcManager instance] exitRoom];
[self hiddenRoomMiniView];
}
#pragma mark - NIMChatManagerDelegate
- (void)onRecvMessages:(NSArray<NIMMessage *> *)messages {
///
if ([XPRoomMiniManager shareManager].getRoomInfo == nil) return;
for (NIMMessage * message in messages) {
//
if (message.session.sessionType != NIMSessionTypeChatroom) {
continue;
}
//
if (![message.session.sessionId isEqualToString:[NSString stringWithFormat:@"%ld", self.roomInfo.roomId]]) {
continue;
}
if (message.messageType == NIMMessageTypeNotification) {
NIMNotificationObject *notiMsg = (NIMNotificationObject *)message.messageObject;
NIMChatroomNotificationContent *content = (NIMChatroomNotificationContent *)notiMsg.content;
[self handleNIMNotificationMessage:content];
} else if (message.messageType == NIMMessageTypeCustom) {
NIMCustomObject *obj = (NIMCustomObject *)message.messageObject;
if (obj.attachment != nil && [obj.attachment isKindOfClass:[AttachmentModel class]]) {
[self handleNIMCustomMessage:obj.attachment];
}
}
}
}
- (void)handleNIMNotificationMessage:(NIMChatroomNotificationContent *)content {
BOOL microQueueChanged = NO;
switch (content.eventType) {
case NIMChatroomEventTypeInfoUpdated: //
{
NSDictionary *data = [content.notifyExt toJSONObject];
int type = [data[@"type"] intValue];
NSArray* microStates;
switch (type) {
case 2:
microStates = @[[MicroStateModel modelWithJSON:data[@"micInfo"]]];
break;
case 3:
microStates = [MicroStateModel modelsWithArray:data[@"micInfo"]];
break;
}
if (microStates && microStates.count > 0) {
for (MicroStateModel *microState in microStates) {
MicroQueueModel *micSequence = [self.micQueue objectForKey:[NSString stringWithFormat:@"%d", microState.position]];
micSequence.microState = microState;
}
microQueueChanged = YES;
}
}
break;
case NIMChatroomEventTypeQueueChange: //
{
NSDictionary* data = (NSDictionary *)content.ext;
NSString* position = [data objectForKey:NIMChatroomEventInfoQueueChangeItemKey];
UserInfoModel* userInfo = [UserInfoModel modelWithJSON:[data objectForKey:NIMChatroomEventInfoQueueChangeItemValueKey]];
NSInteger changeType = [data[NIMChatroomEventInfoQueueChangeTypeKey] integerValue];
//
for (MicroQueueModel *sequence in self.micQueue.allValues) {
if (userInfo.uid == sequence.userInfo.uid) {
sequence.userInfo = nil;
}
}
if (changeType == 1) { //
MicroQueueModel *sequence = [self.micQueue objectForKey:position];
sequence.userInfo = userInfo;
}
microQueueChanged = YES;
}
break;
case NIMChatroomEventTypeExit:
case NIMChatroomEventTypeKicked:
{
for (NIMChatroomNotificationMember *member in content.targets) {
for (MicroQueueModel *sequence in self.micQueue.allValues) {
if (member.userId.integerValue == sequence.userInfo.uid) {
sequence.userInfo = nil;
microQueueChanged = YES;
}
}
}
}
break;
default:
break;
}
if (microQueueChanged) {
[self microQueueUpdated];
}
}
- (void)microQueueUpdated {
BOOL selfNeedBroadcast = NO;
for (int i = 0; i < self.micQueue.allKeys.count; i++) {
MicroQueueModel * model = [self.micQueue objectForKey:[NSString stringWithFormat:@"%d", i]];
if (model.userInfo.uid == [AccountInfoStorage instance].getUid.integerValue) {
selfNeedBroadcast = model.microState.micState == MicroMicStateType_Open;
}
}
[[RtcManager instance] broadcast:selfNeedBroadcast];
}
- (void)handleNIMCustomMessage:(AttachmentModel *)attachment {
if(attachment.first == CustomMessageType_Queue && attachment.second == Custom_Message_Sub_Queue_Invite) {
NSDictionary *dic = attachment.data;
NSString *uid = dic[@"uid"];
if (uid.integerValue == self.userInfo.uid) {
NSNumber *micPosition = dic[@"micPosition"];
NSString *position = micPosition.stringValue;
MicroQueueModel *micro = [self.micQueue objectForKey:position];
if (!micro || micro.userInfo) return; //
RoomInfoModel* roomInfo = self.roomInfo;
NSString* roomId = [NSString stringWithFormat:@"%ld", roomInfo.roomId];
UserInfoModel* userInfo = self.userInfo;
NIMChatroomQueueUpdateRequest *request = [[NIMChatroomQueueUpdateRequest alloc]init];
request.key = position;
2021-12-17 15:18:34 +08:00
request.value = [[self configUpdateChatRoomQueueExt:userInfo] toJSONString];
request.roomId = roomId;
request.transient = YES;
[[NIMSDK sharedSDK].chatroomManager updateChatroomQueueObject:request completion:^(NSError * _Nullable error) {
if (error) return;
[RtcManager instance].localMuted = YES;
TTAlertConfig *config = [[TTAlertConfig alloc] init];
config.title = @"房主或管理员拉你上麦";
config.message = @"你已被房主或管理员拉上麦,但并未开启麦克风。如需要说话,请打开麦克风。";
[TTPopup alertWithConfig:config confirmHandler:^{
} cancelHandler:^{
}];
}];
}
}
}
2021-12-17 15:18:34 +08:00
- (NSDictionary *)configUpdateChatRoomQueueExt:(UserInfoModel *)userInfo {
NSMutableDictionary * dic = [NSMutableDictionary dictionary];
[dic setValue:@(userInfo.gender) forKey:@"gender"];
[dic setValue:userInfo.avatar forKey:@"avatar"];
[dic setValue:@(userInfo.uid) forKey:@"uid"];
[dic setValue:userInfo.nick forKey:@"nick"];
NSString * headWearUrl = userInfo.headwearEffect.length > 0 ? userInfo.headwearEffect : userInfo.headwearPic;
if (headWearUrl.length > 0) {
[dic setValue:headWearUrl forKey:@"headWearUrl"];
}
return dic;
}
2021-12-03 17:07:21 +08:00
#pragma mark - Event Response
- (void)closeButtonAction:(UIButton *)sender {
2021-12-03 19:10:35 +08:00
[[NIMSDK sharedSDK].chatroomManager exitChatroom:self.currentRoomId completion:nil];
2021-12-03 17:07:21 +08:00
[[RtcManager instance] exitRoom];
[[XPRoomMiniManager shareManager] configRoomInfo:nil];
[self hiddenRoomMiniView];
2021-12-03 17:07:21 +08:00
}
- (void)enterRomRecognizer:(UITapGestureRecognizer *)tap {
2021-12-03 19:10:35 +08:00
if (self.currentRoomUid > 0 && self.controller) {
[XPRoomViewController openRoom:self.currentRoomUid viewController:self.controller];
2021-12-03 17:07:21 +08:00
}
}
- (void)roomMiniTag:(UIPanGestureRecognizer*)p {
UIWindow *appWindow = [UIApplication sharedApplication].delegate.window;
CGPoint panPoint = [p locationInView:appWindow];
if (p.state == UIGestureRecognizerStateBegan) {
self.alpha = 1;
} else if(p.state == UIGestureRecognizerStateChanged) {
self.center = CGPointMake(panPoint.x, panPoint.y);
} else if(p.state == UIGestureRecognizerStateEnded
|| p.state == UIGestureRecognizerStateCancelled) {
self.alpha = 1;
CGFloat touchWidth = self.frame.size.width;
CGFloat touchHeight = self.frame.size.height;
CGFloat screenWidth = [[UIScreen mainScreen] bounds].size.width;
CGFloat screenHeight = [[UIScreen mainScreen] bounds].size.height;
// fabs
CGFloat left = fabs(panPoint.x);
CGFloat right = fabs(screenWidth - left);
CGFloat top = fabs(panPoint.y);
CGFloat bottom = fabs(screenHeight - top);
CGFloat minSpace = 0;
minSpace = MIN(MIN(MIN(top, left), bottom), right);
CGPoint newCenter;
CGFloat targetY = 0;
//Y
if (panPoint.y < 15 + touchHeight / 2.0) {
targetY = 15 + touchHeight / 2.0;
}else if (panPoint.y > (screenHeight - touchHeight / 2.0 - 15)) {
targetY = screenHeight - touchHeight / 2.0 - 15;
}else{
targetY = panPoint.y;
}
if (minSpace == left) {
newCenter = CGPointMake(15+touchWidth/2.0, targetY);
}else if (minSpace == right) {
newCenter = CGPointMake(screenWidth - touchWidth/2.0 - 15, targetY);
}else if (minSpace == top) {
newCenter = CGPointMake(panPoint.x, touchWidth / 3);
}else {
newCenter = CGPointMake(panPoint.x, screenHeight - touchWidth / 3);
}
[UIView animateWithDuration:0.25 animations:^{
if (newCenter.y + self.frame.size.height / 2 > KScreenHeight - kSafeAreaBottomHeight - 44) {
self.center = CGPointMake(newCenter.x, KScreenHeight - self.frame.size.height / 2 - kSafeAreaBottomHeight - 44);
}else {
self.center = newCenter;
}
}];
}
}
#pragma mark - Getters And Setters
- (void)setRoomInfo:(RoomInfoModel *)roomInfo {
_roomInfo = roomInfo;
if (_roomInfo) {
self.avatarImageView.imageUrl = _roomInfo.avatar;
if (_roomInfo.title.length > 8) {
_roomInfo.title = [NSString stringWithFormat:@"%@…", [_roomInfo.title substringToIndex:8]];
}
self.nickLabel.text = _roomInfo.title;
self.idLabel.text = [NSString stringWithFormat:@"%@号:%ld", AppName,_roomInfo.erbanNo];
}
}
- (UIImageView *)backImageView {
if (!_backImageView) {
_backImageView = [[UIImageView alloc] init];
_backImageView.userInteractionEnabled = YES;
_backImageView.image = [UIImage imageNamed:@"room_mini_background"];
}
return _backImageView;
}
- (NetImageView *)avatarImageView {
if (!_avatarImageView) {
NetImageConfig * config = [[NetImageConfig alloc] init];
config.imageType = ImageTypeUserIcon;
config.placeHolder = [UIImageConstant defaultAvatarPlaceholder];
_avatarImageView = [[NetImageView alloc] initWithConfig:config];
_avatarImageView.layer.masksToBounds = YES;
_avatarImageView.layer.cornerRadius = (34 * 1.2 - 10)/2;
_avatarImageView.userInteractionEnabled = YES;
}
return _avatarImageView;
}
- (UILabel *)nickLabel {
if (!_nickLabel) {
_nickLabel = [[UILabel alloc] init];
_nickLabel.font = [UIFont systemFontOfSize:12];
_nickLabel.textColor = [ThemeColor mainTextColor];
}
return _nickLabel;
}
- (UILabel *)idLabel {
if (!_idLabel) {
_idLabel = [[UILabel alloc] init];
_idLabel.font = [UIFont systemFontOfSize:10];
_idLabel.textColor = [ThemeColor mainTextColor];
}
return _idLabel;
}
- (UIButton *)closeButton {
if (!_closeButton) {
_closeButton = [UIButton buttonWithType:UIButtonTypeCustom];
[_closeButton setImage:[UIImage imageNamed:@"room_mini_close"] forState:UIControlStateNormal];
[_closeButton addTarget:self action:@selector(closeButtonAction:) forControlEvents:UIControlEventTouchUpInside];
2021-12-04 01:00:15 +08:00
[_closeButton setEnlargeEdgeWithTop:10 right:10 bottom:10 left:10];
2021-12-03 17:07:21 +08:00
}
return _closeButton;
}
- (XPNoteView *)noteView {
if (!_noteView) {
_noteView = [[XPNoteView alloc] init];
_noteView.pillarColor = [UIColor colorWithWhite:1 alpha:0.6];
_noteView.pillarWidth = 2;
[_noteView startAnimation];
}
return _noteView;
}
@end