diff --git a/src/shared/Modules/CompactCommandPad/CompactCommandPad.cpp b/src/shared/Modules/CompactCommandPad/CompactCommandPad.cpp index 95f600a567a7a1d808106fac59393a9f9dade215..c01145d9da25456f16e994c5f74eae51e82e48e5 100644 --- a/src/shared/Modules/CompactCommandPad/CompactCommandPad.cpp +++ b/src/shared/Modules/CompactCommandPad/CompactCommandPad.cpp @@ -28,7 +28,7 @@ CompactCommandPad::CompactCommandPad() customContextMenuActionSetup(); } -CompactCommandPad::~CompactCommandPad() { delete selector; } +CompactCommandPad::~CompactCommandPad() {} XmlObject CompactCommandPad::toXmlObject() { @@ -82,9 +82,9 @@ void CompactCommandPad::setupUi() QVBoxLayout* outerLayout = new QVBoxLayout; outerLayout->setContentsMargins(2, 2, 2, 2); - button = new QPushButton("Edit me"); - outerLayout->addWidget(button); - connect(button, &QPushButton::clicked, + button = std::make_unique<QPushButton, const QString&>("Edit me"); + outerLayout->addWidget(button.get()); + connect(button.get(), &QPushButton::clicked, [=]() { if (timer) @@ -107,8 +107,8 @@ void CompactCommandPad::setupUi() button->setText(label + " [Stop]"); send(); - timer = new QTimer(this); - connect(timer, &QTimer::timeout, this, + timer = std::make_unique<QTimer>(this); + connect(timer.get(), &QTimer::timeout, this, &CompactCommandPad::send); timer->start(continuosSendTimeout); } @@ -118,7 +118,7 @@ void CompactCommandPad::setupUi() setLayout(outerLayout); - selector = new CommandSelector(this); + selector = std::make_unique<CommandSelector>(this); } void CompactCommandPad::send() @@ -128,8 +128,8 @@ void CompactCommandPad::send() void CompactCommandPad::customContextMenuActionSetup() { - QAction* edit = new QAction("Edit button", this); - connect(edit, &QAction::triggered, this, + auto edit = std::make_unique<QAction>("Edit button", this); + connect(edit.get(), &QAction::triggered, this, &CompactCommandPad::buttonEditActionTriggered); - customContextMenuActions.append(edit); + customContextMenuActions.append(std::move(edit)); } diff --git a/src/shared/Modules/CompactCommandPad/CompactCommandPad.h b/src/shared/Modules/CompactCommandPad/CompactCommandPad.h index 7df617b1ac23c8179dbd10916f27940368eb4036..a8dc3861f73b69724b46ae6ee393d9214089740e 100644 --- a/src/shared/Modules/CompactCommandPad/CompactCommandPad.h +++ b/src/shared/Modules/CompactCommandPad/CompactCommandPad.h @@ -42,9 +42,9 @@ private: void setupUi(); void customContextMenuActionSetup(); - CommandSelector* selector; - QPushButton* button; - QTimer* timer; + std::unique_ptr<CommandSelector> selector; + std::unique_ptr<QPushButton> button; + std::unique_ptr<QTimer> timer; QString label; bool selected; diff --git a/src/shared/Modules/CompactCommandPad/SendThread.cpp b/src/shared/Modules/CompactCommandPad/SendThread.cpp index 4fb3c562cf0620046caf28827ff502f501891325..dcd9997dc7305fb938906aedff268140611bf04f 100644 --- a/src/shared/Modules/CompactCommandPad/SendThread.cpp +++ b/src/shared/Modules/CompactCommandPad/SendThread.cpp @@ -18,8 +18,8 @@ #include "SendThread.h" -SendThread::SendThread(MessageBroker* broker, const Message& msg, long timeout) - : broker(broker), msg(msg), timeout(timeout), toStop(false) +SendThread::SendThread(const Message& msg, long timeout) + : msg(msg), timeout(timeout), toStop(false) { connect(this, &SendThread::finished, this, &SendThread::deleteLater); start(); @@ -31,7 +31,7 @@ void SendThread::run() { while (!toStop) { - broker->publish(msg); + MessageBroker::getInstance().publish(msg); QThread::sleep(timeout); } } diff --git a/src/shared/Modules/CompactCommandPad/SendThread.h b/src/shared/Modules/CompactCommandPad/SendThread.h index aa134c19be722ee2849724dc650eaef10f6be75e..3bf9f60841d264b61ee72935a4b1e6bc72f67b3b 100644 --- a/src/shared/Modules/CompactCommandPad/SendThread.h +++ b/src/shared/Modules/CompactCommandPad/SendThread.h @@ -25,14 +25,13 @@ class SendThread : public QThread { public: - SendThread(MessageBroker* broker, const Message& msg, long timeout); + SendThread(const Message& msg, long timeout); void requestStop(); protected: void run() override; private: - MessageBroker* broker; Message msg; long timeout; bool toStop; diff --git a/src/shared/Modules/FileStream/FileStreamModule.cpp b/src/shared/Modules/FileStream/FileStreamModule.cpp index e0226af65cf7c827fcc74e6477e9846e84b1cf72..bd2c94796c737319175ac6f93c1fc5e96fe01bc7 100644 --- a/src/shared/Modules/FileStream/FileStreamModule.cpp +++ b/src/shared/Modules/FileStream/FileStreamModule.cpp @@ -125,10 +125,11 @@ void FileStreamModule::onStartClicked() disableOnStartElement(); for (int i = 0; i < topicViewsList.count(); i++) { - MessageBroker::getInstance().subscribe( - Filter::fromString(topicViewsList[i]->text().trimmed()), this, - [this](const Message& message, const Filter& filter) - { onMsgReceived(message); }); + subscriptions.push_back( + std::move(MessageBroker::getInstance().subscribe( + Filter::fromString(topicViewsList[i]->text().trimmed()), + [this](const Message& message, const Filter& filter) + { onMsgReceived(message); }))); topicViewsList[i]->setEnabled(false); } } @@ -141,8 +142,7 @@ void FileStreamModule::onStopClicked() for (int i = 0; i < topicViewsList.count(); i++) { - MessageBroker::getInstance().unsubscribe( - Filter::fromString(topicViewsList[i]->text().trimmed()), this); + subscriptions.pop_front(); topicViewsList[i]->setEnabled(true); } } @@ -192,30 +192,30 @@ void FileStreamModule::onShowFileClick() void FileStreamModule::addTopic(const QString& topic) { - QLineEdit* topicView = createTopicView(topic); + auto topicView = createTopicView(topic); - topicViewsList.append(topicView); ui->topics_layout->addWidget(topicView); + topicViewsList.append(std::move(topicView)); } -QLineEdit* FileStreamModule::createTopicView(const QString& topic) const +std::unique_ptr<QLineEdit> FileStreamModule::createTopicView( + const QString& topic) const { - QLineEdit* topicView = new QLineEdit(); + auto topicView = std::make_unique<QLineEdit>(); topicView->setText(topic); - connect(topicView, &QLineEdit::textEdited, this, + connect(topicView.get(), &QLineEdit::textEdited, this, &FileStreamModule::onTopicEdit); - return topicView; + return std::move(topicView); } void FileStreamModule::deleteAllTopicViews() { for (int i = 0; i < topicViewsList.count(); i++) { - MessageBroker::getInstance().unsubscribe( - Filter::fromString(topicViewsList[i]->text().trimmed()), this); ui->topics_layout->removeWidget(topicViewsList[i]); topicViewsList[i]->deleteLater(); } + subscriptions.clear(); topicViewsList.clear(); } diff --git a/src/shared/Modules/FileStream/FileStreamModule.h b/src/shared/Modules/FileStream/FileStreamModule.h index 4c430554a00249213d0f7f095442464061c3cae4..5bc7e09fbec7f7497bd8884ee3c3464bd79a46cf 100644 --- a/src/shared/Modules/FileStream/FileStreamModule.h +++ b/src/shared/Modules/FileStream/FileStreamModule.h @@ -40,13 +40,14 @@ protected: void onShowFileClick(); void addTopic(const QString& topic); - QLineEdit* createTopicView(const QString& topic) const; + std::unique_ptr<QLineEdit> createTopicView(const QString& topic) const; void deleteAllTopicViews(); private: Ui::FileStreamModule* ui; - QList<QLineEdit*> topicViewsList; + QList<std::unique_ptr<QLineEdit>> topicViewsList; + QList<std::unique_ptr<Subscription>> subscriptions; QFile file; }; diff --git a/src/shared/Modules/Graph/Graph.cpp b/src/shared/Modules/Graph/Graph.cpp index 2a9f40ac38dc61bfc7c95689ded4bf3bfdd98510..618f0d3f52c7b6a53dd0c7c1cf1e632f027736e5 100644 --- a/src/shared/Modules/Graph/Graph.cpp +++ b/src/shared/Modules/Graph/Graph.cpp @@ -85,11 +85,11 @@ void Graph::fromXmlObject(const XmlObject& obj) void Graph::onSubscribeClicked() { - SubscriptionsPanel* panel = new SubscriptionsPanel(lines.keys()); + auto panel = std::make_unique<SubscriptionsPanel>(lines.keys()); panel->setWindowTitle("Graph subscriptions"); - connect(panel, &SubscriptionsPanel::filterAdded, this, + connect(panel.get(), &SubscriptionsPanel::filterAdded, this, &Graph::onFilterAdded); - connect(panel, &SubscriptionsPanel::filterRemoved, this, + connect(panel.get(), &SubscriptionsPanel::filterRemoved, this, &Graph::onFilterRemoved); panel->show(); } @@ -144,8 +144,8 @@ void Graph::onFilterAdded(const Filter& filter) } plot->replot(); - MessageBroker::getInstance().subscribe( - filter, this, + subscription = MessageBroker::getInstance().subscribe( + filter, [&](const Message& message, const Filter& filter) { if (stopped && !lines.contains(filter)) @@ -251,8 +251,8 @@ void Graph::setupUi() QHBoxLayout* outerLayout = new QHBoxLayout; outerLayout->setContentsMargins(0, 0, 0, 0); - plot = new QCustomPlot; - outerLayout->addWidget(plot); + plot = std::make_unique<QCustomPlot>(); + outerLayout->addWidget(plot.get()); setLayout(outerLayout); @@ -271,35 +271,37 @@ void Graph::setupUi() QCP::iSelectPlottables); plot->setContextMenuPolicy(Qt::CustomContextMenu); - connect(plot, &QCustomPlot::customContextMenuRequested, this, + connect(plot.get(), &QCustomPlot::customContextMenuRequested, this, &QWidget::customContextMenuRequested); } void Graph::customContextMenuActionSetup() { - QAction* subscriptions = new QAction("Manage subscriptions"); + auto subscriptions = std::make_unique<QAction>("Manage subscriptions"); subscriptions->setToolTip("Edit graph series"); - connect(subscriptions, &QAction::triggered, this, + connect(subscriptions.get(), &QAction::triggered, this, &Graph::onSubscribeClicked); - customContextMenuActions.append(subscriptions); + customContextMenuActions.append(std::move(subscriptions)); - QAction* clear = new QAction("Clear"); + auto clear = std::make_unique<QAction>("Clear"); clear->setToolTip("Removes all data currently on the plot"); - connect(clear, &QAction::triggered, this, &Graph::onClearClicked); - customContextMenuActions.append(clear); + connect(clear.get(), &QAction::triggered, this, &Graph::onClearClicked); + customContextMenuActions.append(std::move(clear)); - QAction* stop = new QAction("Stop"); + auto stop = std::make_unique<QAction>("Stop"); stop->setCheckable(true); stop->setChecked(stopped); stop->setToolTip("Pauses the graph"); - connect(stop, &QAction::triggered, this, - [this, stop](bool checked) { onStopClicked(stop, checked); }); - customContextMenuActions.append(stop); + auto* stopAddr = stop.get(); + connect(stop.get(), &QAction::triggered, this, + [this, stopAddr](bool checked) + { onStopClicked(stopAddr, checked); }); + customContextMenuActions.append(std::move(stop)); - QAction* follow = new QAction("Follow"); + auto follow = std::make_unique<QAction>("Follow"); follow->setCheckable(true); follow->setChecked(following); follow->setToolTip("Automatically move the graph to follow new data"); - connect(follow, &QAction::triggered, this, &Graph::onFollowClicked); - customContextMenuActions.append(follow); + connect(follow.get(), &QAction::triggered, this, &Graph::onFollowClicked); + customContextMenuActions.append(std::move(follow)); } diff --git a/src/shared/Modules/Graph/Graph.h b/src/shared/Modules/Graph/Graph.h index 099583f471e80ee62b11ca97dff6dc8ec20d6576..c199292dd2fc1bfd43ed96968bdfcc6197bf36b8 100644 --- a/src/shared/Modules/Graph/Graph.h +++ b/src/shared/Modules/Graph/Graph.h @@ -53,7 +53,7 @@ private: void setupUi(); void customContextMenuActionSetup(); - QCustomPlot* plot; + std::unique_ptr<QCustomPlot> plot; struct Line { @@ -73,4 +73,6 @@ private: bool following = true; int legendFontSize = 15; + + std::unique_ptr<Subscription> subscription; }; diff --git a/src/shared/Modules/IncomingMessagesViewer/IncomingMessagesViewerModule.cpp b/src/shared/Modules/IncomingMessagesViewer/IncomingMessagesViewerModule.cpp index 02399ade42f10db191cfe8b3c07e530db8fc31ea..ca3e401ce4aab1470e75aa9ddfdba37b413ceda8 100644 --- a/src/shared/Modules/IncomingMessagesViewer/IncomingMessagesViewerModule.cpp +++ b/src/shared/Modules/IncomingMessagesViewer/IncomingMessagesViewerModule.cpp @@ -29,11 +29,7 @@ IncomingMessagesViewerModule::IncomingMessagesViewerModule() customContextMenuActionSetup(); } -IncomingMessagesViewerModule::~IncomingMessagesViewerModule() -{ - for (auto filter : filters) - MessageBroker::getInstance().unsubscribe(filter, this); -} +IncomingMessagesViewerModule::~IncomingMessagesViewerModule() {} XmlObject IncomingMessagesViewerModule::toXmlObject() { @@ -42,10 +38,12 @@ XmlObject IncomingMessagesViewerModule::toXmlObject() obj.addAttribute("keepOnlyLastMessage", keepOnlyLastMessage ? "1" : "0"); obj.addAttribute("useTimestamp", useTimestamp ? "1" : "0"); - for (int i = 0; i < filters.count(); i++) + auto filtersList = filters.keys(); + + for (int i = 0; i < filtersList.count(); i++) { XmlObject subscription("subscription"); - subscription.addAttribute("filter", filters[i].toString()); + subscription.addAttribute("filter", filtersList[i].toString()); obj.addChild(subscription); } @@ -69,87 +67,91 @@ void IncomingMessagesViewerModule::fromXmlObject(const XmlObject& xmlObject) void IncomingMessagesViewerModule::onSubscribeClicked() { - SubscriptionsPanel* panel = new SubscriptionsPanel(filters); + auto panel = std::make_unique<SubscriptionsPanel>(filters.keys()); panel->setWindowTitle("Graph subscriptions"); - connect(panel, &SubscriptionsPanel::filterAdded, this, + connect(panel.get(), &SubscriptionsPanel::filterAdded, this, &IncomingMessagesViewerModule::onFilterAdded); - connect(panel, &SubscriptionsPanel::filterRemoved, this, + connect(panel.get(), &SubscriptionsPanel::filterRemoved, this, &IncomingMessagesViewerModule::onFilterRemoved); panel->show(); } void IncomingMessagesViewerModule::onFilterAdded(const Filter& filter) { - filters.append(filter); - - MessageBroker::getInstance().subscribe( - filter, this, - [&](const Message& message, const Filter& filter) - { - QString oldText = ""; - QString time = ""; - // Save the old text - if (!keepOnlyLastMessage) - oldText = edit->toPlainText().mid(0, 10000); - - if (useTimestamp) - { - // If available show the timestamp - auto timestamp = message.getField("timestamp"); - time += "["; - time += QString::number( - (float)timestamp.getUnsignedInteger() / 1e6, 'f', 1); - time += "] "; - } - else + filters.insert( + filter, + MessageBroker::getInstance().subscribe( + filter, + [&](const Message& message, const Filter& filter) { - time += "[" + QTime::currentTime().toString("hh.mm.ss") + "] "; - } - - // Updated the content - edit->setText(time + message.toString() + "\n" + oldText); - }); + QString oldText = ""; + QString time = ""; + + // Save the old text + if (!keepOnlyLastMessage) + oldText = edit->toPlainText().mid(0, 10000); + + if (useTimestamp) + { + // If available show the timestamp + auto timestamp = message.getField("timestamp"); + time += "["; + time += QString::number( + (float)timestamp.getUnsignedInteger() / 1e6, 'f', 1); + time += "] "; + } + else + { + time += + "[" + QTime::currentTime().toString("hh.mm.ss") + "] "; + } + + // Updated the content + edit->setText(time + message.toString() + "\n" + oldText); + })); } void IncomingMessagesViewerModule::onFilterRemoved(const Filter& filter) { - filters.removeAll(filter); - MessageBroker::getInstance().unsubscribe(filter, this); + filters.remove(filter); } void IncomingMessagesViewerModule::setupUi() { - edit = new QTextEdit(); + edit = std::make_unique<QTextEdit>(); edit->setReadOnly(true); edit->setContextMenuPolicy(Qt::ContextMenuPolicy::NoContextMenu); QHBoxLayout* layout = new QHBoxLayout(); layout->setContentsMargins(0, 0, 0, 0); - layout->addWidget(edit); + layout->addWidget(edit.get()); setLayout(layout); } void IncomingMessagesViewerModule::customContextMenuActionSetup() { - QAction* clear = new QAction("Clear"); - connect(clear, &QAction::triggered, this, [this]() { edit->clear(); }); - customContextMenuActions.append(clear); + auto clear = std::make_unique<QAction>("Clear"); + connect(clear.get(), &QAction::triggered, this, + [this]() { edit->clear(); }); + customContextMenuActions.append(std::move(clear)); - QAction* subscriptions = new QAction("Manage subscriptions"); - connect(subscriptions, &QAction::triggered, this, + auto subscriptions = std::make_unique<QAction>("Manage subscriptions"); + connect(subscriptions.get(), &QAction::triggered, this, &IncomingMessagesViewerModule::onSubscribeClicked); - customContextMenuActions.append(subscriptions); + customContextMenuActions.append(std::move(subscriptions)); keepOnlyLastMessageAction = new QAction("Keep only last message"); keepOnlyLastMessageAction->setCheckable(true); connect(keepOnlyLastMessageAction, &QAction::toggled, this, [=](bool value) { keepOnlyLastMessage = value; }); - customContextMenuActions.append(keepOnlyLastMessageAction); + customContextMenuActions.append( + std::unique_ptr<QAction>(keepOnlyLastMessageAction)); useTimestampAction = new QAction("Use timestamp"); useTimestampAction->setCheckable(true); connect(useTimestampAction, &QAction::toggled, this, [=](bool value) { useTimestamp = value; }); - customContextMenuActions.append(useTimestampAction); + customContextMenuActions.append( + std::unique_ptr<QAction>(useTimestampAction)); } diff --git a/src/shared/Modules/IncomingMessagesViewer/IncomingMessagesViewerModule.h b/src/shared/Modules/IncomingMessagesViewer/IncomingMessagesViewerModule.h index ad22e590f10a449617c7b3a215692c03b6d4c0eb..4f3e1f63ed7d11e9624e1f3713caf9af3af087fe 100644 --- a/src/shared/Modules/IncomingMessagesViewer/IncomingMessagesViewerModule.h +++ b/src/shared/Modules/IncomingMessagesViewer/IncomingMessagesViewerModule.h @@ -40,11 +40,11 @@ private slots: void onFilterRemoved(const Filter& filter); private: - QTextEdit* edit; + std::unique_ptr<QTextEdit> edit; void setupUi(); void customContextMenuActionSetup(); - QList<Filter> filters; + QMultiMap<Filter, std::unique_ptr<Subscription>> filters; bool keepOnlyLastMessage = false; QAction* keepOnlyLastMessageAction; diff --git a/src/shared/Modules/MainStateViewer/MainStateViewer.cpp b/src/shared/Modules/MainStateViewer/MainStateViewer.cpp index 1784130744d1559df06e75512765fe37fc704037..e900171cd0df767113516f62c1c59a2ce0407152 100644 --- a/src/shared/Modules/MainStateViewer/MainStateViewer.cpp +++ b/src/shared/Modules/MainStateViewer/MainStateViewer.cpp @@ -30,10 +30,7 @@ MainStateViewerModule::MainStateViewerModule() customContextMenuActionSetup(); } -MainStateViewerModule::~MainStateViewerModule() -{ - MessageBroker::getInstance().unsubscribe(filter, this); -} +MainStateViewerModule::~MainStateViewerModule() {} XmlObject MainStateViewerModule::toXmlObject() { @@ -52,7 +49,7 @@ void MainStateViewerModule::fromXmlObject(const XmlObject& xmlObject) void MainStateViewerModule::setupUi() { - outerLayout = new QHBoxLayout; + outerLayout = std::make_unique<QHBoxLayout>(); outerLayout->setContentsMargins(0, 0, 0, 0); outerLayout->setSpacing(0); @@ -65,13 +62,13 @@ void MainStateViewerModule::setupUi() outerLayout->addWidget(label); } - setLayout(outerLayout); + setLayout(outerLayout.get()); } void MainStateViewerModule::customContextMenuActionSetup() { - QAction* action = new QAction("Choose topic and field"); - connect(action, &QAction::triggered, this, + auto action = std::make_unique<QAction>("Choose topic and field"); + connect(action.get(), &QAction::triggered, this, &MainStateViewerModule::onConfigureClicked); customContextMenuActions.append(action); @@ -85,10 +82,9 @@ void MainStateViewerModule::onConfigureClicked() void MainStateViewerModule::setFilter(const Filter& newFilter) { - MessageBroker::getInstance().unsubscribe(filter, this); - MessageBroker::getInstance().subscribe( - newFilter, this, - [this](const Message& message, const Filter& filter) + subscription->unsubscribe(); + subscription = MessageBroker::getInstance().subscribe( + newFilter, [this](const Message& message, const Filter& filter) { onMsgReceived(message); }); filter = newFilter; } diff --git a/src/shared/Modules/MainStateViewer/MainStateViewer.h b/src/shared/Modules/MainStateViewer/MainStateViewer.h index 3c42783903677a041c3776b1a7d9f0e77a4763e9..1ac1a5782061dca366e40cfe2ab7bcea36f2e8cc 100644 --- a/src/shared/Modules/MainStateViewer/MainStateViewer.h +++ b/src/shared/Modules/MainStateViewer/MainStateViewer.h @@ -46,8 +46,9 @@ private: void setFilter(const Filter& filter); void onMsgReceived(const Message& msg); - QHBoxLayout* outerLayout; + std::unique_ptr<QHBoxLayout> outerLayout; + std::unique_ptr<Subscription> subscription; Filter filter; MainStatesList::State currentState; }; diff --git a/src/shared/Modules/Mavlink/BaseMavlinkModule.cpp b/src/shared/Modules/Mavlink/BaseMavlinkModule.cpp index b10f1a693c1aff77bb901f4a028706f5e897ec49..9f8bdd5ff607b9f17d6f588138b3930ad2f3bee1 100644 --- a/src/shared/Modules/Mavlink/BaseMavlinkModule.cpp +++ b/src/shared/Modules/Mavlink/BaseMavlinkModule.cpp @@ -22,7 +22,8 @@ int BaseMavlinkModule::ACTIVE_MAVLINK_MODULES = 0; -BaseMavlinkModule::BaseMavlinkModule(MavlinkPort *port, ModuleId id) +BaseMavlinkModule::BaseMavlinkModule(std::shared_ptr<MavlinkPort> port, + ModuleId id) : Module(id), port(port), mavlinkCodec(port, this) { setupUi(); @@ -32,8 +33,8 @@ BaseMavlinkModule::BaseMavlinkModule(MavlinkPort *port, ModuleId id) connect(&linkQualityTimer, &QTimer::timeout, this, &BaseMavlinkModule::onLinkQualityTimerTick); - MessageBroker::getInstance().subscribe( - Filter::fromString(SkywardHubStrings::commandsTopic + "/*"), this, + subscription = MessageBroker::getInstance().subscribe( + Filter::fromString(SkywardHubStrings::commandsTopic + "/*"), [this](const Message &message, const Filter &filter) { onCommandReceived(message); }); } @@ -42,9 +43,6 @@ BaseMavlinkModule::~BaseMavlinkModule() { if (startToggleButton->state()) stop(); - - MessageBroker::getInstance().unsubscribe( - Filter::fromString(SkywardHubStrings::commandsTopic + "/*"), this); } XmlObject BaseMavlinkModule::toXmlObject() @@ -200,11 +198,11 @@ void BaseMavlinkModule::setupUi() QHBoxLayout *outerLayout = new QHBoxLayout; outerLayout->setContentsMargins(6, 0, 6, 0); - startToggleButton = new ToggleButton; + startToggleButton = std::make_unique<ToggleButton>(); startToggleButton->setSizePolicy( QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed)); - outerLayout->addWidget(startToggleButton); - connect(startToggleButton, &ToggleButton::toggled, this, + outerLayout->addWidget(startToggleButton.get()); + connect(startToggleButton.get(), &ToggleButton::toggled, this, &BaseMavlinkModule::onStartStreamToggled); QLabel *sysIdLabel = new QLabel("Target system:"); @@ -212,7 +210,7 @@ void BaseMavlinkModule::setupUi() QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed)); outerLayout->addWidget(sysIdLabel); - sysIdComboBox = new QComboBox; + sysIdComboBox = std::make_unique<QComboBox>(); sysIdComboBox->setSizePolicy( QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed)); @@ -220,10 +218,10 @@ void BaseMavlinkModule::setupUi() sysIdComboBox->addItem("Payload", MavlinkCodec::SysIdPayload); sysIdComboBox->addItem("Rig", MavlinkCodec::SysIdRig); sysIdComboBox->addItem("Gs Receiver", MavlinkCodec::SysIdGsReceiver); - outerLayout->addWidget(sysIdComboBox); + outerLayout->addWidget(sysIdComboBox.get()); - childLayout = new QHBoxLayout; - outerLayout->addLayout(childLayout); + childLayout = std::make_unique<QHBoxLayout>(); + outerLayout->addLayout(childLayout.get()); outerLayout->addStretch(); diff --git a/src/shared/Modules/Mavlink/BaseMavlinkModule.h b/src/shared/Modules/Mavlink/BaseMavlinkModule.h index a569d21227bff82af61db4d28506d4a6e1ffe4e0..0114ef321c22f5a667f3a11c90cd20499e9261e2 100644 --- a/src/shared/Modules/Mavlink/BaseMavlinkModule.h +++ b/src/shared/Modules/Mavlink/BaseMavlinkModule.h @@ -40,7 +40,7 @@ class BaseMavlinkModule : public Module { Q_OBJECT public: - BaseMavlinkModule(MavlinkPort *port, ModuleId id); + BaseMavlinkModule(std::shared_ptr<MavlinkPort> port, ModuleId id); ~BaseMavlinkModule(); XmlObject toXmlObject() override; @@ -53,7 +53,7 @@ protected: virtual void childFromXmlObject(const XmlObject &obj) = 0; virtual bool open() = 0; - QHBoxLayout *childLayout; + std::unique_ptr<QHBoxLayout> childLayout; private slots: void onMsgReceived(const Message &msg); void onLinkQualityTimerTick(); @@ -73,11 +73,11 @@ private: void setupUi(); - MavlinkPort *port; + std::shared_ptr<MavlinkPort> port; MavlinkCodec mavlinkCodec; - ToggleButton *startToggleButton; - QComboBox *sysIdComboBox; + std::unique_ptr<ToggleButton> startToggleButton; + std::unique_ptr<QComboBox> sysIdComboBox; std::unique_ptr<QLabel> rateLabel; std::unique_ptr<QCheckBox> logCheckBox; @@ -86,5 +86,7 @@ private: const int linkQualityPeriod = 2000; // [ms] int msgArrived = 0; + std::unique_ptr<Subscription> subscription; + static int ACTIVE_MAVLINK_MODULES; }; \ No newline at end of file diff --git a/src/shared/Modules/Mavlink/MavlinkCodec.cpp b/src/shared/Modules/Mavlink/MavlinkCodec.cpp index 37daea184d8ac5a115df1962a0184fc27276f967..541f48e4d0512cd9766eed69485801544e40469e 100644 --- a/src/shared/Modules/Mavlink/MavlinkCodec.cpp +++ b/src/shared/Modules/Mavlink/MavlinkCodec.cpp @@ -23,7 +23,8 @@ #include "BaseMavlinkModule.h" #include "Modules/SkywardHubStrings.h" -MavlinkCodec::MavlinkCodec(MavlinkPort* port, BaseMavlinkModule* parent) +MavlinkCodec::MavlinkCodec(std::shared_ptr<MavlinkPort> port, + BaseMavlinkModule* parent) : port(port), parent(parent) { } @@ -39,13 +40,13 @@ void MavlinkCodec::send(const mavlink_message_t& msg) void MavlinkCodec::startReading() { - QObject::connect(port, &MavlinkPort::bytesReceived, this, + QObject::connect(port.get(), &MavlinkPort::bytesReceived, this, &MavlinkCodec::onBytesReceived); } void MavlinkCodec::stopReading() { - QObject::disconnect(port, &MavlinkPort::bytesReceived, this, + QObject::disconnect(port.get(), &MavlinkPort::bytesReceived, this, &MavlinkCodec::onBytesReceived); } diff --git a/src/shared/Modules/Mavlink/MavlinkCodec.h b/src/shared/Modules/Mavlink/MavlinkCodec.h index 2d794d50adddab7f88a4c519a673ca8758f3f3db..b32e6620066ed765e572004908ac0db9409ea40c 100644 --- a/src/shared/Modules/Mavlink/MavlinkCodec.h +++ b/src/shared/Modules/Mavlink/MavlinkCodec.h @@ -45,7 +45,8 @@ public: CompIdNone = 0 }; - explicit MavlinkCodec(MavlinkPort* port, BaseMavlinkModule* parent); + explicit MavlinkCodec(std::shared_ptr<MavlinkPort> port, + BaseMavlinkModule* parent); void send(const mavlink_message_t& msg); @@ -81,7 +82,7 @@ private: mavlink_message_t mavlinkMessage; mavlink_status_t mavlinkStatus; - MavlinkPort* port; + std::shared_ptr<MavlinkPort> port; BaseMavlinkModule* parent; QString logFilePath = ""; diff --git a/src/shared/Modules/Mavlink/SerialMavlinkModule.cpp b/src/shared/Modules/Mavlink/SerialMavlinkModule.cpp index b32253957e008e3ff95394e8fad707c8a1ae1f95..b82e034dfbb63109a6859da7bd39a668637f151c 100644 --- a/src/shared/Modules/Mavlink/SerialMavlinkModule.cpp +++ b/src/shared/Modules/Mavlink/SerialMavlinkModule.cpp @@ -21,7 +21,8 @@ #include <QSerialPortInfo> SerialMavlinkModule::SerialMavlinkModule() - : BaseMavlinkModule(&serial, ModuleId::SERIAL_MAVLINK), serial(this) + : serial(std::make_shared<SerialPort>(this)), + BaseMavlinkModule(serial, ModuleId::SERIAL_MAVLINK) { childSetupUi(); } @@ -54,26 +55,26 @@ void SerialMavlinkModule::childSetupUi() QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed)); childLayout->addWidget(portsLabel); - portsComboBox = new QComboBox; + portsComboBox = std::make_unique<QComboBox>(); portsComboBox->setSizePolicy( QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed)); - childLayout->addWidget(portsComboBox); + childLayout->addWidget(portsComboBox.get()); fillPortsComboBox(); - refreshButton = new QPushButton("Refresh"); + refreshButton = std::make_unique<QPushButton>("Refresh"); refreshButton->setSizePolicy( QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed)); - connect(refreshButton, &QPushButton::released, this, + connect(refreshButton.get(), &QPushButton::released, this, &SerialMavlinkModule::onRefreshClicked); - childLayout->addWidget(refreshButton); + childLayout->addWidget(refreshButton.get()); QLabel *baudrateLabel = new QLabel("Baudrate:"); baudrateLabel->setSizePolicy( QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed)); childLayout->addWidget(baudrateLabel); - baudrateComboBox = new QComboBox; + baudrateComboBox = std::make_unique<QComboBox>(); baudrateComboBox->setSizePolicy( QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed)); @@ -81,7 +82,7 @@ void SerialMavlinkModule::childSetupUi() baudrateComboBox->addItem("19200", QSerialPort::Baud19200); baudrateComboBox->addItem("9600", QSerialPort::Baud9600); - childLayout->addWidget(baudrateComboBox); + childLayout->addWidget(baudrateComboBox.get()); } void SerialMavlinkModule::childDisableControls() @@ -104,7 +105,7 @@ bool SerialMavlinkModule::open() int baudRate = baudrateComboBox->currentData().toInt(); // Open the serial port - return serial.open(portName, baudRate); + return serial->open(portName, baudRate); } void SerialMavlinkModule::fillPortsComboBox() diff --git a/src/shared/Modules/Mavlink/SerialMavlinkModule.h b/src/shared/Modules/Mavlink/SerialMavlinkModule.h index 6ae11c16cdbfd90abc2703e02e61bd8fa47f3004..f2692f35aee89b3e0c59f92858254eca110418ec 100644 --- a/src/shared/Modules/Mavlink/SerialMavlinkModule.h +++ b/src/shared/Modules/Mavlink/SerialMavlinkModule.h @@ -41,9 +41,9 @@ private: void fillPortsComboBox(); - SerialPort serial; + std::shared_ptr<SerialPort> serial; - QComboBox *portsComboBox; - QPushButton *refreshButton; - QComboBox *baudrateComboBox; + std::unique_ptr<QComboBox> portsComboBox; + std::unique_ptr<QPushButton> refreshButton; + std::unique_ptr<QComboBox> baudrateComboBox; }; \ No newline at end of file diff --git a/src/shared/Modules/Mavlink/UdpMavlinkModule.cpp b/src/shared/Modules/Mavlink/UdpMavlinkModule.cpp index b529334bc9a28aacbbb514426811b4481485bd38..3b7e8157c74b0f21e195ce69362f988fd15b95fc 100644 --- a/src/shared/Modules/Mavlink/UdpMavlinkModule.cpp +++ b/src/shared/Modules/Mavlink/UdpMavlinkModule.cpp @@ -19,7 +19,8 @@ #include "UdpMavlinkModule.h" UdpMavlinkModule::UdpMavlinkModule() - : BaseMavlinkModule(&udp, ModuleId::UDP_MAVLINK), udp(this) + : udp(std::make_shared<UdpPort>(this)), + BaseMavlinkModule(udp, ModuleId::UDP_MAVLINK) { childSetupUi(); } @@ -51,22 +52,22 @@ void UdpMavlinkModule::childSetupUi() QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed)); childLayout->addWidget(recvPortLabel); - recvPort = new QLineEdit; + recvPort = std::make_unique<QLineEdit>(); recvPort->setSizePolicy( QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed)); recvPort->setValidator(new QIntValidator(0, 0xffff)); - childLayout->addWidget(recvPort); + childLayout->addWidget(recvPort.get()); QLabel *sendPortLabel = new QLabel("Send port:"); sendPortLabel->setSizePolicy( QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed)); childLayout->addWidget(sendPortLabel); - sendPort = new QLineEdit; + sendPort = std::make_unique<QLineEdit>(); sendPort->setSizePolicy( QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed)); sendPort->setValidator(new QIntValidator(0, 0xffff)); - childLayout->addWidget(sendPort); + childLayout->addWidget(sendPort.get()); } void UdpMavlinkModule::childDisableControls() @@ -94,5 +95,5 @@ bool UdpMavlinkModule::open() return false; // Open the serial port - return udp.open(recvPortValue, sendPortValue); + return udp->open(recvPortValue, sendPortValue); } \ No newline at end of file diff --git a/src/shared/Modules/Mavlink/UdpMavlinkModule.h b/src/shared/Modules/Mavlink/UdpMavlinkModule.h index 58a657aaca3fbbe668c054149c806aff19ce202c..539645ed4f242a3acb03c11e1706b752519f543e 100644 --- a/src/shared/Modules/Mavlink/UdpMavlinkModule.h +++ b/src/shared/Modules/Mavlink/UdpMavlinkModule.h @@ -36,8 +36,8 @@ private: void childFromXmlObject(const XmlObject &obj) override; bool open() override; - UdpPort udp; + std::shared_ptr<UdpPort> udp; - QLineEdit *recvPort; - QLineEdit *sendPort; + std::unique_ptr<QLineEdit> recvPort; + std::unique_ptr<QLineEdit> sendPort; }; \ No newline at end of file diff --git a/src/shared/Modules/OrientationVisualizer/OrientationVisualizer.cpp b/src/shared/Modules/OrientationVisualizer/OrientationVisualizer.cpp index 9d0ca4a8ee06bdfe47c76ddb769d3306d51c4189..af31dcf903ba6ad62b9ff157375a626688d019a1 100644 --- a/src/shared/Modules/OrientationVisualizer/OrientationVisualizer.cpp +++ b/src/shared/Modules/OrientationVisualizer/OrientationVisualizer.cpp @@ -34,8 +34,8 @@ OrientationVisualizer::OrientationVisualizer() updateOrientation(QQuaternion(0.707, 0, 0.707, 0)); - MessageBroker::getInstance().subscribe( - Filter::fromString("Mav/ROCKET_FLIGHT_TM"), this, + rocketFlightSub = MessageBroker::getInstance().subscribe( + Filter::fromString("Mav/ROCKET_FLIGHT_TM"), [this](const Message &message, const Filter &filter) { if (nullptr == sourceComboBox) @@ -51,8 +51,8 @@ OrientationVisualizer::OrientationVisualizer() static_cast<float>(message.getField("nas_qz").getDouble())); updateOrientation(q); }); - MessageBroker::getInstance().subscribe( - Filter::fromString("Mav/PAYLOAD_FLIGHT_TM"), this, + payloadFlightSub = MessageBroker::getInstance().subscribe( + Filter::fromString("Mav/PAYLOAD_FLIGHT_TM"), [this](const Message &message, const Filter &filter) { if (nullptr == sourceComboBox) @@ -70,14 +70,7 @@ OrientationVisualizer::OrientationVisualizer() }); } -OrientationVisualizer::~OrientationVisualizer() -{ - // Unsubscribe from message broker - MessageBroker::getInstance().unsubscribe( - Filter::fromString("Mav/ROCKET_FLIGHT_TM"), this); - MessageBroker::getInstance().unsubscribe( - Filter::fromString("Mav/PAYLOAD_FLIGHT_TM"), this); -} +OrientationVisualizer::~OrientationVisualizer() {} void OrientationVisualizer::updateOrientation(QQuaternion q) { diff --git a/src/shared/Modules/OrientationVisualizer/OrientationVisualizer.h b/src/shared/Modules/OrientationVisualizer/OrientationVisualizer.h index 062b3ea4bf75f65fdd33d591117e39fa33344f3e..dc43f7b626e129d84687b03a110ea63527ddf19c 100644 --- a/src/shared/Modules/OrientationVisualizer/OrientationVisualizer.h +++ b/src/shared/Modules/OrientationVisualizer/OrientationVisualizer.h @@ -70,6 +70,9 @@ private: Qt3DCore::QTransform *rocketTransform; Qt3DRender::QCamera *camera; + std::unique_ptr<Subscription> rocketFlightSub; + std::unique_ptr<Subscription> payloadFlightSub; + const float PROJECTION_SIZE = 30.; const int GRID_SPAN = 15; const float GRID_GAP = 4.f; diff --git a/src/shared/Modules/OutgoingMessagesViewer/OutgoingMessagesViewerModule.cpp b/src/shared/Modules/OutgoingMessagesViewer/OutgoingMessagesViewerModule.cpp index 28a67fd84846ddd10fbe095f4cd375354ea45ead..fef7fa13d9c2f559bb63f9ef1fce79d235ce867d 100644 --- a/src/shared/Modules/OutgoingMessagesViewer/OutgoingMessagesViewerModule.cpp +++ b/src/shared/Modules/OutgoingMessagesViewer/OutgoingMessagesViewerModule.cpp @@ -31,19 +31,17 @@ OutgoingMessagesViewerModule::OutgoingMessagesViewerModule() { ui->setupUi(this); - MessageBroker::getInstance().subscribe( - Filter::fromString(SkywardHubStrings::logCommandsTopic), this, + logCommandsSub = MessageBroker::getInstance().subscribe( + Filter::fromString(SkywardHubStrings::logCommandsTopic), [this](const Message& message, const Filter& filter) { addMsgSent(message); }); - MessageBroker::getInstance().subscribe( + mavlinkRecvACK = MessageBroker::getInstance().subscribe( Filter::fromString(SkywardHubStrings::mavlink_received_msg_ACK_topic), - this, [this](const Message& message, const Filter& filter) { handleAck(message); }); - MessageBroker::getInstance().subscribe( + mavlinkRecvNACK = MessageBroker::getInstance().subscribe( Filter::fromString(SkywardHubStrings::mavlink_received_msg_NACK_topic), - this, [this](const Message& message, const Filter& filter) { handleNack(message); }); } diff --git a/src/shared/Modules/OutgoingMessagesViewer/OutgoingMessagesViewerModule.h b/src/shared/Modules/OutgoingMessagesViewer/OutgoingMessagesViewerModule.h index c51592123f215b75a086135d729e33e2ced3b6c1..06856fcad4550028085f9de08f36ada8315228e9 100644 --- a/src/shared/Modules/OutgoingMessagesViewer/OutgoingMessagesViewerModule.h +++ b/src/shared/Modules/OutgoingMessagesViewer/OutgoingMessagesViewerModule.h @@ -68,4 +68,8 @@ private: Ui::OutgoingMessagesViewerModule* ui; QList<MessageLog> messages; int maxSize = 10; + + std::unique_ptr<Subscription> logCommandsSub; + std::unique_ptr<Subscription> mavlinkRecvACK; + std::unique_ptr<Subscription> mavlinkRecvNACK; }; diff --git a/src/shared/Modules/PayloadStateViewer/PayloadStateViewer.cpp b/src/shared/Modules/PayloadStateViewer/PayloadStateViewer.cpp index 0653564eedd3a3466a784ef2ec6d6c073516e476..73c461e9ed43becd4b668f3892a5f7c18eea6e92 100644 --- a/src/shared/Modules/PayloadStateViewer/PayloadStateViewer.cpp +++ b/src/shared/Modules/PayloadStateViewer/PayloadStateViewer.cpp @@ -28,10 +28,7 @@ PayloadStateViewerModule::PayloadStateViewerModule() customContextMenuActionSetup(); } -PayloadStateViewerModule::~PayloadStateViewerModule() -{ - MessageBroker::getInstance().unsubscribe(filter, this); -} +PayloadStateViewerModule::~PayloadStateViewerModule() {} XmlObject PayloadStateViewerModule::toXmlObject() { @@ -68,11 +65,11 @@ void PayloadStateViewerModule::setupUi() void PayloadStateViewerModule::customContextMenuActionSetup() { - QAction* action = new QAction("Choose topic and field"); - connect(action, &QAction::triggered, this, + auto action = std::make_unique<QAction>("Choose topic and field"); + connect(action.get(), &QAction::triggered, this, &PayloadStateViewerModule::onConfigureClicked); - customContextMenuActions.append(action); + customContextMenuActions.append(std::move(action)); } void PayloadStateViewerModule::onConfigureClicked() @@ -83,10 +80,9 @@ void PayloadStateViewerModule::onConfigureClicked() void PayloadStateViewerModule::setFilter(const Filter& newFilter) { - MessageBroker::getInstance().unsubscribe(filter, this); - MessageBroker::getInstance().subscribe( - newFilter, this, - [this](const Message& message, const Filter& filter) + sub->unsubscribe(); + sub = MessageBroker::getInstance().subscribe( + newFilter, [this](const Message& message, const Filter& filter) { onMsgReceived(message); }); filter = newFilter; } diff --git a/src/shared/Modules/PayloadStateViewer/PayloadStateViewer.h b/src/shared/Modules/PayloadStateViewer/PayloadStateViewer.h index 5c2b81af2888c8403d266582e999370647344a59..eff9d5de220dc32e29cf794cd3f27ff0951f9922 100644 --- a/src/shared/Modules/PayloadStateViewer/PayloadStateViewer.h +++ b/src/shared/Modules/PayloadStateViewer/PayloadStateViewer.h @@ -47,6 +47,7 @@ private: QHBoxLayout* outerLayout; + std::unique_ptr<Subscription> sub; Filter filter; PayloadStatesList::State currentState; }; diff --git a/src/shared/Modules/Splitter/Splitter.cpp b/src/shared/Modules/Splitter/Splitter.cpp index a93c2002196c4f75b0081e45d5fbbf4a79117a8b..8d77ddc628b2202d5af9cc22026ee9a79cf4ec3c 100644 --- a/src/shared/Modules/Splitter/Splitter.cpp +++ b/src/shared/Modules/Splitter/Splitter.cpp @@ -61,8 +61,8 @@ void Splitter::fromXmlObject(const XmlObject& obj) for (int i = 0; i < obj.childCount(); i++) { XmlObject xmlChild = obj.childAt(i); - Module* module = ModulesList::getInstance().instantiateModule( - xmlChild.getObjectName()); + auto module = ModulesList::getInstance().instantiateModule( + xmlChild.getObjectName()); if (module) { @@ -78,31 +78,32 @@ void Splitter::fromXmlObject(const XmlObject& obj) splitter->setSizes(intSizes); } -void Splitter::addModule(Module* module) +void Splitter::addModule(std::shared_ptr<Module> module) { addModule(module, splitter->count()); } -void Splitter::addModule(Module* module, int position) +void Splitter::addModule(std::shared_ptr<Module> module, int position) { - connect(module, &Module::replaceMe, this, &Splitter::replaceChild); - connect(module, &Module::closeMe, this, &Splitter::closeChild); - - // Replace the module if there is already one - if (position >= 0 && position < splitter->count()) - delete splitter->widget(position); - - splitter->insertWidget(position, qobject_cast<QWidget*>(module)); + connect(module.get(), &Module::replaceMe, this, &Splitter::replaceChild); + connect(module.get(), &Module::closeMe, this, &Splitter::closeChild); + + // This will replace the child if it is present at <position> + // and will automatically dec ref_count since it being cleared from + // this class' scope. + childModules.insert(position, module); + splitter->insertWidget(position, qobject_cast<QWidget*>(module.get())); } -void Splitter::replaceChild(Module* oldModule, Module* newModule) +void Splitter::replaceChild(Module* oldModule, + std::shared_ptr<Module> newModule) { // Check if the modules are valid if (!oldModule || !newModule) return; // Check if we are trying to replace a module with itself - if (oldModule == newModule) + if (oldModule == newModule.get()) return; auto index = splitter->indexOf(oldModule); @@ -127,13 +128,25 @@ void Splitter::closeChild(Module* module) return; } + for (auto it = childModules.begin(); it != childModules.end();) + { + if (it.value().get() == module) + { + it = childModules.erase(it); + } + else + { + it++; + } + } + // If there is only two children, then the remaining one will replace the // whole splitter if (splitter->count() == 2) { - Module* currentChild = (Module*)splitter->widget(0); + auto currentChild = childModules.last(); - // REmove the children parent. This is essential otherwise when the + // Remove the children parent. This is essential otherwise when the // splitter will be deleted, also the child will be currentChild->setParent(nullptr); @@ -168,16 +181,16 @@ void Splitter::swapOrientation() void Splitter::customContextMenuActionSetup() { - QAction* split = new QAction("Split"); - connect(split, &QAction::triggered, this, + auto split = std::make_unique<QAction>("Split"); + connect(split.get(), &QAction::triggered, this, [this]() { addModule(ModulesList::getInstance().instantiateModule( ModuleId::EMPTY)); }); customContextMenuActions.append(split); - QAction* changeOrientation = new QAction("Swap Orientation"); - connect(changeOrientation, &QAction::triggered, this, + auto changeOrientation = std::make_unique<QAction>("Swap Orientation"); + connect(changeOrientation.get(), &QAction::triggered, this, [this]() { this->swapOrientation(); }); customContextMenuActions.append(changeOrientation); } @@ -187,11 +200,11 @@ void Splitter::setupUi(Qt::Orientation orientation) QVBoxLayout* outerLayout = new QVBoxLayout; outerLayout->setContentsMargins(0, 0, 0, 0); - splitter = new QSplitter(); + splitter = std::make_unique<QSplitter>(); splitter->setOrientation(orientation); splitter->setChildrenCollapsible(false); splitter->setHandleWidth(0); - outerLayout->addWidget(splitter); + outerLayout->addWidget(splitter.get()); // By default add two default modules addModule(ModulesList::getInstance().instantiateModule(ModuleId::EMPTY)); diff --git a/src/shared/Modules/Splitter/Splitter.h b/src/shared/Modules/Splitter/Splitter.h index 0fbb477dc27b8fbbd2dee2397aa9f21d4dc87c9b..3bcaf5790e72738dd1688cec0fa35fcf534e8587 100644 --- a/src/shared/Modules/Splitter/Splitter.h +++ b/src/shared/Modules/Splitter/Splitter.h @@ -33,20 +33,21 @@ public: XmlObject toXmlObject() override; void fromXmlObject(const XmlObject &obj) override; - void addModule(Module *module); - void addModule(Module *module, int position); + void addModule(std::shared_ptr<Module> module); + void addModule(std::shared_ptr<Module> module, int position); Qt::Orientation getOrientation() const; void setOrientation(Qt::Orientation orientation); void swapOrientation(); public slots: - void replaceChild(Module *oldModule, Module *newModule); + void replaceChild(Module *oldModule, std::shared_ptr<Module> newModule); void closeChild(Module *module); private: void customContextMenuActionSetup(); void setupUi(Qt::Orientation orientation = Qt::Horizontal); - QSplitter *splitter; + std::unique_ptr<QSplitter> splitter; + QMap<int, std::shared_ptr<Module>> childModules; }; diff --git a/src/shared/Modules/Tabs/TabsModule.cpp b/src/shared/Modules/Tabs/TabsModule.cpp index 53d3c3c28e5c3e53e19e2eadb57961ba1e67ba12..6d4d4f0fa54a9091da9beac46a7004c8cb49f91f 100644 --- a/src/shared/Modules/Tabs/TabsModule.cpp +++ b/src/shared/Modules/Tabs/TabsModule.cpp @@ -29,9 +29,9 @@ TabsModule::TabsModule() : Module(ModuleId::TABS) setupUi(); customContextMenuActionSetup(); - QObject::connect(tabNames, &QListWidget::currentRowChanged, tabContents, - &QStackedWidget::setCurrentIndex); - QObject::connect(tabNames, &QListWidget::itemDoubleClicked, this, + QObject::connect(tabNames.get(), &QListWidget::currentRowChanged, + tabContents.get(), &QStackedWidget::setCurrentIndex); + QObject::connect(tabNames.get(), &QListWidget::itemDoubleClicked, this, &TabsModule::onDoubleClickedItem); // Automatically add first tab @@ -60,10 +60,8 @@ void TabsModule::fromXmlObject(const XmlObject& xmlObject) tabNames->clear(); for (int i = contentModules.size() - 1; i >= 0; i--) { - auto* module = contentModules[i]; - contentModules.pop_back(); tabContents->removeWidget(tabContents->widget(i)); - delete module; + contentModules.pop_back(); } for (int i = 0; i < xmlObject.childCount(); ++i) @@ -74,7 +72,7 @@ void TabsModule::fromXmlObject(const XmlObject& xmlObject) XmlObject xmlChild = tabNode.childAt(0); - Module* module = ModulesList::getInstance().instantiateModule( + auto module = ModulesList::getInstance().instantiateModule( xmlChild.getObjectName()); if (module != nullptr) { @@ -96,17 +94,17 @@ void TabsModule::fromXmlObject(const XmlObject& xmlObject) tabNames->setCurrentItem(tabNames->item(0)); } -void TabsModule::addTab(const QString& tabName, Module* module) +void TabsModule::addTab(const QString& tabName, std::shared_ptr<Module> module) { - connect(module, &Module::replaceMe, this, &TabsModule::replaceTab); - connect(module, &Module::closeMe, this, &TabsModule::closeTab); + connect(module.get(), &Module::replaceMe, this, &TabsModule::replaceTab); + connect(module.get(), &Module::closeMe, this, &TabsModule::closeTab); auto* listItem = new QListWidgetItem(); listItem->setText(tabName); listItem->setTextAlignment(Qt::AlignCenter); tabNames->addItem(listItem); - tabContents->addWidget(module); + tabContents->addWidget(module.get()); contentModules.append(module); // We set the correct tabName after the widget is added @@ -118,19 +116,19 @@ QString TabsModule::generateUniqueTabName() return QString("Tab %1").arg(tabNames->count()); } -void TabsModule::replaceTab(Module* oldModule, Module* newModule) +void TabsModule::replaceTab(Module* oldModule, + std::shared_ptr<Module> newModule) { // Check if the modules are valid if (!oldModule || !newModule) return; // Check if we are trying to replace a module with itself - if (oldModule == newModule) + if (oldModule == newModule.get()) return; - int index = contentModules.indexOf(oldModule); + auto index = findModuleIndex(oldModule); - // Check if the old module is a child if (index == -1) return; @@ -138,20 +136,19 @@ void TabsModule::replaceTab(Module* oldModule, Module* newModule) tabNames->setCurrentItem(tabNames->item(index)); contentModules.replace(index, newModule); - tabContents->insertWidget(index, newModule); + tabContents->insertWidget(index, newModule.get()); tabContents->removeWidget(oldModule); - tabContents->setCurrentWidget(newModule); + tabContents->setCurrentWidget(newModule.get()); tabContents->update(); - connect(newModule, &Module::replaceMe, this, &TabsModule::replaceTab); - connect(newModule, &Module::closeMe, this, &TabsModule::closeTab); - - delete oldModule; + connect(newModule.get(), &Module::replaceMe, this, &TabsModule::replaceTab); + connect(newModule.get(), &Module::closeMe, this, &TabsModule::closeTab); } void TabsModule::closeTab(Module* module) { - int index = contentModules.indexOf(module); + + int index = findModuleIndex(module); // Check if the given module is a child if (index == -1) @@ -179,17 +176,18 @@ void TabsModule::onDoubleClickedItem(QListWidgetItem* item) void TabsModule::customContextMenuActionSetup() { - auto* newTab = new QAction("New Tab"); - connect(newTab, &QAction::triggered, this, &TabsModule::onMenuNewTabClick); + auto newTab = std::make_unique<QAction>("New Tab"); + connect(newTab.get(), &QAction::triggered, this, + &TabsModule::onMenuNewTabClick); customContextMenuActions.append(newTab); - auto* deleteTab = new QAction("Delete Tab"); - connect(deleteTab, &QAction::triggered, this, + auto deleteTab = std::make_unique<QAction>("Delete Tab"); + connect(deleteTab.get(), &QAction::triggered, this, &TabsModule::onMenuDeleteTabClick); customContextMenuActions.append(deleteTab); - auto* renameTab = new QAction("Rename Tab"); - connect(renameTab, &QAction::triggered, this, + auto renameTab = std::make_unique<QAction>("Rename Tab"); + connect(renameTab.get(), &QAction::triggered, this, &TabsModule::onMenuRenameTabClick); customContextMenuActions.append(renameTab); } @@ -202,7 +200,7 @@ void TabsModule::onMenuNewTabClick() void TabsModule::onMenuDeleteTabClick() { - delete contentModules.at(tabNames->currentRow()); + contentModules.removeAt(tabNames->currentRow()); tabNames->removeItemWidget(tabNames->currentItem()); } @@ -245,7 +243,7 @@ constexpr const char* componentsStyleSheet = R"x( void TabsModule::setupUi() { // Top component (top bar) - tabNames = new QListWidget; + tabNames = std::make_unique<QListWidget>(); tabNames->setFlow(QListView::Flow::LeftToRight); tabNames->setStyleSheet(componentsStyleSheet); tabNames->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); @@ -254,7 +252,7 @@ void TabsModule::setupUi() tabNames->setMaximumHeight(40); // Bottom component - tabContents = new QStackedWidget; + tabContents = std::make_unique<QStackedWidget>(); tabContents->setObjectName("TabsStackedWidget"); tabContents->setStyleSheet(componentsStyleSheet); @@ -263,6 +261,19 @@ void TabsModule::setupUi() outerLayout->setContentsMargins(0, 0, 0, 0); outerLayout->setSpacing(0); - outerLayout->addWidget(tabNames); - outerLayout->addWidget(tabContents); + outerLayout->addWidget(tabNames.get()); + outerLayout->addWidget(tabContents.get()); } + +int TabsModule::findModuleIndex(Module* rawModule) +{ + auto foundModule = + std::find_if(contentModules.begin(), contentModules.end(), + [rawModule](std::shared_ptr<Module>& module) + { return module.get() == rawModule; }); + + // Check if the old module is a child + if (foundModule == contentModules.end()) + return -1; + return contentModules.indexOf(*foundModule); +} \ No newline at end of file diff --git a/src/shared/Modules/Tabs/TabsModule.h b/src/shared/Modules/Tabs/TabsModule.h index d06ba6c804c502de20b0852e35e0a97bc07f1997..4a29470d42592663f2a6ddec04454fa35251ff34 100644 --- a/src/shared/Modules/Tabs/TabsModule.h +++ b/src/shared/Modules/Tabs/TabsModule.h @@ -31,13 +31,13 @@ class TabsModule : public Module public: TabsModule(); - void addTab(const QString& tabName, Module* module); + void addTab(const QString& tabName, std::shared_ptr<Module> module); XmlObject toXmlObject() override; void fromXmlObject(const XmlObject& xmlObject) override; private slots: - void replaceTab(Module* oldModule, Module* newModule); + void replaceTab(Module* oldModule, std::shared_ptr<Module> newModule); void closeTab(Module* module); void onDoubleClickedItem(QListWidgetItem* item); @@ -49,9 +49,11 @@ private: void setupUi(); void customContextMenuActionSetup(); + int findModuleIndex(Module* rawModule); + QString generateUniqueTabName(); - QListWidget* tabNames; - QStackedWidget* tabContents; - QList<Module*> contentModules; + std::unique_ptr<QListWidget> tabNames; + std::unique_ptr<QStackedWidget> tabContents; + QList<std::shared_ptr<Module>> contentModules; }; diff --git a/src/shared/Modules/Test/TestModule.cpp b/src/shared/Modules/Test/TestModule.cpp index fc71da8519cec1882d69f37e2db8eb3089496b7c..21acbacb53832f883cc7eafdd15df9d5fb474d42 100644 --- a/src/shared/Modules/Test/TestModule.cpp +++ b/src/shared/Modules/Test/TestModule.cpp @@ -59,8 +59,8 @@ void TestModule::on_publish_button_clicked() void TestModule::on_subscribe_button_clicked() { - MessageBroker::getInstance().subscribe( - Filter::fromString(ui->subscribe_lineEdit->text().trimmed()), this, + subscription = MessageBroker::getInstance().subscribe( + Filter::fromString(ui->subscribe_lineEdit->text().trimmed()), [this](const Message& message, const Filter& filter) { QString oldText = ui->textArea->toPlainText(); @@ -74,8 +74,7 @@ void TestModule::on_subscribe_button_clicked() void TestModule::on_unsubscribe_button_clicked() { - MessageBroker::getInstance().unsubscribe( - Filter::fromString(ui->subscribe_lineEdit->text().trimmed()), this); + subscription->unsubscribe(); } void TestModule::onMaxCharChanged(int value) { maxChar = value; } diff --git a/src/shared/Modules/Test/TestModule.h b/src/shared/Modules/Test/TestModule.h index 499c719c755edd45795996f6dbc005ad08359a9b..600889392ac61cee070d085eda7d5229b04001e0 100644 --- a/src/shared/Modules/Test/TestModule.h +++ b/src/shared/Modules/Test/TestModule.h @@ -47,4 +47,6 @@ private: Ui::TestModule *ui; int maxChar = 2000; + + std::unique_ptr<Subscription> subscription; }; diff --git a/src/shared/Modules/ValuesConverterViewer/ValuesConverterViewerModule.cpp b/src/shared/Modules/ValuesConverterViewer/ValuesConverterViewerModule.cpp index 33fa9d0aaef09ca2d8deb670bc6611b7ac8d787c..2d3daf75571976b427ae9c18ef9309a947702e5c 100644 --- a/src/shared/Modules/ValuesConverterViewer/ValuesConverterViewerModule.cpp +++ b/src/shared/Modules/ValuesConverterViewer/ValuesConverterViewerModule.cpp @@ -33,8 +33,8 @@ ValuesConverterViewerModule::ValuesConverterViewerModule() ui->setupUi(this); customContextMenuActionSetup(); - MessageBroker::getInstance().subscribe( - Filter::fromString("*"), this, + subscription = MessageBroker::getInstance().subscribe( + Filter::fromString("*"), [this](const Message& message, const Filter& filter) { onMsgReceived(message); }); } @@ -42,7 +42,6 @@ ValuesConverterViewerModule::ValuesConverterViewerModule() ValuesConverterViewerModule::~ValuesConverterViewerModule() { clearLabels(); - MessageBroker::getInstance().unsubscribe(Filter::fromString("*"), this); delete ui; } @@ -81,10 +80,10 @@ void ValuesConverterViewerModule::fromXmlObject(const XmlObject& xmlObject) void ValuesConverterViewerModule::onConfigureClicked() { - ValuesViewerConfigPanel* sPanel = new ValuesViewerConfigPanel(); + auto sPanel = std::make_unique<ValuesViewerConfigPanel>(); sPanel->setRules(rules); sPanel->setColumnsCount(columns); - connect(sPanel, &ValuesViewerConfigPanel::configurationSaved, this, + connect(sPanel.get(), &ValuesViewerConfigPanel::configurationSaved, this, &ValuesConverterViewerModule::onConfigurationSaved); sPanel->show(); } @@ -100,29 +99,22 @@ void ValuesConverterViewerModule::onConfigurationSaved( void ValuesConverterViewerModule::customContextMenuActionSetup() { - QAction* configure = new QAction("Configure"); - connect(configure, &QAction::triggered, this, + auto configure = std::make_unique<QAction, const QString&>("Configure"); + connect(configure.get(), &QAction::triggered, this, &ValuesConverterViewerModule::onConfigureClicked); customContextMenuActions.append(configure); } -QLabel* ValuesConverterViewerModule::createView(const ValueElement& el) const +std::unique_ptr<QLabel> ValuesConverterViewerModule::createView( + const ValueElement& el) const { - QLabel* label = new QLabel(); + auto label = std::make_unique<QLabel>(); label->setText(el.getName()); label->setAlignment(Qt::AlignCenter); - return label; + return std::move(label); } -void ValuesConverterViewerModule::clearLabels() -{ - while (labels.count() > 0) - { - QLabel* l = labels[0]; - labels.removeAll(l); - delete l; - } -} +void ValuesConverterViewerModule::clearLabels() { labels.clear(); } void ValuesConverterViewerModule::createLabels() { @@ -136,12 +128,12 @@ void ValuesConverterViewerModule::createLabels() int row = 0; for (int i = 0; i < rules.count(); i++) { - QLabel* label; + std::unique_ptr<QLabel> label; int labelIndex = findLabelIndexByName(rules[i].getName()); if (labelIndex >= 0 && labelIndex < labels.count()) { - label = labels[labelIndex]; + label = std::move(labels[labelIndex]); } else { @@ -154,7 +146,7 @@ void ValuesConverterViewerModule::createLabels() if (rules[i].isDisplayInView()) { - ui->mainLayout_grid->addWidget(label, row, col); + ui->mainLayout_grid->addWidget(label.get(), row, col); col++; } } @@ -215,14 +207,14 @@ void ValuesConverterViewerModule::onMsgReceived(const Message& msg) void ValuesConverterViewerModule::clearRules() { - for (int i = 0; i < rules.count(); i++) + /*for (int i = 0; i < rules.count(); i++) { if (rules[i].getTopic() != "") { MessageBroker::getInstance().unsubscribe( Filter::fromString(rules[i].getTopic()), this); } - } + }*/ rules.clear(); } diff --git a/src/shared/Modules/ValuesConverterViewer/ValuesConverterViewerModule.h b/src/shared/Modules/ValuesConverterViewer/ValuesConverterViewerModule.h index ecd1614c3cea56d5fd34d08c505302cd72ae0b34..25900788d31971f9b1cb145a6b88f656b57b3ac6 100644 --- a/src/shared/Modules/ValuesConverterViewer/ValuesConverterViewerModule.h +++ b/src/shared/Modules/ValuesConverterViewer/ValuesConverterViewerModule.h @@ -49,7 +49,7 @@ protected: void onConfigureClicked(); void onConfigurationSaved(ValuesViewerConfigPanel* sPanel); - QLabel* createView(const ValueElement& el) const; + std::unique_ptr<QLabel> createView(const ValueElement& el) const; void clearLabels(); void createLabels(); void addRule(const ValueElement& el); @@ -63,6 +63,7 @@ private: Ui::ValuesConverterViewerModule* ui; int minColNumber = 1; int columns = minColNumber; - QList<QLabel*> labels; + QList<std::unique_ptr<QLabel>> labels; QList<ValueElement> rules; + std::unique_ptr<Subscription> subscription; }; diff --git a/src/shared/Modules/ValuesConverterViewer/ValuesViewerConfigPanel.cpp b/src/shared/Modules/ValuesConverterViewer/ValuesViewerConfigPanel.cpp index d3e99f5514d9d417dc2ebf36f9fb5fc84923592b..5f218b7f1b2be0595181c340d5ebfd8ddc506b96 100644 --- a/src/shared/Modules/ValuesConverterViewer/ValuesViewerConfigPanel.cpp +++ b/src/shared/Modules/ValuesConverterViewer/ValuesViewerConfigPanel.cpp @@ -96,7 +96,6 @@ void ValuesViewerConfigPanel::onRemoveClicked() } if (selectedView >= 0 && selectedView < views.count()) { - delete views[selectedView]; views.removeAt(selectedView); } } @@ -137,9 +136,10 @@ int ValuesViewerConfigPanel::computeViewIndex(const QString& viewName) return i; } -QRadioButton* ValuesViewerConfigPanel::createView(const ValueElement& el) +std::unique_ptr<QRadioButton> ValuesViewerConfigPanel::createView( + const ValueElement& el) { - return new QRadioButton(el.toString()); + return std::move(std::make_unique<QRadioButton>(el.toString())); } void ValuesViewerConfigPanel::setTextBoxValues(const ValueElement& el) @@ -179,10 +179,11 @@ int ValuesViewerConfigPanel::findSelectedView() const void ValuesViewerConfigPanel::addRule(int index, const ValueElement& el) { rules.insert(index, el); - QRadioButton* view = createView(el); - views.insert(index, view); - ui->fieldsLayout->insertWidget(index, view); - connect(view, &QRadioButton::clicked, this, + auto view = createView(el); + auto* viewAddr = view.get(); + views.insert(index, std::move(view)); + ui->fieldsLayout->insertWidget(index, viewAddr); + connect(viewAddr, &QRadioButton::clicked, this, &ValuesViewerConfigPanel::onValueElementClicked); } diff --git a/src/shared/Modules/ValuesConverterViewer/ValuesViewerConfigPanel.h b/src/shared/Modules/ValuesConverterViewer/ValuesViewerConfigPanel.h index e0f23ee06d91723ce041817dde303494a29c9174..9360d053f55acf1483279ee2d2e27d08149c33cf 100644 --- a/src/shared/Modules/ValuesConverterViewer/ValuesViewerConfigPanel.h +++ b/src/shared/Modules/ValuesConverterViewer/ValuesViewerConfigPanel.h @@ -53,7 +53,7 @@ protected: void onSaveClicked(); void onEditClicked(); int computeViewIndex(const QString &viewName); - QRadioButton *createView(const ValueElement &el); + std::unique_ptr<QRadioButton> createView(const ValueElement &el); void setTextBoxValues(const ValueElement &el); int findSelectedView() const; void addRule(int index, const ValueElement &el); @@ -65,5 +65,5 @@ private: Ui::ValuesViewerConfigPanel *ui; QList<ValueElement> rules; - QList<QRadioButton *> views; + QList<std::unique_ptr<QRadioButton>> views; }; diff --git a/src/shared/Modules/ValvesViewer/ValvesViewer.cpp b/src/shared/Modules/ValvesViewer/ValvesViewer.cpp index 7b68f3a62e82f5d44de0e1281f64f2695f78361c..c52ae31fe9da917f109a1512a9a9a34f22f5aa93 100644 --- a/src/shared/Modules/ValvesViewer/ValvesViewer.cpp +++ b/src/shared/Modules/ValvesViewer/ValvesViewer.cpp @@ -27,10 +27,7 @@ ValvesViewer::ValvesViewer() : Module(ModuleId::VALVES_VIEWER) customContextMenuActionSetup(); } -ValvesViewer::~ValvesViewer() -{ - MessageBroker::getInstance().unsubscribe(filter, this); -} +ValvesViewer::~ValvesViewer() {} XmlObject ValvesViewer::toXmlObject() { @@ -49,7 +46,7 @@ void ValvesViewer::fromXmlObject(const XmlObject& xmlObject) void ValvesViewer::setupUi() { - outerLayout = new QHBoxLayout; + outerLayout = std::make_unique<QHBoxLayout>(); outerLayout->setContentsMargins(0, 0, 0, 0); outerLayout->setSpacing(0); @@ -62,16 +59,16 @@ void ValvesViewer::setupUi() outerLayout->addWidget(label); } - setLayout(outerLayout); + setLayout(outerLayout.get()); } void ValvesViewer::customContextMenuActionSetup() { - QAction* action = new QAction("Choose topic and field"); - connect(action, &QAction::triggered, this, + auto action = std::make_unique<QAction>("Choose topic and field"); + connect(action.get(), &QAction::triggered, this, &ValvesViewer::onConfigureClicked); - customContextMenuActions.append(action); + customContextMenuActions.append(std::move(action)); } void ValvesViewer::onConfigureClicked() @@ -82,10 +79,8 @@ void ValvesViewer::onConfigureClicked() void ValvesViewer::setFilter(const Filter& newFilter) { - MessageBroker::getInstance().unsubscribe(filter, this); - MessageBroker::getInstance().subscribe( - newFilter, this, - [this](const Message& message, const Filter& filter) + subscription = MessageBroker::getInstance().subscribe( + newFilter, [this](const Message& message, const Filter& filter) { onMsgReceived(message); }); filter = newFilter; } diff --git a/src/shared/Modules/ValvesViewer/ValvesViewer.h b/src/shared/Modules/ValvesViewer/ValvesViewer.h index 5c0b4efd1f0a65705f8f1bcfdac20c34b12accff..7b3b6ac46e5f9c5cd39fb0a18fdd5edd54d94e7f 100644 --- a/src/shared/Modules/ValvesViewer/ValvesViewer.h +++ b/src/shared/Modules/ValvesViewer/ValvesViewer.h @@ -45,8 +45,10 @@ private: void setFilter(const Filter& filter); void onMsgReceived(const Message& msg); - QHBoxLayout* outerLayout; + std::unique_ptr<QHBoxLayout> outerLayout; Filter filter; ValvesList::Valve currentState; + + std::unique_ptr<Subscription> subscription; };