main/core: changed code so that headless would run truly headless with QCoreApplication instead of QApplication

QApplication is designed for GUI/widget programs and thus fails to launch
if no window system is available. For a true headless mode, we must swap
out with QCoreApplication. However, what complicates this is that
QCommandLineParser - the class we use to determine whether we should run
in GUI mode or not - requires an active application instance to work.
This creates an unfortunate catch-22 that ultimately ended in writing a
custom command line parser.

Now we can correctly swap out with QCoreApplication, however this has
exposed other issues regarding functions that unnecessarily rely on QWidget
functions. So they'll need to be sorted out eventually.
This commit is contained in:
itsmattkc
2020-08-22 00:22:19 +10:00
parent 9aabde303e
commit 48ac8ea509
6 changed files with 450 additions and 122 deletions
+90 -21
View File
@@ -34,34 +34,23 @@ extern "C" {
#include <csignal>
#include <QApplication>
#include <QCommandLineParser>
#include <QSurfaceFormat>
#include "core.h"
#include "common/commandlineparser.h"
#include "common/debug.h"
#ifdef USE_CRASHPAD
#include "common/crashpadinterface.h"
#endif // USE_CRASHPAD
int main(int argc, char *argv[]) {
// Set OpenGL display profile (3.2 Core)
QSurfaceFormat format;
format.setVersion(3, 2);
format.setDepthBufferSize(24);
format.setProfile(QSurfaceFormat::CoreProfile);
QSurfaceFormat::setDefaultFormat(format);
//QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
QCoreApplication::setAttribute(Qt::AA_UseHighDpiPixmaps);
// Create application instance
QApplication a(argc, argv);
// Set application metadata
QCoreApplication::setOrganizationName("olivevideoeditor.org");
QCoreApplication::setOrganizationDomain("olivevideoeditor.org");
QCoreApplication::setApplicationName("Olive");
int main(int argc, char *argv[])
{
// Set up debug handler
qInstallMessageHandler(OLIVE_NAMESPACE::DebugHandler);
// Generate version string
QString app_version = APPVERSION;
#ifdef GITHASH
// Anything after the hyphen is considered "unimportant" information. Text BEFORE the hyphen is used in version
@@ -70,14 +59,85 @@ int main(int argc, char *argv[]) {
app_version.append(GITHASH);
#endif
// Set application metadata
QCoreApplication::setOrganizationName("olivevideoeditor.org");
QCoreApplication::setOrganizationDomain("olivevideoeditor.org");
QCoreApplication::setApplicationName("Olive");
QCoreApplication::setApplicationVersion(app_version);
#if (QT_VERSION >= QT_VERSION_CHECK(5, 7, 0))
QGuiApplication::setDesktopFileName("org.olivevideoeditor.Olive");
#endif
// Set up debug handler
qInstallMessageHandler(OLIVE_NAMESPACE::DebugHandler);
//
// Parse command line arguments
//
OLIVE_NAMESPACE::Core::CoreParams startup_params;
CommandLineParser parser;
const CommandLineParser::Option* help_option =
parser.AddOption({QStringLiteral("h"), QStringLiteral("-help")},
QCoreApplication::translate("main", "Show this help text"));
const CommandLineParser::Option* version_option =
parser.AddOption({QStringLiteral("v"), QStringLiteral("-version")},
QCoreApplication::translate("main", "Show application version"));
const CommandLineParser::Option* fullscreen_option =
parser.AddOption({QStringLiteral("f"), QStringLiteral("-fullscreen")},
QCoreApplication::translate("main", "Start in full-screen mode"));
const CommandLineParser::Option* export_option =
parser.AddOption({QStringLiteral("x"), QStringLiteral("-export")},
QCoreApplication::translate("main", "Export only (No GUI)"));
const CommandLineParser::PositionalArgument* project_argument =
parser.AddPositionalArgument(QStringLiteral("project"),
QCoreApplication::translate("main", "Project to open on startup"));
parser.Process(argc, argv);
if (help_option->IsSet()) {
// Show help
parser.PrintHelp(argv[0]);
return 0;
}
if (version_option->IsSet()) {
// Print version
printf("%s\n", app_version.toUtf8().constData());
return 0;
}
if (export_option->IsSet()) {
startup_params.set_run_mode(OLIVE_NAMESPACE::Core::CoreParams::kHeadlessExport);
}
startup_params.set_fullscreen(fullscreen_option->IsSet());
startup_params.set_startup_project(project_argument->GetSetting());
// Set OpenGL display profile (3.2 Core)
QSurfaceFormat format;
format.setVersion(3, 2);
format.setDepthBufferSize(24);
format.setProfile(QSurfaceFormat::CoreProfile);
QSurfaceFormat::setDefaultFormat(format);
// Enable application automatically using higher resolution images from icons
QCoreApplication::setAttribute(Qt::AA_UseHighDpiPixmaps);
// Create application instance
std::unique_ptr<QCoreApplication> a;
if (startup_params.run_mode() == OLIVE_NAMESPACE::Core::CoreParams::kRunNormal) {
a.reset(new QApplication(argc, argv));
} else {
a.reset(new QCoreApplication(argc, argv));
}
// Register FFmpeg codecs and filters (deprecated in 4.0+)
#if LIBAVFORMAT_VERSION_INT < AV_VERSION_INT(58, 9, 100)
@@ -94,5 +154,14 @@ int main(int argc, char *argv[]) {
}
#endif // USE_CRASHPAD
return OLIVE_NAMESPACE::Core::instance()->execute(&a);
// Start core
OLIVE_NAMESPACE::Core c(startup_params);
c.Start();
int ret = a->exec();
// Clear core memory
c.Stop();
return ret;
}