X-Git-Url: http://git.osdn.net/view?a=blobdiff_plain;f=src%2Fwin_main.cpp;h=e2722d533b18d15c84a30f6bc453d1ad29ff34fb;hb=5f218915041e3798e37b2e3a2242b0866ee1eba8;hp=3ecb53ab39890914d9bbbcaec07a72b9c7f14ee8;hpb=8e4e3814081edfe8c7e160ec804b8ebb7101888f;p=x264-launcher%2Fx264-launcher.git diff --git a/src/win_main.cpp b/src/win_main.cpp index 3ecb53a..e2722d5 100644 --- a/src/win_main.cpp +++ b/src/win_main.cpp @@ -1,6 +1,6 @@ /////////////////////////////////////////////////////////////////////////////// // Simple x264 Launcher -// Copyright (C) 2004-2015 LoRd_MuldeR +// Copyright (C) 2004-2020 LoRd_MuldeR // // This program is free software; you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by @@ -42,7 +42,6 @@ #include "win_about.h" #include "win_preferences.h" #include "win_updater.h" -#include "binaries.h" #include "resource.h" //MUtils @@ -72,7 +71,7 @@ #include #include #include - +#include #include //Constants @@ -91,7 +90,7 @@ static const int vsynth_rev = 24; #define INIT_ERROR_EXIT() do { close(); qApp->exit(-1); return; } while(0) #define SETUP_WEBLINK(OBJ, URL) do { (OBJ)->setData(QVariant(QUrl(URL))); connect((OBJ), SIGNAL(triggered()), this, SLOT(showWebLink())); } while(0) #define APP_IS_READY (m_initialized && (!m_fileTimer->isActive()) && (QApplication::activeModalWidget() == NULL)) -#define ENSURE_APP_IS_READY() do { if(!APP_IS_READY) { MUtils::Sound::beep(MUtils::Sound::BEEP_WRN); qWarning("Cannot perfrom this action at this time!"); return; } } while(0) +#define ENSURE_APP_IS_READY() do { if(!APP_IS_READY) { MUtils::Sound::beep(MUtils::Sound::BEEP_WRN); qWarning("Cannot perfrom this action at this time!"); return; } } while(0) #define X264_STRCMP(X,Y) ((X).compare((Y), Qt::CaseInsensitive) == 0) /////////////////////////////////////////////////////////////////////////////// @@ -110,6 +109,7 @@ MainWindow::MainWindow(const MUtils::CPUFetaures::cpu_info_t &cpuFeatures, MUtil m_pendingFiles(new QStringList()), m_preferences(NULL), m_recentlyUsed(NULL), + m_postOperation(POST_OP_DONOTHING), m_initialized(false), ui(new Ui::MainWindow()) { @@ -141,6 +141,9 @@ MainWindow::MainWindow(const MUtils::CPUFetaures::cpu_info_t &cpuFeatures, MUtil m_options.reset(new OptionsModel(m_sysinfo.data())); OptionsModel::loadTemplate(m_options.data(), QString::fromLatin1(tpl_last)); + //DPI scaling + MUtils::GUI::scale_widget(this); + //Freeze minimum size setMinimumSize(size()); ui->splitter->setSizes(QList() << 16 << 196); @@ -166,10 +169,9 @@ MainWindow::MainWindow(const MUtils::CPUFetaures::cpu_info_t &cpuFeatures, MUtil //Setup view ui->jobsView->horizontalHeader()->setSectionHidden(3, true); ui->jobsView->horizontalHeader()->setResizeMode(0, QHeaderView::Stretch); - ui->jobsView->horizontalHeader()->setResizeMode(1, QHeaderView::Fixed); - ui->jobsView->horizontalHeader()->setResizeMode(2, QHeaderView::Fixed); - ui->jobsView->horizontalHeader()->resizeSection(1, 150); - ui->jobsView->horizontalHeader()->resizeSection(2, 90); + ui->jobsView->horizontalHeader()->setResizeMode(1, QHeaderView::ResizeToContents); + ui->jobsView->horizontalHeader()->setResizeMode(2, QHeaderView::ResizeToContents); + ui->jobsView->horizontalHeader()->setMinimumSectionSize(96); ui->jobsView->verticalHeader()->setResizeMode(QHeaderView::ResizeToContents); connect(ui->jobsView->selectionModel(), SIGNAL(currentChanged(QModelIndex, QModelIndex)), this, SLOT(jobSelected(QModelIndex, QModelIndex))); @@ -216,25 +218,36 @@ MainWindow::MainWindow(const MUtils::CPUFetaures::cpu_info_t &cpuFeatures, MUtil connect(ui->actionJob_MoveDown, SIGNAL(triggered()), this, SLOT(moveButtonPressed() )); //Enable menu - connect(ui->actionOpen, SIGNAL(triggered()), this, SLOT(openActionTriggered())); - connect(ui->actionAbout, SIGNAL(triggered()), this, SLOT(showAbout())); - connect(ui->actionPreferences, SIGNAL(triggered()), this, SLOT(showPreferences())); - connect(ui->actionCheckForUpdates, SIGNAL(triggered()), this, SLOT(checkUpdates())); + connect(ui->actionOpen, SIGNAL(triggered()), this, SLOT(openActionTriggered())); + connect(ui->actionCleanup_Finished, SIGNAL(triggered()), this, SLOT(cleanupActionTriggered())); + connect(ui->actionCleanup_Enqueued, SIGNAL(triggered()), this, SLOT(cleanupActionTriggered())); + connect(ui->actionPostOp_DoNothing, SIGNAL(triggered()), this, SLOT(postOpActionTriggered())); + connect(ui->actionPostOp_PowerDown, SIGNAL(triggered()), this, SLOT(postOpActionTriggered())); + connect(ui->actionPostOp_Hibernate, SIGNAL(triggered()), this, SLOT(postOpActionTriggered())); + connect(ui->actionAbout, SIGNAL(triggered()), this, SLOT(showAbout())); + connect(ui->actionPreferences, SIGNAL(triggered()), this, SLOT(showPreferences())); + connect(ui->actionCheckForUpdates, SIGNAL(triggered()), this, SLOT(checkUpdates())); + ui->actionCleanup_Finished->setData(QVariant(bool(0))); + ui->actionCleanup_Enqueued->setData(QVariant(bool(1))); + ui->actionPostOp_DoNothing->setData(QVariant(POST_OP_DONOTHING)); + ui->actionPostOp_PowerDown->setData(QVariant(POST_OP_POWERDOWN)); + ui->actionPostOp_Hibernate->setData(QVariant(POST_OP_HIBERNATE)); + ui->actionPostOp_Hibernate->setEnabled(MUtils::OS::is_hibernation_supported()); //Setup web-links SETUP_WEBLINK(ui->actionWebMulder, home_url); SETUP_WEBLINK(ui->actionWebX264, "http://www.videolan.org/developers/x264.html"); SETUP_WEBLINK(ui->actionWebX265, "http://www.videolan.org/developers/x265.html"); - SETUP_WEBLINK(ui->actionWebKomisar, "http://komisar.gin.by/"); - SETUP_WEBLINK(ui->actionWebVideoLAN, "http://download.videolan.org/pub/x264/binaries/"); - SETUP_WEBLINK(ui->actionWebJEEB, "http://x264.fushizen.eu/"); - SETUP_WEBLINK(ui->actionWebFreeCodecs, "http://www.free-codecs.com/x264_video_codec_download.htm"); - SETUP_WEBLINK(ui->actionWebX265BinRU, "http://x265.ru/en/builds/"); - SETUP_WEBLINK(ui->actionWebX265BinEU, "http://builds.x265.eu/"); - SETUP_WEBLINK(ui->actionWebX265BinORG, "http://chromashift.org/x265_builds/"); - SETUP_WEBLINK(ui->actionWebX265BinFF, "http://ffmpeg.zeranoe.com/builds/"); - SETUP_WEBLINK(ui->actionWebAvisynth32, "http://sourceforge.net/projects/avisynth2/files/AviSynth%202.5/"); - SETUP_WEBLINK(ui->actionWebAvisynth64, "http://code.google.com/p/avisynth64/downloads/list"); + SETUP_WEBLINK(ui->actionWebX264LigH, "http://www.mediafire.com/?bxvu1vvld31k1"); + SETUP_WEBLINK(ui->actionWebX264VideoLAN, "http://artifacts.videolan.org/x264/"); + SETUP_WEBLINK(ui->actionWebX264Komisar, "http://komisar.gin.by/"); + SETUP_WEBLINK(ui->actionWebX265LigH, "http://www.mediafire.com/?6lfp2jlygogwa"); + SETUP_WEBLINK(ui->actionWebX264FreeCodecs, "http://www.free-codecs.com/x264_video_codec_download.htm"); + SETUP_WEBLINK(ui->actionWebX265Fllear, "http://x265.ru/en/builds/"); + SETUP_WEBLINK(ui->actionWebX265Snowfag, "http://builds.x265.eu/"); + SETUP_WEBLINK(ui->actionWebX265FreeCodecs, "http://www.free-codecs.com/x265_hevc_encoder_download.htm"); + SETUP_WEBLINK(ui->actionWebAvisynth32, "https://sourceforge.net/projects/avisynth2/files/AviSynth%202.6/"); + SETUP_WEBLINK(ui->actionWebAvisynth64, "http://forum.doom9.org/showthread.php?t=152800"); SETUP_WEBLINK(ui->actionWebAvisynthPlus, "http://www.avs-plus.net/"); SETUP_WEBLINK(ui->actionWebVapourSynth, "http://www.vapoursynth.com/"); SETUP_WEBLINK(ui->actionWebVapourSynthDocs, "http://www.vapoursynth.com/doc/"); @@ -344,6 +357,7 @@ void MainWindow::addButtonPressed() void MainWindow::openActionTriggered() { ENSURE_APP_IS_READY(); + qWarning("openActionTriggered()"); QStringList fileList = QFileDialog::getOpenFileNames(this, tr("Open Source File(s)"), m_recentlyUsed->sourceDirectory(), AddJobDialog::getInputFilterLst(), NULL, QFileDialog::DontUseNativeDialog); if(!fileList.empty()) @@ -366,6 +380,76 @@ void MainWindow::openActionTriggered() } /* +* The "clean-up" action was invoked +*/ +void MainWindow::cleanupActionTriggered(void) +{ + ENSURE_APP_IS_READY(); + + QAction *const sender = dynamic_cast(QObject::sender()); + if (sender) + { + const QVariant data = sender->data(); + if (data.isValid() && (data.type() == QVariant::Bool)) + { + const bool mode = data.toBool(); + const int rows = m_jobList->rowCount(QModelIndex()); + QList jobIndices; + for (int i = 0; i < rows; i++) + { + const JobStatus status = m_jobList->getJobStatus(m_jobList->index(i, 0, QModelIndex())); + if (mode && (status == JobStatus_Enqueued)) + { + jobIndices.append(i); + } + else if ((!mode) && ((status == JobStatus_Completed) || (status == JobStatus_Aborted) || (status == JobStatus_Failed))) + { + jobIndices.append(i); + } + } + if (!jobIndices.isEmpty()) + { + QListIterator iter(jobIndices); + iter.toBack(); + while(iter.hasPrevious()) + { + m_jobList->deleteJob(m_jobList->index(iter.previous(), 0, QModelIndex())); + } + } + else + { + MUtils::Sound::beep(MUtils::Sound::BEEP_WRN); + } + } + } +} + +/* +* The "clean-up" action was invoked +*/ +void MainWindow::postOpActionTriggered(void) +{ + ENSURE_APP_IS_READY(); + + QAction *const sender = dynamic_cast(QObject::sender()); + if (sender) + { + const QVariant data = sender->data(); + if (data.isValid() && (data.type() == QVariant::Int)) + { + const postOp_t mode = (postOp_t)data.toInt(); + if ((mode >= POST_OP_DONOTHING) && (mode <= POST_OP_HIBERNATE)) + { + m_postOperation = mode; + ui->actionPostOp_PowerDown->setChecked(mode == POST_OP_POWERDOWN); + ui->actionPostOp_Hibernate->setChecked(mode == POST_OP_HIBERNATE); + ui->actionPostOp_DoNothing->setChecked(mode == POST_OP_DONOTHING); + } + } + } +} + +/* * The "start" button was clicked */ void MainWindow::startButtonPressed(void) @@ -673,8 +757,9 @@ void MainWindow::launchNextJob(void) qWarning("No enqueued jobs left to be started!"); - if(m_preferences->getShutdownComputer()) + if(m_postOperation) { + qDebug("Post operation has been scheduled! (m_postOperation: %d)", m_postOperation); QTimer::singleShot(0, this, SLOT(shutdownComputer())); } } @@ -686,27 +771,31 @@ void MainWindow::saveLogFile(const QModelIndex &index) { if(index.isValid()) { - if(LogFileModel *log = m_jobList->getLogFile(index)) + const LogFileModel *const logData = m_jobList->getLogFile(index); + const QString &outputFilePath = m_jobList->getJobOutputFile(index); + if(logData && (!outputFilePath.isEmpty())) { - QDir(QString("%1/logs").arg(x264_data_path())).mkpath("."); - QString logFilePath = QString("%1/logs/LOG.%2.%3.txt").arg(x264_data_path(), QDate::currentDate().toString(Qt::ISODate), QTime::currentTime().toString(Qt::ISODate).replace(':', "-")); - QFile outFile(logFilePath); - if(outFile.open(QIODevice::WriteOnly)) + const QFileInfo outputFileInfo(outputFilePath); + if (outputFileInfo.absoluteDir().exists()) { - QTextStream outStream(&outFile); - outStream.setCodec("UTF-8"); - outStream.setGenerateByteOrderMark(true); - - const int rows = log->rowCount(QModelIndex()); - for(int i = 0; i < rows; i++) + const QString outputDir = outputFileInfo.absolutePath(), outputName = outputFileInfo.fileName(); + const QString logFilePath = MUtils::make_unique_file(outputDir, outputName, QLatin1String("log"), true); + if (!logFilePath.isEmpty()) + { + qDebug("Saving log file to: \"%s\"", MUTILS_UTF8(logFilePath)); + if (!logData->saveToLocalFile(logFilePath)) + { + qWarning("Failed to open log file for writing:\n%s", logFilePath.toUtf8().constData()); + } + } + else { - outStream << log->data(log->index(i, 0, QModelIndex()), Qt::DisplayRole).toString() << QLatin1String("\r\n"); + qWarning("Failed to generate log file name. Giving up!"); } - outFile.close(); } else { - qWarning("Failed to open log file for writing:\n%s", logFilePath.toUtf8().constData()); + qWarning("Output directory does not seem to exist. Giving up!"); } } } @@ -718,16 +807,23 @@ void MainWindow::saveLogFile(const QModelIndex &index) void MainWindow::shutdownComputer(void) { ENSURE_APP_IS_READY(); + qDebug("shutdownComputer (m_postOperation: %d)", m_postOperation); if(countPendingJobs() > 0) { - qDebug("Still have pending jobs, won't shutdown yet!"); + qWarning("Still have pending jobs, won't shutdown yet!"); return; } + if ((m_postOperation != POST_OP_POWERDOWN) && (m_postOperation != POST_OP_HIBERNATE)) + { + qWarning("No post-operation has been schedule!"); + } + const int iTimeout = 30; const Qt::WindowFlags flags = Qt::WindowStaysOnTopHint | Qt::CustomizeWindowHint | Qt::WindowTitleHint | Qt::MSWindowsFixedSizeDialogHint | Qt::WindowSystemMenuHint; - const QString text = QString("%1%2%1").arg(QString().fill(' ', 18), tr("Warning: Computer will shutdown in %1 seconds...")); + const bool hibernate = (m_postOperation == POST_OP_HIBERNATE); + const QString text = QString("%1%2%1").arg(QString().fill(' ', 18), hibernate ? tr("Warning: Computer will hibernate in %1 seconds...") : tr("Warning: Computer will shutdown in %1 seconds...")); qWarning("Initiating shutdown sequence!"); @@ -772,7 +868,7 @@ void MainWindow::shutdownComputer(void) qWarning("Shutting down !!!"); - if(MUtils::OS::shutdown_computer("Simple x264 Launcher: All jobs completed, shutting down!", 10, true, false)) + if(MUtils::OS::shutdown_computer("Simple x264 Launcher: All jobs completed, shutting down!", 10, true, hibernate)) { qApp->closeAllWindows(); } @@ -799,10 +895,11 @@ void MainWindow::init(void) //--------------------------------------- qDebug("[Validating binaries]"); - if(!BinariesCheckThread::check(m_sysinfo.data())) + QString failedPath; + if(!BinariesCheckThread::check(m_sysinfo.data(), &failedPath)) { - QMessageBox::critical(this, tr("Invalid File!"), tr("At least one required tool is missing or is not a valid Win32/Win64 binary.
Please re-install the program in order to fix the problem!
").replace("-", "−")); - qFatal("At least one required tool is missing or is not a valid Win32/Win64 binary!"); + QMessageBox::critical(this, tr("Invalid File!"), tr("At least one tool is missing or is not a valid Win32/Win64 binary:
%1

Please re-install the program in order to fix the problem!").replace("-", "−").arg(Qt::escape(QDir::toNativeSeparators(failedPath)))); + qFatal("At least one tool is missing or is not a valid Win32/Win64 binary. Program will exit now!"); } qDebug(" "); @@ -1302,18 +1399,22 @@ void MainWindow::closeEvent(QCloseEvent *e) //Save pending jobs for next time, if desired by user if(countPendingJobs() > 0) { - int ret = QMessageBox::question(this, tr("Jobs Are Pending"), tr("You still have pending jobs. How do you want to proceed?"), tr("Save Pending Jobs"), tr("Discard")); - if(ret == 0) + if (!m_preferences->getSaveQueueNoConfirm()) { - m_jobList->saveQueuedJobs(); + const int ret = QMessageBox::question(this, tr("Jobs Are Pending"), tr("You still have some pending jobs in your queue. How do you want to proceed?"), tr("Save Jobs"), tr("Always Save Jobs"), tr("Discard Jobs")); + if ((ret >= 0) && (ret <= 1)) + { + if (ret > 0) + { + m_preferences->setSaveQueueNoConfirm(true); + PreferencesModel::savePreferences(m_preferences.data()); + } + m_jobList->saveQueuedJobs(); + } } else { - if(QMessageBox::warning(this, tr("Jobs Are Pending"), tr("Do you really want to discard all pending jobs?"), QMessageBox::Yes | QMessageBox::No, QMessageBox::No) != QMessageBox::Yes) - { - e->ignore(); - return; - } + m_jobList->saveQueuedJobs(); } }