mirror of
https://github.com/isledecomp/SIEdit.git
synced 2024-11-27 01:25:45 -05:00
app: add object-focused tab
This commit is contained in:
parent
9ce113f1f0
commit
0fb49a780b
10 changed files with 233 additions and 40 deletions
|
@ -17,11 +17,15 @@ set(PROJECT_SOURCES
|
|||
panels/riff.cpp
|
||||
panels/riff.h
|
||||
|
||||
abstractsiitemmodel.cpp
|
||||
abstractsiitemmodel.h
|
||||
chunkmodel.cpp
|
||||
chunkmodel.h
|
||||
main.cpp
|
||||
mainwindow.cpp
|
||||
mainwindow.h
|
||||
objectmodel.cpp
|
||||
objectmodel.h
|
||||
)
|
||||
|
||||
if(${QT_VERSION_MAJOR} GREATER_EQUAL 6)
|
||||
|
|
26
app/abstractsiitemmodel.cpp
Normal file
26
app/abstractsiitemmodel.cpp
Normal file
|
@ -0,0 +1,26 @@
|
|||
#include "abstractsiitemmodel.h"
|
||||
|
||||
using namespace si;
|
||||
|
||||
AbstractSIItemModel::AbstractSIItemModel(QObject *parent) :
|
||||
QAbstractItemModel{parent},
|
||||
chunk_(nullptr)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void AbstractSIItemModel::SetChunk(si::Chunk *c)
|
||||
{
|
||||
beginResetModel();
|
||||
chunk_ = c;
|
||||
endResetModel();
|
||||
}
|
||||
|
||||
si::Chunk *AbstractSIItemModel::GetChunkFromIndex(const QModelIndex &index) const
|
||||
{
|
||||
if (!index.isValid()) {
|
||||
return chunk_;
|
||||
} else {
|
||||
return static_cast<Chunk*>(index.internalPointer());
|
||||
}
|
||||
}
|
25
app/abstractsiitemmodel.h
Normal file
25
app/abstractsiitemmodel.h
Normal file
|
@ -0,0 +1,25 @@
|
|||
#ifndef ABSTRACTSIITEMMODEL_H
|
||||
#define ABSTRACTSIITEMMODEL_H
|
||||
|
||||
#include <chunk.h>
|
||||
#include <QAbstractItemModel>
|
||||
|
||||
class AbstractSIItemModel : public QAbstractItemModel
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
explicit AbstractSIItemModel(QObject *parent = nullptr);
|
||||
|
||||
void SetChunk(si::Chunk *c);
|
||||
|
||||
protected:
|
||||
si::Chunk *GetChunkFromIndex(const QModelIndex &index) const;
|
||||
|
||||
si::Chunk *root() const { return chunk_; }
|
||||
|
||||
private:
|
||||
si::Chunk *chunk_;
|
||||
|
||||
};
|
||||
|
||||
#endif // ABSTRACTSIITEMMODEL_H
|
|
@ -2,13 +2,12 @@
|
|||
|
||||
#include <iostream>
|
||||
|
||||
#define super QAbstractItemModel
|
||||
#define super AbstractSIItemModel
|
||||
|
||||
using namespace si;
|
||||
|
||||
ChunkModel::ChunkModel(QObject *parent) :
|
||||
super{parent},
|
||||
chunk_(nullptr)
|
||||
super{parent}
|
||||
{
|
||||
}
|
||||
|
||||
|
@ -45,7 +44,7 @@ QModelIndex ChunkModel::parent(const QModelIndex &index) const
|
|||
}
|
||||
|
||||
size_t row = grandparent->IndexOfChild(parent);
|
||||
return createIndex(row, 0, parent);
|
||||
return createIndex(int(row), 0, parent);
|
||||
}
|
||||
|
||||
int ChunkModel::rowCount(const QModelIndex &parent) const
|
||||
|
@ -55,7 +54,7 @@ int ChunkModel::rowCount(const QModelIndex &parent) const
|
|||
return 0;
|
||||
}
|
||||
|
||||
return c->GetChildCount();
|
||||
return int(c->GetChildCount());
|
||||
}
|
||||
|
||||
QVariant ChunkModel::data(const QModelIndex &index, int role) const
|
||||
|
@ -99,19 +98,3 @@ QVariant ChunkModel::headerData(int section, Qt::Orientation orientation, int ro
|
|||
|
||||
return super::headerData(section, orientation, role);
|
||||
}
|
||||
|
||||
void ChunkModel::SetChunk(si::Chunk *c)
|
||||
{
|
||||
beginResetModel();
|
||||
chunk_ = c;
|
||||
endResetModel();
|
||||
}
|
||||
|
||||
si::Chunk *ChunkModel::GetChunkFromIndex(const QModelIndex &index) const
|
||||
{
|
||||
if (!index.isValid()) {
|
||||
return chunk_;
|
||||
} else {
|
||||
return static_cast<Chunk*>(index.internalPointer());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
#ifndef CHUNKMODEL_H
|
||||
#define CHUNKMODEL_H
|
||||
|
||||
#include <chunk.h>
|
||||
#include <QAbstractItemModel>
|
||||
#include "abstractsiitemmodel.h"
|
||||
|
||||
class ChunkModel : public QAbstractItemModel
|
||||
class ChunkModel : public AbstractSIItemModel
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
enum Columns
|
||||
{
|
||||
|
@ -25,13 +25,6 @@ public:
|
|||
virtual QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override;
|
||||
virtual QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const override;
|
||||
|
||||
void SetChunk(si::Chunk *c);
|
||||
|
||||
private:
|
||||
si::Chunk *GetChunkFromIndex(const QModelIndex &index) const;
|
||||
|
||||
si::Chunk *chunk_;
|
||||
|
||||
};
|
||||
|
||||
#endif // CHUNKMODEL_H
|
||||
|
|
|
@ -16,12 +16,18 @@ MainWindow::MainWindow(QWidget *parent) :
|
|||
splitter->setChildrenCollapsible(false);
|
||||
this->setCentralWidget(splitter);
|
||||
|
||||
model_.SetChunk(&chunk_);
|
||||
auto tree_tab = new QTabWidget();
|
||||
splitter->addWidget(tree_tab);
|
||||
|
||||
auto tree = new QTreeView();
|
||||
tree->setModel(&model_);
|
||||
splitter->addWidget(tree);
|
||||
connect(tree->selectionModel(), &QItemSelectionModel::currentRowChanged, this, &MainWindow::SelectionChanged);
|
||||
auto simple_tree = new QTreeView();
|
||||
simple_tree->setModel(&object_model_);
|
||||
tree_tab->addTab(simple_tree, tr("Simple"));
|
||||
connect(simple_tree->selectionModel(), &QItemSelectionModel::currentRowChanged, this, &MainWindow::SelectionChanged);
|
||||
|
||||
auto lowlevel_tree = new QTreeView();
|
||||
lowlevel_tree->setModel(&chunk_model_);
|
||||
tree_tab->addTab(lowlevel_tree, tr("Advanced"));
|
||||
connect(lowlevel_tree->selectionModel(), &QItemSelectionModel::currentRowChanged, this, &MainWindow::SelectionChanged);
|
||||
|
||||
config_stack_ = new QStackedWidget();
|
||||
splitter->addWidget(config_stack_);
|
||||
|
@ -51,10 +57,12 @@ MainWindow::MainWindow(QWidget *parent) :
|
|||
|
||||
void MainWindow::OpenFilename(const QString &s)
|
||||
{
|
||||
model_.SetChunk(nullptr);
|
||||
object_model_.SetChunk(nullptr);
|
||||
chunk_model_.SetChunk(nullptr);
|
||||
SetPanel(panel_blank_, nullptr);
|
||||
chunk_.Read(s.toStdString());
|
||||
model_.SetChunk(&chunk_);
|
||||
object_model_.SetChunk(&chunk_);
|
||||
chunk_model_.SetChunk(&chunk_);
|
||||
}
|
||||
|
||||
void MainWindow::InitializeMenuBar()
|
||||
|
|
|
@ -6,6 +6,7 @@
|
|||
#include <QStackedWidget>
|
||||
|
||||
#include "chunkmodel.h"
|
||||
#include "objectmodel.h"
|
||||
#include "panels/mxch.h"
|
||||
#include "panels/mxhd.h"
|
||||
#include "panels/mxob.h"
|
||||
|
@ -30,7 +31,8 @@ private:
|
|||
|
||||
void SetPanel(Panel *panel, si::Chunk *chunk);
|
||||
|
||||
ChunkModel model_;
|
||||
ObjectModel object_model_;
|
||||
ChunkModel chunk_model_;
|
||||
si::Chunk chunk_;
|
||||
|
||||
QStackedWidget *config_stack_;
|
||||
|
|
119
app/objectmodel.cpp
Normal file
119
app/objectmodel.cpp
Normal file
|
@ -0,0 +1,119 @@
|
|||
#include "objectmodel.h"
|
||||
|
||||
#define super AbstractSIItemModel
|
||||
|
||||
using namespace si;
|
||||
|
||||
ObjectModel::ObjectModel(QObject *parent) :
|
||||
super{parent}
|
||||
{
|
||||
}
|
||||
|
||||
int ObjectModel::columnCount(const QModelIndex &parent) const
|
||||
{
|
||||
return kColCount;
|
||||
}
|
||||
|
||||
QModelIndex ObjectModel::index(int row, int column, const QModelIndex &parent) const
|
||||
{
|
||||
return createIndex(row, column, GetItem(row));
|
||||
}
|
||||
|
||||
QModelIndex ObjectModel::parent(const QModelIndex &index) const
|
||||
{
|
||||
return QModelIndex();
|
||||
}
|
||||
|
||||
int ObjectModel::rowCount(const QModelIndex &parent) const
|
||||
{
|
||||
if (parent.isValid()) {
|
||||
return 0;
|
||||
} else {
|
||||
Chunk *mxof = GetMxOf();
|
||||
if (!mxof) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
return mxof->data("Offsets").size() / sizeof(u32);
|
||||
}
|
||||
}
|
||||
|
||||
QVariant ObjectModel::data(const QModelIndex &index, int role) const
|
||||
{
|
||||
u32 offset;
|
||||
Chunk *c = GetItem(index.row(), &offset);
|
||||
|
||||
switch (role) {
|
||||
case Qt::DisplayRole:
|
||||
|
||||
switch (index.column()) {
|
||||
case kColIndex:
|
||||
return index.row();
|
||||
case kColOffset:
|
||||
return QStringLiteral("0x%1").arg(QString::number(offset, 16).toUpper());
|
||||
case kColName:
|
||||
if (c) {
|
||||
Chunk *mxob = c->FindChildWithType(Chunk::TYPE_MxOb);
|
||||
if (mxob) {
|
||||
return QString(mxob->data("Name"));
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
return QVariant();
|
||||
}
|
||||
|
||||
QVariant ObjectModel::headerData(int section, Qt::Orientation orientation, int role) const
|
||||
{
|
||||
if (orientation == Qt::Horizontal && role == Qt::DisplayRole) {
|
||||
switch (section) {
|
||||
case kColIndex:
|
||||
return tr("Index");
|
||||
case kColOffset:
|
||||
return tr("Offset");
|
||||
case kColName:
|
||||
return tr("Name");
|
||||
}
|
||||
}
|
||||
|
||||
return super::headerData(section, orientation, role);
|
||||
}
|
||||
|
||||
Chunk *ObjectModel::GetMxOf() const
|
||||
{
|
||||
Chunk *root = this->root();
|
||||
if (!root) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return root->FindChildWithType(Chunk::TYPE_MxOf);
|
||||
}
|
||||
|
||||
Chunk *ObjectModel::GetItem(size_t index, si::u32 *offset_out) const
|
||||
{
|
||||
Chunk *mxof = GetMxOf();
|
||||
if (!mxof) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
const Data &offset_bytes = mxof->data("Offsets");
|
||||
if (index >= offset_bytes.size()/sizeof(u32)) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
const u32 *offsets = reinterpret_cast<const u32*>(offset_bytes.data());
|
||||
u32 offset = offsets[index];
|
||||
if (offset_out) {
|
||||
*offset_out = offset;
|
||||
}
|
||||
|
||||
if (offset == 0) {
|
||||
return NULL;
|
||||
} else {
|
||||
return root()->FindChildWithOffset(offset);
|
||||
}
|
||||
}
|
33
app/objectmodel.h
Normal file
33
app/objectmodel.h
Normal file
|
@ -0,0 +1,33 @@
|
|||
#ifndef OBJECTMODEL_H
|
||||
#define OBJECTMODEL_H
|
||||
|
||||
#include "abstractsiitemmodel.h"
|
||||
|
||||
class ObjectModel : public AbstractSIItemModel
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
enum Columns {
|
||||
kColIndex,
|
||||
kColOffset,
|
||||
kColName,
|
||||
|
||||
kColCount
|
||||
};
|
||||
|
||||
explicit ObjectModel(QObject *parent = nullptr);
|
||||
|
||||
virtual int columnCount(const QModelIndex &parent = QModelIndex()) const override;
|
||||
virtual QModelIndex index(int row, int column, const QModelIndex &parent = QModelIndex()) const override;
|
||||
virtual QModelIndex parent(const QModelIndex &index) const override;
|
||||
virtual int rowCount(const QModelIndex &parent = QModelIndex()) const override;
|
||||
virtual QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override;
|
||||
virtual QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const override;
|
||||
|
||||
private:
|
||||
si::Chunk *GetMxOf() const;
|
||||
si::Chunk *GetItem(size_t index, si::u32 *offset_out = NULL) const;
|
||||
|
||||
};
|
||||
|
||||
#endif // OBJECTMODEL_H
|
|
@ -92,7 +92,7 @@ void MxChPanel::OnOpeningData(Chunk *chunk)
|
|||
}
|
||||
|
||||
const Data &data = chunk->data("Data");
|
||||
QByteArray ba(data.data(), data.size());
|
||||
QByteArray ba(data.data(), int(data.size()));
|
||||
data_edit_->setPlainText(ba.toHex());
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue