From 6f32e995938f58d0aa10823f04d3729586a0b3cf Mon Sep 17 00:00:00 2001 From: blue Date: Wed, 1 Mar 2023 22:32:41 +0300 Subject: [PATCH] an idea how to manage info object better --- core/account.cpp | 2 +- core/conference.cpp | 10 +- core/conference.h | 2 +- core/handlers/vcardhandler.cpp | 13 +- core/rosteritem.cpp | 5 +- core/rosteritem.h | 2 +- shared/info.cpp | 327 +++++++++++++++++++++++++++-- shared/info.h | 57 ++++- ui/squawk.cpp | 2 +- ui/widgets/info/contactgeneral.cpp | 8 +- ui/widgets/info/contactgeneral.h | 1 - ui/widgets/info/info.cpp | 24 ++- 12 files changed, 390 insertions(+), 63 deletions(-) diff --git a/core/account.cpp b/core/account.cpp index 98862a4..0970a6e 100644 --- a/core/account.cpp +++ b/core/account.cpp @@ -735,7 +735,7 @@ void Core::Account::requestInfo(const QString& jid) { void Core::Account::updateInfo(const Shared::Info& info) { //TODO switch case of what kind of entity this info update is about //right now it could be only about myself - vh->uploadVCard(info.vcard); + vh->uploadVCard(info.getVCardRef()); } QString Core::Account::getAvatarPath() const { diff --git a/core/conference.cpp b/core/conference.cpp index a984f41..065490c 100644 --- a/core/conference.cpp +++ b/core/conference.cpp @@ -339,18 +339,16 @@ bool Core::Conference::setAvatar(const QByteArray& data, Archive::AvatarInfo& in return result; } -Shared::VCard Core::Conference::handleResponseVCard(const QXmppVCardIq& card, const QString &resource) +void Core::Conference::handleResponseVCard(const QXmppVCardIq& card, const QString &resource, Shared::VCard& out) { - Shared::VCard result = RosterItem::handleResponseVCard(card, resource); + RosterItem::handleResponseVCard(card, resource, out); if (resource.size() > 0) { emit changeParticipant(resource, { - {"avatarState", static_cast(result.getAvatarType())}, - {"avatarPath", result.getAvatarPath()} + {"avatarState", static_cast(out.getAvatarType())}, + {"avatarPath", out.getAvatarPath()} }); } - - return result; } QMap Core::Conference::getAllAvatars() const diff --git a/core/conference.h b/core/conference.h index 4e0e463..41141ad 100644 --- a/core/conference.h +++ b/core/conference.h @@ -52,7 +52,7 @@ public: void setAutoJoin(bool p_autoJoin); void handlePresence(const QXmppPresence & pres) override; bool setAutoGeneratedAvatar(const QString& resource = "") override; - Shared::VCard handleResponseVCard(const QXmppVCardIq & card, const QString &resource) override; + void handleResponseVCard(const QXmppVCardIq & card, const QString &resource, Shared::VCard& out) override; QMap getAllAvatars() const; signals: diff --git a/core/handlers/vcardhandler.cpp b/core/handlers/vcardhandler.cpp index ca8b29b..33c9cdb 100644 --- a/core/handlers/vcardhandler.cpp +++ b/core/handlers/vcardhandler.cpp @@ -101,7 +101,7 @@ void Core::VCardHandler::onVCardReceived(const QXmppVCardIq& card) { } Shared::Info info(jid, Shared::EntryType::contact); - info.vcard = item->handleResponseVCard(card, resource); + item->handleResponseVCard(card, resource, info.getVCardRef()); emit acc->infoReady(info); } @@ -187,14 +187,15 @@ void Core::VCardHandler::onOwnVCardReceived(const QXmppVCardIq& card) { ownVCardRequestInProgress = false; - Shared::Info info(acc->getBareJid(), Shared::EntryType::ownAccount, true); - initializeVCard(info.vcard, card); + Shared::Info info(acc->getBareJid(), Shared::EntryType::ownAccount); + Shared::VCard& vCard = info.getVCardRef(); + initializeVCard(vCard, card); if (avatarType.size() > 0) { - info.vcard.setAvatarType(Shared::Avatar::valid); - info.vcard.setAvatarPath(path + "avatar." + avatarType); + vCard.setAvatarType(Shared::Avatar::valid); + vCard.setAvatarPath(path + "avatar." + avatarType); } else { - info.vcard.setAvatarType(Shared::Avatar::empty); + vCard.setAvatarType(Shared::Avatar::empty); } emit acc->infoReady(info); diff --git a/core/rosteritem.cpp b/core/rosteritem.cpp index 1b8d1e6..0bac4a4 100644 --- a/core/rosteritem.cpp +++ b/core/rosteritem.cpp @@ -506,14 +506,13 @@ bool Core::RosterItem::readAvatarInfo(Archive::AvatarInfo& target, const QString return archive->readAvatarInfo(target, resource); } -Shared::VCard Core::RosterItem::handleResponseVCard(const QXmppVCardIq& card, const QString& resource) +void Core::RosterItem::handleResponseVCard(const QXmppVCardIq& card, const QString& resource, Shared::VCard& vCard) { Archive::AvatarInfo info; Archive::AvatarInfo newInfo; bool hasAvatar = readAvatarInfo(info, resource); QByteArray ava = card.photo(); - Shared::VCard vCard; initializeVCard(vCard, card); Shared::Avatar type = Shared::Avatar::empty; QString path = ""; @@ -546,8 +545,6 @@ Shared::VCard Core::RosterItem::handleResponseVCard(const QXmppVCardIq& card, co if (resource.size() == 0) { emit avatarChanged(vCard.getAvatarType(), vCard.getAvatarPath()); } - - return vCard; } void Core::RosterItem::clearArchiveRequests() diff --git a/core/rosteritem.h b/core/rosteritem.h index 5f99017..7c82945 100644 --- a/core/rosteritem.h +++ b/core/rosteritem.h @@ -72,7 +72,7 @@ public: QString folderPath() const; bool readAvatarInfo(Archive::AvatarInfo& target, const QString& resource = "") const; virtual bool setAutoGeneratedAvatar(const QString& resource = ""); - virtual Shared::VCard handleResponseVCard(const QXmppVCardIq& card, const QString& resource); + virtual void handleResponseVCard(const QXmppVCardIq& card, const QString& resource, Shared::VCard& out); virtual void handlePresence(const QXmppPresence& pres) = 0; bool changeMessage(const QString& id, const QMap& data); diff --git a/shared/info.cpp b/shared/info.cpp index a0ac299..c0d6f26 100644 --- a/shared/info.cpp +++ b/shared/info.cpp @@ -16,32 +16,315 @@ #include "info.h" -Shared::Info::Info(const QString& p_jid, EntryType p_type, bool p_editable): - type(p_type), - jid(p_jid), - editable(p_editable), - vcard(), - activeKeys(), - inactiveKeys() -{} +Shared::Info::Info(const QString& addr, EntryType tp): + type(tp), + address(addr), + vcard(nullptr), + activeKeys(nullptr), + inactiveKeys(nullptr) +{ + switch (type) { + case EntryType::none: + break; + case EntryType::contact: + case EntryType::ownAccount: + vcard = new VCard(); + activeKeys = new std::list(); + inactiveKeys = new std::list(); + break; + default: + throw 352; + } +} Shared::Info::Info(): - type(EntryType::contact), - jid(), - editable(false), - vcard(), - activeKeys(), - inactiveKeys() + type(EntryType::none), + address(""), + vcard(nullptr), + activeKeys(nullptr), + inactiveKeys(nullptr) {} Shared::Info::Info(const Shared::Info& other): type(other.type), - jid(other.jid), - editable(other.editable), - vcard(other.vcard), - activeKeys(other.activeKeys), - inactiveKeys(other.inactiveKeys) -{} + address(other.address), + vcard(nullptr), + activeKeys(nullptr), + inactiveKeys(nullptr) +{ + switch (type) { + case EntryType::none: + break; + case EntryType::contact: + case EntryType::ownAccount: + vcard = new VCard(other.getVCardRef()); + activeKeys = new std::list(other.getActiveKeysRef()); + inactiveKeys = new std::list(other.getInactiveKeysRef()); + break; + default: + throw 353; + } +} -Shared::Info::~Info() -{} +Shared::Info::~Info() { + turnIntoNone(); +} + +void Shared::Info::turnIntoNone() { + switch (type) { + case EntryType::none: + break; + case EntryType::contact: + case EntryType::ownAccount: + delete vcard; + vcard = nullptr; + delete activeKeys; + activeKeys = nullptr; + delete inactiveKeys; + inactiveKeys = nullptr; + break; + default: + break; + } + type = EntryType::none; +} + +void Shared::Info::turnIntoContact( + const Shared::VCard& crd, + const std::list& aks, + const std::list& iaks +) { + switch (type) { + case EntryType::none: + vcard = new VCard(crd); + activeKeys = new std::list(aks); + inactiveKeys = new std::list(iaks); + break; + case EntryType::contact: + case EntryType::ownAccount: + *vcard = crd; + *activeKeys = aks; + *inactiveKeys = iaks; + break; + default: + break; + } + + type = EntryType::contact; +} + +void Shared::Info::turnIntoContact( + Shared::VCard* crd, + std::list* aks, + std::list* iaks +) { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + delete vcard; + delete activeKeys; + delete inactiveKeys; + [[fallthrough]]; + case EntryType::none: + vcard = crd; + activeKeys = aks; + inactiveKeys = iaks; + break; + default: + break; + } + + type = EntryType::contact; +} + +void Shared::Info::turnIntoOwnAccount( + const Shared::VCard& crd, + const std::list& aks, + const std::list& iaks +) { + switch (type) { + case EntryType::none: + vcard = new VCard(crd); + activeKeys = new std::list(aks); + inactiveKeys = new std::list(iaks); + break; + case EntryType::contact: + case EntryType::ownAccount: + *vcard = crd; + *activeKeys = aks; + *inactiveKeys = iaks; + break; + default: + break; + } + + type = EntryType::ownAccount; +} + +void Shared::Info::turnIntoOwnAccount( + Shared::VCard* crd, + std::list* aks, + std::list* iaks +) { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + delete vcard; + delete activeKeys; + delete inactiveKeys; + [[fallthrough]]; + case EntryType::none: + vcard = crd; + activeKeys = aks; + inactiveKeys = iaks; + break; + default: + break; + } + + type = EntryType::ownAccount; +} + +void Shared::Info::setAddress(const QString& addr) { + address = addr;} + +QString Shared::Info::getAddress() const { + return address;} + +const QString& Shared::Info::getAddressRef() const { + return address;} + +Shared::EntryType Shared::Info::getType() const { + return type;} + +std::list & Shared::Info::getActiveKeysRef() { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + return *activeKeys; + break; + default: + throw 354; + } +} + +const std::list & Shared::Info::getActiveKeysRef() const { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + return *activeKeys; + break; + default: + throw 355; + } +} + +std::list* Shared::Info::getActiveKeys() { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + return activeKeys; + break; + default: + throw 356; + } +} + +const std::list* Shared::Info::getActiveKeys() const { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + return activeKeys; + break; + default: + throw 357; + } +} + +std::list & Shared::Info::getInactiveKeysRef() { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + return *inactiveKeys; + break; + default: + throw 358; + } +} + +const std::list & Shared::Info::getInactiveKeysRef() const { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + return *inactiveKeys; + break; + default: + throw 359; + } +} + +std::list* Shared::Info::getInactiveKeys() { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + return inactiveKeys; + break; + default: + throw 360; + } +} + +const std::list* Shared::Info::getInactiveKeys() const { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + return inactiveKeys; + break; + default: + throw 361; + } +} + +const Shared::VCard & Shared::Info::getVCardRef() const { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + return *vcard; + break; + default: + throw 362; + } +} + +Shared::VCard & Shared::Info::getVCardRef() { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + return *vcard; + break; + default: + throw 363; + } +} + +const Shared::VCard * Shared::Info::getVCard() const { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + return vcard; + break; + default: + throw 364; + } +} + +Shared::VCard * Shared::Info::getVCard() { + switch (type) { + case EntryType::contact: + case EntryType::ownAccount: + return vcard; + break; + default: + throw 365; + } +} diff --git a/shared/info.h b/shared/info.h index 90248c3..b0f495e 100644 --- a/shared/info.h +++ b/shared/info.h @@ -34,16 +34,59 @@ namespace Shared { class Info { public: Info(); - Info(const QString& jid, EntryType = EntryType::contact, bool editable = false); + Info(const QString& address, EntryType = EntryType::none); Info(const Info& other); - ~Info(); + virtual ~Info(); + QString getAddress() const; + const QString& getAddressRef() const; + void setAddress(const QString& address); + + EntryType getType() const; + void turnIntoNone(); + void turnIntoContact( + const VCard& card = VCard(), + const std::list& activeKeys = {}, + const std::list& inactiveKeys = {} + ); + void turnIntoContact( + VCard* card = new VCard, + std::list* activeKeys = new std::list, + std::list* inactiveKeys = new std::list + ); + void turnIntoOwnAccount( + const VCard& card = VCard(), + const std::list& activeKeys = {}, + const std::list& inactiveKeys = {} + ); + void turnIntoOwnAccount( + VCard* card = new VCard, + std::list* activeKeys = new std::list, + std::list* inactiveKeys = new std::list + ); + + const VCard& getVCardRef() const; + VCard& getVCardRef(); + const VCard* getVCard() const; + VCard* getVCard(); + + const std::list& getActiveKeysRef() const; + std::list& getActiveKeysRef(); + const std::list* getActiveKeys() const; + std::list* getActiveKeys(); + + const std::list& getInactiveKeysRef() const; + std::list& getInactiveKeysRef(); + const std::list* getInactiveKeys() const; + std::list* getInactiveKeys(); + +private: EntryType type; - QString jid; - bool editable; - VCard vcard; - std::list activeKeys; - std::list inactiveKeys; + QString address; + + VCard* vcard; + std::list* activeKeys; + std::list* inactiveKeys; }; } diff --git a/ui/squawk.cpp b/ui/squawk.cpp index 2c969da..ce759ac 100644 --- a/ui/squawk.cpp +++ b/ui/squawk.cpp @@ -412,7 +412,7 @@ void Squawk::onRosterContextMenu(const QPoint& point) { } void Squawk::responseInfo(const Shared::Info& info) { - std::map::const_iterator itr = infoWidgets.find(info.jid); + std::map::const_iterator itr = infoWidgets.find(info.getAddressRef()); if (itr != infoWidgets.end()) { itr->second->setData(info); itr->second->hideProgress(); diff --git a/ui/widgets/info/contactgeneral.cpp b/ui/widgets/info/contactgeneral.cpp index ccc6996..e469fcb 100644 --- a/ui/widgets/info/contactgeneral.cpp +++ b/ui/widgets/info/contactgeneral.cpp @@ -30,7 +30,6 @@ UI::ContactGeneral::ContactGeneral(QWidget* parent): currentAvatarType(Shared::Avatar::empty), currentAvatarPath(""), currentJid(""), - editable(false), avatarDiablog(nullptr) { m_ui->setupUi(this); @@ -74,6 +73,9 @@ void UI::ContactGeneral::setEditable(bool edit) { m_ui->avatarButton->setMenu(nullptr); } } + + m_ui->actionSetAvatar->setEnabled(edit); + m_ui->actionClearAvatar->setEnabled(false); //need to unlock it explicitly after the type of avatar is clear! } void UI::ContactGeneral::deleteAvatarDialog() { @@ -92,7 +94,7 @@ void UI::ContactGeneral::initializeActions() { connect(setAvatar, &QAction::triggered, this, &UI::ContactGeneral::onSetAvatar); connect(clearAvatar, &QAction::triggered, this, &UI::ContactGeneral::onClearAvatar); - setAvatar->setEnabled(editable); + setAvatar->setEnabled(false); clearAvatar->setEnabled(false); } @@ -138,7 +140,7 @@ void UI::ContactGeneral::updateAvatar() { qreal aspectRatio = w / h; m_ui->avatarButton->setIconSize(QSize(height * aspectRatio, height)); m_ui->avatarButton->setIcon(QIcon(currentAvatarPath)); - m_ui->actionClearAvatar->setEnabled(editable); + m_ui->actionClearAvatar->setEnabled(m_ui->actionSetAvatar->isEnabled()); //I assume that if set avatar is enabled then we can also clear break; } } diff --git a/ui/widgets/info/contactgeneral.h b/ui/widgets/info/contactgeneral.h index 2817e91..33b4c28 100644 --- a/ui/widgets/info/contactgeneral.h +++ b/ui/widgets/info/contactgeneral.h @@ -67,7 +67,6 @@ private: Shared::Avatar currentAvatarType; QString currentAvatarPath; QString currentJid; - bool editable; QFileDialog* avatarDiablog; static const std::set supportedTypes; diff --git a/ui/widgets/info/info.cpp b/ui/widgets/info/info.cpp index e951e97..a400f22 100644 --- a/ui/widgets/info/info.cpp +++ b/ui/widgets/info/info.cpp @@ -45,17 +45,19 @@ UI::Info::~Info() { void UI::Info::setData(const Shared::Info& info) { bool editable = false; - switch (info.type) { + switch (info.getType()) { case Shared::EntryType::ownAccount: editable = true; + [[fallthrough]]; case Shared::EntryType::contact: { - QDateTime receivingTime = info.vcard.getReceivingTime(); + const Shared::VCard card = info.getVCardRef(); + QDateTime receivingTime = card.getReceivingTime(); m_ui->receivingTimeLabel->show(); m_ui->receivingTimeLabel->setText(tr("Received %1 at %2").arg(receivingTime.date().toString()).arg(receivingTime.time().toString())); - initializeContactGeneral(jid, info.vcard, editable); - initializeContactContacts(jid, info.vcard, editable); - initializeDescription(info.vcard.getDescription(), editable); - type = info.type; + initializeContactGeneral(jid, card, editable); + initializeContactContacts(jid, card, editable); + initializeDescription(card.getDescription(), editable); + type = info.getType(); } break; default: @@ -99,11 +101,13 @@ void UI::Info::initializeButtonBox() { void UI::Info::onButtonBoxAccepted() { if (type == Shared::EntryType::ownAccount) { - Shared::Info info; - contactGeneral->fillVCard(info.vcard); - contactContacts->fillVCard(info.vcard); - info.vcard.setDescription(description->description()); + Shared::Info info(jid, Shared::EntryType::ownAccount); + Shared::VCard& card = info.getVCardRef(); + contactGeneral->fillVCard(card); + contactContacts->fillVCard(card); + card.setDescription(description->description()); emit saveInfo(info); + emit close(); } }