Forráskód Böngészése

#IQRV #comment [Feature][Plugin] 添加自定义GUI窗口的示例

gifur 4 éve
szülő
commit
102d31b299

+ 2 - 0
CMakeLists.txt

@@ -283,6 +283,7 @@ set(PACK_INSTALL_AD_DIR "${PACK_INSTALL_RVC_DIR}/addata")
 set(RVC_INCLUDE_PATH  "${PACK_INSTALL_PREFIX_CUR_VER}/include")
 set(RVC_LIBRARY_PATH   "${PACK_INSTALL_PREFIX_CUR_VER}/lib")
 set(RVC_RUNTIME_PATH "${PACK_INSTALL_PREFIX_CUR_VER}/bin")
+set(RVC_PLUGINS_PATH "${RVC_RUNTIME_PATH}/plugins")
 set(RVC_MODULE_PATH  "${PACK_INSTALL_PREFIX_CUR_VER}/mod")
 set(RVC_CONFIG_PATH    "${PACK_INSTALL_PREFIX_CUR_VER}/cfg")
 set(RVC_VENDOR_PATH  "${PACK_INSTALL_PREFIX_CUR_VER}/dep")
@@ -414,6 +415,7 @@ add_subdirectory(ThirdParty)
 add_subdirectory(Other)
 add_subdirectory(Module)
 add_subdirectory(Tool)
+add_subdirectory(Plugins)
 if(BUILD_DEVADAPTER)
 	add_subdirectory(DevAdapter)
 endif(BUILD_DEVADAPTER)

+ 29 - 0
Plugins/CMakeLists.txt

@@ -0,0 +1,29 @@
+if(SIMULATE_ON)
+	rvc_set_library_output_dir("${RVC_INSTALL_PREFIX}${RVC_RUNTIME_PATH}")
+endif(SIMULATE_ON)
+
+set(PLUGINS_CONAN_DEP_LIBS)
+set(PLUGINS_COMM_INCLUDE_DIRS ${CMAKE_CURRENT_SOURCE_DIR}/include)
+
+set(CMAKE_AUTOUIC ON)
+set(CMAKE_AUTOMOC ON)
+set(CMAKE_AUTORCC ON)
+
+if(ARCH_AARCH64)
+    if(NOT CONAN_QT_ROOT)
+        conan_cmake_run(REQUIRES qt/5.11.3@LR04.02_ThirdParty/testing BASIC_SETUP CMAKE_TARGETS)
+    endif(NOT CONAN_QT_ROOT)
+    set(QT5_HINT_PATH ${CONAN_QT_ROOT})
+else()
+if(MSVC)
+    set(QT5_HINT_PATH "C:/Qt/Qt5.14.2/5.14.2/msvc2017/")
+else()
+    set(QT5_HINT_PATH "/opt/Qt5.14.2/5.14.2/gcc_64/lib/cmake/")
+endif(MSVC)
+endif(ARCH_AARCH64)
+
+# rvc_add_all_cmake_subdirectory()
+add_subdirectory(MediaDevDetect)
+
+# 汇总要依赖拷贝的第三方库
+set(RVC_CONAN_DEP_LIBS ${RVC_CONAN_DEP_LIBS} ${PLUGINS_CONAN_DEP_LIBS} PARENT_SCOPE)

+ 27 - 0
Plugins/MediaDevDetect/CMakeLists.txt

@@ -0,0 +1,27 @@
+set(MODULE_NAME "mediadetect")
+set(MODULE_PREFIX "MEDIA_DEV_DETECT")
+
+find_package(Qt5 COMPONENTS Widgets REQUIRED 
+    HINTS ${QT5_HINT_PATH} NO_SYSTEM_ENVIRONMENT_PATH )
+
+find_package(Qt5UiTools HINTS ${QT5_HINT_PATH} NO_SYSTEM_ENVIRONMENT_PATH )
+
+set(${MODULE_PREFIX}_SRCS
+    mainform.cpp
+    mainform.ui
+    mediadevdetect.cpp
+    mediadevdetect.h
+)
+
+add_library(${MODULE_NAME} SHARED ${${MODULE_PREFIX}_SRCS})
+target_include_directories(${MODULE_NAME} PRIVATE ${PLUGINS_COMM_INCLUDE_DIRS} ${CMAKE_CURRENT_SOURCE_DIR})
+set_target_properties(${MODULE_NAME} PROPERTIES AUTOMOC TRUE)
+
+list(APPEND ${MODULE_PREFIX}_LIBS Qt5::Widgets Qt5::Core Qt5::Gui Qt5::UiTools)
+target_link_libraries(${MODULE_NAME} ${${MODULE_PREFIX}_LIBS})
+
+install(TARGETS ${MODULE_NAME} 
+    RUNTIME DESTINATION "${RVC_PLUGINS_PATH}"
+    ARCHIVE DESTINATION "${RVC_LIBRARY_PATH}"
+    LIBRARY DESTINATION "${RVC_PLUGINS_PATH}"
+	COMPONENT libraries)

+ 20 - 0
Plugins/MediaDevDetect/mainform.cpp

@@ -0,0 +1,20 @@
+#include "mainform.h"
+#include "ui_mainform.h"
+#include <QMessageBox>
+
+MainForm::MainForm(QWidget *parent) :
+    QWidget(parent),
+    ui(new Ui::MainForm)
+{
+    ui->setupUi(this);
+}
+
+MainForm::~MainForm()
+{
+    delete ui;
+}
+
+void MainForm::on_pushButton_clicked()
+{
+    QMessageBox::information(this, "TSET", tst);
+}

+ 25 - 0
Plugins/MediaDevDetect/mainform.h

@@ -0,0 +1,25 @@
+#ifndef MAINFORM_H
+#define MAINFORM_H
+
+#include <QWidget>
+
+namespace Ui {
+class MainForm;
+}
+
+class MainForm : public QWidget
+{
+    Q_OBJECT
+
+public:
+    explicit MainForm(QWidget *parent = nullptr);
+    ~MainForm();
+    QString tst;
+private slots:
+    void on_pushButton_clicked();
+
+private:
+    Ui::MainForm *ui;
+};
+
+#endif // MAINFORM_H

+ 35 - 0
Plugins/MediaDevDetect/mainform.ui

@@ -0,0 +1,35 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>MainForm</class>
+ <widget class="QWidget" name="MainForm">
+  <property name="geometry">
+   <rect>
+    <x>0</x>
+    <y>0</y>
+    <width>400</width>
+    <height>300</height>
+   </rect>
+  </property>
+  <property name="windowTitle">
+   <string>Form</string>
+  </property>
+  <layout class="QGridLayout" name="gridLayout">
+   <item row="1" column="0">
+    <widget class="Line" name="line">
+     <property name="orientation">
+      <enum>Qt::Horizontal</enum>
+     </property>
+    </widget>
+   </item>
+   <item row="0" column="0">
+    <widget class="QPushButton" name="pushButton">
+     <property name="text">
+      <string>PushButton</string>
+     </property>
+    </widget>
+   </item>
+  </layout>
+ </widget>
+ <resources/>
+ <connections/>
+</ui>

+ 35 - 0
Plugins/MediaDevDetect/mediadevdetect.cpp

@@ -0,0 +1,35 @@
+#include "mediadevdetect.h"
+#include "mainform.h"
+
+QString MediaDevDetect::getVersion()
+{
+    return QString("1.2.3.4");
+}
+
+InterfaceType MediaDevDetect::getType()
+{
+    return WidgetType;
+}
+
+QString MediaDevDetect::getDisplayText()
+{
+    return QString("秦时明月");
+}
+
+QWidget* MediaDevDetect::getComponent(QWidget *parent, const QStringList& param)
+{
+    MainForm* item = new MainForm(parent);
+    item->tst = param[0];
+    item->setWindowTitle(item->tst);
+    return item;
+}
+
+QVariantList MediaDevDetect::getMoreDetail()
+{
+    QVariantList vars;
+    QVariant var1("Hello");
+    QVariant var2(1234);
+    QVariant var3(3.141592653579);
+    vars << var1 << var2 << var3;
+    return vars;
+}

+ 27 - 0
Plugins/MediaDevDetect/mediadevdetect.h

@@ -0,0 +1,27 @@
+#ifndef MEDIADEVDETECT_H
+#define MEDIADEVDETECT_H
+
+#include "CustomImportInterface.h"
+#include <QtCore/qglobal.h>
+
+#if defined(MEDIADEVDETECT_LIBRARY)
+#  define MEDIADEVDETECT_EXPORT Q_DECL_EXPORT
+#else
+#  define MEDIADEVDETECT_EXPORT Q_DECL_IMPORT
+#endif
+
+class MEDIADEVDETECT_EXPORT MediaDevDetect : public QObject, CustomImportInterface
+{
+    Q_OBJECT
+    Q_PLUGIN_METADATA(IID "org.cmbchina.rvcterminal.CustomImportInterface/1.0")
+    Q_INTERFACES(CustomImportInterface)
+
+public:
+    QString getVersion() override;
+    QWidget* getComponent(QWidget *parent, const QStringList& param) override;
+    QVariantList getMoreDetail() override;
+    QString getDisplayText() override;
+    InterfaceType getType() override;
+};
+
+#endif // MEDIADEVDETECT_H

+ 24 - 0
Plugins/Tutorial.md

@@ -0,0 +1,24 @@
+# GUI 插件开发指导
+
+* 以前可视柜台启动界面由实体单独管理,改动范围仅在实体层,现在启动界面由**SpShell**生成渲染
+* 为了让大家能添加自己的交互界面,而不涉及到框架改动,框架添加了动态加载子窗口界面的功能,以扩展应用的业务功能
+* 该功能使用了**QT Plugin**的机制,所以开发流程需要按照QT的方式实施
+
+## 开发指引
+
+### 工程创建
+
+* 在Plugins文件夹下创建自己的窗口库CMake工程,要求输出的是动态库(`.so`或.`dll`)
+* 继承 *Plugins/include/CustomImportInterface.h* 中的类:`CustomImportInterface`,并先声明实现相关的纯虚成员函数
+* 输出目录为终端的*bin/plugins*文件夹
+
+### 转移战场,设计窗口类
+
+* 先使用**QtCreator**以`QWidget`控件设计和开发相关的功能,记住是`QWidget`,因为接口限定提取出来的是该类型
+* 将实现的`QWidget`类和相关的其他实现文件(如有)迁移到先前建立的Plugin工程下
+* 实现`CustomImportInterface`的`getComponent`接口返回该`QWidget`类的对象指针
+
+### 输出运行
+
+* 编译Plugins工程并运行框架
+* 查看 工具 -> 选项 中,在*自定义*菜单选项的子菜单下查看是否该新控件选项,点击看右侧的实现效果

+ 34 - 0
Plugins/include/CustomImportInterface.h

@@ -0,0 +1,34 @@
+#ifndef CUSTOMIMPORTINTERFACE_H
+#define CUSTOMIMPORTINTERFACE_H
+
+#include <QObject>
+#include <QWidget>
+#include <QString>
+#include <QVariantList>
+#include <QVariant>
+
+enum InterfaceType
+{
+    WidgetType
+};
+
+class CustomImportInterface
+{
+public:
+    virtual ~CustomImportInterface() = default;
+    virtual QString getVersion() = 0;
+    virtual InterfaceType getType() = 0;
+    virtual QString getDisplayText() = 0;
+    virtual QWidget* getComponent(QWidget *parent, const QStringList& param) = 0;
+    virtual QVariantList getMoreDetail() = 0;
+};
+
+
+QT_BEGIN_NAMESPACE
+
+#define CustomInterface_iid "org.cmbchina.rvcterminal.CustomImportInterface/1.0"
+
+Q_DECLARE_INTERFACE(CustomImportInterface, CustomInterface_iid)
+QT_END_NAMESPACE
+
+#endif // CUSTOMIMPORTINTERFACE_H