diff --git a/src/core/core.cpp b/src/core/core.cpp index 631a0e1cb..2bbc2d210 100644 --- a/src/core/core.cpp +++ b/src/core/core.cpp @@ -22,6 +22,7 @@ #include "corefile.h" #include "src/core/coreav.h" #include "src/core/toxstring.h" +#include "src/model/groupinvite.h" #include "src/nexus.h" #include "src/persistence/profile.h" #include "src/persistence/settings.h" @@ -489,20 +490,22 @@ void Core::onConnectionStatusChanged(Tox*, uint32_t friendId, TOX_CONNECTION sta } } -void Core::onGroupInvite(Tox*, uint32_t friendId, TOX_CONFERENCE_TYPE type, const uint8_t* data, +void Core::onGroupInvite(Tox*, uint32_t friendId, TOX_CONFERENCE_TYPE type, const uint8_t* cookie, size_t length, void* vCore) { Core* core = static_cast(vCore); - QByteArray pk((char*)data, length); + // static_cast is used twice to replace using unsafe reinterpret_cast + const QByteArray data(static_cast(static_cast(cookie)), length); + const GroupInvite inviteInfo(friendId, type, data); switch (type) { case TOX_CONFERENCE_TYPE_TEXT: qDebug() << QString("Text group invite by %1").arg(friendId); - emit core->groupInviteReceived(friendId, type, pk); + emit core->groupInviteReceived(inviteInfo); break; case TOX_CONFERENCE_TYPE_AV: qDebug() << QString("AV group invite by %1").arg(friendId); - emit core->groupInviteReceived(friendId, type, pk); + emit core->groupInviteReceived(inviteInfo); break; default: @@ -1193,32 +1196,33 @@ bool Core::parseConferenceJoinError(TOX_ERR_CONFERENCE_JOIN error) const /** * @brief Accept a groupchat invite. - * @param friendId Id of friend in friend list. - * @param type Chat type (TEXT or AV). - * @param friendGroupPK Received via the `conference_invite` event. - * @param length The size of @friend_group_public_key. + * @param inviteInfo Object which contains info about group invitation * * @return Conference number on success, UINT32_MAX on failure. */ -uint32_t Core::joinGroupchat(int32_t friendId, uint8_t type, const uint8_t* friendGroupPK, - uint16_t length) const +uint32_t Core::joinGroupchat(const GroupInvite& inviteInfo) const { - switch (type) { + const uint32_t friendId = inviteInfo.getFriendId(); + const uint8_t confType = inviteInfo.getType(); + const QByteArray invite = inviteInfo.getInvite(); + const uint8_t* const cookie = static_cast(static_cast(invite.data())); + const size_t cookieLength = invite.length(); + switch (confType) { case TOX_CONFERENCE_TYPE_TEXT: { qDebug() << QString("Trying to join text groupchat invite sent by friend %1").arg(friendId); TOX_ERR_CONFERENCE_JOIN error; - uint32_t groupId = tox_conference_join(tox, friendId, friendGroupPK, length, &error); + uint32_t groupId = tox_conference_join(tox, friendId, cookie, cookieLength, &error); return parseConferenceJoinError(error) ? groupId : std::numeric_limits::max(); } case TOX_CONFERENCE_TYPE_AV: { qDebug() << QString("Trying to join AV groupchat invite sent by friend %1").arg(friendId); - return toxav_join_av_groupchat(tox, friendId, friendGroupPK, length, + return toxav_join_av_groupchat(tox, friendId, cookie, cookieLength, CoreAV::groupCallCallback, const_cast(this)); } default: - qWarning() << "joinGroupchat: Unknown groupchat type " << type; + qWarning() << "joinGroupchat: Unknown groupchat type " << confType; } return std::numeric_limits::max(); diff --git a/src/core/core.h b/src/core/core.h index 2940f80fc..e69d8cfd2 100644 --- a/src/core/core.h +++ b/src/core/core.h @@ -30,6 +30,7 @@ #include class CoreAV; +class GroupInvite; class Profile; class QTimer; @@ -61,7 +62,8 @@ public: bool isFriendOnline(uint32_t friendId) const; bool hasFriendWithPublicKey(const ToxPk& publicKey) const; - uint32_t joinGroupchat(int32_t friendId, uint8_t type, const uint8_t* pubkey, uint16_t length) const; + uint32_t joinGroupchat(const GroupInvite& inviteInfo) const; + void quitGroupChat(int groupId) const; QString getUsername() const; Status getStatus() const; @@ -133,7 +135,7 @@ signals: void friendLastSeenChanged(uint32_t friendId, const QDateTime& dateTime); void emptyGroupCreated(int groupnumber); - void groupInviteReceived(uint32_t friendId, uint8_t type, QByteArray publicKey); + void groupInviteReceived(const GroupInvite& inviteInfo); void groupMessageReceived(int groupnumber, int peernumber, const QString& message, bool isAction); void groupNamelistChanged(int groupnumber, int peernumber, uint8_t change); void groupTitleChanged(int groupnumber, const QString& author, const QString& title); @@ -189,7 +191,7 @@ private: static void onConnectionStatusChanged(Tox* tox, uint32_t friendId, TOX_CONNECTION status, void* core); static void onGroupInvite(Tox* tox, uint32_t friendId, TOX_CONFERENCE_TYPE type, - const uint8_t* data, size_t length, void* vCore); + const uint8_t* cookie, size_t length, void* vCore); static void onGroupMessage(Tox* tox, uint32_t groupId, uint32_t peerId, TOX_MESSAGE_TYPE type, const uint8_t* cMessage, size_t length, void* vCore); static void onGroupNamelistChange(Tox* tox, uint32_t groupId, uint32_t peerId, diff --git a/src/widget/form/groupinviteform.cpp b/src/widget/form/groupinviteform.cpp index 6e6afc897..5e00c545d 100644 --- a/src/widget/form/groupinviteform.cpp +++ b/src/widget/form/groupinviteform.cpp @@ -21,6 +21,7 @@ #include "ui_mainwindow.h" #include "src/core/core.h" +#include "src/model/groupinvite.h" #include "src/nexus.h" #include "src/persistence/settings.h" #include "src/widget/contentlayout.h" @@ -111,29 +112,29 @@ void GroupInviteForm::show(ContentLayout* contentLayout) /** * @brief Adds group invite - * @param friendId Id of a friend that invited you - * @param type Type of the invitation - text or AV - * @param invite Information that invited person needs to see an invitation + * @param inviteInfo Object which contains info about group invitation * @return true if notification is needed, false otherwise */ -bool GroupInviteForm::addGroupInvite(int32_t friendId, uint8_t type, QByteArray invite) +bool GroupInviteForm::addGroupInvite(const GroupInvite& inviteInfo) { // supress duplicate invite messages for (GroupInviteWidget* existing : invites) { - if (existing->getInviteInfo().getInvite() == invite) { + if (existing->getInviteInfo().getInvite() == inviteInfo.getInvite()) { return false; } } - GroupInviteWidget* widget = new GroupInviteWidget(this, GroupInvite(friendId, type, invite)); + + GroupInviteWidget* widget = new GroupInviteWidget(this, inviteInfo); scroll->widget()->layout()->addWidget(widget); invites.append(widget); - connect(widget, &GroupInviteWidget::accepted, [this](const GroupInvite& inviteInfo) { + connect(widget, &GroupInviteWidget::accepted, [this] (const GroupInvite& inviteInfo) { + deleteInviteWidget(inviteInfo); + emit groupInviteAccepted(inviteInfo); + }); + + connect(widget, &GroupInviteWidget::rejected, [this] (const GroupInvite& inviteInfo) { deleteInviteWidget(inviteInfo); - emit groupInviteAccepted(inviteInfo.getFriendId(), inviteInfo.getType(), - inviteInfo.getInvite()); }); - connect(widget, &GroupInviteWidget::rejected, - [this](const GroupInvite& inviteInfo) { deleteInviteWidget(inviteInfo); }); if (isVisible()) { emit groupInvitesSeen(); return false; diff --git a/src/widget/form/groupinviteform.h b/src/widget/form/groupinviteform.h index bf1470b2c..27c21b0f5 100644 --- a/src/widget/form/groupinviteform.h +++ b/src/widget/form/groupinviteform.h @@ -20,12 +20,12 @@ #ifndef GROUPINVITEFORM_H #define GROUPINVITEFORM_H -#include "src/model/groupinvite.h" #include "src/widget/gui.h" #include class ContentLayout; +class GroupInvite; class GroupInviteWidget; class QGroupBox; @@ -46,12 +46,12 @@ public: ~GroupInviteForm(); void show(ContentLayout* contentLayout); - bool addGroupInvite(int32_t friendId, uint8_t type, QByteArray invite); + bool addGroupInvite(const GroupInvite& inviteInfo); bool isShown() const; signals: void groupCreate(uint8_t type); - void groupInviteAccepted(int32_t friendId, uint8_t type, QByteArray invite); + void groupInviteAccepted(const GroupInvite& inviteInfo); void groupInvitesSeen(); protected: diff --git a/src/widget/widget.cpp b/src/widget/widget.cpp index cb4b9b5d3..9a12b7461 100644 --- a/src/widget/widget.cpp +++ b/src/widget/widget.cpp @@ -44,6 +44,7 @@ #include "friendlistwidget.h" #include "friendwidget.h" #include "groupwidget.h" +#include "src/model/groupinvite.h" #include "maskablepixmapwidget.h" #include "splitterrestorer.h" #include "systemtrayicon.h" @@ -1645,33 +1646,35 @@ void Widget::copyFriendIdToClipboard(int friendId) } } -void Widget::onGroupInviteReceived(int32_t friendId, uint8_t type, QByteArray invite) +void Widget::onGroupInviteReceived(const GroupInvite& inviteInfo) { - Friend* f = FriendList::findFriend(friendId); + const uint32_t friendId = inviteInfo.getFriendId(); + const Friend* f = FriendList::findFriend(friendId); updateFriendActivity(f); - if (type == TOX_CONFERENCE_TYPE_TEXT || type == TOX_CONFERENCE_TYPE_AV) { + const uint8_t confType = inviteInfo.getType(); + if (confType == TOX_CONFERENCE_TYPE_TEXT || confType == TOX_CONFERENCE_TYPE_AV) { if (Settings::getInstance().getAutoGroupInvite(f->getPublicKey())) { - onGroupInviteAccepted(friendId, type, invite); + onGroupInviteAccepted(inviteInfo); } else { - if (!groupInviteForm->addGroupInvite(friendId, type, invite)) { + if (!groupInviteForm->addGroupInvite(inviteInfo)) { return; } + ++unreadGroupInvites; groupInvitesUpdate(); newMessageAlert(window(), isActiveWindow(), true, true); } } else { - qWarning() << "onGroupInviteReceived: Unknown groupchat type:" << type; + qWarning() << "onGroupInviteReceived: Unknown groupchat type:" << confType; return; } } -void Widget::onGroupInviteAccepted(int32_t friendId, uint8_t type, QByteArray invite) +void Widget::onGroupInviteAccepted(const GroupInvite& inviteInfo) { - int groupId = - Nexus::getCore()->joinGroupchat(friendId, type, (uint8_t*)invite.data(), invite.length()); - if (groupId < 0) { + const uint32_t groupId = Core::getInstance()->joinGroupchat(inviteInfo); + if (groupId == std::numeric_limits::max()) { qWarning() << "onGroupInviteAccepted: Unable to accept group invite"; return; } diff --git a/src/widget/widget.h b/src/widget/widget.h index 5fb10ed1f..ec74ed690 100644 --- a/src/widget/widget.h +++ b/src/widget/widget.h @@ -43,6 +43,7 @@ class GenericChatroomWidget; class FriendWidget; class GroupWidget; class Group; +class GroupInvite; class Friend; class QSplitter; class VideoSurface; @@ -161,8 +162,8 @@ public slots: void onMessageSendResult(uint32_t friendId, const QString& message, int messageId); void onReceiptRecieved(int friendId, int receipt); void onEmptyGroupCreated(int groupId); - void onGroupInviteReceived(int32_t friendId, uint8_t type, QByteArray invite); - void onGroupInviteAccepted(int32_t friendId, uint8_t type, QByteArray invite); + void onGroupInviteReceived(const GroupInvite& inviteInfo); + void onGroupInviteAccepted(const GroupInvite& inviteInfo); void onGroupMessageReceived(int groupnumber, int peernumber, const QString& message, bool isAction); void onGroupNamelistChanged(int groupnumber, int peernumber, uint8_t change); void onGroupTitleChanged(int groupnumber, const QString& author, const QString& title);