簡體   English   中英

如何在Qt中的插件和主應用程序之間通信?

[英]How to communicate between plugin and main application in Qt?

我需要讓我的繪圖板應用程序及其幾何圖形插件(繪制矩形,圓形等)相互通信:加載.so文件時,主應用程序將獲得一個具體的工廠來實例化一個圖形類和一個按鈕。 (將在主應用程序中加載以表示該圖)。 單擊按鈕時,應用程序可以繪制該圖。

我愚蠢地實現了這一點:

主應用程序具有一個QString來標識客戶端選擇的圖形對象。 我在工廠中存儲了一個QString *pointQString *point ,並編寫如下代碼:

QPushButton *CircleFactory::MyButton()
{
    QPushButton *drawCircleBut = new QPushButton;
    drawCircleBut->setIcon(QIcon(":/shape/circle"));
    connect(drawCircleBut, SIGNAL(clicked()), this, SLOT(changeShape()));
    return drawCircleBut;
}

void CircleFactory::changeShape()
{
    *point = ID_LABEL;
}

我相信必須有更好的方法來解決此問題...請給我一些建議。

最簡單的解決方案是利用QObject的屬性系統:

QPushButton * CircleFactory::MyButton()
{
  QScopedPointer<QPushButton> button(new QPushButton);
  button->setIcon(QIcon(":/shape/circle"));
  button->setProperty("identity", ID_LABEL);
  return button->take();
}

然后,在連接到這些按鈕的任何插槽中,您都可以輕松檢查它們的身份;

void Foo::buttonClicked() {
  qDebug() << "clicked on:" << sender()->property("identity");
}

這樣,您就不需要全局變量。

我質疑按鈕是否需要以這種方式標識自己。 我擔心的是您正在使用按鈕的標識,然后以某種方式返回到圓形對象或正確的插件。

相反,圈子工廠應該提供一個已經連接到正確插槽的按鈕。 如果不可能,那么您將不得不進一步解釋“繪圖板應用程序”的設計和預期功能。 您可能會想像到,這樣的應用程序應該如何工作還很遙遠-對您而言顯而易見的對其他人而言並不明顯。

另一個解決方案是擴展幾何圖形插件界面,以便只有插件知道如何調用其形狀以及如果將其表示為QIcon則看起來如何。 該應用程序本身對圓形或矩形一無所知。

#include <QString>

class GeometricPluginInterface
{
public:
   GeometricPluginInterface() {}
   virtual ~GeometricPluginInterface() {}

   virtual QString name() const = 0;
   virtual QIcon icon() const = 0;

};

在啟動應用程序時,您可以將所有已加載的插件存儲在QList (例如QList<GeometricPluginInterface*> m_plugins; )。 如果用按鈕填充UI,則可以遍歷列表,並使用從插件本身獲取的圖標為每個插件創建QPushButton 您可以像代碼中那樣通過lambda(自C ++ 11起)將按鈕的clicked信號連接到插槽。

foreach (GeometricPluginInterface *plugin, m_plugins) {
   QPushButton *button = new QPushButton;
   button->setIcon(plugin->icon());
   connect(button, &QPushButton::clicked,
           [this, plugin] {
      geometryButtonClicked(plugin->name());
   });
   ui->buttonLayout->addWidget(button);
}

void GeometricPluginInterface::geometryButtonClicked(const QString &geometryName)
{
   qDebug() << "Geometry clicked: " << geometryName;
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM