Update volume_level locally immediately.

This commit is contained in:
levlam 2021-02-02 00:40:40 +03:00
parent 1f1d1b442b
commit 658db2defd
5 changed files with 73 additions and 8 deletions

View File

@ -967,8 +967,8 @@ GroupCallManager::GroupCallParticipants *GroupCallManager::add_group_call_partic
return participants.get();
}
const GroupCallParticipant *GroupCallManager::get_group_call_participant(
const GroupCallParticipants *group_call_participants, UserId user_id) {
GroupCallParticipant *GroupCallManager::get_group_call_participant(GroupCallParticipants *group_call_participants,
UserId user_id) {
for (auto &group_call_participant : group_call_participants->participants) {
if (group_call_participant.user_id == user_id) {
return &group_call_participant;
@ -1373,6 +1373,8 @@ int GroupCallManager::process_group_call_participant(InputGroupCallId input_grou
participant.is_volume_level_local = true;
participant.volume_level = old_participant.volume_level;
}
participant.pending_volume_level = old_participant.pending_volume_level;
participant.pending_volume_level_generation = old_participant.pending_volume_level_generation;
participant.is_min = false;
LOG(INFO) << "Edit " << old_participant << " to " << participant;
@ -1821,10 +1823,59 @@ void GroupCallManager::set_group_call_participant_volume_level(GroupCallId group
return promise.set_error(Status::Error(400, "Can't change self volume level"));
}
td_->create_handler<EditGroupCallMemberQuery>(std::move(promise))
auto participant = get_group_call_participant(add_group_call_participants(input_group_call_id), user_id);
if (participant == nullptr) {
return promise.set_error(Status::Error(400, "Can't find group call participant"));
}
if (participant->get_volume_level() == volume_level) {
return promise.set_value(Unit());
}
participant->pending_volume_level = volume_level;
participant->pending_volume_level_generation = ++set_volume_level_generation_;
send_update_group_call_participant(input_group_call_id, *participant);
auto query_promise = PromiseCreator::lambda([actor_id = actor_id(this), input_group_call_id, user_id,
generation = participant->pending_volume_level_generation,
promise = std::move(promise)](Result<Unit> &&result) mutable {
if (result.is_error()) {
promise.set_error(result.move_as_error());
} else {
send_closure(actor_id, &GroupCallManager::on_set_group_call_participant_volume_level, input_group_call_id,
user_id, generation, std::move(promise));
}
});
td_->create_handler<EditGroupCallMemberQuery>(std::move(query_promise))
->send(input_group_call_id, user_id, false, volume_level);
}
void GroupCallManager::on_set_group_call_participant_volume_level(InputGroupCallId input_group_call_id, UserId user_id,
uint64 generation, Promise<Unit> &&promise) {
if (G()->close_flag()) {
return promise.set_value(Unit());
}
auto *group_call = get_group_call(input_group_call_id);
if (group_call == nullptr || !group_call->is_inited || !group_call->is_active || !group_call->is_joined) {
return promise.set_value(Unit());
}
auto participant = get_group_call_participant(add_group_call_participants(input_group_call_id), user_id);
if (participant == nullptr || participant->pending_volume_level_generation != generation) {
return promise.set_value(Unit());
}
if (participant->volume_level != participant->pending_volume_level || !participant->is_volume_level_local) {
LOG(ERROR) << "Failed to set volume level of " << user_id << " in " << input_group_call_id;
participant->pending_volume_level = 0;
send_update_group_call_participant(input_group_call_id, *participant);
} else {
participant->pending_volume_level = 0;
}
promise.set_value(Unit());
}
void GroupCallManager::load_group_call_participants(GroupCallId group_call_id, int32 limit, Promise<Unit> &&promise) {
if (limit <= 0) {
return promise.set_error(Status::Error(400, "Parameter limit must be positive"));

View File

@ -167,9 +167,12 @@ class GroupCallManager : public Actor {
GroupCallParticipants *add_group_call_participants(InputGroupCallId input_group_call_id);
const GroupCallParticipant *get_group_call_participant(const GroupCallParticipants *group_call_participants,
static GroupCallParticipant *get_group_call_participant(GroupCallParticipants *group_call_participants,
UserId user_id);
void on_set_group_call_participant_volume_level(InputGroupCallId input_group_call_id, UserId user_id,
uint64 generation, Promise<Unit> &&promise);
void on_group_call_left(InputGroupCallId input_group_call_id, int32 audio_source, bool need_rejoin);
void on_group_call_left_impl(GroupCall *group_call, bool need_rejoin);
@ -234,6 +237,8 @@ class GroupCallManager : public Actor {
std::unordered_map<InputGroupCallId, unique_ptr<PendingJoinRequest>, InputGroupCallIdHash> pending_join_requests_;
uint64 join_group_request_generation_ = 0;
uint64 set_volume_level_generation_ = 0;
MultiTimeout check_group_call_is_joined_timeout_{"CheckGroupCallIsJoinedTimeout"};
MultiTimeout pending_send_speaking_action_timeout_{"PendingSendSpeakingActionTimeout"};
MultiTimeout recent_speaker_update_timeout_{"RecentSpeakerUpdateTimeout"};

View File

@ -46,6 +46,10 @@ bool GroupCallParticipant::is_versioned_update(const tl_object_ptr<telegram_api:
return participant->just_joined_ || participant->left_ || participant->versioned_;
}
int32 GroupCallParticipant::get_volume_level() const {
return pending_volume_level != 0 ? pending_volume_level : volume_level;
}
bool GroupCallParticipant::update_can_be_muted(bool can_manage, bool is_self, bool is_admin) {
bool new_can_be_muted_for_all_users = false;
bool new_can_be_unmuted_for_all_users = false;
@ -90,7 +94,7 @@ td_api::object_ptr<td_api::groupCallParticipant> GroupCallParticipant::get_group
return td_api::make_object<td_api::groupCallParticipant>(
contacts_manager->get_user_id_object(user_id, "get_group_call_participant_object"), audio_source, is_speaking,
can_be_muted_for_all_users, can_be_unmuted_for_all_users, can_be_muted_only_for_self,
can_be_unmuted_only_for_self, is_muted, can_self_unmute, volume_level, order);
can_be_unmuted_only_for_self, is_muted, can_self_unmute, get_volume_level(), order);
}
bool operator==(const GroupCallParticipant &lhs, const GroupCallParticipant &rhs) {
@ -100,7 +104,7 @@ bool operator==(const GroupCallParticipant &lhs, const GroupCallParticipant &rhs
lhs.can_be_muted_only_for_self == rhs.can_be_muted_only_for_self &&
lhs.can_be_unmuted_only_for_self == rhs.can_be_unmuted_only_for_self && lhs.is_muted == rhs.is_muted &&
lhs.can_self_unmute == rhs.can_self_unmute && lhs.is_speaking == rhs.is_speaking &&
lhs.volume_level == rhs.volume_level && lhs.order == rhs.order;
lhs.get_volume_level() == rhs.get_volume_level() && lhs.order == rhs.order;
}
bool operator!=(const GroupCallParticipant &lhs, const GroupCallParticipant &rhs) {

View File

@ -39,6 +39,9 @@ struct GroupCallParticipant {
int32 local_active_date = 0;
int64 order = 0;
int32 pending_volume_level = 0;
uint64 pending_volume_level_generation = 0;
static constexpr int32 MIN_VOLUME_LEVEL = 1;
static constexpr int32 MAX_VOLUME_LEVEL = 20000;
@ -58,6 +61,8 @@ struct GroupCallParticipant {
return user_id.is_valid();
}
int32 get_volume_level() const;
td_api::object_ptr<td_api::groupCallParticipant> get_group_call_participant_object(
ContactsManager *contacts_manager) const;
};

View File

@ -2676,7 +2676,7 @@ class CliClient final : public Actor {
get_args(args, group_call_id, user_id, is_muted);
send_request(td_api::make_object<td_api::toggleGroupCallParticipantIsMuted>(as_group_call_id(group_call_id),
as_user_id(user_id), is_muted));
} else if (op == "tgcpvl") {
} else if (op == "sgcpvl") {
string group_call_id;
string user_id;
int32 volume_level;