麦克风开关修复
This commit is contained in:
parent
732e2bfcfb
commit
67baeb15f3
@ -436,6 +436,7 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
int? _pendingSelfMicSwitchGuardUntilMs;
|
||||
num? _pendingSelfMicReleaseIndex;
|
||||
int? _pendingSelfMicReleaseGuardUntilMs;
|
||||
final Set<String> _confirmedSelfMicIdentityKeys = <String>{};
|
||||
int? _seatResizeOccupantPreserveUntilMs;
|
||||
_RoomRtcLocalAudioRole? _lastAppliedLocalAudioRole;
|
||||
bool? _lastAppliedLocalAudioMuted;
|
||||
@ -529,6 +530,7 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
currentUser?.id?.trim() ?? "",
|
||||
currentUser?.account?.trim() ?? "",
|
||||
currentUser?.getID().trim() ?? "",
|
||||
..._confirmedSelfMicIdentityKeys,
|
||||
}..removeWhere((item) => item.isEmpty);
|
||||
}
|
||||
|
||||
@ -550,6 +552,16 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
return _userProfileIdentityKeys(user).any(identityKeys.contains);
|
||||
}
|
||||
|
||||
void _rememberConfirmedSelfMicIdentity(SocialChatUserProfile? user) {
|
||||
_confirmedSelfMicIdentityKeys
|
||||
..clear()
|
||||
..addAll(_userProfileIdentityKeys(user));
|
||||
}
|
||||
|
||||
void _clearConfirmedSelfMicIdentity() {
|
||||
_confirmedSelfMicIdentityKeys.clear();
|
||||
}
|
||||
|
||||
///房间红包列表
|
||||
List<SCRoomRedPacketListRes> redPacketList = [];
|
||||
|
||||
@ -2522,7 +2534,10 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
notifyListeners();
|
||||
final currentUserId =
|
||||
(AccountStorage().getCurrentUser()?.userProfile?.id ?? "").trim();
|
||||
final seatIndex = userOnMaiInIndex(currentUserId);
|
||||
final seatIndex =
|
||||
currentUserId.isNotEmpty
|
||||
? userOnMaiInIndex(currentUserId)
|
||||
: (_currentUserMicSeat()?.micIndex ?? -1);
|
||||
if (seatIndex < 0) {
|
||||
notifyListeners();
|
||||
return;
|
||||
@ -2545,14 +2560,18 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
Future<void> handleSelfMicRemovedByRemote({
|
||||
bool refreshMicList = true,
|
||||
}) async {
|
||||
final currentUserKeys = _currentUserIdentityKeys();
|
||||
final currentUserId =
|
||||
(AccountStorage().getCurrentUser()?.userProfile?.id ?? "").trim();
|
||||
if (currentUserId.isEmpty) {
|
||||
if (currentUserKeys.isEmpty) {
|
||||
await _switchRoomRtcToAudience();
|
||||
return;
|
||||
}
|
||||
|
||||
final currentSeatIndex = userOnMaiInIndex(currentUserId);
|
||||
final currentSeatIndex =
|
||||
currentUserId.isNotEmpty
|
||||
? userOnMaiInIndex(currentUserId)
|
||||
: (_currentUserMicSeat()?.micIndex ?? -1);
|
||||
isMic = true;
|
||||
_clearSelfMicSwitchGuard(clearPreferredIndex: true);
|
||||
_clearSelfMicGoUpGuard(clearPreferredIndex: true);
|
||||
@ -2561,9 +2580,10 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
} else {
|
||||
_clearSelfMicReleaseGuard();
|
||||
}
|
||||
_clearUserFromSeats(currentUserId);
|
||||
_clearCurrentUserFromSeats();
|
||||
_roomRtcRoleIsBroadcaster = false;
|
||||
_syncSelfMicRuntimeState();
|
||||
_clearConfirmedSelfMicIdentity();
|
||||
notifyListeners();
|
||||
|
||||
await _switchRoomRtcToAudience();
|
||||
@ -5049,6 +5069,7 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
_clearSelfMicSwitchGuard(clearPreferredIndex: true);
|
||||
_clearSelfMicGoUpGuard(clearPreferredIndex: true);
|
||||
_clearSelfMicReleaseGuard();
|
||||
_clearConfirmedSelfMicIdentity();
|
||||
_seatResizeOccupantPreserveUntilMs = null;
|
||||
roomIsMute = false;
|
||||
rtmProvider?.roomAllMsgList.clear();
|
||||
@ -5207,16 +5228,21 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
).catchError((_) {});
|
||||
}
|
||||
|
||||
void _clearUserFromSeats(String? userId, {num? exceptIndex}) {
|
||||
final normalizedUserId = (userId ?? "").trim();
|
||||
if (normalizedUserId.isEmpty) {
|
||||
void _clearCurrentUserFromSeats({num? exceptIndex}) {
|
||||
_clearUsersFromSeatsByIdentityKeys(
|
||||
_currentUserIdentityKeys(),
|
||||
exceptIndex: exceptIndex,
|
||||
);
|
||||
}
|
||||
|
||||
void _clearUsersFromSeatsByIdentityKeys(
|
||||
Set<String> lookupKeys, {
|
||||
num? exceptIndex,
|
||||
}) {
|
||||
lookupKeys.removeWhere((item) => item.trim().isEmpty);
|
||||
if (lookupKeys.isEmpty) {
|
||||
return;
|
||||
}
|
||||
final lookupKeys = <String>{normalizedUserId};
|
||||
final currentUserKeys = _currentUserIdentityKeys();
|
||||
if (currentUserKeys.contains(normalizedUserId)) {
|
||||
lookupKeys.addAll(currentUserKeys);
|
||||
}
|
||||
roomWheatMap.forEach((seatIndex, seat) {
|
||||
final seatUserKeys = _userProfileIdentityKeys(seat.user);
|
||||
if (!seatUserKeys.any(lookupKeys.contains) || seatIndex == exceptIndex) {
|
||||
@ -5232,6 +5258,7 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
required SCMicGoUpRes micGoUpRes,
|
||||
required bool selfMicMuted,
|
||||
}) {
|
||||
_rememberConfirmedSelfMicIdentity(myUser);
|
||||
final previousSelfSeatIndex = userOnMaiInIndex(myUser.id ?? "");
|
||||
final isSeatSwitching =
|
||||
previousSelfSeatIndex > -1 && previousSelfSeatIndex != targetIndex;
|
||||
@ -5246,7 +5273,7 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
_clearSelfMicSwitchGuard();
|
||||
_startSelfMicGoUpGuard(targetIndex: targetIndex);
|
||||
}
|
||||
_clearUserFromSeats(myUser.id, exceptIndex: targetIndex);
|
||||
_clearCurrentUserFromSeats(exceptIndex: targetIndex);
|
||||
|
||||
final currentSeat = roomWheatMap[targetIndex];
|
||||
final currentUser = myUser.copyWith(roles: currenRoom?.entrants?.roles);
|
||||
@ -5269,6 +5296,82 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
_syncSelfMicRuntimeState();
|
||||
}
|
||||
|
||||
SocialChatUserProfile? _resolveSelfMicGoUpUser({
|
||||
required SocialChatUserProfile? localUser,
|
||||
required SCMicGoUpRes micGoUpRes,
|
||||
}) {
|
||||
final responseUser = _profileFromMicGoUpUser(micGoUpRes.user);
|
||||
if (localUser == null) {
|
||||
return responseUser;
|
||||
}
|
||||
if (responseUser == null) {
|
||||
return localUser.copyWith(roles: currenRoom?.entrants?.roles);
|
||||
}
|
||||
return localUser.copyWith(
|
||||
id: _firstNonBlankText([localUser.id, responseUser.id]),
|
||||
account: _firstNonBlankText([localUser.account, responseUser.account]),
|
||||
userAvatar: _firstNonBlankText([
|
||||
localUser.userAvatar,
|
||||
responseUser.userAvatar,
|
||||
]),
|
||||
userNickname: _firstNonBlankText([
|
||||
localUser.userNickname,
|
||||
responseUser.userNickname,
|
||||
]),
|
||||
roles: _firstNonBlankText([
|
||||
localUser.roles,
|
||||
responseUser.roles,
|
||||
currenRoom?.entrants?.roles,
|
||||
]),
|
||||
charmLevel: localUser.charmLevel ?? responseUser.charmLevel,
|
||||
heartbeatVal: localUser.heartbeatVal ?? responseUser.heartbeatVal,
|
||||
userSex: localUser.userSex ?? responseUser.userSex,
|
||||
);
|
||||
}
|
||||
|
||||
SocialChatUserProfile? _profileFromMicGoUpUser(User? user) {
|
||||
if (user == null) {
|
||||
return null;
|
||||
}
|
||||
final id = _firstNonBlankText([user.id]);
|
||||
final account = _firstNonBlankText([user.account]);
|
||||
if (id == null && account == null) {
|
||||
return null;
|
||||
}
|
||||
return SocialChatUserProfile(
|
||||
id: id,
|
||||
account: account,
|
||||
charmLevel: user.charmLevel,
|
||||
heartbeatVal: user.heartbeatVal,
|
||||
roles: _firstNonBlankText([user.roles, currenRoom?.entrants?.roles]),
|
||||
userAvatar: _firstNonBlankText([user.userAvatar]),
|
||||
userNickname: _firstNonBlankText([user.userNickname, user.account]),
|
||||
userSex: user.userSex,
|
||||
);
|
||||
}
|
||||
|
||||
@visibleForTesting
|
||||
void debugApplySelfMicGoUpResponse({
|
||||
SocialChatUserProfile? localUser,
|
||||
required num targetIndex,
|
||||
required SCMicGoUpRes micGoUpRes,
|
||||
}) {
|
||||
final selfUser = _resolveSelfMicGoUpUser(
|
||||
localUser: localUser,
|
||||
micGoUpRes: micGoUpRes,
|
||||
);
|
||||
if (selfUser == null) {
|
||||
return;
|
||||
}
|
||||
_applySelfMicGoUpState(
|
||||
myUser: selfUser,
|
||||
targetIndex: targetIndex,
|
||||
micGoUpRes: micGoUpRes,
|
||||
selfMicMuted: micGoUpRes.micMute ?? false,
|
||||
);
|
||||
notifyListeners();
|
||||
}
|
||||
|
||||
void _openRoomUserInfoCard(String? userId) {
|
||||
final normalizedUserId = (userId ?? '').trim();
|
||||
if (normalizedUserId.isEmpty) {
|
||||
@ -5332,9 +5435,13 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
|
||||
final targetIndex = micGoUpRes.micIndex ?? index;
|
||||
final selfMicMuted = micGoUpRes.micMute ?? false;
|
||||
if (myUser != null) {
|
||||
final selfUser = _resolveSelfMicGoUpUser(
|
||||
localUser: myUser,
|
||||
micGoUpRes: micGoUpRes,
|
||||
);
|
||||
if (selfUser != null) {
|
||||
_applySelfMicGoUpState(
|
||||
myUser: myUser,
|
||||
myUser: selfUser,
|
||||
targetIndex: targetIndex,
|
||||
micGoUpRes: micGoUpRes,
|
||||
selfMicMuted: selfMicMuted,
|
||||
@ -5392,8 +5499,15 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
|
||||
final currentUserId =
|
||||
AccountStorage().getCurrentUser()?.userProfile?.id ?? "";
|
||||
final currentUserSeatIndex = userOnMaiInIndex(currentUserId);
|
||||
if (roomWheatMap[index]?.user?.id == currentUserId) {
|
||||
final currentUserKeys = _currentUserIdentityKeys();
|
||||
final currentUserSeatIndex =
|
||||
currentUserId.trim().isNotEmpty
|
||||
? userOnMaiInIndex(currentUserId)
|
||||
: (_currentUserMicSeat()?.micIndex ?? -1);
|
||||
if (_userProfileMatchesAnyIdentity(
|
||||
roomWheatMap[index]?.user,
|
||||
currentUserKeys,
|
||||
)) {
|
||||
isMic = true;
|
||||
}
|
||||
_clearSelfMicSwitchGuard(clearPreferredIndex: true);
|
||||
@ -5406,8 +5520,9 @@ class RealTimeCommunicationManager extends ChangeNotifier {
|
||||
SCHeartbeatUtils.cancelAnchorTimer();
|
||||
|
||||
await _switchRoomRtcToAudience();
|
||||
_clearUserFromSeats(currentUserId);
|
||||
_clearCurrentUserFromSeats();
|
||||
_syncSelfMicRuntimeState();
|
||||
_clearConfirmedSelfMicIdentity();
|
||||
notifyListeners();
|
||||
requestMicrophoneListRefresh(
|
||||
notifyIfUnchanged: false,
|
||||
|
||||
@ -3,6 +3,8 @@ import 'package:shared_preferences/shared_preferences.dart';
|
||||
import 'package:yumi/services/audio/rtc_manager.dart';
|
||||
import 'package:yumi/shared/business_logic/models/res/login_res.dart';
|
||||
import 'package:yumi/shared/business_logic/models/res/mic_res.dart';
|
||||
import 'package:yumi/shared/business_logic/models/res/sc_mic_go_up_res.dart'
|
||||
as mic_go_up;
|
||||
import 'package:yumi/shared/data_sources/sources/local/user_manager.dart';
|
||||
|
||||
void main() {
|
||||
@ -55,4 +57,30 @@ void main() {
|
||||
expect(rtcProvider.isOnMaiInIndex(2), isTrue);
|
||||
expect(rtcProvider.userOnMaiInIndex('user-1'), 2);
|
||||
});
|
||||
|
||||
test('self go-up uses response user when local profile is unavailable', () {
|
||||
SharedPreferences.setMockInitialValues({});
|
||||
final rtcProvider =
|
||||
RealTimeCommunicationManager()..roomWheatMap = {4: MicRes(micIndex: 4)};
|
||||
|
||||
rtcProvider.debugApplySelfMicGoUpResponse(
|
||||
targetIndex: 4,
|
||||
micGoUpRes: mic_go_up.SCMicGoUpRes(
|
||||
micIndex: 4,
|
||||
micMute: false,
|
||||
micLock: false,
|
||||
roomToken: 'token',
|
||||
user: mic_go_up.User(
|
||||
id: 'user-android',
|
||||
account: 'android-account',
|
||||
userNickname: 'Android User',
|
||||
),
|
||||
),
|
||||
);
|
||||
|
||||
expect(rtcProvider.isOnMai(), isTrue);
|
||||
expect(rtcProvider.isOnMaiInIndex(4), isTrue);
|
||||
expect(rtcProvider.roomWheatMap[4]?.user?.id, 'user-android');
|
||||
expect(rtcProvider.roomWheatMap[4]?.user?.account, 'android-account');
|
||||
});
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user