#include "graphicspage.hpp" #include "sdlinit.hpp" #include #include #include #include #ifdef MAC_OS_X_VERSION_MIN_REQUIRED #undef MAC_OS_X_VERSION_MIN_REQUIRED // We need to do this because of Qt: https://bugreports.qt-project.org/browse/QTBUG-22154 #define MAC_OS_X_VERSION_MIN_REQUIRED __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ #endif // MAC_OS_X_VERSION_MIN_REQUIRED #include #include Launcher::GraphicsPage::GraphicsPage(QWidget* parent) : QWidget(parent) { setObjectName("GraphicsPage"); setupUi(this); // Set the maximum res we can set in windowed mode QRect res = getMaximumResolution(); customWidthSpinBox->setMaximum(res.width()); customHeightSpinBox->setMaximum(res.height()); connect(windowModeComboBox, qOverload(&QComboBox::currentIndexChanged), this, &GraphicsPage::slotFullScreenChanged); connect(standardRadioButton, &QRadioButton::toggled, this, &GraphicsPage::slotStandardToggled); connect(screenComboBox, qOverload(&QComboBox::currentIndexChanged), this, &GraphicsPage::screenChanged); connect(framerateLimitCheckBox, &QCheckBox::toggled, this, &GraphicsPage::slotFramerateLimitToggled); } bool Launcher::GraphicsPage::setupSDL() { bool sdlConnectSuccessful = initSDL(); if (!sdlConnectSuccessful) { return false; } int displays = SDL_GetNumVideoDisplays(); if (displays < 0) { QMessageBox msgBox; msgBox.setWindowTitle(tr("Error receiving number of screens")); msgBox.setIcon(QMessageBox::Critical); msgBox.setStandardButtons(QMessageBox::Ok); msgBox.setText( tr("
SDL_GetNumVideoDisplays failed:

") + QString::fromUtf8(SDL_GetError()) + "
"); msgBox.exec(); return false; } screenComboBox->clear(); mResolutionsPerScreen.clear(); for (int i = 0; i < displays; i++) { mResolutionsPerScreen.append(getAvailableResolutions(i)); screenComboBox->addItem(QString(tr("Screen ")) + QString::number(i + 1)); } screenChanged(0); // Disconnect from SDL processes quitSDL(); return true; } bool Launcher::GraphicsPage::loadSettings() { if (!setupSDL()) return false; // Visuals const int vsync = Settings::video().mVsyncMode; vSyncComboBox->setCurrentIndex(vsync); const Settings::WindowMode windowMode = Settings::video().mWindowMode; windowModeComboBox->setCurrentIndex(static_cast(windowMode)); handleWindowModeChange(windowMode); if (Settings::video().mWindowBorder) windowBorderCheckBox->setCheckState(Qt::Checked); // aaValue is the actual value (0, 1, 2, 4, 8, 16) const int aaValue = Settings::video().mAntialiasing; // aaIndex is the index into the allowed values in the pull down. const int aaIndex = antiAliasingComboBox->findText(QString::number(aaValue)); if (aaIndex != -1) antiAliasingComboBox->setCurrentIndex(aaIndex); const int width = Settings::video().mResolutionX; const int height = Settings::video().mResolutionY; QString resolution = QString::number(width) + QString(" × ") + QString::number(height); screenComboBox->setCurrentIndex(Settings::video().mScreen); int resIndex = resolutionComboBox->findText(resolution, Qt::MatchStartsWith); if (resIndex != -1) { standardRadioButton->toggle(); resolutionComboBox->setCurrentIndex(resIndex); } else { customRadioButton->toggle(); customWidthSpinBox->setValue(width); customHeightSpinBox->setValue(height); } const float fpsLimit = Settings::video().mFramerateLimit; if (fpsLimit != 0) { framerateLimitCheckBox->setCheckState(Qt::Checked); framerateLimitSpinBox->setValue(fpsLimit); } return true; } void Launcher::GraphicsPage::saveSettings() { // Visuals Settings::video().mVsyncMode.set(static_cast(vSyncComboBox->currentIndex())); Settings::video().mWindowMode.set(static_cast(windowModeComboBox->currentIndex())); Settings::video().mWindowBorder.set(windowBorderCheckBox->checkState() == Qt::Checked); Settings::video().mAntialiasing.set(antiAliasingComboBox->currentText().toInt()); int cWidth = 0; int cHeight = 0; if (standardRadioButton->isChecked()) { QRegularExpression resolutionRe("^(\\d+) × (\\d+)"); QRegularExpressionMatch match = resolutionRe.match(resolutionComboBox->currentText().simplified()); if (match.hasMatch()) { cWidth = match.captured(1).toInt(); cHeight = match.captured(2).toInt(); } } else { cWidth = customWidthSpinBox->value(); cHeight = customHeightSpinBox->value(); } Settings::video().mResolutionX.set(cWidth); Settings::video().mResolutionY.set(cHeight); Settings::video().mScreen.set(screenComboBox->currentIndex()); if (framerateLimitCheckBox->checkState() != Qt::Unchecked) { Settings::video().mFramerateLimit.set(framerateLimitSpinBox->value()); } else if (Settings::video().mFramerateLimit != 0) { Settings::video().mFramerateLimit.set(0); } } QStringList Launcher::GraphicsPage::getAvailableResolutions(int screen) { QStringList result; SDL_DisplayMode mode; int modeIndex, modes = SDL_GetNumDisplayModes(screen); if (modes < 0) { QMessageBox msgBox; msgBox.setWindowTitle(tr("Error receiving resolutions")); msgBox.setIcon(QMessageBox::Critical); msgBox.setStandardButtons(QMessageBox::Ok); msgBox.setText( tr("
SDL_GetNumDisplayModes failed:

") + QString::fromUtf8(SDL_GetError()) + "
"); msgBox.exec(); return result; } for (modeIndex = 0; modeIndex < modes; modeIndex++) { if (SDL_GetDisplayMode(screen, modeIndex, &mode) < 0) { QMessageBox msgBox; msgBox.setWindowTitle(tr("Error receiving resolutions")); msgBox.setIcon(QMessageBox::Critical); msgBox.setStandardButtons(QMessageBox::Ok); msgBox.setText( tr("
SDL_GetDisplayMode failed:

") + QString::fromUtf8(SDL_GetError()) + "
"); msgBox.exec(); return result; } auto str = Misc::getResolutionText(mode.w, mode.h, "%i × %i (%i:%i)"); result.append(QString(str.c_str())); } result.removeDuplicates(); return result; } QRect Launcher::GraphicsPage::getMaximumResolution() { QRect max; for (QScreen* screen : QGuiApplication::screens()) { QRect res = screen->geometry(); if (res.width() > max.width()) max.setWidth(res.width()); if (res.height() > max.height()) max.setHeight(res.height()); } return max; } void Launcher::GraphicsPage::screenChanged(int screen) { if (screen >= 0) { resolutionComboBox->clear(); resolutionComboBox->addItems(mResolutionsPerScreen[screen]); } } void Launcher::GraphicsPage::slotFullScreenChanged(int mode) { handleWindowModeChange(static_cast(mode)); } void Launcher::GraphicsPage::handleWindowModeChange(Settings::WindowMode mode) { if (mode == Settings::WindowMode::Fullscreen || mode == Settings::WindowMode::WindowedFullscreen) { standardRadioButton->toggle(); customRadioButton->setEnabled(false); customWidthSpinBox->setEnabled(false); customHeightSpinBox->setEnabled(false); windowBorderCheckBox->setEnabled(false); } else { customRadioButton->setEnabled(true); customWidthSpinBox->setEnabled(true); customHeightSpinBox->setEnabled(true); windowBorderCheckBox->setEnabled(true); } } void Launcher::GraphicsPage::slotStandardToggled(bool checked) { if (checked) { resolutionComboBox->setEnabled(true); customWidthSpinBox->setEnabled(false); customHeightSpinBox->setEnabled(false); } else { resolutionComboBox->setEnabled(false); customWidthSpinBox->setEnabled(true); customHeightSpinBox->setEnabled(true); } } void Launcher::GraphicsPage::slotFramerateLimitToggled(bool checked) { framerateLimitSpinBox->setEnabled(checked); }