rpcsx/rpcs3/rpcs3qt/save_manager_dialog.cpp

564 lines
18 KiB
C++
Raw Normal View History

2020-12-05 13:08:24 +01:00
#include "save_manager_dialog.h"
2017-08-14 02:17:45 +02:00
2022-02-02 15:36:15 +01:00
#include "custom_table_widget_item.h"
#include "qt_utils.h"
2020-02-22 20:42:49 +01:00
#include "gui_settings.h"
#include "persistent_settings.h"
2017-08-14 02:17:45 +02:00
#include "Emu/System.h"
#include "Emu/system_utils.hpp"
2017-08-14 02:17:45 +02:00
#include "Loader/PSF.h"
2019-07-27 14:37:54 +02:00
#include <QtConcurrent>
2022-02-02 15:36:15 +01:00
#include <QDateTime>
2017-08-14 02:17:45 +02:00
#include <QHBoxLayout>
#include <QHeaderView>
#include <QMenu>
#include <QMessageBox>
2020-02-22 20:42:49 +01:00
#include <QGuiApplication>
#include <QUrl>
#include <QDesktopServices>
2022-02-02 15:36:15 +01:00
#include <QPainter>
2019-08-10 13:24:14 +02:00
#include <QScreen>
#include <QScrollBar>
2017-08-14 02:17:45 +02:00
#include "Utilities/File.h"
LOG_CHANNEL(gui_log, "GUI");
2017-08-14 02:17:45 +02:00
namespace
{
// Helper converters
constexpr auto qstr = QString::fromStdString;
2021-02-15 12:34:10 +01:00
[[maybe_unused]] inline std::string sstr(const QString& _in) { return _in.toStdString(); }
2017-08-14 02:17:45 +02:00
2019-08-10 13:47:25 +02:00
QString FormatTimestamp(u64 time)
{
2022-02-02 15:36:15 +01:00
QDateTime dateTime;
dateTime.setTime_t(time);
return dateTime.toString("yyyy-MM-dd HH:mm:ss");
}
2017-08-14 02:17:45 +02:00
/**
* This certainly isn't ideal for this code, as it essentially copies cellSaveData. But, I have no other choice without adding public methods to cellSaveData.
*/
std::vector<SaveDataEntry> GetSaveEntries(const std::string& base_dir)
{
std::vector<SaveDataEntry> save_entries;
// get the saves matching the supplied prefix
for (const auto& entry : fs::dir(base_dir))
{
if (!entry.is_directory || entry.name == "." || entry.name == "..")
2017-08-14 02:17:45 +02:00
{
continue;
}
// PSF parameters
const auto [psf, errc] = psf::load(base_dir + entry.name + "/PARAM.SFO");
2017-08-14 02:17:45 +02:00
if (psf.empty())
{
gui_log.error("Failed to load savedata: %s (%s)", base_dir + "/" + entry.name, errc);
2017-08-14 02:17:45 +02:00
continue;
}
SaveDataEntry save_entry2;
save_entry2.dirName = psf.at("SAVEDATA_DIRECTORY").as_string();
save_entry2.listParam = psf.at("SAVEDATA_LIST_PARAM").as_string();
save_entry2.title = psf.at("TITLE").as_string();
save_entry2.subtitle = psf.at("SUB_TITLE").as_string();
save_entry2.details = psf.at("DETAIL").as_string();
save_entry2.size = 0;
2017-11-30 21:55:26 +01:00
for (const auto& entry2 : fs::dir(base_dir + entry.name))
2017-08-14 02:17:45 +02:00
{
save_entry2.size += entry2.size;
}
save_entry2.atime = entry.atime;
save_entry2.mtime = entry.mtime;
save_entry2.ctime = entry.ctime;
if (fs::is_file(base_dir + entry.name + "/ICON0.PNG"))
{
fs::file icon = fs::file(base_dir + entry.name + "/ICON0.PNG");
std::vector<uchar> iconData;
2021-04-07 23:05:18 +02:00
icon.read(iconData, icon.size());
2017-08-14 02:17:45 +02:00
save_entry2.iconBuf = iconData;
}
save_entry2.isNew = false;
save_entries.emplace_back(save_entry2);
}
return save_entries;
}
}
save_manager_dialog::save_manager_dialog(std::shared_ptr<gui_settings> gui_settings, std::shared_ptr<persistent_settings> persistent_settings, std::string dir, QWidget* parent)
: QDialog(parent)
, m_dir(dir)
2021-04-07 23:05:18 +02:00
, m_gui_settings(std::move(gui_settings))
, m_persistent_settings(std::move(persistent_settings))
2017-08-14 02:17:45 +02:00
{
setWindowTitle(tr("Save Manager"));
setMinimumSize(QSize(400, 400));
setAttribute(Qt::WA_DeleteOnClose);
2017-08-14 02:17:45 +02:00
2021-04-07 23:05:18 +02:00
Init();
2017-08-14 02:17:45 +02:00
}
/*
* Future proofing. Makes it easier in future if I add ability to change directories
*/
2021-04-07 23:05:18 +02:00
void save_manager_dialog::Init()
2017-08-14 02:17:45 +02:00
{
// Table
m_list = new QTableWidget(this);
//m_list->setItemDelegate(new table_item_delegate(this)); // to get rid of cell selection rectangles include "table_item_delegate.h"
m_list->setSelectionMode(QAbstractItemView::SelectionMode::ExtendedSelection);
2017-08-14 02:17:45 +02:00
m_list->setSelectionBehavior(QAbstractItemView::SelectRows);
m_list->setContextMenuPolicy(Qt::CustomContextMenu);
2022-02-02 15:36:15 +01:00
m_list->setColumnCount(5);
m_list->setVerticalScrollMode(QAbstractItemView::ScrollPerPixel);
m_list->setHorizontalScrollMode(QAbstractItemView::ScrollPerPixel);
m_list->verticalScrollBar()->setSingleStep(20);
m_list->horizontalScrollBar()->setSingleStep(10);
2022-02-02 15:36:15 +01:00
m_list->setHorizontalHeaderLabels(QStringList() << tr("Icon") << tr("Title & Subtitle") << tr("Last Modified") << tr("Save ID") << tr("Notes"));
m_list->horizontalHeader()->setSectionResizeMode(0, QHeaderView::Fixed);
m_list->horizontalHeader()->setStretchLastSection(true);
// Bottom bar
2021-04-07 23:05:18 +02:00
const int icon_size = m_gui_settings->GetValue(gui::sd_icon_size).toInt();
2022-02-02 15:36:15 +01:00
m_icon_size = QSize(icon_size, icon_size);
2020-04-06 17:54:33 +02:00
QLabel* label_icon_size = new QLabel(tr("Icon size:"), this);
2022-02-02 15:36:15 +01:00
QSlider* slider_icon_size = new QSlider(Qt::Horizontal, this);
slider_icon_size->setMinimum(60);
slider_icon_size->setMaximum(225);
slider_icon_size->setValue(m_icon_size.height());
2017-08-14 02:17:45 +02:00
QPushButton* push_close = new QPushButton(tr("&Close"), this);
push_close->setAutoDefault(true);
2022-02-02 15:36:15 +01:00
// Details
m_details_icon = new QLabel(this);
m_details_icon->setMinimumSize(320, 176);
m_details_title = new QLabel(tr("Select an item to view details"), this);
m_details_title->setWordWrap(true);
m_details_subtitle = new QLabel(this);
m_details_subtitle->setWordWrap(true);
m_details_modified = new QLabel(this);
m_details_modified->setWordWrap(true);
m_details_details = new QLabel(this);
m_details_details->setWordWrap(true);
m_details_note = new QLabel(this);
m_details_note->setWordWrap(true);
m_button_delete = new QPushButton(tr("Delete Selection"), this);
m_button_delete->setDisabled(true);
m_button_folder = new QPushButton(tr("View Folder"), this);
m_button_delete->setDisabled(true);
// Details layout
QVBoxLayout *vbox_details = new QVBoxLayout();
vbox_details->addWidget(m_details_icon);
vbox_details->addWidget(m_details_title);
vbox_details->addWidget(m_details_subtitle);
vbox_details->addWidget(m_details_modified);
vbox_details->addWidget(m_details_details);
vbox_details->addWidget(m_details_note);
vbox_details->addStretch();
vbox_details->addWidget(m_button_delete);
vbox_details->setAlignment(m_button_delete, Qt::AlignHCenter);
vbox_details->addWidget(m_button_folder);
vbox_details->setAlignment(m_button_folder, Qt::AlignHCenter);
// List + Details
QHBoxLayout *hbox_content = new QHBoxLayout();
hbox_content->addWidget(m_list);
hbox_content->addLayout(vbox_details);
// Items below list
QHBoxLayout* hbox_buttons = new QHBoxLayout();
2022-02-02 15:36:15 +01:00
hbox_buttons->addWidget(label_icon_size);
hbox_buttons->addWidget(slider_icon_size);
2017-08-14 02:17:45 +02:00
hbox_buttons->addStretch();
hbox_buttons->addWidget(push_close);
// main layout
QVBoxLayout* vbox_main = new QVBoxLayout();
vbox_main->setAlignment(Qt::AlignCenter);
2022-02-02 15:36:15 +01:00
vbox_main->addLayout(hbox_content);
2017-08-14 02:17:45 +02:00
vbox_main->addLayout(hbox_buttons);
setLayout(vbox_main);
UpdateList();
2022-02-02 15:36:15 +01:00
m_list->sortByColumn(1, Qt::AscendingOrder);
2017-08-14 02:17:45 +02:00
2018-03-28 20:08:15 +02:00
if (restoreGeometry(m_gui_settings->GetValue(gui::sd_geometry).toByteArray()))
2019-08-10 13:24:14 +02:00
resize(size().expandedTo(QGuiApplication::primaryScreen()->availableSize() * 0.5));
2017-08-14 02:17:45 +02:00
// Connects and events
connect(push_close, &QAbstractButton::clicked, this, &save_manager_dialog::close);
2022-02-02 15:36:15 +01:00
connect(m_button_delete, &QAbstractButton::clicked, this, &save_manager_dialog::OnEntriesRemove);
connect(m_button_folder, &QAbstractButton::clicked, [this]()
2022-02-02 15:36:15 +01:00
{
const int idx = m_list->currentRow();
QTableWidgetItem* item = m_list->item(idx, 1);
if (!item)
{
return;
}
const int idx_real = item->data(Qt::UserRole).toInt();
const QString path = qstr(m_dir + m_save_entries[idx_real].dirName + "/");
QDesktopServices::openUrl(QUrl::fromLocalFile(path));
2022-02-02 15:36:15 +01:00
});
connect(slider_icon_size, &QAbstractSlider::valueChanged, this, &save_manager_dialog::SetIconSize);
connect(m_list->horizontalHeader(), &QHeaderView::sectionClicked, this, &save_manager_dialog::OnSort);
2017-08-14 02:17:45 +02:00
connect(m_list, &QTableWidget::customContextMenuRequested, this, &save_manager_dialog::ShowContextMenu);
connect(m_list, &QTableWidget::cellChanged, [&](int row, int col)
{
QTableWidgetItem* user_item = m_list->item(row, 1);
QTableWidgetItem* text_item = m_list->item(row, col);
if (!user_item || !text_item)
{
return;
}
const int original_index = user_item->data(Qt::UserRole).toInt();
const SaveDataEntry originalEntry = m_save_entries[original_index];
const QString original_dir_name = qstr(originalEntry.dirName);
QVariantMap notes = m_persistent_settings->GetValue(gui::persistent::save_notes).toMap();
notes[original_dir_name] = text_item->text();
m_persistent_settings->SetValue(gui::persistent::save_notes, notes);
2017-08-14 02:17:45 +02:00
});
2022-02-02 15:36:15 +01:00
connect(m_list, &QTableWidget::itemSelectionChanged, this, &save_manager_dialog::UpdateDetails);
2017-08-14 02:17:45 +02:00
}
void save_manager_dialog::UpdateList()
{
2021-04-07 23:05:18 +02:00
if (m_dir.empty())
2017-08-14 02:17:45 +02:00
{
m_dir = rpcs3::utils::get_hdd0_dir() + "home/" + Emu.GetUsr() + "/savedata/";
2017-08-14 02:17:45 +02:00
}
m_save_entries = GetSaveEntries(m_dir);
m_list->clearContents();
m_list->setRowCount(static_cast<int>(m_save_entries.size()));
const QVariantMap notes = m_persistent_settings->GetValue(gui::persistent::save_notes).toMap();
2017-08-14 02:17:45 +02:00
if (m_gui_settings->GetValue(gui::m_enableUIColors).toBool())
{
m_icon_color = m_gui_settings->GetValue(gui::sd_icon_color).value<QColor>();
}
else
{
m_icon_color = gui::utils::get_label_color("save_manager_icon_background_color");
}
2019-07-27 14:37:54 +02:00
QList<int> indices;
2020-12-18 08:39:54 +01:00
for (usz i = 0; i < m_save_entries.size(); ++i)
2019-07-27 16:30:34 +02:00
indices.append(static_cast<int>(i));
2019-07-27 14:37:54 +02:00
2021-04-07 23:05:18 +02:00
const std::function<QPixmap(const int&)> get_icon = [this](const int& row)
2017-08-14 02:17:45 +02:00
{
2019-07-27 14:37:54 +02:00
const auto& entry = m_save_entries[row];
2022-02-02 15:36:15 +01:00
QPixmap icon = QPixmap(320, 176);
if (!icon.loadFromData(entry.iconBuf.data(), static_cast<uint>(entry.iconBuf.size())))
{
gui_log.warning("Loading icon for save %s failed", entry.dirName);
icon = QPixmap(320, 176);
icon.fill(m_icon_color);
2022-02-02 15:36:15 +01:00
}
return icon;
};
// NOTE: Due to a Qt bug in Qt 5.15.2, QtConcurrent::blockingMapped has a high risk of deadlocking. So let's just use QtConcurrent::mapped.
const QList<QPixmap> icons = QtConcurrent::mapped(indices, get_icon).results();
for (int i = 0; i < icons.count(); ++i)
{
const auto& entry = m_save_entries[i];
2022-02-02 15:36:15 +01:00
QString title = qstr(entry.title) + QStringLiteral("\n") + qstr(entry.subtitle);
QString dir_name = qstr(entry.dirName);
2017-08-14 02:17:45 +02:00
2022-02-02 15:36:15 +01:00
custom_table_widget_item* iconItem = new custom_table_widget_item;
iconItem->setData(Qt::UserRole, icons[i]);
2022-02-02 15:36:15 +01:00
iconItem->setFlags(iconItem->flags() & ~Qt::ItemIsEditable);
m_list->setItem(i, 0, iconItem);
2022-02-02 15:36:15 +01:00
2017-08-14 02:17:45 +02:00
QTableWidgetItem* titleItem = new QTableWidgetItem(title);
titleItem->setData(Qt::UserRole, i); // For sorting to work properly
2017-08-14 02:17:45 +02:00
titleItem->setFlags(titleItem->flags() & ~Qt::ItemIsEditable);
m_list->setItem(i, 1, titleItem);
2017-08-14 02:17:45 +02:00
2022-02-02 15:36:15 +01:00
QTableWidgetItem* timeItem = new QTableWidgetItem(FormatTimestamp(entry.mtime));
timeItem->setFlags(timeItem->flags() & ~Qt::ItemIsEditable);
m_list->setItem(i, 2, timeItem);
2017-08-14 02:17:45 +02:00
QTableWidgetItem* dirNameItem = new QTableWidgetItem(dir_name);
2017-08-14 02:17:45 +02:00
dirNameItem->setFlags(dirNameItem->flags() & ~Qt::ItemIsEditable);
m_list->setItem(i, 3, dirNameItem);
2017-08-14 02:17:45 +02:00
QTableWidgetItem* noteItem = new QTableWidgetItem();
noteItem->setFlags(noteItem->flags() | Qt::ItemIsEditable);
if (notes.contains(dir_name))
2017-08-14 02:17:45 +02:00
{
noteItem->setText(notes[dir_name].toString());
2017-08-14 02:17:45 +02:00
}
m_list->setItem(i, 4, noteItem);
}
UpdateIcons();
2022-02-02 15:36:15 +01:00
2017-08-14 02:17:45 +02:00
m_list->horizontalHeader()->resizeSections(QHeaderView::ResizeToContents);
m_list->verticalHeader()->resizeSections(QHeaderView::ResizeToContents);
2021-04-07 23:05:18 +02:00
const QSize tableSize(
2017-08-14 02:17:45 +02:00
m_list->verticalHeader()->width() + m_list->horizontalHeader()->length() + m_list->frameWidth() * 2,
m_list->horizontalHeader()->height() + m_list->verticalHeader()->length() + m_list->frameWidth() * 2);
2021-04-07 23:05:18 +02:00
const QSize preferredSize = minimumSize().expandedTo(sizeHint() - m_list->sizeHint() + tableSize);
2017-08-14 02:17:45 +02:00
2021-04-07 23:05:18 +02:00
const QSize maxSize(preferredSize.width(), static_cast<int>(QGuiApplication::primaryScreen()->geometry().height() * 0.6));
2017-10-28 16:22:18 +02:00
resize(preferredSize.boundedTo(maxSize));
2017-08-14 02:17:45 +02:00
}
void save_manager_dialog::HandleRepaintUiRequest()
{
const QSize window_size = size();
const Qt::SortOrder sort_order = m_sort_ascending ? Qt::AscendingOrder : Qt::DescendingOrder;
UpdateList();
m_list->sortByColumn(m_sort_column, sort_order);
resize(window_size);
}
2021-04-07 23:05:18 +02:00
QPixmap save_manager_dialog::GetResizedIcon(int i) const
2022-02-02 15:36:15 +01:00
{
2020-01-16 18:29:37 +01:00
const qreal dpr = devicePixelRatioF();
2022-02-02 15:36:15 +01:00
const int width = m_icon_size.width() * dpr;
const int height = m_icon_size.height() * dpr * 176 / 320;
2019-07-27 14:37:54 +02:00
QTableWidgetItem* item = m_list->item(i, 0);
if (!item)
2022-02-02 15:36:15 +01:00
{
return QPixmap();
2019-07-27 14:37:54 +02:00
}
2021-04-07 23:05:18 +02:00
const QPixmap data = item->data(Qt::UserRole).value<QPixmap>();
2022-02-02 15:36:15 +01:00
2019-07-27 14:37:54 +02:00
QPixmap icon = QPixmap(data.size() * dpr);
icon.setDevicePixelRatio(dpr);
icon.fill(m_icon_color);
QPainter painter(&icon);
2020-02-09 22:41:41 +01:00
painter.setRenderHint(QPainter::SmoothPixmapTransform);
2019-07-27 14:37:54 +02:00
painter.drawPixmap(0, 0, data);
return icon.scaled(width, height, Qt::KeepAspectRatio, Qt::SmoothTransformation);
2019-07-27 14:37:54 +02:00
}
void save_manager_dialog::UpdateIcons()
{
QList<int> indices;
for (int i = 0; i < m_list->rowCount(); ++i)
indices.append(i);
2021-04-07 23:05:18 +02:00
const std::function<QPixmap(const int&)> get_scaled = [this](const int& i)
2019-07-27 14:37:54 +02:00
{
return GetResizedIcon(i);
};
// NOTE: Due to a Qt bug in Qt 5.15.2, QtConcurrent::blockingMapped has a high risk of deadlocking. So let's just use QtConcurrent::mapped.
const QList<QPixmap> scaled = QtConcurrent::mapped(indices, get_scaled).results();
for (int i = 0; i < m_list->rowCount() && i < scaled.count(); ++i)
{
if (QTableWidgetItem* icon_item = m_list->item(i, 0))
icon_item->setData(Qt::DecorationRole, scaled[i]);
}
2022-02-02 15:36:15 +01:00
m_list->resizeRowsToContents();
2022-02-02 15:36:15 +01:00
m_list->resizeColumnToContents(0);
}
2017-08-14 02:17:45 +02:00
/**
* Copied method to do sort from save_data_list_dialog
*/
void save_manager_dialog::OnSort(int logicalIndex)
2017-08-14 02:17:45 +02:00
{
if (logicalIndex >= 0)
2017-08-14 02:17:45 +02:00
{
if (logicalIndex == m_sort_column)
2017-08-14 02:17:45 +02:00
{
m_sort_ascending ^= true;
2017-08-14 02:17:45 +02:00
}
else
{
m_sort_ascending = true;
2017-08-14 02:17:45 +02:00
}
m_sort_column = logicalIndex;
2021-04-07 23:05:18 +02:00
const Qt::SortOrder sort_order = m_sort_ascending ? Qt::AscendingOrder : Qt::DescendingOrder;
m_list->sortByColumn(m_sort_column, sort_order);
2017-08-14 02:17:45 +02:00
}
}
2019-05-24 23:54:14 +02:00
// Remove a save file, need to be confirmed.
2017-08-14 02:17:45 +02:00
void save_manager_dialog::OnEntryRemove()
{
2021-04-07 23:05:18 +02:00
const int idx = m_list->currentRow();
2017-08-14 02:17:45 +02:00
if (idx != -1)
{
QTableWidgetItem* item = m_list->item(idx, 1);
if (!item)
{
return;
}
const int idx_real = item->data(Qt::UserRole).toInt();
if (QMessageBox::question(this, tr("Delete Confirmation"), tr("Are you sure you want to delete:\n%1?").arg(qstr(m_save_entries[idx_real].title)), QMessageBox::Yes, QMessageBox::No) == QMessageBox::Yes)
2017-08-14 02:17:45 +02:00
{
2017-08-14 04:35:40 +02:00
fs::remove_all(m_dir + m_save_entries[idx_real].dirName + "/");
m_list->removeRow(idx);
2017-08-14 02:17:45 +02:00
}
}
}
void save_manager_dialog::OnEntriesRemove()
{
QModelIndexList selection(m_list->selectionModel()->selectedRows());
if (selection.empty())
{
return;
}
if (selection.size() == 1)
{
OnEntryRemove();
return;
}
if (QMessageBox::question(this, tr("Delete Confirmation"), tr("Are you sure you want to delete these %n items?", "", selection.size()), QMessageBox::Yes, QMessageBox::No) == QMessageBox::Yes)
{
2019-08-10 13:24:14 +02:00
std::sort(selection.rbegin(), selection.rend());
for (QModelIndex index : selection)
{
QTableWidgetItem* item = m_list->item(index.row(), 1);
if (!item)
{
continue;
}
const int idx_real = item->data(Qt::UserRole).toInt();
fs::remove_all(m_dir + m_save_entries[idx_real].dirName + "/");
m_list->removeRow(index.row());
}
}
}
2019-05-24 23:54:14 +02:00
// Pop-up a small context-menu, being a replacement for save_data_manage_dialog
2017-08-14 02:17:45 +02:00
void save_manager_dialog::ShowContextMenu(const QPoint &pos)
{
2021-04-07 23:05:18 +02:00
const int idx = m_list->currentRow();
if (idx == -1)
{
return;
}
2017-08-14 02:17:45 +02:00
const bool selectedItems = m_list->selectionModel()->selectedRows().size() > 1;
QAction* removeAct = new QAction(tr("&Remove"), this);
QAction* showDirAct = new QAction(tr("&Open Save Directory"), this);
2017-08-14 02:17:45 +02:00
QMenu* menu = new QMenu();
2017-08-14 02:17:45 +02:00
menu->addAction(removeAct);
menu->addAction(showDirAct);
2017-08-14 02:17:45 +02:00
showDirAct->setEnabled(!selectedItems);
2017-08-14 02:17:45 +02:00
removeAct->setEnabled(idx != -1);
// Events
connect(removeAct, &QAction::triggered, this, &save_manager_dialog::OnEntriesRemove); // entriesremove handles case of one as well
connect(showDirAct, &QAction::triggered, [=, this]()
{
QTableWidgetItem* item = m_list->item(idx, 1);
if (!item)
{
return;
}
const int idx_real = item->data(Qt::UserRole).toInt();
const QString path = qstr(m_dir + m_save_entries[idx_real].dirName + "/");
QDesktopServices::openUrl(QUrl::fromLocalFile(path));
});
2017-08-14 02:17:45 +02:00
menu->exec(m_list->viewport()->mapToGlobal(pos));
2017-08-14 02:17:45 +02:00
}
2022-02-02 15:36:15 +01:00
void save_manager_dialog::SetIconSize(int size)
{
m_icon_size = QSize(size, size);
UpdateIcons();
m_gui_settings->SetValue(gui::sd_icon_size, size);
}
void save_manager_dialog::closeEvent(QCloseEvent *event)
{
m_gui_settings->SetValue(gui::sd_geometry, saveGeometry());
QDialog::closeEvent(event);
}
2022-02-02 15:36:15 +01:00
void save_manager_dialog::UpdateDetails()
{
if (const int selected = m_list->selectionModel()->selectedRows().size(); selected != 1)
2022-02-02 15:36:15 +01:00
{
m_details_icon->setPixmap(QPixmap());
m_details_subtitle->setText("");
m_details_modified->setText("");
m_details_details->setText("");
m_details_note->setText("");
if (selected > 1)
{
m_button_delete->setDisabled(false);
m_details_title->setText(tr("%1 items selected").arg(selected));
}
else
{
m_button_delete->setDisabled(true);
m_details_title->setText(tr("Select an item to view details"));
}
m_button_folder->setDisabled(true);
}
else
{
const int row = m_list->currentRow();
QTableWidgetItem* item = m_list->item(row, 1);
QTableWidgetItem* icon_item = m_list->item(row, 0);
if (!item || !icon_item)
{
return;
}
const int idx = item->data(Qt::UserRole).toInt();
2022-02-02 15:36:15 +01:00
const SaveDataEntry& save = m_save_entries[idx];
m_details_icon->setPixmap(icon_item->data(Qt::UserRole).value<QPixmap>());
2022-02-02 15:36:15 +01:00
m_details_title->setText(qstr(save.title));
m_details_subtitle->setText(qstr(save.subtitle));
m_details_modified->setText(tr("Last modified: %1").arg(FormatTimestamp(save.mtime)));
m_details_details->setText(tr("Details:\n").append(qstr(save.details)));
QString note = tr("Note:\n");
if (const QVariantMap map = m_persistent_settings->GetValue(gui::persistent::save_notes).toMap();
map.contains(qstr(save.dirName)))
{
2022-02-02 15:36:15 +01:00
note.append(map[qstr(save.dirName)].toString());
}
2022-02-02 15:36:15 +01:00
m_details_note->setText(note);
m_button_delete->setDisabled(false);
m_button_folder->setDisabled(false);
}
}