Add edit-undo history to tileset metatile editing
This commit is contained in:
parent
888270f3ef
commit
e42c2e1a81
7 changed files with 149 additions and 14 deletions
|
@ -407,7 +407,15 @@
|
|||
<addaction name="actionChange_Metatiles_Count"/>
|
||||
<addaction name="actionChange_Palettes"/>
|
||||
</widget>
|
||||
<widget class="QMenu" name="menuEdit">
|
||||
<property name="title">
|
||||
<string>Edit</string>
|
||||
</property>
|
||||
<addaction name="actionUndo"/>
|
||||
<addaction name="actionRedo"/>
|
||||
</widget>
|
||||
<addaction name="menuFile"/>
|
||||
<addaction name="menuEdit"/>
|
||||
<addaction name="menuTools"/>
|
||||
</widget>
|
||||
<widget class="QStatusBar" name="statusbar"/>
|
||||
|
@ -439,6 +447,22 @@
|
|||
<string>Change Palettes</string>
|
||||
</property>
|
||||
</action>
|
||||
<action name="actionUndo">
|
||||
<property name="text">
|
||||
<string>Undo</string>
|
||||
</property>
|
||||
<property name="shortcut">
|
||||
<string>Ctrl+Z</string>
|
||||
</property>
|
||||
</action>
|
||||
<action name="actionRedo">
|
||||
<property name="text">
|
||||
<string>Redo</string>
|
||||
</property>
|
||||
<property name="shortcut">
|
||||
<string>Ctrl+Y</string>
|
||||
</property>
|
||||
</action>
|
||||
</widget>
|
||||
<resources/>
|
||||
<connections/>
|
||||
|
|
|
@ -14,6 +14,7 @@ public:
|
|||
uint8_t layerType;
|
||||
|
||||
Metatile *copy();
|
||||
void copyInPlace(Metatile*);
|
||||
static int getBlockIndex(int);
|
||||
};
|
||||
|
||||
|
|
|
@ -13,14 +13,18 @@ public:
|
|||
this->metatile = metatile;
|
||||
this->primaryTileset = primaryTileset;
|
||||
this->secondaryTileset = secondaryTileset;
|
||||
this->clearLastModifiedCoords();
|
||||
}
|
||||
void draw();
|
||||
void setTilesets(Tileset*, Tileset*);
|
||||
void setMetatile(Metatile*);
|
||||
void clearLastModifiedCoords();
|
||||
private:
|
||||
Metatile* metatile;
|
||||
Tileset *primaryTileset;
|
||||
Tileset *secondaryTileset;
|
||||
QPoint prevChangedTile;
|
||||
void getBoundedCoords(QPointF, int*, int*);
|
||||
signals:
|
||||
void tileChanged(int, int);
|
||||
void selectedTilesChanged(QPoint, int, int);
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
|
||||
#include <QMainWindow>
|
||||
#include "project.h"
|
||||
#include "history.h"
|
||||
#include "paletteeditor.h"
|
||||
#include "tileseteditormetatileselector.h"
|
||||
#include "tileseteditortileselector.h"
|
||||
|
@ -12,6 +13,22 @@ namespace Ui {
|
|||
class TilesetEditor;
|
||||
}
|
||||
|
||||
class MetatileHistoryItem {
|
||||
public:
|
||||
MetatileHistoryItem(uint16_t metatileId, Metatile *prevMetatile, Metatile *newMetatile) {
|
||||
this->metatileId = metatileId;
|
||||
this->prevMetatile = prevMetatile;
|
||||
this->newMetatile = newMetatile;
|
||||
}
|
||||
~MetatileHistoryItem() {
|
||||
delete this->prevMetatile;
|
||||
delete this->newMetatile;
|
||||
}
|
||||
uint16_t metatileId;
|
||||
Metatile *prevMetatile;
|
||||
Metatile *newMetatile;
|
||||
};
|
||||
|
||||
class TilesetEditor : public QMainWindow
|
||||
{
|
||||
Q_OBJECT
|
||||
|
@ -41,10 +58,6 @@ private slots:
|
|||
|
||||
void on_checkBox_yFlip_stateChanged(int arg1);
|
||||
|
||||
void on_comboBox_metatileBehaviors_currentIndexChanged(const QString &arg1);
|
||||
|
||||
void on_comboBox_layerType_currentIndexChanged(int index);
|
||||
|
||||
void on_actionSave_Tileset_triggered();
|
||||
|
||||
void on_actionImport_Primary_Tiles_triggered();
|
||||
|
@ -55,6 +68,14 @@ private slots:
|
|||
|
||||
void on_actionChange_Palettes_triggered();
|
||||
|
||||
void on_actionUndo_triggered();
|
||||
|
||||
void on_actionRedo_triggered();
|
||||
|
||||
void on_comboBox_metatileBehaviors_activated(const QString &arg1);
|
||||
|
||||
void on_comboBox_layerType_activated(int arg1);
|
||||
|
||||
private:
|
||||
void closeEvent(QCloseEvent*);
|
||||
void initMetatileSelector();
|
||||
|
@ -65,6 +86,7 @@ private:
|
|||
void importTilesetTiles(Tileset*, bool);
|
||||
void refresh();
|
||||
Ui::TilesetEditor *ui;
|
||||
History<MetatileHistoryItem*> metatileHistory;
|
||||
TilesetEditorMetatileSelector *metatileSelector = nullptr;
|
||||
TilesetEditorTileSelector *tileSelector = nullptr;
|
||||
MetatileLayersItem *metatileLayersItem = nullptr;
|
||||
|
|
|
@ -18,6 +18,14 @@ Metatile* Metatile::copy() {
|
|||
return copy;
|
||||
}
|
||||
|
||||
void Metatile::copyInPlace(Metatile *other) {
|
||||
this->behavior = other->behavior;
|
||||
this->layerType = other->layerType;
|
||||
for (int i = 0; i < this->tiles->length(); i++) {
|
||||
(*this->tiles)[i] = other->tiles->at(i);
|
||||
}
|
||||
}
|
||||
|
||||
int Metatile::getBlockIndex(int index) {
|
||||
if (index < Project::getNumMetatilesPrimary()) {
|
||||
return index;
|
||||
|
|
|
@ -29,12 +29,14 @@ void MetatileLayersItem::draw() {
|
|||
|
||||
void MetatileLayersItem::setMetatile(Metatile *metatile) {
|
||||
this->metatile = metatile;
|
||||
this->clearLastModifiedCoords();
|
||||
}
|
||||
|
||||
void MetatileLayersItem::setTilesets(Tileset *primaryTileset, Tileset *secondaryTileset) {
|
||||
this->primaryTileset = primaryTileset;
|
||||
this->secondaryTileset = secondaryTileset;
|
||||
this->draw();
|
||||
this->clearLastModifiedCoords();
|
||||
}
|
||||
|
||||
void MetatileLayersItem::mousePressEvent(QGraphicsSceneMouseEvent *event) {
|
||||
|
@ -45,17 +47,17 @@ void MetatileLayersItem::mousePressEvent(QGraphicsSceneMouseEvent *event) {
|
|||
emit this->selectedTilesChanged(selectionOrigin, dimensions.x(), dimensions.y());
|
||||
this->drawSelection();
|
||||
} else {
|
||||
QPointF pos = event->pos();
|
||||
int x = static_cast<int>(pos.x()) / 16;
|
||||
int y = static_cast<int>(pos.y()) / 16;
|
||||
emit this->tileChanged(x, y);
|
||||
int x, y;
|
||||
this->getBoundedCoords(event->pos(), &x, &y);
|
||||
if (prevChangedTile.x() != x || prevChangedTile.y() != y) {
|
||||
this->prevChangedTile.setX(x);
|
||||
this->prevChangedTile.setY(y);
|
||||
emit this->tileChanged(x, y);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void MetatileLayersItem::mouseMoveEvent(QGraphicsSceneMouseEvent *event) {
|
||||
QPointF pos = event->pos();
|
||||
int x = static_cast<int>(pos.x()) / 16;
|
||||
int y = static_cast<int>(pos.y()) / 16;
|
||||
if (event->buttons() & Qt::RightButton) {
|
||||
SelectablePixmapItem::mouseMoveEvent(event);
|
||||
QPoint selectionOrigin = this->getSelectionStart();
|
||||
|
@ -63,7 +65,13 @@ void MetatileLayersItem::mouseMoveEvent(QGraphicsSceneMouseEvent *event) {
|
|||
emit this->selectedTilesChanged(selectionOrigin, dimensions.x(), dimensions.y());
|
||||
this->drawSelection();
|
||||
} else {
|
||||
emit this->tileChanged(x, y);
|
||||
int x, y;
|
||||
this->getBoundedCoords(event->pos(), &x, &y);
|
||||
if (prevChangedTile.x() != x || prevChangedTile.y() != y) {
|
||||
this->prevChangedTile.setX(x);
|
||||
this->prevChangedTile.setY(y);
|
||||
emit this->tileChanged(x, y);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -77,3 +85,17 @@ void MetatileLayersItem::mouseReleaseEvent(QGraphicsSceneMouseEvent *event) {
|
|||
|
||||
this->draw();
|
||||
}
|
||||
|
||||
void MetatileLayersItem::clearLastModifiedCoords() {
|
||||
this->prevChangedTile.setX(-1);
|
||||
this->prevChangedTile.setY(-1);
|
||||
}
|
||||
|
||||
void MetatileLayersItem::getBoundedCoords(QPointF pos, int *x, int *y) {
|
||||
*x = static_cast<int>(pos.x()) / 16;
|
||||
*y = static_cast<int>(pos.y()) / 16;
|
||||
if (*x < 0) *x = 0;
|
||||
if (*y < 0) *y = 0;
|
||||
if (*x > 3) *x = 3;
|
||||
if (*y > 1) *y = 1;
|
||||
}
|
||||
|
|
|
@ -49,6 +49,9 @@ void TilesetEditor::init(Project *project, QString primaryTilesetLabel, QString
|
|||
this->initTileSelector();
|
||||
this->initSelectedTileItem();
|
||||
this->metatileSelector->select(0);
|
||||
|
||||
MetatileHistoryItem *commit = new MetatileHistoryItem(0, nullptr, this->metatile->copy());
|
||||
metatileHistory.push(commit);
|
||||
}
|
||||
|
||||
void TilesetEditor::setTilesets(QString primaryTilesetLabel, QString secondaryTilesetLabel) {
|
||||
|
@ -191,6 +194,7 @@ void TilesetEditor::onSelectedTilesChanged() {
|
|||
}
|
||||
|
||||
void TilesetEditor::onMetatileLayerTileChanged(int x, int y) {
|
||||
Metatile *prevMetatile = this->metatile->copy();
|
||||
int maxTileIndex = x < 2 ? 3 : 7;
|
||||
QPoint dimensions = this->tileSelector->getSelectionDimensions();
|
||||
QList<Tile> tiles = this->tileSelector->getSelectedTiles();
|
||||
|
@ -213,6 +217,9 @@ void TilesetEditor::onMetatileLayerTileChanged(int x, int y) {
|
|||
this->metatileSelector->draw();
|
||||
this->metatileLayersItem->draw();
|
||||
this->hasUnsavedChanges = true;
|
||||
|
||||
MetatileHistoryItem *commit = new MetatileHistoryItem(metatileSelector->getSelectedMetatile(), prevMetatile, this->metatile->copy());
|
||||
metatileHistory.push(commit);
|
||||
}
|
||||
|
||||
void TilesetEditor::onMetatileLayerSelectionChanged(QPoint selectionOrigin, int width, int height) {
|
||||
|
@ -228,6 +235,7 @@ void TilesetEditor::onMetatileLayerSelectionChanged(QPoint selectionOrigin, int
|
|||
}
|
||||
}
|
||||
this->tileSelector->setExternalSelection(width, height, tiles);
|
||||
this->metatileLayersItem->clearLastModifiedCoords();
|
||||
}
|
||||
|
||||
void TilesetEditor::on_spinBox_paletteSelector_valueChanged(int paletteId)
|
||||
|
@ -241,6 +249,7 @@ void TilesetEditor::on_spinBox_paletteSelector_valueChanged(int paletteId)
|
|||
if (this->paletteEditor) {
|
||||
this->paletteEditor->setPaletteId(paletteId);
|
||||
}
|
||||
this->metatileLayersItem->clearLastModifiedCoords();
|
||||
}
|
||||
|
||||
void TilesetEditor::on_checkBox_xFlip_stateChanged(int checked)
|
||||
|
@ -248,6 +257,7 @@ void TilesetEditor::on_checkBox_xFlip_stateChanged(int checked)
|
|||
this->tileXFlip = checked;
|
||||
this->tileSelector->setTileFlips(this->tileXFlip, this->tileYFlip);
|
||||
this->drawSelectedTiles();
|
||||
this->metatileLayersItem->clearLastModifiedCoords();
|
||||
}
|
||||
|
||||
void TilesetEditor::on_checkBox_yFlip_stateChanged(int checked)
|
||||
|
@ -255,19 +265,26 @@ void TilesetEditor::on_checkBox_yFlip_stateChanged(int checked)
|
|||
this->tileYFlip = checked;
|
||||
this->tileSelector->setTileFlips(this->tileXFlip, this->tileYFlip);
|
||||
this->drawSelectedTiles();
|
||||
this->metatileLayersItem->clearLastModifiedCoords();
|
||||
}
|
||||
|
||||
void TilesetEditor::on_comboBox_metatileBehaviors_currentIndexChanged(const QString &metatileBehavior)
|
||||
void TilesetEditor::on_comboBox_metatileBehaviors_activated(const QString &metatileBehavior)
|
||||
{
|
||||
if (this->metatile) {
|
||||
Metatile *prevMetatile = this->metatile->copy();
|
||||
this->metatile->behavior = static_cast<uint8_t>(project->metatileBehaviorMap[metatileBehavior]);
|
||||
MetatileHistoryItem *commit = new MetatileHistoryItem(metatileSelector->getSelectedMetatile(), prevMetatile, this->metatile->copy());
|
||||
metatileHistory.push(commit);
|
||||
}
|
||||
}
|
||||
|
||||
void TilesetEditor::on_comboBox_layerType_currentIndexChanged(int layerType)
|
||||
void TilesetEditor::on_comboBox_layerType_activated(int layerType)
|
||||
{
|
||||
if (this->metatile) {
|
||||
Metatile *prevMetatile = this->metatile->copy();
|
||||
this->metatile->layerType = static_cast<uint8_t>(layerType);
|
||||
MetatileHistoryItem *commit = new MetatileHistoryItem(metatileSelector->getSelectedMetatile(), prevMetatile, this->metatile->copy());
|
||||
metatileHistory.push(commit);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -475,3 +492,40 @@ void TilesetEditor::onPaletteEditorChangedPaletteColor() {
|
|||
void TilesetEditor::onPaletteEditorChangedPalette(int paletteId) {
|
||||
this->on_spinBox_paletteSelector_valueChanged(paletteId);
|
||||
}
|
||||
|
||||
void TilesetEditor::on_actionUndo_triggered()
|
||||
{
|
||||
MetatileHistoryItem *commit = this->metatileHistory.current();
|
||||
if (!commit) return;
|
||||
Metatile *prev = commit->prevMetatile;
|
||||
if (!prev) return;
|
||||
this->metatileHistory.back();
|
||||
|
||||
Metatile *temp = Tileset::getMetatile(commit->metatileId, this->primaryTileset, this->secondaryTileset);
|
||||
if (temp) {
|
||||
this->metatile = temp;
|
||||
this->metatile->copyInPlace(prev);
|
||||
this->metatileSelector->select(commit->metatileId);
|
||||
this->metatileSelector->draw();
|
||||
this->metatileLayersItem->draw();
|
||||
this->metatileLayersItem->clearLastModifiedCoords();
|
||||
}
|
||||
}
|
||||
|
||||
void TilesetEditor::on_actionRedo_triggered()
|
||||
{
|
||||
MetatileHistoryItem *commit = this->metatileHistory.next();
|
||||
if (!commit) return;
|
||||
Metatile *next = commit->newMetatile;
|
||||
if (!next) return;
|
||||
|
||||
Metatile *temp = Tileset::getMetatile(commit->metatileId, this->primaryTileset, this->secondaryTileset);
|
||||
if (temp) {
|
||||
this->metatile = Tileset::getMetatile(commit->metatileId, this->primaryTileset, this->secondaryTileset);
|
||||
this->metatile->copyInPlace(next);
|
||||
this->metatileSelector->select(commit->metatileId);
|
||||
this->metatileSelector->draw();
|
||||
this->metatileLayersItem->draw();
|
||||
this->metatileLayersItem->clearLastModifiedCoords();
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue