diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/citra_qt/main.cpp | 95 | ||||
| -rw-r--r-- | src/citra_qt/main.h | 7 | ||||
| -rw-r--r-- | src/citra_qt/main.ui | 7 |
3 files changed, 91 insertions, 18 deletions
diff --git a/src/citra_qt/main.cpp b/src/citra_qt/main.cpp index 4c3edf87a..a1a4865bd 100644 --- a/src/citra_qt/main.cpp +++ b/src/citra_qt/main.cpp | |||
| @@ -7,6 +7,7 @@ | |||
| 7 | #include <QtGui> | 7 | #include <QtGui> |
| 8 | #include <QDesktopWidget> | 8 | #include <QDesktopWidget> |
| 9 | #include <QFileDialog> | 9 | #include <QFileDialog> |
| 10 | #include <QMessageBox> | ||
| 10 | #include "qhexedit.h" | 11 | #include "qhexedit.h" |
| 11 | #include "main.h" | 12 | #include "main.h" |
| 12 | 13 | ||
| @@ -140,6 +141,16 @@ GMainWindow::GMainWindow() : emu_thread(nullptr) | |||
| 140 | ui.actionDisplay_widget_title_bars->setChecked(settings.value("displayTitleBars", true).toBool()); | 141 | ui.actionDisplay_widget_title_bars->setChecked(settings.value("displayTitleBars", true).toBool()); |
| 141 | OnDisplayTitleBars(ui.actionDisplay_widget_title_bars->isChecked()); | 142 | OnDisplayTitleBars(ui.actionDisplay_widget_title_bars->isChecked()); |
| 142 | 143 | ||
| 144 | // Prepare actions for recent files | ||
| 145 | for (int i = 0; i < max_recent_files_item; ++i) { | ||
| 146 | actions_recent_files[i] = new QAction(this); | ||
| 147 | actions_recent_files[i]->setVisible(false); | ||
| 148 | connect(actions_recent_files[i], SIGNAL(triggered()), this, SLOT(OnMenuRecentFile())); | ||
| 149 | |||
| 150 | ui.menu_recent_files->addAction(actions_recent_files[i]); | ||
| 151 | } | ||
| 152 | UpdateRecentFiles(); | ||
| 153 | |||
| 143 | // Setup connections | 154 | // Setup connections |
| 144 | connect(ui.action_Load_File, SIGNAL(triggered()), this, SLOT(OnMenuLoadFile())); | 155 | connect(ui.action_Load_File, SIGNAL(triggered()), this, SLOT(OnMenuLoadFile())); |
| 145 | connect(ui.action_Load_Symbol_Map, SIGNAL(triggered()), this, SLOT(OnMenuLoadSymbolMap())); | 156 | connect(ui.action_Load_Symbol_Map, SIGNAL(triggered()), this, SLOT(OnMenuLoadSymbolMap())); |
| @@ -213,6 +224,10 @@ void GMainWindow::OnDisplayTitleBars(bool show) | |||
| 213 | void GMainWindow::BootGame(const std::string& filename) { | 224 | void GMainWindow::BootGame(const std::string& filename) { |
| 214 | LOG_INFO(Frontend, "Citra starting...\n"); | 225 | LOG_INFO(Frontend, "Citra starting...\n"); |
| 215 | 226 | ||
| 227 | // Shutdown previous session if the emu thread is still active... | ||
| 228 | if (emu_thread != nullptr) | ||
| 229 | ShutdownGame(); | ||
| 230 | |||
| 216 | // Initialize the core emulation | 231 | // Initialize the core emulation |
| 217 | System::Init(render_window); | 232 | System::Init(render_window); |
| 218 | 233 | ||
| @@ -272,18 +287,43 @@ void GMainWindow::ShutdownGame() { | |||
| 272 | render_window->hide(); | 287 | render_window->hide(); |
| 273 | } | 288 | } |
| 274 | 289 | ||
| 275 | void GMainWindow::OnMenuLoadFile() | 290 | void GMainWindow::UpdateRecentFiles() { |
| 276 | { | 291 | QSettings settings; |
| 292 | QStringList recent_files = settings.value("recentFiles").toStringList(); | ||
| 293 | |||
| 294 | unsigned int num_recent_files = std::min(recent_files.size(), static_cast<int>(max_recent_files_item)); | ||
| 295 | |||
| 296 | for (unsigned int i = 0; i < num_recent_files; i++) { | ||
| 297 | QString text = QString("&%1. %2").arg(i + 1).arg(QFileInfo(recent_files[i]).fileName()); | ||
| 298 | actions_recent_files[i]->setText(text); | ||
| 299 | actions_recent_files[i]->setData(recent_files[i]); | ||
| 300 | actions_recent_files[i]->setVisible(true); | ||
| 301 | } | ||
| 302 | |||
| 303 | for (int j = num_recent_files; j < max_recent_files_item; ++j) { | ||
| 304 | actions_recent_files[j]->setVisible(false); | ||
| 305 | } | ||
| 306 | |||
| 307 | // Grey out the recent files menu if the list is empty | ||
| 308 | if (num_recent_files == 0) { | ||
| 309 | ui.menu_recent_files->setEnabled(false); | ||
| 310 | } else { | ||
| 311 | ui.menu_recent_files->setEnabled(true); | ||
| 312 | } | ||
| 313 | } | ||
| 314 | |||
| 315 | void GMainWindow::OnMenuLoadFile() { | ||
| 277 | QSettings settings; | 316 | QSettings settings; |
| 278 | QString rom_path = settings.value("romsPath", QString()).toString(); | 317 | QString rom_path = settings.value("romsPath", QString()).toString(); |
| 279 | 318 | ||
| 280 | QString filename = QFileDialog::getOpenFileName(this, tr("Load File"), rom_path, tr("3DS executable (*.3ds *.3dsx *.elf *.axf *.cci *.cxi)")); | 319 | QString filename = QFileDialog::getOpenFileName(this, tr("Load File"), rom_path, tr("3DS executable (*.3ds *.3dsx *.elf *.axf *.cci *.cxi)")); |
| 281 | if (filename.size()) { | 320 | if (filename.size()) { |
| 282 | settings.setValue("romsPath", QFileInfo(filename).path()); | 321 | settings.setValue("romsPath", QFileInfo(filename).path()); |
| 283 | 322 | // Update recent files list | |
| 284 | // Shutdown previous session if the emu thread is still active... | 323 | QStringList recent_files = settings.value("recentFiles").toStringList(); |
| 285 | if (emu_thread != nullptr) | 324 | recent_files.prepend(filename); |
| 286 | ShutdownGame(); | 325 | settings.setValue("recentFiles", recent_files); |
| 326 | UpdateRecentFiles(); // Update UI | ||
| 287 | 327 | ||
| 288 | BootGame(filename.toLatin1().data()); | 328 | BootGame(filename.toLatin1().data()); |
| 289 | } | 329 | } |
| @@ -301,8 +341,32 @@ void GMainWindow::OnMenuLoadSymbolMap() { | |||
| 301 | } | 341 | } |
| 302 | } | 342 | } |
| 303 | 343 | ||
| 304 | void GMainWindow::OnStartGame() | 344 | void GMainWindow::OnMenuRecentFile() { |
| 305 | { | 345 | QAction* action = qobject_cast<QAction*>(sender()); |
| 346 | assert(action); | ||
| 347 | |||
| 348 | QString filename = action->data().toString(); | ||
| 349 | QFileInfo file_info(filename); | ||
| 350 | if (file_info.exists()) { | ||
| 351 | BootGame(filename.toLatin1().data()); | ||
| 352 | } else { | ||
| 353 | // Display an error message and remove the file from the list. | ||
| 354 | QMessageBox::information(this, tr("File not found"), tr("File \"%1\" not found").arg(filename)); | ||
| 355 | |||
| 356 | QSettings settings; | ||
| 357 | QStringList recent_files = settings.value("recentFiles").toStringList(); | ||
| 358 | recent_files.removeOne(filename); | ||
| 359 | settings.setValue("recentFiles", recent_files); | ||
| 360 | |||
| 361 | action->setVisible(false); | ||
| 362 | // Grey out the recent files menu if the list is empty | ||
| 363 | if (ui.menu_recent_files->isEmpty()) { | ||
| 364 | ui.menu_recent_files->setEnabled(false); | ||
| 365 | } | ||
| 366 | } | ||
| 367 | } | ||
| 368 | |||
| 369 | void GMainWindow::OnStartGame() { | ||
| 306 | emu_thread->SetRunning(true); | 370 | emu_thread->SetRunning(true); |
| 307 | 371 | ||
| 308 | ui.action_Start->setEnabled(false); | 372 | ui.action_Start->setEnabled(false); |
| @@ -312,8 +376,7 @@ void GMainWindow::OnStartGame() | |||
| 312 | ui.action_Stop->setEnabled(true); | 376 | ui.action_Stop->setEnabled(true); |
| 313 | } | 377 | } |
| 314 | 378 | ||
| 315 | void GMainWindow::OnPauseGame() | 379 | void GMainWindow::OnPauseGame() { |
| 316 | { | ||
| 317 | emu_thread->SetRunning(false); | 380 | emu_thread->SetRunning(false); |
| 318 | 381 | ||
| 319 | ui.action_Start->setEnabled(true); | 382 | ui.action_Start->setEnabled(true); |
| @@ -325,8 +388,7 @@ void GMainWindow::OnStopGame() { | |||
| 325 | ShutdownGame(); | 388 | ShutdownGame(); |
| 326 | } | 389 | } |
| 327 | 390 | ||
| 328 | void GMainWindow::OnOpenHotkeysDialog() | 391 | void GMainWindow::OnOpenHotkeysDialog() { |
| 329 | { | ||
| 330 | GHotkeysDialog dialog(this); | 392 | GHotkeysDialog dialog(this); |
| 331 | dialog.exec(); | 393 | dialog.exec(); |
| 332 | } | 394 | } |
| @@ -358,13 +420,11 @@ void GMainWindow::ToggleWindowMode() { | |||
| 358 | } | 420 | } |
| 359 | } | 421 | } |
| 360 | 422 | ||
| 361 | void GMainWindow::OnConfigure() | 423 | void GMainWindow::OnConfigure() { |
| 362 | { | ||
| 363 | //GControllerConfigDialog* dialog = new GControllerConfigDialog(controller_ports, this); | 424 | //GControllerConfigDialog* dialog = new GControllerConfigDialog(controller_ports, this); |
| 364 | } | 425 | } |
| 365 | 426 | ||
| 366 | void GMainWindow::closeEvent(QCloseEvent* event) | 427 | void GMainWindow::closeEvent(QCloseEvent* event) { |
| 367 | { | ||
| 368 | // Save window layout | 428 | // Save window layout |
| 369 | QSettings settings(QSettings::IniFormat, QSettings::UserScope, "Citra team", "Citra"); | 429 | QSettings settings(QSettings::IniFormat, QSettings::UserScope, "Citra team", "Citra"); |
| 370 | settings.setValue("geometry", saveGeometry()); | 430 | settings.setValue("geometry", saveGeometry()); |
| @@ -388,8 +448,7 @@ void GMainWindow::closeEvent(QCloseEvent* event) | |||
| 388 | #undef main | 448 | #undef main |
| 389 | #endif | 449 | #endif |
| 390 | 450 | ||
| 391 | int main(int argc, char* argv[]) | 451 | int main(int argc, char* argv[]) { |
| 392 | { | ||
| 393 | Log::Filter log_filter(Log::Level::Info); | 452 | Log::Filter log_filter(Log::Level::Info); |
| 394 | Log::SetFilter(&log_filter); | 453 | Log::SetFilter(&log_filter); |
| 395 | 454 | ||
diff --git a/src/citra_qt/main.h b/src/citra_qt/main.h index 61114a04d..4b260ae8b 100644 --- a/src/citra_qt/main.h +++ b/src/citra_qt/main.h | |||
| @@ -24,6 +24,8 @@ class GMainWindow : public QMainWindow | |||
| 24 | { | 24 | { |
| 25 | Q_OBJECT | 25 | Q_OBJECT |
| 26 | 26 | ||
| 27 | static const int max_recent_files_item = 10; ///< Max number of recently loaded items to keep track | ||
| 28 | |||
| 27 | // TODO: Make use of this! | 29 | // TODO: Make use of this! |
| 28 | enum { | 30 | enum { |
| 29 | UI_IDLE, | 31 | UI_IDLE, |
| @@ -58,6 +60,8 @@ private: | |||
| 58 | void BootGame(const std::string& filename); | 60 | void BootGame(const std::string& filename); |
| 59 | void ShutdownGame(); | 61 | void ShutdownGame(); |
| 60 | 62 | ||
| 63 | void UpdateRecentFiles(); | ||
| 64 | |||
| 61 | void closeEvent(QCloseEvent* event) override; | 65 | void closeEvent(QCloseEvent* event) override; |
| 62 | 66 | ||
| 63 | private slots: | 67 | private slots: |
| @@ -66,6 +70,7 @@ private slots: | |||
| 66 | void OnStopGame(); | 70 | void OnStopGame(); |
| 67 | void OnMenuLoadFile(); | 71 | void OnMenuLoadFile(); |
| 68 | void OnMenuLoadSymbolMap(); | 72 | void OnMenuLoadSymbolMap(); |
| 73 | void OnMenuRecentFile(); | ||
| 69 | void OnOpenHotkeysDialog(); | 74 | void OnOpenHotkeysDialog(); |
| 70 | void OnConfigure(); | 75 | void OnConfigure(); |
| 71 | void OnDisplayTitleBars(bool); | 76 | void OnDisplayTitleBars(bool); |
| @@ -86,6 +91,8 @@ private: | |||
| 86 | CallstackWidget* callstackWidget; | 91 | CallstackWidget* callstackWidget; |
| 87 | GPUCommandStreamWidget* graphicsWidget; | 92 | GPUCommandStreamWidget* graphicsWidget; |
| 88 | GPUCommandListWidget* graphicsCommandsWidget; | 93 | GPUCommandListWidget* graphicsCommandsWidget; |
| 94 | |||
| 95 | QAction* actions_recent_files[max_recent_files_item]; | ||
| 89 | }; | 96 | }; |
| 90 | 97 | ||
| 91 | #endif // _CITRA_QT_MAIN_HXX_ | 98 | #endif // _CITRA_QT_MAIN_HXX_ |
diff --git a/src/citra_qt/main.ui b/src/citra_qt/main.ui index b2ce8167d..1ba700a3a 100644 --- a/src/citra_qt/main.ui +++ b/src/citra_qt/main.ui | |||
| @@ -52,9 +52,16 @@ | |||
| 52 | <property name="title"> | 52 | <property name="title"> |
| 53 | <string>&File</string> | 53 | <string>&File</string> |
| 54 | </property> | 54 | </property> |
| 55 | <widget class="QMenu" name="menu_recent_files"> | ||
| 56 | <property name="title"> | ||
| 57 | <string>Recent Files</string> | ||
| 58 | </property> | ||
| 59 | </widget> | ||
| 55 | <addaction name="action_Load_File"/> | 60 | <addaction name="action_Load_File"/> |
| 56 | <addaction name="action_Load_Symbol_Map"/> | 61 | <addaction name="action_Load_Symbol_Map"/> |
| 57 | <addaction name="separator"/> | 62 | <addaction name="separator"/> |
| 63 | <addaction name="menu_recent_files"/> | ||
| 64 | <addaction name="separator"/> | ||
| 58 | <addaction name="action_Exit"/> | 65 | <addaction name="action_Exit"/> |
| 59 | </widget> | 66 | </widget> |
| 60 | <widget class="QMenu" name="menu_Emulation"> | 67 | <widget class="QMenu" name="menu_Emulation"> |