本系列所有文章可以在這里查看[http://blog.csdn.net/cloud_castle/article/category/2123873](http://blog.csdn.net/cloud_castle/article/category/2123873)
接上文[Qt5官方demo解析集19——Chapter 5: Using List Property Types](http://blog.csdn.net/cloud_castle/article/details/36898495)
在前文中我們定義的PieChart和PieSlice這兩個自定義QML類型只用來供app.qml文件使用,如果希望我們所定義的類型可以被多個qml使用,那么可以將其創建為可擴展的插件。由于是將C++定義的類創建為供QML使用的插件,所以這與我們原先創建C++的插件略有不同。
1、首先我們需要繼承QQmlExtensionPlugin類,這是一個抽象基類,提供了可供QML裝載的插件。
2、接著我們需要在其子類中使用Q_PLUGIN_METADATA宏將其這個插件注冊到Qt的元對象系統中。
3、重寫純虛函數registerTypes(),并在其中使用qmlRegisterType()注冊插件中的QML類型,這與我們之前在main函數中做的一樣。
4、然后我們需要編寫一個插件的工程文件,包括TEMPLATE、CONFIG、DESTDIR、TARGET等等。
5、最后,我們還需要創建一個qmldir文件來描述這個插件。
先看下工程目錄,其中piechart與pieslice并沒有任何變化:

這實際上是兩個工程,我們完全可以單獨編譯import來生成dll插件,然后放在合適的地方供app工程使用。我們先來看import工程中的文件
chartsplugin.h:
~~~
#ifndef CHARTSPLUGIN_H
#define CHARTSPLUGIN_H
//![0]
#include <QQmlExtensionPlugin>
class ChartsPlugin : public QQmlExtensionPlugin // 繼承QQmlExtensionPlugin
{
Q_OBJECT
Q_PLUGIN_METADATA(IID "org.qt-project.Qt.QQmlExtensionInterface") // 為這個插件定義了一個唯一的接口,并注冊至元對象系統
public:
void registerTypes(const char *uri); // 注冊類型函數重載
};
//![0]
#endif
~~~
chartsplugin.cpp:
~~~
#include "chartsplugin.h"
//![0]
#include "piechart.h"
#include "pieslice.h"
#include <qqml.h>
void ChartsPlugin::registerTypes(const char *uri) // 實現插件中類型的注冊
{
qmlRegisterType<PieChart>(uri, 1, 0, "PieChart");
qmlRegisterType<PieSlice>(uri, 1, 0, "PieSlice");
}
//![0]
~~~
可以看到QML插件注冊的代碼也很間斷,但真正的實現還在于下面兩個文件:
qmldir這個文件只有兩句話:
~~~
module Charts // 定義了組件名稱空間為Charts,這個名稱也是我們最后import時使用的
plugin chartsplugin // 定義插件,與上面的chartsplugin一致
~~~
然后是我們的import.pro文件:
~~~
TEMPLATE = lib // 生成庫文件
CONFIG += plugin // 該庫是一個插件
QT += qml quick
DESTDIR = ../Charts // 從Debug目錄跳出到Build目錄,并建立Charts目錄,以存放dll與qmldir文件
TARGET = $$qtLibraryTarget(chartsplugin)
HEADERS += piechart.h \
pieslice.h \
chartsplugin.h
SOURCES += piechart.cpp \
pieslice.cpp \
chartsplugin.cpp
DESTPATH=$$[QT_INSTALL_EXAMPLES]/qml/tutorials/extending/chapter6-plugins/Charts // 設置了一個變量指向這個Charts目錄
target.path=$$DESTPATH
qmldir.files=$$PWD/qmldir
qmldir.path=$$DESTPATH
INSTALLS += target qmldir
OTHER_FILES += qmldir
# Copy the qmldir file to the same folder as the plugin binary
QMAKE_POST_LINK += $$QMAKE_COPY $$replace($$list($$quote($$PWD/qmldir) $$DESTDIR), /, $$QMAKE_DIR_SEP)
~~~
這樣,在這個工程編譯后,我們將在build目錄中的Charts文件夾中找到我們的chartsplugind.dll與qmldir文件。d表示由debug編譯產生。
接下來的app項目調用了這個插件并繪制了這個餅狀圖:
app.qml:
~~~
import QtQuick 2.0
import Charts 1.0 // 這里會有一條紅色波浪線,QtCreator會抱怨可能找不到這個模塊
// 你可以不管它,也可以設置qmlplugindump讓QtQuick獲知到這個模塊的信息
Item {
width: 300; height: 200
PieChart { // 我們可以像前面的例子一樣使用我們自定義的類型
anchors.centerIn: parent
width: 100; height: 100
slices: [
PieSlice {
anchors.fill: parent
color: "red"
fromAngle: 0; angleSpan: 110
},
PieSlice {
anchors.fill: parent
color: "black"
fromAngle: 110; angleSpan: 50
},
PieSlice {
anchors.fill: parent
color: "blue"
fromAngle: 160; angleSpan: 100
}
]
}
}
~~~
main.cpp中不需要做額外的工作:
~~~
#include <QtQuick/QQuickView>
#include <QGuiApplication>
int main(int argc, char *argv[])
{
QGuiApplication app(argc, argv);
QQuickView view;
view.setResizeMode(QQuickView::SizeRootObjectToView);
view.setSource(QUrl("qrc:///app.qml"));
view.show();
return app.exec();
}
~~~
app.pro:
~~~
TARGET = chapter6-plugins // 設置項目名
QT += qml quick
# Avoid going to debug/release subdirectory
# so that our application will see the
# import path for the Charts module.
win32: DESTDIR = ./ // 這一句將程序從debug移到上級build目錄,也就是Charts的同級目錄,這樣使得程序可以到上面生成的插件
SOURCES += main.cpp
RESOURCES += app.qrc
~~~
最后還有一個根工程文件chapter6-plugins.pro:
~~~
TEMPLATE = subdirs // 編譯下面SUBDIRS定義的子目錄
CONFIG += ordered // 順序編譯,可能是基于效率不太被推薦,不過在這個小例子中就無所謂了
SUBDIRS = \
import \ // 先編譯import目錄里的工程
app.pro // 然后編譯app工程
~~~
最后還是看下效果唄~

- 前言
- 1——Fortune Server/Client
- 2——Multicast Sender/Receiverz
- 3——Broadcast Sender/Receiver
- 4——Blocking Fortune Client
- 5——Threaded Fortune Server
- 5(總結)——Fortune例程的各個實現區別
- 6——Loopback Example
- 7——Analog Clock Example
- 8——Shaped Clock Example
- 9——Analog Clock Window Example
- 10——Qt Quick Particles Examples - Emitters
- 11——Qt Quick Particles Examples - Affectors
- 12——Qt Quick Particles Examples - CustomParticles
- 13——Qt Quick Particles Examples - Image Particles
- 14——Qt Quick Particles Examples - System
- 15——Chapter 1: Creating a New Type
- 16——Chapter 2: Connecting to C++ Methods and Signals
- 17——Chapter 3: Adding Property Bindings
- 18——Chapter 4: Using Custom Property Types
- 19——Chapter 5: Using List Property Types
- 20——Chapter 6: Writing an Extension Plugin
- 21——Extending QML - Adding Types Example
- 22——Extending QML - Object and List Property Types Example
- 23——Extending QML - Inheritance and Coercion Example
- 24——Extending QML - Default Property Example
- 25——Extending QML - Methods Example
- 26——Extending QML - Grouped Properties Example
- 27——Extending QML - Attached Properties Example
- 28——Extending QML - Signal Support Example
- 29——Extending QML - Property Value Source Example
- 30——Extending QML - Binding Example
- 31——StocQt
- 32——Qt Quick Examples - Threading
- 33——Qt Quick Examples - Window and Screen
- 34——Concentric Circles Example
- 35——Music Player
- 36——Wiggly Example
- 37——Vector Deformation