Important: Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

QMLソースを、Qtのバージョンによって、コンパイル時に切り替えることは可能でしょうか?



  • Qt5.0.2とQt5.3.0の双方で動作するコードを書きたいと思っているのですが、
    Qt5.0.2とQt5.3.0では、QMLのimportのバージョンやエレメントにも差があり、
    同じソースコードをそのまま動作させることができません。

    ファーラム内を探してみたところ、C++では、下記のような記述で、
    Qtのバージョンによってソースコードを切り替えることができるようなのですが、

    @
    #if QT_VERSION >= 0x050000
    #include <QtWidgets/QDockWidget>
    #else
    #include <QtGui/QDockWidget>
    #endif
    @

    同じようなことが、QMLで可能でしょうか?
    #if ~#endifのような、ソースコードを条件で変更できるような構文はないか、
    色々調べてみたのですが、”QMLではできない”、といった情報しか見つけられませんでした・・・。

    もし可能、ということであればご教示頂けないでしょうか。
    不可能であれば、あきらめます。



  • まずは、フランス人なので、日本語の何かがおかしかったらすみません。

    ある方法は、Qtのバージョンによって、別のQMLファイルをロードすることが可能だと思います。
    ただし、両方のQMLファイルはほとんど同じだと言う事になりますが、多分そのほうが楽になります。そうしたら、C++だけで #if~#endif を使う必要になります。



  • ご回答ありがとうございます。

    ある方法は、Qtのバージョンによって、別のQMLファイルをロードすることが可 能だと思います。

    すみません・・・、
    Qtの知識に乏しいため、具体的な方法がわからないのですが、
    これは、Qtのバージョンによって、ソースを部分的に変更するのではなく、
    読み込むQMLソースそのものを切り替える、
    ということになりますでしょうか?

    その場合、
    MakeFileの記述でQMLソースごと切り替えるようなイメージでしょうか?

    それとも、
    QMLのLoader、もしくは、JavaScriptのQt.createComponent、などで、
    Qtバージョン判定を何らかの方法で行って、
    対象のQMLソースを読み込んで切り替えるようなイメージでしょうか?



  • "読み込むQMLソースそのものを切り替える、ということになりますでしょうか?"

    はい、そう言う事になります。
    こちらもQMLの知識は乏しいですが、例えばQQuickViewを使って、下記のコードでどうでしょうか?
    @QQuickView *view = new QQuickView;
    #if QT_VERSION // こちらはQtバージョンの条件
    view->setSource(file1);
    #else
    view->setSource(file2);
    #endif@



  • サンプルコード、ありがとうございます。

    ここで読み込んだQMLがQML上でどのような関係になるのか、
    このC++関数を呼び出すタイミングにもよりそうですので、
    色々試してみようと思います。

    *)
    ちなみに、もとの質問になりますが、
    QMLには、#if~#endif、のような、条件でソースを切り替えるような記述は、
    無い、ということになるのでしょうか?



  • 申し訳ありませんが、QMLでそんな条件が可能かどうかわかりません。



  • QMLで読み込むファイルを切り替える方法としては以下の方法が考えられます
    若干テクニックが必要になるものもあります。
    どれも ifdef を書くような形ではなく、ファイルを切り替える形になります。

    QQmlFileSelector を使う

    Qt 5.2以降で利用可能です。5.0ではセレクタを使用せず、5.3ではセレクタを使用するようにすれば対応できそうです。
    http://qt-project.org/doc/qt-5/qqmlfileselector.html

    プロパティ等を使ってソースファイル名を変更する

    ex.
    @property string qtver: "qt50"
    Loader { source: qtver + "/myelement.qml" }@
    qtverの内容はC++側から変更します

    Qt.createComponent のエラーで処理する

    対応していないバージョンではエラーで読み込めない事を利用します。
    ex.
    @var component = Qt.createComponent("qt53/myelement.qml")
    if (component.status === Component.Error)
    component = Qt.createComponent("qt50/myelement.qml")@

    ファイル内で一部を切り替えたい場合、import の切替は不可能です。JavaScript であれば C++ 側で Qt のバージョンをQMLから読み取れるようにしておいて if 文で切り替える手はあります。



  • 追記: LoaderやQt.createComponent()を使わずにエレメントを if 文等で切り替えるようなこともできません。



  • 詳しいご説明ありがとうございます。

    ご提示頂いた、Loader、Qt.createComponent、を使用する方法で、
    検討させて頂こうと思います。
    (3.の方法が色々応用できそうな気がします)


Log in to reply