Publisher
オブジェクトを定期的に発行するクラスQImage
を作成しました。
しかし、QImage
をQML要素に描画するのは大変です。 Image
およびCanvas
QMLコンポーネントはQUrl
の代わりにQImage
を必要とするようですが、QImage
からQUrl
へ。 Edit4:QUrlと言っても、画像をURLに変換しようとしているわけではありません。それはナンセンスです。つまり、ディスク上にないこのイメージへの参照を生成したいということです。QMLコンポーネントが要求しているデータ型はURLです。
いくつかの調査を行ったところ、QQuickImageProvider
が解決策を提供していることがわかりましたが、QImage
信号をQUrl
に変換する方法を説明したドキュメントは見つかりませんでした描画に使用します。サンプルコードまたはリファレンスドキュメントをいただければ幸いです。
ご協力いただきありがとうございます!
編集1:
私はここを見てきました: http://qt-project.org/doc/qt-5.0/qtquick/qquickimageprovider.html QImageをクイック画像に渡す方法がわかりませんプロバイダーとそれからQUrlを作成します。
編集2。これがヘッダーです。実装は重要ではありません。
class Publisher
{
Q_OBJECT
public:
Publisher(QObject* parent = 0);
virtual ~Publisher(void);
Q_SIGNALS:
void newImage(const QImage& newImage);
};
編集3。ここに私のQMLコードがありますが、QImageを描画する方法がわかりませんので、このコードは無意味です。
私のmain.cppファイル:
int main(int argc, char *argv[])
{
QGuiApplication app(argc, argv);
qmlRegisterType<Publisher>("Components", 1, 0, "Publisher");
QtQuick2ApplicationViewer viewer;
viewer.setMainQmlFile(QStringLiteral("qml/QQuickViewExample/main.qml"));
viewer.showExpanded();
return app.exec();
}
main.qmlファイル:
import QtQuick 2.0
import Components 1.0
Rectangle {
id : testRect
width: 360
height: 360
Image{
anchors.fill: parent
id: myImage
Publisher {
id: myPub
onNewImage: {
myImage.source = newImage; #I know this doesnt work, it needs a QUrl and not a QImage
}
}
}
}
言い換えると、QImageを運ぶ信号を発するクラスがあり、そのイメージでQMLのアイテムを更新したいのですか?さまざまなソリューションがありますが、いずれも「QImageからQUrlへの変換」を含みません(つまり、画像データを保持するdata
URLを取得する必要はありません...)
これは、QMLファイルでプレーンImage
アイテムを使用できることを意味します。
QQuickImageProvider
サブクラスを作成します。 QImage
メンバー(プロバイダーへの画像)を提供し、requestImage
をオーバーライドしてその画像を提供します(実際に要求されるid
は重要ではありません。以下を参照)。 QImage
を受け取り、メンバーを更新します。Publisher
信号をプロバイダーのスロットに接続しますQQmlEngine::addImageProvider
_を介してプロバイダーをQMLエンジンにインストールします(_QQuickView::engine
_を参照)。再びid
は実際には問題ではなく、賢明なものを使用してくださいQMLでは、このようなソースで単純なImage
要素を使用します
_Image {
id: myImage
source: "image://providerIdPassedToAddImageProvider/foobar"
}
_
foobar
がプロバイダーに渡されますが、これも重要ではありません。
私たちはもうすぐそこにいます。今では、QMLワールドのイメージ更新をPushだけで行う必要があります(そうでなければ、Imageはいつそれ自体を更新するかを知ることはありません)。 Connections
要素と少しのJSを使用してこれを行う方法については、 私の答えはこちら を参照してください。
一般に、Publisher
をQMLタイプにする必要はなく、C++でoneインスタンスを作成し、それを介してQMLワールドに公開するだけです。 _QQmlContext::setContextProperty
_。
QQuickPaintedItem
は、Paint
を取るQPainter
メソッドを提供するため、おそらくジョブにとって最も便利です。したがって、大きな計画は
QQuickPaintedItem
:サブクラスは、ペイントされるQImage
を格納し、新しいQImageを設定するスロットを持っています。また、そのPaint
実装は、_QPainter::drawImage
_を使用して画像を単純にペイントします。qmlRegisterType
を介してQMLワールドにサブクラスを公開します(QMLで使用できるように)新しい画像を運ぶ信号をアイテムのスロットに接続する方法を見つけてください。
これは難しい部分かもしれません。
C++で接続を実行するには、アイテムが作成されたことを把握する(およびそのポインターを取得する)方法が必要です。通常、これはobjectName
プロパティを何らかの値に割り当て、ルートオブジェクト(QQuickView::rootObject()
によって返される)でfindChild
を使用して、アイテム自体。その後、通常どおりconnect
を使用できます。
Or、代わりにQMLで公開されたパブリッシャーC++オブジェクトのConnections
要素を介して、上記のようにQMLで接続を実行できます。
_MyItem {
id: myItem
}
Connections {
target: thePublisherObjectExposedFromC++
onNewImage: myItem.setImage(image)
}
_
これには、MyItemインスタンスをいつ作成しても動作するという利点があります。 QMLでQImage
タイプを処理できるかどうかわからないので、100%確実に機能するかどうかはわかりません。
QMLに埋め込みたい画像生成C++クラスがあったときは、C++クラスをQDeclarativeItem
のサブクラスにすることで常にそれを行いました(新しいQtQuick 2.0に相当するものがありますもちろん)、適切な描画コードでPaintメソッドをオーバーライドします。
void MyItem::Paint(QPainter* Painter,const QStyleOptionGraphicsItem*,QWidget*) {
Painter->drawImage(QPointF(0.0f,0.0f),_image);
}
適切なサイズのQImageが既にある場合...およびJob Done。アニメーションの場合、描画する新しいものがあるときにupdate()にpingを実行します。