make opened files use a complex table view

This commit is contained in:
alison wright 2019-09-28 06:54:04 -04:00
parent 62253abab0
commit 89414dd5ec
4 changed files with 139 additions and 31 deletions

View File

@ -2,24 +2,6 @@
#include "quam/main_window.h" #include "quam/main_window.h"
#include "quam/pak.h" #include "quam/pak.h"
static void setListToDir(QListWidget &list, PakDir const &dir) {
list.clear();
for(auto const &kv : dir) {
auto const &name = kv.first;
auto const &node = kv.second;
auto var = QVariant::fromValue(node);
auto item = new QListWidgetItem{&list};
item->setText(QString::fromStdString(name));
item->setData(Qt::UserRole, var);
if(std::holds_alternative<PakDir>(node)) {
item->setIcon(QIcon::fromTheme("folder"));
} else {
item->setIcon(QIcon::fromTheme("text-x-generic"));
}
list.addItem(item);
}
}
MainWindow::MainWindow(QWidget *parent) : MainWindow::MainWindow(QWidget *parent) :
QMainWindow{parent}, QMainWindow{parent},
Ui::MainWindow{}, Ui::MainWindow{},
@ -27,8 +9,10 @@ MainWindow::MainWindow(QWidget *parent) :
{ {
setupUi(this); setupUi(this);
actionOpen->setShortcut(QKeySequence(QKeySequence::Open)); actionOpen->setShortcut(QKeySequence{QKeySequence::Open});
actionQuit->setShortcut(QKeySequence(QKeySequence::Quit)); actionQuit->setShortcut(QKeySequence{QKeySequence::Quit});
tableWidget->sortByColumn(Pak::ColumnId, Qt::AscendingOrder);
} }
void MainWindow::fileOpen() { void MainWindow::fileOpen() {
@ -38,13 +22,14 @@ void MainWindow::fileOpen() {
tr("Open Archive"), tr("Open Archive"),
QString{}, QString{},
tr("Quake PACK file (*.pak);;" tr("Quake PACK file (*.pak);;"
"Quake WAD2 file (*.wad);;"
"All files (*)")); "All files (*)"));
if(!fileName.isEmpty()) { if(!fileName.isEmpty()) {
try { try {
auto st = openReadBin(fileName.toStdString()); auto st = openReadBin(fileName.toStdString());
auto pak = readPak(st); auto pak = readPak(st);
setListToDir(*listWidget, pak); setTableToPakDir(*tableWidget, pak);
} catch(std::exception const &exc) { } catch(std::exception const &exc) {
m_errors.showMessage(tr(exc.what())); m_errors.showMessage(tr(exc.what()));
} }

View File

@ -16,7 +16,71 @@
<widget class="QWidget" name="centralwidget"> <widget class="QWidget" name="centralwidget">
<layout class="QHBoxLayout" name="horizontalLayout_2"> <layout class="QHBoxLayout" name="horizontalLayout_2">
<item> <item>
<widget class="QListWidget" name="listWidget"/> <widget class="QTableWidget" name="tableWidget">
<property name="verticalScrollBarPolicy">
<enum>Qt::ScrollBarAlwaysOn</enum>
</property>
<property name="horizontalScrollBarPolicy">
<enum>Qt::ScrollBarAlwaysOff</enum>
</property>
<property name="autoScroll">
<bool>false</bool>
</property>
<property name="tabKeyNavigation">
<bool>true</bool>
</property>
<property name="alternatingRowColors">
<bool>true</bool>
</property>
<property name="selectionMode">
<enum>QAbstractItemView::SingleSelection</enum>
</property>
<property name="selectionBehavior">
<enum>QAbstractItemView::SelectRows</enum>
</property>
<property name="showGrid">
<bool>false</bool>
</property>
<property name="sortingEnabled">
<bool>true</bool>
</property>
<attribute name="horizontalHeaderVisible">
<bool>true</bool>
</attribute>
<attribute name="horizontalHeaderShowSortIndicator" stdset="0">
<bool>true</bool>
</attribute>
<attribute name="horizontalHeaderStretchLastSection">
<bool>true</bool>
</attribute>
<attribute name="verticalHeaderVisible">
<bool>false</bool>
</attribute>
<column>
<property name="text">
<string>ID</string>
</property>
<property name="toolTip">
<string>The ID of the file. This is the N-th file in the archive.</string>
</property>
</column>
<column>
<property name="text">
<string>Size</string>
</property>
<property name="toolTip">
<string>The size of the file in bytes.</string>
</property>
</column>
<column>
<property name="text">
<string>Name</string>
</property>
<property name="toolTip">
<string>The name of the file.</string>
</property>
</column>
</widget>
</item> </item>
<item> <item>
<widget class="QPlainTextEdit" name="textEdit"/> <widget class="QPlainTextEdit" name="textEdit"/>

View File

@ -8,7 +8,7 @@ struct PakHeader {
struct PakEntry { struct PakEntry {
std::string name; std::string name;
PakFile data; PakFile file;
}; };
static constexpr quint32 sizeOfPakEntry = 64; static constexpr quint32 sizeOfPakEntry = 64;
@ -33,7 +33,7 @@ static PakHeader readPakHeader(std::istream &st) {
return hdr; return hdr;
} }
static PakEntry readPakEntry(std::istream &st) { static PakEntry readPakEntry(std::istream &st, quint32 id) {
auto entName = readBytes<56>(st); auto entName = readBytes<56>(st);
auto entOffset = readLE<quint32>(st); auto entOffset = readLE<quint32>(st);
auto entSize = readLE<quint32>(st); auto entSize = readLE<quint32>(st);
@ -42,9 +42,10 @@ static PakEntry readPakEntry(std::istream &st) {
st.seekg(entOffset); st.seekg(entOffset);
PakFile bytes; PakFile file;
bytes.resize(entSize); file.id = id;
st.read(bytes.data(), entSize); file.resize(entSize);
st.read(file.data(), entSize);
st.seekg(pos); st.seekg(pos);
@ -59,7 +60,7 @@ static PakEntry readPakEntry(std::istream &st) {
PakEntry ent; PakEntry ent;
ent.name = std::move(name); ent.name = std::move(name);
ent.data = std::move(bytes); ent.file = std::move(file);
return ent; return ent;
} }
@ -82,12 +83,57 @@ PakDir readPak(std::istream &st) {
PakDir root; PakDir root;
for(quint32 i = 0; i < hdr.dirNum; i++) { for(quint32 id = 0; id < hdr.dirNum; id++) {
auto ent = readPakEntry(st); auto ent = readPakEntry(st, id);
insertFile(root, std::move(ent.name), std::move(ent.data)); insertFile(root, std::move(ent.name), std::move(ent.file));
} }
return root; return root;
} }
void setTableToPakDir(QTableWidget &table, PakDir const &dir) {
constexpr auto Flags = Qt::ItemIsSelectable |
Qt::ItemIsDragEnabled |
Qt::ItemIsEnabled |
Qt::ItemNeverHasChildren;
auto sorted = table.isSortingEnabled();
table.clearContents();
table.setSortingEnabled(false);
quint32 row{0};
for(auto const &kv : dir) {
auto const &name = kv.first;
auto const &node = kv.second;
table.setRowCount(row + 1);
{
auto item = new QTableWidgetItem;
item->setFlags(Flags);
if(auto file = std::get_if<PakFile>(&node)) {
item->setText(QString::number(file->id));
}
table.setItem(row, Pak::ColumnId, item);
}
{
auto item = new QTableWidgetItem;
item->setFlags(Flags);
if(auto file = std::get_if<PakFile>(&node)) {
item->setText(QString::number(file->size()));
}
table.setItem(row, Pak::ColumnSize, item);
}
{
auto item = new QTableWidgetItem;
auto icon = std::holds_alternative<PakDir>(node) ? "folder" :
"text-x-generic";
item->setFlags(Flags);
item->setText(QString::fromStdString(name));
item->setIcon(QIcon::fromTheme(icon));
table.setItem(row, Pak::ColumnName, item);
}
++row;
}
table.setSortingEnabled(sorted);
table.resizeColumnsToContents();
}
// EOF // EOF

View File

@ -1,5 +1,15 @@
#pragma once #pragma once
#include <QTableWidget>
namespace Pak {
enum PakColumn {
ColumnId,
ColumnSize,
ColumnName,
};
}
struct PakNode; struct PakNode;
struct PakDir : public std::map<std::string, PakNode> { struct PakDir : public std::map<std::string, PakNode> {
@ -9,6 +19,8 @@ Q_DECLARE_METATYPE(PakDir)
struct PakFile : public QByteArray { struct PakFile : public QByteArray {
using QByteArray::QByteArray; using QByteArray::QByteArray;
quint32 id{0};
}; };
Q_DECLARE_METATYPE(PakFile) Q_DECLARE_METATYPE(PakFile)
@ -18,5 +30,6 @@ struct PakNode : public std::variant<PakDir, PakFile> {
Q_DECLARE_METATYPE(PakNode) Q_DECLARE_METATYPE(PakNode)
PakDir readPak(std::istream &st); PakDir readPak(std::istream &st);
void setTableToPakDir(QTableWidget &table, PakDir const &dir);
// EOF // EOF