Qt 5.1和Mac:使macdeployqt无法正常工作的错误

时间:2013-07-04 17:41:06

标签: macos qt macdeployqt

自Mac OS X 5.1rc2的版本Qt以来,我遇到了问题。(5.1也受影响,而不是5.1rc1)
当我构建我的应用程序并在二进制文件上执行otool -L以查看共享库的路径时,我得到:(这只是一个示例,我为了清楚起见删除了其中一些)

/System/Library/Frameworks/AppKit.framework/Versions/C/AppKit 
    (compatibility version 45.0.0, current version 1187.37.0)
/Users/chris/**Qt5.1.0//5.1.0**/clang_64/lib/QtWebKitWidgets.framework/Versions/5/QtWebKitWidgets
    (compatibility version 5.1.0, current version 5.1.0)
/Users/chris/Qt5.1.0//5.1.0/clang_64/lib/QtQuick.framework/Versions/5/QtQuick
    (compatibility version 5.1.0, current version 5.1.0)
/Users/chris/Qt5.1.0//5.1.0/clang_64/lib/QtQml.framework/Versions/5/QtQml
    (compatibility version 5.1.0, current version 5.1.0)
/Users/chris/Qt5.1.0//5.1.0/clang_64/lib/QtNetwork.framework/Versions/5/QtNetwork
    (compatibility version 5.1.0, current version 5.1.0)
/Users/chris/Qt5.1.0//5.1.0/clang_64/lib/QtCore.framework/Versions/5/QtCore
    (compatibility version 5.1.0, current version 5.1.0)
/Users/chris/Qt5.1.0//5.1.0/clang_64/lib/QtGui.framework/Versions/5/QtGui
    (compatibility version 5.1.0, current version 5.1.0)

正如您所看到的,Qt库的路径中存在双斜杠。 当我使用macdeployqt部署我的应用程序时,这些路径不会更改为本地框架(@executable_path /../ Frameworks / ...),因为这... 我必须使用install_name_tool手动完成它,这真的很烦人。

我该怎么做才能解决这个问题? (我已经尝试重新安装Qt,清理,再次运行qmake并重建而不做更改)

9 个答案:

答案 0 :(得分:10)

有同样的问题。我申请了下一个解决方法:

在我构建程序之后,我已将exe内部的链接更改为正确的

install_name_tool -change /Users/username/Qt5.1.0//5.1.0/clang_64/lib/QtQuick.framework/Versions/5/QtQuick  /Users/username/Qt5.1.0/5.1.0/clang_64/lib/QtQuick.framework/Versions/5/QtQuick <YourExecutable>

在此解决方法之后,macdeployqt已将exe内的所有链接更改为相对链接。

但是我的应用程序破了。问题是我已将所有图像和QML文件添加到资源中。我运行macdeployqt后 - 我无法运行我的应用程序。当我用gdb运行它时 - 我看到下一个错误:

QQmlApplicationEngine failed to load component 
qrc:/qml/main.qml:-1 File not found

Error: Your root item has to be a Window.

所以我的所有资源都变得不可用了。有谁知道如何解决这个问题?

我也开始讨论qt forum

更新,如何部署:

  1. 使用this script删除动态链接路径中的双斜杠。

    ./ fixqt.sh~ / Qt5.1.0 / 5.1.0 / clang_64

  2. 从此repository构建macdeployqt工具。

  3. 运行macdeployqt并使用qml源指定dir:

    macdeployqt MyApp.app/ -qmldir = .. / src / qml -dmg

  4. 在这些步骤之后,我设法在不同的OS X系统上运行我的应用程序,而没有安装QT。我已将所有qml文件和图像添加到资源中。 QtQuick和QtQuick.2模块复制在MyApp.app/Content/MacOS /

    希望有所帮助

答案 1 :(得分:6)

我将此作为解决方案发布,因为我刚刚将这个过程丢失(另一天)到5.3(我认为它与5.4相同)。

macdeployqt现在按预期工作,但此处失败的文档是您需要为每个qml目录指定 绝对路径 (相对可能有效)但我一点也没有运气。

以下是我为发布流程解决的问题:

在项目文件中我现在有

  mac {
    CONFIG += x86
    CONFIG += c++11
    #Disable these for development
    QMAKE_MACOSX_DEPLOYMENT_TARGET = 10.9 #I'm not sure I need this
    QMAKE_POST_LINK = {path to macdeployqt}/macdeployqt {appname}.app -qmldir=$$PWD/qml/{appname}/ -verbose=3
  }

这实际上是: macdeployqt appname.app - /path/to/source/code/appname/qml/appname/ -verbose=3

当指定绝对路径时,它似乎工作正常但是当我使用相对路径时,我遇到了几个问题。 PWD是源目录,可执行文件从构建目录运行。构建的绝对路径为OUT_PWD

在项目的发布配置中保持这一点的美妙之处在于我正常调试(没有应用程序包),并且发布包正在从创建者正确构建。从理论上讲,我可以将它包装成Jenkins版本,并且一劳永逸地完成这个问题。

简答

macdeployqt必须扫描您的qml文件,否则导入将被破坏,您将看到如下错误:

QQmlApplicationEngine failed to load component
qrc:/qml/LightAssistant.qml:5 module "QtQuick.Dialogs" is not installed
qrc:/qml/LightAssistant.qml:3 module "QtQuick.Window" is not installed
qrc:/qml/LightAssistant.qml:4 module "QtQuick.Controls" is not installed
qrc:/qml/LightAssistant.qml:1 module "QtQuick" is not installed
qrc:/qml/LightAssistant.qml:2 module "QtQuick.Layouts" is not installed

最后,我的目录结构如下所示:

  Project
    - qml
      - appname
        files1.qml
        files2.qml
        ...
        filesX.qml 
    - js
    - images

然后将它们打包到资源文件中,根据定义,它不会被复制到构建目录,因此macdeployqt不能扫描它们,除非路径是完美的。通过使用这个构建过程,我在构建(发布)中有一个步骤来处理它,并且在我调试时我不必运行macdeployqt。请记住,如果你使用app_bundle,你需要在每个构建上运行macdeployqt,这将真正搞乱你的调试工作流程。

答案 2 :(得分:4)

这个主题:

http://www.qtcentre.org/threads/55277-Qt-5-1-and-Mac-Bug-making-macdeployqt-not-working-properly

包含以下链接:

https://gist.github.com/lasconic/5965542

通过lasconic(不是我的工作)来写这个剧本:

BIN_FILE=YOURBINARY
for P in `otool -L $BIN_FILE | awk '{print $1}'` 
do 
    if [[ "$P" == *//* ]] 
    then 
        PSLASH=$(echo $P | sed 's,//,/,g')
        install_name_tool -change $P $PSLASH $BIN_FILE
    fi 
done 

QTDIR=$1
for F in `find $QTDIR/lib $QTDIR/plugins $QTDIR/qml  -perm 755 -type f` 
do 
    for P in `otool -L $F | awk '{print $1}'`
    do   
        if [[ "$P" == *//* ]] 
        then 
            PSLASH=$(echo $P | sed 's,//,/,g')
            install_name_tool -change $P $PSLASH $F
        fi 
     done
done

您只需将YOURBINARY替换为例如myapp.app/Contents/MacOS/myapp

QTDIR=$1QTDIR=/Users/MyName/Qt5.1.0/5.1.0/clang_64

将文件保存在与myapp.app

相同的目录中

运行它
sh thankslasconic.sh

然后你可以运行

macdeployqt myapp.app

它应该有效。对我来说确实如此。这就是我在这里发帖的原因。

答案 3 :(得分:1)

我认为这是一个安装程序错误。所有图书馆和工具(由安装人员编译/链接?)引用... / Qt5.1.0 // 5.1.0 / ...(带双斜杠)

我已尝试使用相同结果的Mac在线和离线安装程序。

我已将此报告为错误。 https://bugreports.qt-project.org/browse/QTBUG-32467

答案 4 :(得分:1)

正如后续行动一样,这个错误似乎在Qt5.1.1中得到修复 https://bugreports.qt.io/browse/QTBUG-32365

答案 5 :(得分:0)

答案 6 :(得分:0)

尝试使用qt 5.1.1进行上述所有操作,但始终遇到此问题:

QMessageLogger::fatal(char const*, ...) const + 161
QGuiApplicationPrivate::createPlatformIntegration() + 1763
QGuiApplicationPrivate::createEventDispatcher() + 28
QCoreApplication::init() + 101
QCoreApplication::QCoreApplication(QCoreApplicationPrivate&) + 42

所以我创造了这个灵药,YMMV:

1)从github获得上面提到的大多数有用的macqtdeploy。

2)构建这个新的macqtdeploy

3)仅将此添加到main.cpp for mac os x。在启动qapplication之前,这会将“-platformpluginpath”写入argv。

int macStart(int argc, char *argv[]) {
    QFileInfo fi(argv[0]);
    QDir plugd(fi.dir());
    plugd.cdUp();
    plugd.cd("PlugIns");
    QString plugins = plugd.absolutePath();
    qDebug() << "PlugIns" << plugins;

    char* argv_sub[argc + 2];
    for (int i = 0; i < argc; ++i) {
        char* temp = (char*) malloc(strlen(argv[i]) + 1);
        strcpy(temp, argv[i]);
        argv_sub[i] = temp;
    }

    char ppp[255];
    strcpy(ppp, "-platformpluginpath");
    argv_sub[argc] = ppp;

    char pathx[2048];
    strcpy(pathx, (char*) plugd.absolutePath().toLocal8Bit().constData());
    argv_sub[argc + 1] = pathx;

    DCApplication app(argc + 2, argv_sub);
    app.startup();
    return app.exec();
}

4)构建应用

5)在app上运行新的macqtdeploy

6)善良

答案 7 :(得分:0)

将插件文件夹设置为libraryPaths

QStringList paths;
paths.append("folder with plugins"); //can be inside bundle
QApplication::setLibraryPaths(paths);

答案 8 :(得分:0)

在使用QML查找与macdeployqt和QT Quick 2.0类似的错误时,我总是在讨论中结束。

我发现的错误是:

chapter

和此:

# app/models/manga.rb class Manga < ActiveRecord::Base has_many :chapters end # app/models/chapter.rb class Chapter < ActiveRecord::Base belongs_to :manga has_many :pejis end # app/models/peji.rb class Peji < ActiveRecord::Base belongs_to :chapter end

我在这里为这种错误创建了一个单独的问题: QT Quick (QML) assemble mac-.bundle -> not a dynamic library error when using macdeployqt

以防有人遇到同样的问题并阅读此帖子。