summaryrefslogtreecommitdiff
path: root/Source/Core/DolphinQt/Config/Graphics/AdvancedWidget.cpp
blob: 05ddd8406f838b88adbd31d482da8e4b0396c324 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
// Copyright 2017 Dolphin Emulator Project
// Licensed under GPLv2+
// Refer to the license.txt file included.

#include "DolphinQt/Config/Graphics/AdvancedWidget.h"

#include <QCheckBox>
#include <QGridLayout>
#include <QGroupBox>
#include <QLabel>
#include <QSpinBox>
#include <QVBoxLayout>

#include "Core/Config/GraphicsSettings.h"
#include "Core/Config/SYSCONFSettings.h"
#include "Core/ConfigManager.h"
#include "Core/Core.h"

#include "DolphinQt/Config/Graphics/GraphicsBool.h"
#include "DolphinQt/Config/Graphics/GraphicsChoice.h"
#include "DolphinQt/Config/Graphics/GraphicsInteger.h"
#include "DolphinQt/Config/Graphics/GraphicsWindow.h"
#include "DolphinQt/Settings.h"

#include "VideoCommon/VideoConfig.h"

AdvancedWidget::AdvancedWidget(GraphicsWindow* parent) : GraphicsWidget(parent)
{
  CreateWidgets();
  LoadSettings();
  ConnectWidgets();
  AddDescriptions();

  connect(parent, &GraphicsWindow::BackendChanged, this, &AdvancedWidget::OnBackendChanged);
  connect(&Settings::Instance(), &Settings::EmulationStateChanged, this,
          [=](Core::State state) { OnEmulationStateChanged(state != Core::State::Uninitialized); });

  OnBackendChanged();
  OnEmulationStateChanged(Core::GetState() != Core::State::Uninitialized);
}

void AdvancedWidget::CreateWidgets()
{
  auto* main_layout = new QVBoxLayout;

  // Debugging
  auto* debugging_box = new QGroupBox(tr("Debugging"));
  auto* debugging_layout = new QGridLayout();
  debugging_box->setLayout(debugging_layout);

  m_enable_wireframe = new GraphicsBool(tr("Enable Wireframe"), Config::GFX_ENABLE_WIREFRAME);
  m_show_statistics = new GraphicsBool(tr("Show Statistics"), Config::GFX_OVERLAY_STATS);
  m_enable_format_overlay =
      new GraphicsBool(tr("Texture Format Overlay"), Config::GFX_TEXFMT_OVERLAY_ENABLE);
  m_enable_api_validation =
      new GraphicsBool(tr("Enable API Validation Layers"), Config::GFX_ENABLE_VALIDATION_LAYER);

  debugging_layout->addWidget(m_enable_wireframe, 0, 0);
  debugging_layout->addWidget(m_show_statistics, 0, 1);
  debugging_layout->addWidget(m_enable_format_overlay, 1, 0);
  debugging_layout->addWidget(m_enable_api_validation, 1, 1);

  // Utility
  auto* utility_box = new QGroupBox(tr("Utility"));
  auto* utility_layout = new QGridLayout();
  utility_box->setLayout(utility_layout);

  m_load_custom_textures = new GraphicsBool(tr("Load Custom Textures"), Config::GFX_HIRES_TEXTURES);
  m_prefetch_custom_textures =
      new GraphicsBool(tr("Prefetch Custom Textures"), Config::GFX_CACHE_HIRES_TEXTURES);
  m_dump_efb_target = new GraphicsBool(tr("Dump EFB Target"), Config::GFX_DUMP_EFB_TARGET);
  m_disable_vram_copies =
      new GraphicsBool(tr("Disable EFB VRAM Copies"), Config::GFX_HACK_DISABLE_COPY_TO_VRAM);

  utility_layout->addWidget(m_load_custom_textures, 0, 0);
  utility_layout->addWidget(m_prefetch_custom_textures, 0, 1);

  utility_layout->addWidget(m_disable_vram_copies, 1, 0);

  utility_layout->addWidget(m_dump_efb_target, 1, 1);

  // Freelook
  auto* freelook_box = new QGroupBox(tr("Free Look"));
  auto* freelook_layout = new QGridLayout();
  freelook_box->setLayout(freelook_layout);

  m_enable_freelook = new GraphicsBool(tr("Enable"), Config::GFX_FREE_LOOK);
  m_freelook_control_type = new GraphicsChoice({tr("Six Axis"), tr("First Person"), tr("Orbital")},
                                               Config::GFX_FREE_LOOK_CONTROL_TYPE);

  freelook_layout->addWidget(m_enable_freelook, 0, 0);
  freelook_layout->addWidget(new QLabel(tr("Control Type:")), 1, 0);
  freelook_layout->addWidget(m_freelook_control_type, 1, 1);

  // Texture dumping
  auto* texture_dump_box = new QGroupBox(tr("Texture Dumping"));
  auto* texture_dump_layout = new QGridLayout();
  texture_dump_box->setLayout(texture_dump_layout);
  m_dump_textures = new GraphicsBool(tr("Enable"), Config::GFX_DUMP_TEXTURES);
  m_dump_base_textures = new GraphicsBool(tr("Dump Base Textures"), Config::GFX_DUMP_BASE_TEXTURES);
  m_dump_mip_textures = new GraphicsBool(tr("Dump Mip Maps"), Config::GFX_DUMP_MIP_TEXTURES);

  texture_dump_layout->addWidget(m_dump_textures, 0, 0);

  texture_dump_layout->addWidget(m_dump_base_textures, 1, 0);
  texture_dump_layout->addWidget(m_dump_mip_textures, 1, 1);

  // Frame dumping
  auto* dump_box = new QGroupBox(tr("Frame Dumping"));
  auto* dump_layout = new QGridLayout();
  dump_box->setLayout(dump_layout);

  m_use_fullres_framedumps = new GraphicsBool(tr("Dump at Internal Resolution"),
                                              Config::GFX_INTERNAL_RESOLUTION_FRAME_DUMPS);
  m_dump_use_ffv1 = new GraphicsBool(tr("Use Lossless Codec (FFV1)"), Config::GFX_USE_FFV1);
  m_dump_bitrate = new GraphicsInteger(0, 1000000, Config::GFX_BITRATE_KBPS, 1000);

  dump_layout->addWidget(m_use_fullres_framedumps, 0, 0);
#if defined(HAVE_FFMPEG)
  dump_layout->addWidget(m_dump_use_ffv1, 0, 1);
  dump_layout->addWidget(new QLabel(tr("Bitrate (kbps):")), 1, 0);
  dump_layout->addWidget(m_dump_bitrate, 1, 1);
#endif

  // Misc.
  auto* misc_box = new QGroupBox(tr("Misc"));
  auto* misc_layout = new QGridLayout();
  misc_box->setLayout(misc_layout);

  m_enable_cropping = new GraphicsBool(tr("Crop"), Config::GFX_CROP);
  m_enable_prog_scan = new QCheckBox(tr("Enable Progressive Scan"));
  m_backend_multithreading =
      new GraphicsBool(tr("Backend Multithreading"), Config::GFX_BACKEND_MULTITHREADING);

  misc_layout->addWidget(m_enable_cropping, 0, 0);
  misc_layout->addWidget(m_enable_prog_scan, 0, 1);
  misc_layout->addWidget(m_backend_multithreading, 1, 0);
#ifdef _WIN32
  m_borderless_fullscreen =
      new GraphicsBool(tr("Borderless Fullscreen"), Config::GFX_BORDERLESS_FULLSCREEN);

  misc_layout->addWidget(m_borderless_fullscreen, 1, 1);
#endif

  // Experimental.
  auto* experimental_box = new QGroupBox(tr("Experimental"));
  auto* experimental_layout = new QGridLayout();
  experimental_box->setLayout(experimental_layout);

  m_defer_efb_access_invalidation =
      new GraphicsBool(tr("Defer EFB Cache Invalidation"), Config::GFX_HACK_EFB_DEFER_INVALIDATION);

  experimental_layout->addWidget(m_defer_efb_access_invalidation, 0, 0);

  main_layout->addWidget(debugging_box);
  main_layout->addWidget(utility_box);
  main_layout->addWidget(freelook_box);
  main_layout->addWidget(texture_dump_box);
  main_layout->addWidget(dump_box);
  main_layout->addWidget(misc_box);
  main_layout->addWidget(experimental_box);
  main_layout->addStretch();

  setLayout(main_layout);
}

void AdvancedWidget::ConnectWidgets()
{
  connect(m_load_custom_textures, &QCheckBox::toggled, this, &AdvancedWidget::SaveSettings);
  connect(m_dump_use_ffv1, &QCheckBox::toggled, this, &AdvancedWidget::SaveSettings);
  connect(m_enable_prog_scan, &QCheckBox::toggled, this, &AdvancedWidget::SaveSettings);
  connect(m_enable_freelook, &QCheckBox::toggled, this, &AdvancedWidget::SaveSettings);
  connect(m_dump_textures, &QCheckBox::toggled, this, &AdvancedWidget::SaveSettings);
}

void AdvancedWidget::LoadSettings()
{
  m_prefetch_custom_textures->setEnabled(Config::Get(Config::GFX_HIRES_TEXTURES));
  m_dump_bitrate->setEnabled(!Config::Get(Config::GFX_USE_FFV1));

  m_enable_prog_scan->setChecked(Config::Get(Config::SYSCONF_PROGRESSIVE_SCAN));

  m_freelook_control_type->setEnabled(Config::Get(Config::GFX_FREE_LOOK));
  m_dump_mip_textures->setEnabled(Config::Get(Config::GFX_DUMP_TEXTURES));
  m_dump_base_textures->setEnabled(Config::Get(Config::GFX_DUMP_TEXTURES));
}

void AdvancedWidget::SaveSettings()
{
  m_prefetch_custom_textures->setEnabled(Config::Get(Config::GFX_HIRES_TEXTURES));
  m_dump_bitrate->setEnabled(!Config::Get(Config::GFX_USE_FFV1));

  Config::SetBase(Config::SYSCONF_PROGRESSIVE_SCAN, m_enable_prog_scan->isChecked());

  m_freelook_control_type->setEnabled(Config::Get(Config::GFX_FREE_LOOK));
  m_dump_mip_textures->setEnabled(Config::Get(Config::GFX_DUMP_TEXTURES));
  m_dump_base_textures->setEnabled(Config::Get(Config::GFX_DUMP_TEXTURES));
}

void AdvancedWidget::OnBackendChanged()
{
}

void AdvancedWidget::OnEmulationStateChanged(bool running)
{
  m_enable_prog_scan->setEnabled(!running);
}

void AdvancedWidget::AddDescriptions()
{
  static const char TR_WIREFRAME_DESCRIPTION[] =
      QT_TR_NOOP("Renders the scene as a wireframe.\n\nIf unsure, leave this unchecked.");
  static const char TR_SHOW_STATS_DESCRIPTION[] =
      QT_TR_NOOP("Shows various rendering statistics.\n\nIf unsure, leave this unchecked.");
  static const char TR_TEXTURE_FORMAT_DESCRIPTION[] = QT_TR_NOOP(
      "Modifies textures to show the format they're encoded in.\n\nMay require an emulation "
      "reset to apply.\n\nIf unsure, leave this unchecked.");
  static const char TR_VALIDATION_LAYER_DESCRIPTION[] =
      QT_TR_NOOP("Enables validation of API calls made by the video backend, which may assist in "
                 "debugging graphical issues.\n\nIf unsure, leave this unchecked.");
  static const char TR_DUMP_TEXTURE_DESCRIPTION[] =
      QT_TR_NOOP("Dumps decoded game textures based on the other flags to "
                 "User/Dump/Textures/<game_id>/.\n\nIf unsure, leave "
                 "this unchecked.");
  static const char TR_DUMP_MIP_TEXTURE_DESCRIPTION[] = QT_TR_NOOP(
      "Whether to dump mipmapped game textures to "
      "User/Dump/Textures/<game_id>/.  This includes arbitrary mipmapped textures if 'Arbitrary "
      "Mipmap Detection' is enabled in Enhancements.\n\nIf unsure, leave "
      "this checked.");
  static const char TR_DUMP_BASE_TEXTURE_DESCRIPTION[] = QT_TR_NOOP(
      "Whether to dump base game textures to "
      "User/Dump/Textures/<game_id>/.  This includes arbitrary base textures if 'Arbitrary "
      "Mipmap Detection' is enabled in Enhancements.\n\nIf unsure, leave "
      "this checked.");
  static const char TR_LOAD_CUSTOM_TEXTURE_DESCRIPTION[] = QT_TR_NOOP(
      "Loads custom textures from User/Load/Textures/<game_id>/.\n\nIf unsure, leave this "
      "unchecked.");
  static const char TR_CACHE_CUSTOM_TEXTURE_DESCRIPTION[] = QT_TR_NOOP(
      "Caches custom textures to system RAM on startup.\n\nThis can require exponentially "
      "more RAM but fixes possible stuttering.\n\nIf unsure, leave this unchecked.");
  static const char TR_DUMP_EFB_DESCRIPTION[] = QT_TR_NOOP(
      "Dumps the contents of EFB copies to User/Dump/Textures/.\n\nIf unsure, leave this "
      "unchecked.");
  static const char TR_DISABLE_VRAM_COPIES_DESCRIPTION[] =
      QT_TR_NOOP("Disables the VRAM copy of the EFB, forcing a round-trip to RAM. Inhibits all "
                 "upscaling.\n\nIf unsure, leave this unchecked.");
  static const char TR_INTERNAL_RESOLUTION_FRAME_DUMPING_DESCRIPTION[] = QT_TR_NOOP(
      "Creates frame dumps and screenshots at the internal resolution of the renderer, rather than "
      "the size of the window it is displayed within.\n\nIf the aspect ratio is widescreen, the "
      "output image will be scaled horizontally to preserve the vertical resolution.\n\nIf "
      "unsure, leave this unchecked.");
#if defined(HAVE_FFMPEG)
  static const char TR_USE_FFV1_DESCRIPTION[] =
      QT_TR_NOOP("Encodes frame dumps using the FFV1 codec.\n\nIf unsure, leave this unchecked.");
#endif
  static const char TR_FREE_LOOK_DESCRIPTION[] = QT_TR_NOOP(
      "Allows manipulation of the in-game camera. Move the mouse while holding the right button "
      "to pan or middle button to roll.\n\nUse the WASD keys while holding SHIFT to move the "
      "camera. Press SHIFT+2 to increase speed or SHIFT+1 to decrease speed. Press SHIFT+R "
      "to reset the camera or SHIFT+F to reset the speed.\n\nIf unsure, leave this unchecked. ");
  static const char TR_FREE_LOOK_CONTROL_TYPE_DESCRIPTION[] = QT_TR_NOOP(
      "Changes the in-game camera type during freelook.\n\n"
      "Six Axis: Offers full camera control on all axes, akin to moving a spacecraft in zero "
      "gravity. This is the most powerful freelook option but is the most challenging to use.\n"
      "First Person: Controls the free camera similarly to a first person video game. The camera "
      "can rotate and travel, but roll is impossible. Easy to use, but limiting.\n"
      "Orbital: Rotates the free camera around the original camera. Has no lateral movement, only "
      "rotation and you may zoom up to the camera's origin point.");
  static const char TR_CROPPING_DESCRIPTION[] =
      QT_TR_NOOP("Crops the picture from its native aspect ratio to 4:3 or "
                 "16:9.\n\nIf unsure, leave this unchecked.");
  static const char TR_PROGRESSIVE_SCAN_DESCRIPTION[] = QT_TR_NOOP(
      "Enables progressive scan if supported by the emulated software. Most games don't have "
      "any issue with this.\n\nIf unsure, leave this unchecked.");
  static const char TR_BACKEND_MULTITHREADING_DESCRIPTION[] =
      QT_TR_NOOP("Enables multithreaded command submission in backends where supported. Enabling "
                 "this option may result in a performance improvement on systems with more than "
                 "two CPU cores. Currently, this is limited to the Vulkan backend.\n\nIf unsure, "
                 "leave this checked.");
  static const char TR_DEFER_EFB_ACCESS_INVALIDATION_DESCRIPTION[] = QT_TR_NOOP(
      "Defers invalidation of the EFB access cache until a GPU synchronization command "
      "is executed. If disabled, the cache will be invalidated with every draw call. "
      "\n\nMay improve performance in some games which rely on CPU EFB Access at the cost "
      "of stability.\n\nIf unsure, leave this unchecked.");

#ifdef _WIN32
  static const char TR_BORDERLESS_FULLSCREEN_DESCRIPTION[] = QT_TR_NOOP(
      "Implements fullscreen mode with a borderless window spanning the whole screen instead of "
      "using exclusive mode. Allows for faster transitions between fullscreen and windowed mode, "
      "but slightly increases input latency, makes movement less smooth and slightly decreases "
      "performance.\n\nIf unsure, leave this unchecked.");
#endif

  AddDescription(m_enable_wireframe, TR_WIREFRAME_DESCRIPTION);
  AddDescription(m_show_statistics, TR_SHOW_STATS_DESCRIPTION);
  AddDescription(m_enable_format_overlay, TR_TEXTURE_FORMAT_DESCRIPTION);
  AddDescription(m_enable_api_validation, TR_VALIDATION_LAYER_DESCRIPTION);
  AddDescription(m_dump_textures, TR_DUMP_TEXTURE_DESCRIPTION);
  AddDescription(m_dump_mip_textures, TR_DUMP_MIP_TEXTURE_DESCRIPTION);
  AddDescription(m_dump_base_textures, TR_DUMP_BASE_TEXTURE_DESCRIPTION);
  AddDescription(m_load_custom_textures, TR_LOAD_CUSTOM_TEXTURE_DESCRIPTION);
  AddDescription(m_prefetch_custom_textures, TR_CACHE_CUSTOM_TEXTURE_DESCRIPTION);
  AddDescription(m_dump_efb_target, TR_DUMP_EFB_DESCRIPTION);
  AddDescription(m_disable_vram_copies, TR_DISABLE_VRAM_COPIES_DESCRIPTION);
  AddDescription(m_use_fullres_framedumps, TR_INTERNAL_RESOLUTION_FRAME_DUMPING_DESCRIPTION);
#ifdef HAVE_FFMPEG
  AddDescription(m_dump_use_ffv1, TR_USE_FFV1_DESCRIPTION);
#endif
  AddDescription(m_enable_cropping, TR_CROPPING_DESCRIPTION);
  AddDescription(m_enable_prog_scan, TR_PROGRESSIVE_SCAN_DESCRIPTION);
  AddDescription(m_enable_freelook, TR_FREE_LOOK_DESCRIPTION);
  AddDescription(m_freelook_control_type, TR_FREE_LOOK_CONTROL_TYPE_DESCRIPTION);
  AddDescription(m_backend_multithreading, TR_BACKEND_MULTITHREADING_DESCRIPTION);
#ifdef _WIN32
  AddDescription(m_borderless_fullscreen, TR_BORDERLESS_FULLSCREEN_DESCRIPTION);
#endif
  AddDescription(m_defer_efb_access_invalidation, TR_DEFER_EFB_ACCESS_INVALIDATION_DESCRIPTION);
}