diff --git a/src/common/settings.h b/src/common/settings.h index 4ead68e66..3e28619d1 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -498,6 +498,13 @@ struct Values { Setting custom_bottom_height{240, "custom_bottom_height"}; Setting custom_second_layer_opacity{100, "custom_second_layer_opacity"}; + SwitchableSetting screen_top_stretch{false, "screen_top_stretch"}; + Setting screen_top_leftright_padding{0, "screen_top_leftright_padding"}; + Setting screen_top_topbottom_padding{0, "screen_top_topbottom_padding"}; + SwitchableSetting screen_bottom_stretch{false, "screen_bottom_stretch"}; + Setting screen_bottom_leftright_padding{0, "screen_bottom_leftright_padding"}; + Setting screen_bottom_topbottom_padding{0, "screen_bottom_topbottom_padding"}; + SwitchableSetting bg_red{0.f, "bg_red"}; SwitchableSetting bg_green{0.f, "bg_green"}; SwitchableSetting bg_blue{0.f, "bg_blue"}; diff --git a/src/core/frontend/framebuffer_layout.cpp b/src/core/frontend/framebuffer_layout.cpp index 56bab1155..fbb4667fc 100644 --- a/src/core/frontend/framebuffer_layout.cpp +++ b/src/core/frontend/framebuffer_layout.cpp @@ -173,9 +173,20 @@ FramebufferLayout SingleFrameLayout(u32 width, u32 height, bool swapped, bool up emulation_aspect_ratio = (swapped) ? BOT_SCREEN_ASPECT_RATIO : TOP_SCREEN_ASPECT_RATIO; } + const bool stretched = (Settings::values.screen_top_stretch.GetValue() && !swapped) || + (Settings::values.screen_bottom_stretch.GetValue() && swapped); float window_aspect_ratio = static_cast(height) / width; - if (window_aspect_ratio < emulation_aspect_ratio) { + if (stretched) { + top_screen = {Settings::values.screen_top_leftright_padding.GetValue(), + Settings::values.screen_top_topbottom_padding.GetValue(), + width - Settings::values.screen_top_leftright_padding.GetValue(), + height - Settings::values.screen_top_topbottom_padding.GetValue()}; + bot_screen = {Settings::values.screen_bottom_leftright_padding.GetValue(), + Settings::values.screen_bottom_topbottom_padding.GetValue(), + width - Settings::values.screen_bottom_leftright_padding.GetValue(), + height - Settings::values.screen_bottom_topbottom_padding.GetValue()}; + } else if (window_aspect_ratio < emulation_aspect_ratio) { top_screen = top_screen.TranslateX((screen_window_area.GetWidth() - top_screen.GetWidth()) / 2); bot_screen = diff --git a/src/lime/config.cpp b/src/lime/config.cpp index 165df98b6..e67b7ed9f 100644 --- a/src/lime/config.cpp +++ b/src/lime/config.cpp @@ -164,6 +164,7 @@ void Config::ReadValues() { ReadSetting("Layout", Settings::values.swap_screen); ReadSetting("Layout", Settings::values.upright_screen); ReadSetting("Layout", Settings::values.large_screen_proportion); + ReadSetting("Layout", Settings::values.custom_layout); ReadSetting("Layout", Settings::values.custom_top_x); ReadSetting("Layout", Settings::values.custom_top_y); @@ -175,6 +176,13 @@ void Config::ReadValues() { ReadSetting("Layout", Settings::values.custom_bottom_height); ReadSetting("Layout", Settings::values.custom_second_layer_opacity); + ReadSetting("Layout", Settings::values.screen_top_stretch); + ReadSetting("Layout", Settings::values.screen_top_leftright_padding); + ReadSetting("Layout", Settings::values.screen_top_topbottom_padding); + ReadSetting("Layout", Settings::values.screen_bottom_stretch); + ReadSetting("Layout", Settings::values.screen_bottom_leftright_padding); + ReadSetting("Layout", Settings::values.screen_bottom_topbottom_padding); + // Utility ReadSetting("Utility", Settings::values.dump_textures); ReadSetting("Utility", Settings::values.custom_textures); diff --git a/src/lime_qt/configuration/config.cpp b/src/lime_qt/configuration/config.cpp index 7453587b8..3aa60b225 100644 --- a/src/lime_qt/configuration/config.cpp +++ b/src/lime_qt/configuration/config.cpp @@ -518,6 +518,7 @@ void Config::ReadLayoutValues() { if (global) { ReadBasicSetting(Settings::values.mono_render_option); + ReadBasicSetting(Settings::values.custom_layout); ReadBasicSetting(Settings::values.custom_top_x); ReadBasicSetting(Settings::values.custom_top_y); @@ -528,6 +529,13 @@ void Config::ReadLayoutValues() { ReadBasicSetting(Settings::values.custom_bottom_width); ReadBasicSetting(Settings::values.custom_bottom_height); ReadBasicSetting(Settings::values.custom_second_layer_opacity); + + ReadBasicSetting(Settings::values.screen_top_stretch); + ReadBasicSetting(Settings::values.screen_top_leftright_padding); + ReadBasicSetting(Settings::values.screen_top_topbottom_padding); + ReadBasicSetting(Settings::values.screen_bottom_stretch); + ReadBasicSetting(Settings::values.screen_bottom_leftright_padding); + ReadBasicSetting(Settings::values.screen_bottom_topbottom_padding); } qt_config->endGroup(); @@ -1060,6 +1068,7 @@ void Config::SaveLayoutValues() { if (global) { WriteBasicSetting(Settings::values.mono_render_option); + WriteBasicSetting(Settings::values.custom_layout); WriteBasicSetting(Settings::values.custom_top_x); WriteBasicSetting(Settings::values.custom_top_y); @@ -1070,6 +1079,13 @@ void Config::SaveLayoutValues() { WriteBasicSetting(Settings::values.custom_bottom_width); WriteBasicSetting(Settings::values.custom_bottom_height); WriteBasicSetting(Settings::values.custom_second_layer_opacity); + + WriteBasicSetting(Settings::values.screen_top_stretch); + WriteBasicSetting(Settings::values.screen_top_leftright_padding); + WriteBasicSetting(Settings::values.screen_top_topbottom_padding); + WriteBasicSetting(Settings::values.screen_bottom_stretch); + WriteBasicSetting(Settings::values.screen_bottom_leftright_padding); + WriteBasicSetting(Settings::values.screen_bottom_topbottom_padding); } qt_config->endGroup(); diff --git a/src/lime_qt/configuration/configure_layout.cpp b/src/lime_qt/configuration/configure_layout.cpp index 64f9c905e..95c129f3b 100644 --- a/src/lime_qt/configuration/configure_layout.cpp +++ b/src/lime_qt/configuration/configure_layout.cpp @@ -18,25 +18,44 @@ ConfigureLayout::ConfigureLayout(QWidget* parent) SetupPerGameUI(); SetConfiguration(); - ui->layout_group->setEnabled(!Settings::values.custom_layout); + ui->large_screen_proportion->setEnabled( + (Settings::values.layout_option.GetValue() == Settings::LayoutOption::LargeScreen)); + connect(ui->layout_combobox, + static_cast(&QComboBox::currentIndexChanged), this, + [this](int currentIndex) { + ui->large_screen_proportion->setEnabled( + currentIndex == (uint)(Settings::LayoutOption::LargeScreen)); + }); ui->custom_layout_group->setEnabled( (Settings::values.layout_option.GetValue() == Settings::LayoutOption::CustomLayout)); connect(ui->layout_combobox, static_cast(&QComboBox::currentIndexChanged), this, [this](int currentIndex) { - ui->custom_layout_group->setEnabled(ui->layout_combobox->currentIndex() == + ui->custom_layout_group->setEnabled(currentIndex == (uint)(Settings::LayoutOption::CustomLayout)); }); - ui->large_screen_proportion->setEnabled( - (Settings::values.layout_option.GetValue() == Settings::LayoutOption::LargeScreen)); + ui->screen_top_leftright_padding->setEnabled(Settings::values.screen_top_stretch.GetValue()); + connect(ui->screen_top_stretch, static_cast(&QCheckBox::stateChanged), + this, + [this](bool checkState) { ui->screen_top_leftright_padding->setEnabled(checkState); }); + ui->screen_top_topbottom_padding->setEnabled(Settings::values.screen_top_stretch.GetValue()); + connect(ui->screen_top_stretch, static_cast(&QCheckBox::stateChanged), + this, + [this](bool checkState) { ui->screen_top_topbottom_padding->setEnabled(checkState); }); + ui->screen_bottom_leftright_padding->setEnabled( + Settings::values.screen_bottom_topbottom_padding.GetValue()); connect( - ui->layout_combobox, static_cast(&QComboBox::currentIndexChanged), - this, [this](int currentIndex) { - ui->large_screen_proportion->setEnabled(ui->layout_combobox->currentIndex() == - (uint)(Settings::LayoutOption::LargeScreen)); - }); + ui->screen_bottom_stretch, static_cast(&QCheckBox::stateChanged), + this, + [this](bool checkState) { ui->screen_bottom_leftright_padding->setEnabled(checkState); }); + ui->screen_bottom_topbottom_padding->setEnabled( + Settings::values.screen_bottom_topbottom_padding.GetValue()); + connect( + ui->screen_bottom_stretch, static_cast(&QCheckBox::stateChanged), + this, + [this](bool checkState) { ui->screen_bottom_topbottom_padding->setEnabled(checkState); }); connect(ui->bg_button, &QPushButton::clicked, this, [this] { const QColor new_bg_color = QColorDialog::getColor(bg_color); @@ -66,6 +85,7 @@ void ConfigureLayout::SetConfiguration() { ui->toggle_swap_screen->setChecked(Settings::values.swap_screen.GetValue()); ui->toggle_upright_screen->setChecked(Settings::values.upright_screen.GetValue()); ui->large_screen_proportion->setValue(Settings::values.large_screen_proportion.GetValue()); + ui->custom_top_x->setValue(Settings::values.custom_top_x.GetValue()); ui->custom_top_y->setValue(Settings::values.custom_top_y.GetValue()); ui->custom_top_width->setValue(Settings::values.custom_top_width.GetValue()); @@ -76,6 +96,17 @@ void ConfigureLayout::SetConfiguration() { ui->custom_bottom_height->setValue(Settings::values.custom_bottom_height.GetValue()); ui->custom_second_layer_opacity->setValue( Settings::values.custom_second_layer_opacity.GetValue()); + + ui->screen_top_stretch->setChecked(Settings::values.screen_top_stretch.GetValue()); + ui->screen_top_leftright_padding->setValue( + Settings::values.screen_top_leftright_padding.GetValue()); + ui->screen_top_topbottom_padding->setValue( + Settings::values.screen_top_topbottom_padding.GetValue()); + ui->screen_bottom_stretch->setChecked(Settings::values.screen_bottom_stretch.GetValue()); + ui->screen_bottom_leftright_padding->setValue( + Settings::values.screen_bottom_leftright_padding.GetValue()); + ui->screen_bottom_topbottom_padding->setValue( + Settings::values.screen_bottom_topbottom_padding.GetValue()); bg_color = QColor::fromRgbF(Settings::values.bg_red.GetValue(), Settings::values.bg_green.GetValue(), Settings::values.bg_blue.GetValue()); @@ -102,6 +133,13 @@ void ConfigureLayout::ApplyConfiguration() { Settings::values.custom_bottom_height = ui->custom_bottom_height->value(); Settings::values.custom_second_layer_opacity = ui->custom_second_layer_opacity->value(); + Settings::values.screen_top_stretch = ui->screen_top_stretch->checkState(); + Settings::values.screen_top_leftright_padding = ui->screen_top_leftright_padding->value(); + Settings::values.screen_top_topbottom_padding = ui->screen_top_topbottom_padding->value(); + Settings::values.screen_bottom_stretch = ui->screen_bottom_stretch->checkState(); + Settings::values.screen_bottom_leftright_padding = ui->screen_bottom_leftright_padding->value(); + Settings::values.screen_bottom_topbottom_padding = ui->screen_bottom_topbottom_padding->value(); + ConfigurationShared::ApplyPerGameSetting(&Settings::values.layout_option, ui->layout_combobox); ConfigurationShared::ApplyPerGameSetting(&Settings::values.swap_screen, ui->toggle_swap_screen, swap_screen); diff --git a/src/lime_qt/configuration/configure_layout.ui b/src/lime_qt/configuration/configure_layout.ui index cca9e1186..34b30751d 100644 --- a/src/lime_qt/configuration/configure_layout.ui +++ b/src/lime_qt/configuration/configure_layout.ui @@ -177,219 +177,394 @@ + + + + + + + + 0 + 0 + + + + Custom Layout + + - - - - 0 - 0 - - - - Custom Layout - - - - - - - - Top Screen - - - - - - X Position - - - - - - - QAbstractSpinBox::NoButtons - - - 2147483647 - - - - - - - Y Position - - - - - - - QAbstractSpinBox::NoButtons - - - 2147483647 - - - - - - - Width - - - - - - - QAbstractSpinBox::NoButtons - - - 2147483647 - - - - - - - Height - - - - - - - QAbstractSpinBox::NoButtons - - - 2147483647 - - - - - - - - - - - 0 - 0 - - - - Bottom Screen - - - - - - X Position - - - - - - - QAbstractSpinBox::NoButtons - - - 2147483647 - - - - - - - Y Position - - - - - - - QAbstractSpinBox::NoButtons - - - 2147483647 - - - - - - - Width - - - - - - - QAbstractSpinBox::NoButtons - - - 2147483647 - - - - - - - Height - - - - - - - QAbstractSpinBox::NoButtons - - - 2147483647 - - - - - - - - - - - - + + + + + Top Screen + + + + - <html><head/><body><p>NOTE: Values are in pixels starting from the top left corner of the display. Positive numbers only.</p></body></html> + X Position - - - - - - - - <html><head/><body><p>Bottom Screen Opacity % (OpenGL Only)</p></body></html> - - - - - + + - QAbstractSpinBox::PlusMinus + QAbstractSpinBox::NoButtons - - 10 + + px - 100 + 2147483647 + + + + + + + Y Position + + + + + + + QAbstractSpinBox::NoButtons + + + px + + + 2147483647 + + + + + + + Width + + + + + + + QAbstractSpinBox::NoButtons + + + px + + + 2147483647 + + + + + + + Height + + + + + + + QAbstractSpinBox::NoButtons + + + px + + + 2147483647 - - - + + + + + + + 0 + 0 + + + + Bottom Screen + + + + + + X Position + + + + + + + QAbstractSpinBox::NoButtons + + + px + + + 2147483647 + + + + + + + Y Position + + + + + + + QAbstractSpinBox::NoButtons + + + px + + + 2147483647 + + + + + + + Width + + + + + + + QAbstractSpinBox::NoButtons + + + px + + + 2147483647 + + + + + + + Height + + + + + + + QAbstractSpinBox::NoButtons + + + px + + + 2147483647 + + + + + + + + + + + + + + <html><head/><body><p>Bottom Screen Opacity % (OpenGL Only)</p></body></html> + + + + + + + QAbstractSpinBox::PlusMinus + + + 10 + + + 100 + + + + + + + + + + + + + 0 + 0 + + + + Single Screen Layout + + + + + + + + Top Screen + + + + + + Stretch + + + + + + + QAbstractSpinBox::NoButtons + + + px + + + 2147483647 + + + + + + + Left/Right Padding + + + + + + + Top/Bottom Padding + + + + + + + QAbstractSpinBox::NoButtons + + + px + + + 2147483647 + + + + + + + + + + + + + + + + + + 0 + 0 + + + + Bottom Screen + + + + + + Left/Right Padding + + + + + + + Top/Bottom Padding + + + + + + + QAbstractSpinBox::NoButtons + + + px + + + 2147483647 + + + + + + + QAbstractSpinBox::NoButtons + + + px + + + 2147483647 + + + + + + + Stretch + + + + + + + + + + + + + + + + + + + + + Note: These settings affect the Single Screen and Separate Windows layouts + + + +