Add class GroupCallParticipantOrder.

This commit is contained in:
levlam 2021-03-15 18:32:28 +03:00
parent ff3600b762
commit be68cda22f
7 changed files with 151 additions and 30 deletions

View File

@ -321,6 +321,7 @@ set(TDLIB_SOURCE
td/telegram/Global.cpp td/telegram/Global.cpp
td/telegram/GroupCallManager.cpp td/telegram/GroupCallManager.cpp
td/telegram/GroupCallParticipant.cpp td/telegram/GroupCallParticipant.cpp
td/telegram/GroupCallParticipantOrder.cpp
td/telegram/HashtagHints.cpp td/telegram/HashtagHints.cpp
td/telegram/InlineQueriesManager.cpp td/telegram/InlineQueriesManager.cpp
td/telegram/InputDialogId.cpp td/telegram/InputDialogId.cpp
@ -500,6 +501,7 @@ set(TDLIB_SOURCE
td/telegram/GroupCallId.h td/telegram/GroupCallId.h
td/telegram/GroupCallManager.h td/telegram/GroupCallManager.h
td/telegram/GroupCallParticipant.h td/telegram/GroupCallParticipant.h
td/telegram/GroupCallParticipantOrder.h
td/telegram/HashtagHints.h td/telegram/HashtagHints.h
td/telegram/InlineQueriesManager.h td/telegram/InlineQueriesManager.h
td/telegram/InputDialogId.h td/telegram/InputDialogId.h

View File

@ -25,7 +25,6 @@
#include "td/utils/misc.h" #include "td/utils/misc.h"
#include "td/utils/Random.h" #include "td/utils/Random.h"
#include <limits>
#include <map> #include <map>
#include <unordered_set> #include <unordered_set>
#include <utility> #include <utility>
@ -664,7 +663,7 @@ struct GroupCallManager::GroupCall {
struct GroupCallManager::GroupCallParticipants { struct GroupCallManager::GroupCallParticipants {
vector<GroupCallParticipant> participants; vector<GroupCallParticipant> participants;
string next_offset; string next_offset;
int64 min_order = std::numeric_limits<int64>::max(); GroupCallParticipantOrder min_order = GroupCallParticipantOrder::max();
bool are_administrators_loaded = false; bool are_administrators_loaded = false;
vector<UserId> administrator_user_ids; vector<UserId> administrator_user_ids;
@ -1050,7 +1049,7 @@ void GroupCallManager::on_update_group_call_rights(InputGroupCallId input_group_
} }
reload_group_call(input_group_call_id, Auto()); reload_group_call(input_group_call_id, Auto());
sync_group_call_participants(input_group_call_id); // participant order is different for administrators sync_group_call_participants(input_group_call_id); // participant order is different for administrators
} }
void GroupCallManager::reload_group_call(InputGroupCallId input_group_call_id, void GroupCallManager::reload_group_call(InputGroupCallId input_group_call_id,
@ -1528,7 +1527,8 @@ void GroupCallManager::on_sync_group_call_participants_failed(InputGroupCallId i
sync_participants_timeout_.add_timeout_in(group_call->group_call_id.get(), 1.0); sync_participants_timeout_.add_timeout_in(group_call->group_call_id.get(), 1.0);
} }
int64 GroupCallManager::get_real_participant_order(const GroupCallParticipant &participant, int64 min_order) const { GroupCallParticipantOrder GroupCallManager::get_real_participant_order(const GroupCallParticipant &participant,
GroupCallParticipantOrder min_order) const {
auto real_order = participant.get_real_order(); auto real_order = participant.get_real_order();
if (real_order < min_order && participant.is_self) { if (real_order < min_order && participant.is_self) {
return min_order; return min_order;
@ -1536,7 +1536,7 @@ int64 GroupCallManager::get_real_participant_order(const GroupCallParticipant &p
if (real_order >= min_order) { if (real_order >= min_order) {
return real_order; return real_order;
} }
return 0; return GroupCallParticipantOrder();
} }
void GroupCallManager::process_group_call_participants( void GroupCallManager::process_group_call_participants(
@ -1566,7 +1566,7 @@ void GroupCallManager::process_group_call_participants(
} }
} }
int64 min_order = std::numeric_limits<int64>::max(); auto min_order = GroupCallParticipantOrder::max();
for (auto &participant : participants) { for (auto &participant : participants) {
GroupCallParticipant group_call_participant(participant); GroupCallParticipant group_call_participant(participant);
if (!group_call_participant.is_valid()) { if (!group_call_participant.is_valid()) {
@ -1598,13 +1598,13 @@ void GroupCallManager::process_group_call_participants(
for (auto participant_it = group_participants.begin(); participant_it != group_participants.end();) { for (auto participant_it = group_participants.begin(); participant_it != group_participants.end();) {
auto &participant = *participant_it; auto &participant = *participant_it;
if (old_participant_dialog_ids.count(participant.dialog_id) == 0) { if (old_participant_dialog_ids.count(participant.dialog_id) == 0) {
CHECK(participant.order == 0 || participant.order >= min_order); CHECK(!participant.order.is_valid() || participant.order >= min_order);
++participant_it; ++participant_it;
continue; continue;
} }
// not synced user, needs to be deleted // not synced user, needs to be deleted
if (participant.order != 0) { if (participant.order.is_valid()) {
CHECK(participant.order >= participants_it->second->min_order); CHECK(participant.order >= participants_it->second->min_order);
if (participant.is_self) { if (participant.is_self) {
if (participant.order != min_order) { if (participant.order != min_order) {
@ -1612,7 +1612,7 @@ void GroupCallManager::process_group_call_participants(
send_update_group_call_participant(input_group_call_id, participant); send_update_group_call_participant(input_group_call_id, participant);
} }
} else { } else {
participant.order = 0; participant.order = GroupCallParticipantOrder();
send_update_group_call_participant(input_group_call_id, participant); send_update_group_call_participant(input_group_call_id, participant);
} }
} }
@ -1635,7 +1635,7 @@ void GroupCallManager::process_group_call_participants(
for (auto &participant : participants_it->second->participants) { for (auto &participant : participants_it->second->participants) {
auto real_order = get_real_participant_order(participant, min_order); auto real_order = get_real_participant_order(participant, min_order);
if (old_min_order > real_order && real_order >= min_order) { if (old_min_order > real_order && real_order >= min_order) {
CHECK(participant.order == 0 || participant.order == old_min_order); CHECK(!participant.order.is_valid() || participant.order == old_min_order);
participant.order = real_order; participant.order = real_order;
send_update_group_call_participant(input_group_call_id, participant); send_update_group_call_participant(input_group_call_id, participant);
} }
@ -1659,7 +1659,8 @@ void GroupCallManager::update_group_call_participants_can_be_muted(InputGroupCal
CHECK(participants != nullptr); CHECK(participants != nullptr);
LOG(INFO) << "Update group call participants can_be_muted in " << input_group_call_id; LOG(INFO) << "Update group call participants can_be_muted in " << input_group_call_id;
for (auto &participant : participants->participants) { for (auto &participant : participants->participants) {
if (update_group_call_participant_can_be_muted(can_manage, participants, participant) && participant.order != 0) { if (update_group_call_participant_can_be_muted(can_manage, participants, participant) &&
participant.order.is_valid()) {
send_update_group_call_participant(input_group_call_id, participant); send_update_group_call_participant(input_group_call_id, participant);
} }
} }
@ -1696,7 +1697,7 @@ int GroupCallManager::process_group_call_participant(InputGroupCallId input_grou
if (old_participant.dialog_id == participant.dialog_id || (old_participant.is_self && participant.is_self)) { if (old_participant.dialog_id == participant.dialog_id || (old_participant.is_self && participant.is_self)) {
if (participant.joined_date == 0) { if (participant.joined_date == 0) {
LOG(INFO) << "Remove " << old_participant; LOG(INFO) << "Remove " << old_participant;
if (old_participant.order != 0) { if (old_participant.order.is_valid()) {
send_update_group_call_participant(input_group_call_id, participant); send_update_group_call_participant(input_group_call_id, participant);
} }
on_remove_group_call_participant(input_group_call_id, participant.dialog_id); on_remove_group_call_participant(input_group_call_id, participant.dialog_id);
@ -1712,7 +1713,7 @@ int GroupCallManager::process_group_call_participant(InputGroupCallId input_grou
update_group_call_participant_can_be_muted(can_manage, participants, participant); update_group_call_participant_can_be_muted(can_manage, participants, participant);
LOG(INFO) << "Edit " << old_participant << " to " << participant; LOG(INFO) << "Edit " << old_participant << " to " << participant;
if (old_participant != participant && (old_participant.order != 0 || participant.order != 0)) { if (old_participant != participant && (old_participant.order.is_valid() || participant.order.is_valid())) {
send_update_group_call_participant(input_group_call_id, participant); send_update_group_call_participant(input_group_call_id, participant);
} }
on_participant_speaking_in_group_call(input_group_call_id, participant); on_participant_speaking_in_group_call(input_group_call_id, participant);
@ -1738,7 +1739,7 @@ int GroupCallManager::process_group_call_participant(InputGroupCallId input_grou
participant.is_just_joined = false; participant.is_just_joined = false;
update_group_call_participant_can_be_muted(can_manage, participants, participant); update_group_call_participant_can_be_muted(can_manage, participants, participant);
participants->participants.push_back(std::move(participant)); participants->participants.push_back(std::move(participant));
if (participants->participants.back().order != 0) { if (participants->participants.back().order.is_valid()) {
send_update_group_call_participant(input_group_call_id, participants->participants.back()); send_update_group_call_participant(input_group_call_id, participants->participants.back());
} }
on_add_group_call_participant(input_group_call_id, participants->participants.back().dialog_id); on_add_group_call_participant(input_group_call_id, participants->participants.back().dialog_id);
@ -1774,7 +1775,7 @@ void GroupCallManager::on_update_dialog_about(DialogId dialog_id, const string &
CHECK(participant != nullptr); CHECK(participant != nullptr);
if ((from_server || participant->is_fake) && participant->about != about) { if ((from_server || participant->is_fake) && participant->about != about) {
participant->about = about; participant->about = about;
if (participant->order != 0) { if (participant->order.is_valid()) {
send_update_group_call_participant(input_group_call_id, *participant); send_update_group_call_participant(input_group_call_id, *participant);
} }
} }
@ -2565,7 +2566,7 @@ void GroupCallManager::toggle_group_call_participant_is_muted(GroupCallId group_
*participant = std::move(participant_copy); *participant = std::move(participant_copy);
participant->pending_is_muted_generation = ++toggle_is_muted_generation_; participant->pending_is_muted_generation = ++toggle_is_muted_generation_;
if (participant->order != 0) { if (participant->order.is_valid()) {
send_update_group_call_participant(input_group_call_id, *participant); send_update_group_call_participant(input_group_call_id, *participant);
} }
@ -2605,7 +2606,7 @@ void GroupCallManager::on_toggle_group_call_participant_is_muted(InputGroupCallI
participant->server_is_muted_by_admin != participant->pending_is_muted_by_admin || participant->server_is_muted_by_admin != participant->pending_is_muted_by_admin ||
participant->server_is_muted_locally != participant->pending_is_muted_locally) { participant->server_is_muted_locally != participant->pending_is_muted_locally) {
LOG(ERROR) << "Failed to mute/unmute " << dialog_id << " in " << input_group_call_id; LOG(ERROR) << "Failed to mute/unmute " << dialog_id << " in " << input_group_call_id;
if (participant->order != 0) { if (participant->order.is_valid()) {
send_update_group_call_participant(input_group_call_id, *participant); send_update_group_call_participant(input_group_call_id, *participant);
} }
} }
@ -2655,7 +2656,7 @@ void GroupCallManager::set_group_call_participant_volume_level(GroupCallId group
participant->pending_volume_level = volume_level; participant->pending_volume_level = volume_level;
participant->pending_volume_level_generation = ++set_volume_level_generation_; participant->pending_volume_level_generation = ++set_volume_level_generation_;
if (participant->order != 0) { if (participant->order.is_valid()) {
send_update_group_call_participant(input_group_call_id, *participant); send_update_group_call_participant(input_group_call_id, *participant);
} }
@ -2693,7 +2694,7 @@ void GroupCallManager::on_set_group_call_participant_volume_level(InputGroupCall
if (participant->volume_level != participant->pending_volume_level) { if (participant->volume_level != participant->pending_volume_level) {
LOG(ERROR) << "Failed to set volume level of " << dialog_id << " in " << input_group_call_id; LOG(ERROR) << "Failed to set volume level of " << dialog_id << " in " << input_group_call_id;
participant->pending_volume_level = 0; participant->pending_volume_level = 0;
if (participant->order != 0) { if (participant->order.is_valid()) {
send_update_group_call_participant(input_group_call_id, *participant); send_update_group_call_participant(input_group_call_id, *participant);
} }
} else { } else {
@ -2750,7 +2751,7 @@ void GroupCallManager::toggle_group_call_participant_is_hand_raised(GroupCallId
participant->have_pending_is_hand_raised = true; participant->have_pending_is_hand_raised = true;
participant->pending_is_hand_raised = is_hand_raised; participant->pending_is_hand_raised = is_hand_raised;
participant->pending_is_hand_raised_generation = ++toggle_is_hand_raised_generation_; participant->pending_is_hand_raised_generation = ++toggle_is_hand_raised_generation_;
if (participant->order != 0) { if (participant->order.is_valid()) {
send_update_group_call_participant(input_group_call_id, *participant); send_update_group_call_participant(input_group_call_id, *participant);
} }
@ -2788,7 +2789,7 @@ void GroupCallManager::on_toggle_group_call_participant_is_hand_raised(InputGrou
participant->have_pending_is_hand_raised = false; participant->have_pending_is_hand_raised = false;
if (participant->get_is_hand_raised() != participant->pending_is_hand_raised) { if (participant->get_is_hand_raised() != participant->pending_is_hand_raised) {
LOG(ERROR) << "Failed to change raised hand state for " << dialog_id << " in " << input_group_call_id; LOG(ERROR) << "Failed to change raised hand state for " << dialog_id << " in " << input_group_call_id;
if (participant->order != 0) { if (participant->order.is_valid()) {
send_update_group_call_participant(input_group_call_id, *participant); send_update_group_call_participant(input_group_call_id, *participant);
} }
} }
@ -2941,9 +2942,9 @@ void GroupCallManager::try_clear_group_call_participants(InputGroupCallId input_
group_call->version = -1; group_call->version = -1;
for (auto &participant : participants->participants) { for (auto &participant : participants->participants) {
if (participant.order != 0) { if (participant.order.is_valid()) {
CHECK(participant.order >= participants->min_order); CHECK(participant.order >= participants->min_order);
participant.order = 0; participant.order = GroupCallParticipantOrder();
send_update_group_call_participant(input_group_call_id, participant); send_update_group_call_participant(input_group_call_id, participant);
} }
on_remove_group_call_participant(input_group_call_id, participant.dialog_id); on_remove_group_call_participant(input_group_call_id, participant.dialog_id);
@ -3305,7 +3306,7 @@ DialogId GroupCallManager::set_group_call_participant_is_speaking_by_source(Inpu
participant.local_active_date = max(participant.local_active_date, date); participant.local_active_date = max(participant.local_active_date, date);
} }
participant.order = get_real_participant_order(participant, participants_it->second->min_order); participant.order = get_real_participant_order(participant, participants_it->second->min_order);
if (participant.order != 0) { if (participant.order.is_valid()) {
send_update_group_call_participant(input_group_call_id, participant); send_update_group_call_participant(input_group_call_id, participant);
} }
} }

View File

@ -180,7 +180,8 @@ class GroupCallManager : public Actor {
void on_sync_group_call_participants_failed(InputGroupCallId input_group_call_id); void on_sync_group_call_participants_failed(InputGroupCallId input_group_call_id);
int64 get_real_participant_order(const GroupCallParticipant &participant, int64 min_order) const; GroupCallParticipantOrder get_real_participant_order(const GroupCallParticipant &participant,
GroupCallParticipantOrder min_order) const;
void process_group_call_participants(InputGroupCallId group_call_id, void process_group_call_participants(InputGroupCallId group_call_id,
vector<tl_object_ptr<telegram_api::groupCallParticipant>> &&participants, vector<tl_object_ptr<telegram_api::groupCallParticipant>> &&participants,

View File

@ -52,6 +52,10 @@ bool GroupCallParticipant::is_versioned_update(const tl_object_ptr<telegram_api:
return participant->just_joined_ || participant->left_ || participant->versioned_; return participant->just_joined_ || participant->left_ || participant->versioned_;
} }
GroupCallParticipantOrder GroupCallParticipant::get_real_order() const {
return GroupCallParticipantOrder(max(active_date, local_active_date), 0, joined_date);
}
bool GroupCallParticipant::get_is_muted_by_themselves() const { bool GroupCallParticipant::get_is_muted_by_themselves() const {
return have_pending_is_muted ? pending_is_muted_by_themselves : server_is_muted_by_themselves; return have_pending_is_muted ? pending_is_muted_by_themselves : server_is_muted_by_themselves;
} }
@ -228,7 +232,7 @@ td_api::object_ptr<td_api::groupCallParticipant> GroupCallParticipant::get_group
td->messages_manager_->get_message_sender_object(dialog_id), audio_source, about, is_speaking, td->messages_manager_->get_message_sender_object(dialog_id), audio_source, about, is_speaking,
get_is_hand_raised(), can_be_muted_for_all_users, can_be_unmuted_for_all_users, can_be_muted_only_for_self, get_is_hand_raised(), can_be_muted_for_all_users, can_be_unmuted_for_all_users, can_be_muted_only_for_self,
can_be_unmuted_only_for_self, get_is_muted_for_all_users(), get_is_muted_locally(), get_is_muted_by_themselves(), can_be_unmuted_only_for_self, get_is_muted_for_all_users(), get_is_muted_locally(), get_is_muted_by_themselves(),
get_volume_level(), order); get_volume_level(), order.get_group_call_participant_order_object());
} }
bool operator==(const GroupCallParticipant &lhs, const GroupCallParticipant &rhs) { bool operator==(const GroupCallParticipant &lhs, const GroupCallParticipant &rhs) {

View File

@ -7,6 +7,7 @@
#pragma once #pragma once
#include "td/telegram/DialogId.h" #include "td/telegram/DialogId.h"
#include "td/telegram/GroupCallParticipantOrder.h"
#include "td/telegram/td_api.h" #include "td/telegram/td_api.h"
#include "td/telegram/telegram_api.h" #include "td/telegram/telegram_api.h"
@ -41,7 +42,7 @@ struct GroupCallParticipant {
bool is_just_joined = false; bool is_just_joined = false;
bool is_speaking = false; bool is_speaking = false;
int32 local_active_date = 0; int32 local_active_date = 0;
int64 order = 0; GroupCallParticipantOrder order;
int32 pending_volume_level = 0; int32 pending_volume_level = 0;
uint64 pending_volume_level_generation = 0; uint64 pending_volume_level_generation = 0;
@ -71,9 +72,7 @@ struct GroupCallParticipant {
bool set_pending_is_muted(bool is_muted, bool can_manage, bool is_admin); bool set_pending_is_muted(bool is_muted, bool can_manage, bool is_admin);
int64 get_real_order() const { GroupCallParticipantOrder get_real_order() const;
return (static_cast<int64>(max(active_date, local_active_date)) << 32) + joined_date;
}
bool is_valid() const { bool is_valid() const {
return dialog_id.is_valid(); return dialog_id.is_valid();

View File

@ -0,0 +1,60 @@
//
// Copyright Aliaksei Levin (levlam@telegram.org), Arseny Smirnov (arseny30@gmail.com) 2014-2021
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
//
#include "td/telegram/GroupCallParticipantOrder.h"
#include <limits>
#include <tuple>
namespace td {
GroupCallParticipantOrder GroupCallParticipantOrder::max() {
return GroupCallParticipantOrder(std::numeric_limits<int32>::max(), std::numeric_limits<int64>::max(),
std::numeric_limits<int32>::max());
}
bool GroupCallParticipantOrder::is_valid() const {
return *this != GroupCallParticipantOrder();
}
int64 GroupCallParticipantOrder::get_group_call_participant_order_object() const {
return (static_cast<int64>(active_date) << 32) + joined_date;
}
bool operator==(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs) {
return lhs.active_date == rhs.active_date && lhs.joined_date == rhs.joined_date &&
lhs.raise_hand_rating == rhs.raise_hand_rating;
}
bool operator!=(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs) {
return !(lhs == rhs);
}
bool operator<(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs) {
return std::tie(lhs.active_date, lhs.raise_hand_rating, lhs.joined_date) <
std::tie(rhs.active_date, rhs.raise_hand_rating, rhs.joined_date);
}
bool operator<=(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs) {
return !(rhs < lhs);
}
bool operator>(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs) {
return rhs < lhs;
}
bool operator>=(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs) {
return !(lhs < rhs);
}
StringBuilder &operator<<(StringBuilder &string_builder,
const GroupCallParticipantOrder &group_call_participant_order) {
return string_builder << group_call_participant_order.active_date << '/'
<< group_call_participant_order.raise_hand_rating << '/'
<< group_call_participant_order.joined_date;
}
} // namespace td

View File

@ -0,0 +1,54 @@
//
// Copyright Aliaksei Levin (levlam@telegram.org), Arseny Smirnov (arseny30@gmail.com) 2014-2021
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
//
#pragma once
#include "td/utils/common.h"
#include "td/utils/StringBuilder.h"
namespace td {
class GroupCallParticipantOrder {
int32 active_date = 0;
int32 joined_date = 0;
int64 raise_hand_rating = 0;
friend StringBuilder &operator<<(StringBuilder &string_builder,
const GroupCallParticipantOrder &group_call_participant_order);
friend bool operator==(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs);
friend bool operator<(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs);
public:
GroupCallParticipantOrder() = default;
GroupCallParticipantOrder(int32 active_date, int64 raise_hand_rating, int32 joined_date)
: active_date(active_date), joined_date(joined_date), raise_hand_rating(raise_hand_rating) {
}
static GroupCallParticipantOrder max();
bool is_valid() const;
int64 get_group_call_participant_order_object() const;
};
bool operator==(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs);
bool operator!=(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs);
bool operator<(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs);
bool operator<=(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs);
bool operator>(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs);
bool operator>=(const GroupCallParticipantOrder &lhs, const GroupCallParticipantOrder &rhs);
StringBuilder &operator<<(StringBuilder &string_builder, const GroupCallParticipantOrder &group_call_participant_order);
} // namespace td