导入QML模块问题



  • 先看第一种情况:
    1.假设现在需要创建一个Test工程,文件结构如下:

    | Test
    | + Component
    | | A.qml
    | | B.qml  
    | main.qml  
    

    2.在QT中创建Test工程:

    | Test.pro
    | +资源
    | |+qml.qrc
    | | |+ /
    | | | | main.qml
    

    3.在项目名处选择添加现有文件A.qml和B.qml(不将A/B.qml添加到资源文件中):

    | Test.pro
    | +资源
    | |+qml.qrc
    | | |+ /
    | | | | main.qml
    | + QML
    | | + Component
    | | | A.qml
    | | | B.qml  
    

    4.在main.qml文件使用了A组件,并且加入了import "./Component",A组件也高亮显示,但是在运行的时候却提示 A is not a type

    第二种情况:
    将第一种情况的第三步变为:A/B.qml文件都添加到资源文件中:

    | Test.pro
    | +资源
    | |+qml.qrc
    | | |+ /
    | | | | main.qml
    | | | | Component/A.qml
    | | | | Component/B.qml
    

    此时在main.qml中不需要import语句可以直接使用A组件。

    第三种情况:
    1.假设现在需要创建一个Test工程,文件结构如下:

    | Test
    | + Component1
    | | A.qml
    | + Component2
    | | B.qml
    | main.qml  
    

    2.同第一种情况2

    3.在项目名处选择添加现有文件A.qml和B.qml(不将A/B.qml添加到资源文件中):

    | Test.pro
    | +资源
    | |+qml.qrc
    | | |+ /
    | | | | main.qml
    | + QML
    | | + Component1
    | | | A.qml
    | | + Component2
    | | | B.qml
    

    4.在A组件中使用了B组件,并且加入了import "./Component",正常。

    所以我想问: 资源文件中的QML文件使用的自定义组件是否必须要添加到资源文件中才能使用?



  • @kian

    用到了 qrc 比如是新建了一个带有c++代码的项目。但是仔细想想,如果你是想探索使用纯QML实现的模块,那么新建一个 QtQuick UI 这个纯QML想更加有助于理解QML模块的概念。

    如何在 QtQuick 项目中正确使用 qrc,这是一个指定思考的问题,你可以@Jason

    可以看看

    在qml工程中怎么使用qmldir进行模块管理

    自定义QML模块

    下面是有关 QtQuick UI 的问答。

    什么是 QtQuick UI

    1. 是一个由 qmlproject 为后缀名的文件所管理的纯 QML 项目。

    2. qmlproject 文件本身就是 qml 的语法。

    3. 按下 ctrl + N,仔细找,一定能找到 QtQuick UI 这个选项的。

    使用 QtQuick UI 项目有什么好处?

    1. 首先 QtQuick UI 是一个纯 QML 项目,没有 c++ 的文件,也就意味着不用编译c++,就像浏览器打开 html 那样,QML 的文件使用一个名为 qmlscene 的程序打开的。

    2. 其次使用 QML 的目的是快速开发,而c++ 和 qrc 资源文件漫长的编译时间让快速开发成为一个不小的障碍。

    既然 QtQuick UI 是纯 QML 项目,是不是意味着无法直接和 C++ 交互?

    是的,但是可以通过插件的方式来处理, qmlscene 支持加载 QtQuick 2 插件。怎么构建 一个 QtQuick 2 插件呢?直接搜索即可找到你想要的。

    既然 qmlproject 是纯 QML 项目的项目文件,那么和 pro 有什么类似的功能吗?

    1. pro 文件是管理 Qt C++ 的项目文件,可以在里面指定源码, qrc 资源,OTHER_FILES,c\c++ 库。

    2. 相对于 proqmlproject 也有源码和资源的概念。源码直接是 *.qml,资源的话,一般是指图片。

    3. 这里给出一些使用技巧。先看如下的代码示例:

    /* File generated by Qt Creator */
    
    import QmlProject 1.1
    
    Project {
         mainFile: "main.qml"
    
        /* Include .qml, .js, and image files from current directory and subdirectories */
        QmlFiles {
            directory: "."
        }
        JavaScriptFiles {
            directory: "."
        }
        ImageFiles {
            directory: "."
        }
        /* List of plugin directories passed to QML runtime */
        // importPaths: [ "../exampleplugin" ]
    }
    

    语法是 QML,有 import,也有一个根对象。

    mainFile: "main.qml"

    这个项目文件指明了此项的入口文件是 main.qml

    如果你把行代码注释的话,是不是这个项目就没有入口文件,然后就无法启动了呢?

    答案是否定的。由于没有在 qmlproject 中指定入口文件,所以 qmlscene 就会直接运行当前,你所打开的那个 qml 文件。这样就可以有更高级的用法了。例如我编写一个 test_my_button.qml 用来测试自定义的 Button,此时只要注释掉 qmlproject 中的 mainFile ,然后在编辑器打开 test_my_button.qmlctrl+R 运行,就可以看到按钮的效果了,测试变得如此简单

    往下看 QmlFiles,嗯,见文生义。就是指定 directory (目录)下的所有 *.qml 文件。

    其他 JavaScriptFilesImageFiles

    然后你问我想在我这个 QtQuick UI 项目中显示其他格式的文件,怎么写?

    这里就要祭出 Files 了。

    Files {
        fileter: "*.md"
        directory: "."
    }
    

    这段就是获取所有文件后缀名为 md 的文件。

    importPaths 这个东西文章不好写。你直接看这个项目 Sparrow.2,代码层面去理解他吧。(下载,然后用 QtCreator 打开 *.qmlproject 文件)。

    QtQuick 进阶

    未完待续。

    如果你觉得赞,可以去我 github follow 我,或者去我的博客,亦或者继续回复,问你的问题。



  • @qyvlik 很强大的小q,拿出了QBS作为构建系统。这里也就接着qyvlik来回答你的问题了。
    首先,import语句能够访问文件路径、资源路径以及网络路径。这个是要清楚的。
    其次,如果你创建的不是纯Qt Quick UI项目,那么C++文件是必不可少的,此时需要了解的是,组件是否能够被找到取决于我们的QQmlApplicationEngine::importPathList( )下面有没有我们制作的组件。最后,使用qrc:/开头的相对路径可以很容易保证当我们复制整个项目的时候,相对路径都不会变。另外,将QML放入资源几乎不会拖慢加载速度。因为事实上,QML文件比图片、音频文件小得多,所以值得推荐。



  • @jiangcaiyang

    好像没有说到 QBS 。



  • @qyvlik
    感谢回答!之前没有用过qmlproject。
    QT用了大半年了,所写的代码基本上都是C++/QML混合编程,GUI和逻辑分成两端来处理。功能是实现了,但是文件结构很乱,而且代码再利用率很低,常用组件没有分离出来。所以想对文件结构做一个调整,但是我又不想将所有的常用组件丢到qml.qrc里面去,看起来感觉很乱。
    按照你所给的Sparrow例子,将常用的QML组件做成一个module,然后在其他的qmlproject的importPaths中加入该module的路径,的确时可以改善文件结构。与C++进行交互的时候,也可以直接定义一个接口类,并将该类作为插件导入到qmlproject中。但是采用这种方法,只是提供一个快速预览的功能,并不能发布一个可执行文件。所以,如果我需要发布一个可执行文件,仍然需要使用pro文件。
    根据你提供的资料,我想到了两种方法对文件结构进行优化:
    1.创建多个qrc文件,每个qrc文件中加入对应类型的常用组件,组件之间可以相互使用,不需要import语句。
    2.将常用的组件全部打包做成一个module,然后修改.pro文件的QML_IMPORT_PATH , 并且在main.cpp中调用addImportPath()导入module路径,最后在工程中需要使用该module的qml文件中使用import语句导入该module即可。



  • @qyvlik 你建立的QmlProject就是QBS构建系统的哦。😽



  • @jiangcaiyang导入QML模块问题 中说:

    QBS构建系统

    QT的构建系统不是分为三类:qmake,qbs,qmlproject吗



  • @kian 我混乱了,我一直认为qmlproject是基于QBS的一个项目类型,QBS是构建系统。



  • @kian Qt的构建系统是cmake、qmake、qbs。🐄 🐄 🐄


Log in to reply
 

最近的回复

  • 就在不久前我分享了USD在Windows上的构建方法,其实我也一直没有放弃在开发领域最擅长的Linux中构建USD。不过,在Linux中要成功地构建USD,比Windows的要难不少。尤其是各种麻烦的依赖库,仍然要解决才行。之前一直在CentOS 7构建,没有成功,而且CentOS构建的话,相关的资料更少,坑更多,而Deepin是国产的Linux桌面系统,友好一些,这样可以少一些困难。目前成功地在Deepin Linux上顺利地编译成功了。

    那么,咱们开始在Linux构建USD吧。

    测试并且安装Python

    有些Linux发行版,默认安装了Python,有的则没。如果你安装了Python,可以测试一下,命令是:

    python --version

    如果报错,那么使用apt安装吧。

    sudo apt install python

    为了安装PyOpenGL等库,还是推荐安装pip。有关安装pip的资料还是挺多的,pip类似npm,是一个包管理器,非常方便,推荐安装。这里有一个获取pip的脚本。我发出来。获取pip的命令是:

    python -m get-pip.py

    拿到USD的代码

    毕竟是在github中获取的USD代码,那么最好安装git,并且设置github的账户以及公钥。然后熟练利用git命令进行如下的操作:

    git clone https://github.com/PixarAnimationStudios/USD

    获取USD依赖的库

    由于依然在github上获取相关的库,获取库的速度大家都知道比较慢,于是我将库上传到我创建的USD小组里了,大家感兴趣的话,可以加入这个QQ群(小组),获取相关的库,然后解压之。
    上海USD小组

    获取USD其它的依赖(包括cmake)

    由于Linux开源的特性,很多底层的库都要到包管理器中寻找,如果编译出错了。记得勤用apt来搜索相关的库。命令是:

    apt search cmake
    pip install pyside2

    值得注意的是,USD在19.11的时候,明确说不支持cmake2了,看来大家要在apt中安装cmake3了。

    编译

    USD在Linux的编译和Windows的差不多,差别在于一个是用Shell脚本,另外一个是用bat脚本。这里我将Shell脚本贴出来给大家参考:

    #!/bin/sh # 最后构建USD项目 baseDir=${baseDir:=$(cd `dirname $0`; pwd)} echo $baseDir pushd $baseDir sudo python $baseDir/USD/build_scripts/build_usd.py -j 4 -v --python --build-args=USD,"-DPYSIDE_USE_PYSIDE2=TRUE -DPYSIDE_BIN_DIR=/usr/local/lib/python2.7/dist-packages/PySide2 -DBOOST_LIBRARYDIR=" /usr/local/USD popd 编译可能遇到的问题 权限问题。这个是最常见的了。Windows的权限问题没有那么严重,而Linux是权限everywhere。于是安装USD的时候,它推荐的位置是/usr/local/USD,这个地方是要权限的。所以记得用sudo,没有设置密码的赶紧用passwd root设置密码了。 遇到找不到编译器的问题。很简单,没有安装编译器呗。Linux默认编译器是g++,所以一定要执行

    sudo apt install g++

    这样才能够解决找不到编译器的问题。同样的,如果想要以后对USD进行调试,那么gdb也是必不可少的,推荐一同安装。

    编译完成

    如果你到了这一步,那么非常恭喜,你已经克服了超多的难关,到达了胜利的彼岸。但是不是要测试一下是否成功地运行了USD呢?我们还是要运行一下USDView来测试一下的嘛。于是我们还是要写一段shell脚本来测试USDView的运行情况:

    #!/bin/sh export LD_LIBRARY_PATH=/usr/local/USD/lib64:$LD_LIBRARY_PATH export PYTHONPATH=$PYTHONPATH:/usr/local/USD/lib/python /usr/local/USD/bin/usdview /media/jiangyimin/Data/models/UsdSkelExamples/HumanFemale/HumanFemale.walk.usd

    由于要寻找库的路径,因此记得及时设置LD_LIBRARY_PATH环境变量。如果一切顺利的话,那么会出现这样的效果:Linux运行USDView

    read more
  • 记住了哦,USD不是咱们所说的美元哦,是迪士尼皮克斯工作室推出的一款动画全流程的工具,简单地说,是用来串流程的,USD的使用借鉴了脚本编程的一些思想,让动画的资产变得可配置,也变得可维护。让同时其提出的几个工具,使得它变成一个较为完整的工具链。
    USD的官方网站(开源)在这里。

    https://openusd.org

    接下来我将告诉大家如何在Windows下构建USD。

    安装Python

    首先呢,是安装USD的依赖项。USD的依赖项挺多,最重要的是Python,因为USD的构建脚本就是用Python写的。所以去Python官网下载Python吧,目前测试成功的是Python2.7。当然你也可以安装Python 3.5,只是我没有测试过,不清楚是否可用。Python的下载地址是:

    https://www.python.org/downloads

    一般来说,安装好了Python,它会给你设置环境变量,或者有一些教程让你们设定环境变量,不过呢,这里我不建议设定环境变量,这样让我们的所有软件运行环境都污染了(可能没有什么事),之后我会写一个脚本来教大家如何书写批处理来让简化操作,真正做到“即用即走”。

    下载Visual Studio 2017

    这不用强调了吧。目前VS2017是必备的软件了,而且有免费社区版,再也不用破解了,赶紧下载一个。安装在合适的位置就好了。

    安装Maya 2018

    一般来说,Maya每年都有发布一个版本,但是2018的格外稳定,推荐安装。为什么要安装Maya呢?因为Maya是一款几乎全能的DCC,可以导出很多模型到USD中,所以USD顺便构建了Maya的插件(这个插件名字叫usdMaya,不过核心代码转到了Autodesk里了,详见https://github.com/Autodesk/maya-usd,此插件除了PXR的USD,还有AL的USD),我也将Maya 2018放在了我们讨论小组群中,大家可以下载。
    USD研究小组.jpg
    我将Maya 2018安装到D:\Develop\Autodesk\Maya2018中。

    安装USD的其余依赖项

    由于USD的python脚本会使用curl或者是powershell的下载功能进行下载,但是由于很多依赖项是从github下载的,下载速度实在是太慢了,所以我将其余的依赖项打包好了,放在USD_dependencies文件夹中,供需要的朋友下载。USD的依赖项已经上传到我们讨论小组群群里了,大家可以下载。
    USD研究小组.jpg

    编写构建USD的脚本

    我的USD安装的位置是D:\Develop\USD,打算安装的位置是D:\Develop\USD_build_19_11,根据这两个路径开始编写构建USD的脚本:

    :: 构建USD的脚本 :: 设置编译器的很多环境变量 set Path=D:\Develop\Python27;^ D:\Develop\Python27\Scripts;^ D:\Develop\NASM;^ D:\Develop\Autodesk\Maya2018\bin;^ D:\Develop\cmake\bin;^ %Path% set PYTHONPATH=%PYTHONPATH%;D:\Develop\Autodesk\Maya2018\Python\Lib\site-packages;D:\Develop\Autodesk\Maya2018\Python\Lib\site-packages :: 复制pyside2-uic到pyside-uic.exe 中,使其造成能够找到pyside2-uic.exe的假象 copy D:\Develop\Autodesk\Maya2018\bin\pyside2-uic D:\Develop\Autodesk\Maya2018\bin\pyside2-uic.exe :: 使用pip安装PyOpenGL pip install PyOpenGL :: 复制本地build_usd_local.bat 到 目标的路径上 copy /Y %cd%\build_usd_local.py D:\Develop\USD\build_scripts call D:\Develop\VS2017\VC\Auxiliary\Build\vcvars64.bat :: 最后构建USD项目 python D:\Develop\USD\build_scripts\build_usd_local.py ^ -j4 ^ --build-args "USD,-DPYSIDE_USE_PYSIDE2=TRUE -DPYSIDE_BIN_DIR=D:\Develop\Autodesk\Maya2018\bin" ^ --maya --maya-location "D:\Develop\Autodesk\Maya2018\bin" ^ --materialx ^ D:\Develop\USD_build_19_11 :: 最后删除build_usd_local文件 del D:\Develop\USD\build_scripts\build_usd_local.py pause

    大家成功了吗?肯定有遇到很多问题,包括我遇到的一直卡住的Boost编译问题。大家遇到什么编译问题,可以在此留言,我会尽可能回答大家问题。

    成功编译USD后,可以编写插件来试试USDView,大家可以试试看吧,不过仍然要设置环境变量。USDView运行的脚本如下:

    set Path=^ D:\Develop\Python27;^ D:\Develop\USD_Build\lib;^ D:\Develop\USD_Build\bin;^ D:\Develop\USD_Build\third_party\maya\lib;^ D:\Develop\Autodesk\Maya2018\bin;^ %Path% set MAYA_PLUG_IN_PATH=%MAYA_PLUG_IN_PATH%;^ D:\Develop\USD_Build\third_party\maya\plugin set PYTHONPATH=%PYTHONPATH%;^ D:\Develop\USD_Build\lib\python;^ D:\Develop\Autodesk\Maya2018\Python\Lib\site-packages set MAYA_SCRIPT_PATH=%MAYA_SCRIPT_PATH%;^ D:\Develop\USD_Build\third_party\maya\lib\usd\usdMaya\resources;^ D:\Develop\USD_Build\third_party\maya\plugin\pxrUsdPreviewSurface\resources set XBMLANGPATH=%XBMLANGPATH%;^ D:\Develop\USD_Build\third_party\maya\lib\usd\usdMaya\resources @python "D:\Develop\USD_Build\bin\usdview" %cd%\7_29_1.usda

    USDView运行的截图是这样的:
    USDView运行效果

    看到最终结果,还是很有成就感的。

    read more
  • @天幸健 要么程序一启动就camera.start(),然后再camera.stop(),接着需要的时候再camera.start()。

    read more
  • @jcy 我现在程序一启动就加载了Camera 组件,但是当我要启动摄像头时,调用camera.start() 还是会卡一下

    read more

关注我们

微博
QQ群