简体   繁体   English

带有可选 gui 的 Qt 应用程序

[英]Qt application with optional gui

I am going to write program using Qt for some image processing and I want it to be able to run in non-gui mode (daemon mode?).我将使用 Qt 编写程序进行一些图像处理,我希望它能够在非 gui 模式(守护进程模式?)下运行。 I'm inspired by VLC player, which is "typically" GUI program, where you can configure it using GUI, but you can also run it in non-gui option when it runs without GUI.我的灵感来自 VLC 播放器,它是“典型的”GUI 程序,您可以在其中使用 GUI 对其进行配置,但是当它在没有 GUI 的情况下运行时,您也可以在non-gui选项中运行它。 Then it uses some configuration file created in GUI mode.然后它使用一些在 GUI 模式下创建的配置文件。

Question is how should be such a program design?问题是这样的程序应该如何设计? Should be some program core, which is GUI independent and depending on options it is being connected with GUI interface?应该是一些程序核心,它是独立于 GUI 的,并且取决于它与 GUI 界面连接的选项?

Yes, you could use a "headless" or "gui" option for the binary using QCommandLineParser .是的,您可以使用QCommandLineParser对二进制文件使用“无头”或“gui”选项。 Note that it is only available from 5.3, but the migration path is pretty smooth within the major series if you still do not use that.请注意,它仅从 5.3 开始可用,但是如果您仍然不使用它,则在主要系列中的迁移路径非常顺畅。

main.cpp主程序

#include <QApplication>
#include <QLabel>
#include <QDebug>
#include <QCommandLineParser>
#include <QCommandLineOption>

int main(int argc, char **argv)
{
    QApplication application(argc, argv);
    QCommandLineParser parser;
    parser.setApplicationDescription("My program");
    parser.addHelpOption();
    parser.addVersionOption();

    // A boolean option for running it via GUI (--gui)
    QCommandLineOption guiOption(QStringList() << "gui", "Running it via GUI.");
    parser.addOption(guiOption);

    // Process the actual command line arguments given by the user
    parser.process(application);
    QLabel label("Runninig in GUI mode");
    if (parser.isSet(guiOption))
        label.show();
    else
        qDebug() << "Running in headless mode";

    return application.exec();
}

main.pro主程序

TEMPLATE = app
TARGET = main
QT += widgets
SOURCES += main.cpp

Build and Run构建和运行

qmake && make && ./main
qmake && make && ./main --gui

Usage用法

    Usage: ./main [options]
My program

Options:
  -h, --help     Displays this help.
  -v, --version  Displays version information.
  --gui          Running it via GUI.

You can pass an argument to your application when starting to show in gui or non-gui modes.当开始以 gui 或非 gui 模式显示时,您可以将参数传递给您的应用程序。 For example if you pass -non-gui parameter when running in command line then the application should not show the main window and it should do some other stuff :例如,如果在命令行中运行时传递 -non-gui 参数,则应用程序不应显示主窗口,而应执行其他操作:

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);

    MainWindow w;

    bool GUIMode=true;

    int num = qApp->argc() ;
    for ( int i = 0; i < num; i++ )
    {
        QString s = qApp->argv()[i] ;
        if ( s.startsWith( "-non-gui" ) )
            GUIMode = false;
    }

    if(GUIMode)
    {
         w.show();
    }
    else
    {
        //start some non gui functions
    }

    return a.exec();
}

The example by lpapp above didn't work for me, as I got上面 lpapp 的例子对我不起作用,因为我得到了

qt.qpa.screen: QXcbConnection: Could not connect to display localhost:10.0
Could not connect to any X display.

when running without an X display (any value for DISPLAY, not just localhost:10.0 ).在没有 X 显示的情况下运行时(DISPLAY 的任何值,而不仅仅是localhost:10.0 )。

There was a workaround - export QT_QPA_PLATFORM='offscreen' - but that's not a command line option, your user is expected to do it, which isn't nice.有一个解决方法 - export QT_QPA_PLATFORM='offscreen' - 但这不是命令行选项,您的用户应该这样做,这不好。

So, following posting a question here, further research lead me to the following QT5 document that explains the "approved" way to start up with or without a GUI depending on command line options:因此,在此处发布问题后,进一步研究将我引向以下 QT5 文档,该文档解释了根据命令行选项使用或不使用 GUI 启动的“已批准”方式:

https://doc.qt.io/qt-5/qapplication.html#details https://doc.qt.io/qt-5/qapplication.html#details

However, your mileage may vary.但是,您的里程可能会有所不同。 The example there didn't "just work" for me, either!那里的例子对我来说也不“只是工作”!

I had to use the command line arg to then choose one of two methods to run.我必须使用命令行 arg 然后选择两种方法之一来运行。 Each method created its own app object (QCoreApplication for headless, QApplication for GUI, as the docs show) and then running the app.每个方法都创建了自己的应用程序对象(QCoreApplication for headless,QApplication for GUI,如文档所示)然后运行应用程序。

It may be because I'm working with "mostly Qt 4" code and compiling on Qt 5 that things are being a bit odd but this method now works, so I've not investigated further.可能是因为我正在使用“主要是 Qt 4”代码并在 Qt 5 上编译,事情有点奇怪,但这种方法现在有效,所以我没有进一步调查。

With Qt5, running a Qt application with the command line argument -platform offscreen does draw offscreen.使用 Qt5,运行带有命令行参数-platform offscreen的 Qt 应用程序会在-platform offscreen绘制。

See the documentation https://doc.qt.io/qt-5/qguiapplication.html#QGuiApplication请参阅文档https://doc.qt.io/qt-5/qguiapplication.html#QGuiApplication

The options currently supported are the following:当前支持的选项如下:

-platform platformName [:options], specifies the Qt Platform Abstraction (QPA) plugin. -platform platformName [:options],指定Qt Platform Abstraction (QPA) 插件。

Overrides the QT_QPA_PLATFORM environment variable.覆盖 QT_QPA_PLATFORM 环境变量。

The supported platform names are listed in the platformName docs .支持的平台名称列在platformName docs 中

Tested with Qt 5.15.1使用 Qt 5.15.1 测试

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM