Add onBorderMetatileChanged, onBorderResized, implement some basic border API

This commit is contained in:
GriffinR 2022-08-29 12:44:17 -04:00
parent 8f90ca64b4
commit 21ed9bc140
9 changed files with 122 additions and 18 deletions

View file

@ -17,6 +17,10 @@
#define DEFAULT_BORDER_WIDTH 2 #define DEFAULT_BORDER_WIDTH 2
#define DEFAULT_BORDER_HEIGHT 2 #define DEFAULT_BORDER_HEIGHT 2
// Maximum based only on data type (u8) of map border width/height
#define MAX_BORDER_WIDTH 255
#define MAX_BORDER_HEIGHT 255
// Number of metatiles to draw out from edge of map. Could allow modification of this in the future. // Number of metatiles to draw out from edge of map. Could allow modification of this in the future.
// porymap will reflect changes to it, but the value is hard-coded in the projects at the moment // porymap will reflect changes to it, but the value is hard-coded in the projects at the moment
#define BORDER_DISTANCE 7 #define BORDER_DISTANCE 7
@ -82,6 +86,9 @@ public:
bool getBlock(int x, int y, Block *out); bool getBlock(int x, int y, Block *out);
void setBlock(int x, int y, Block block, bool enableScriptCallback = false); void setBlock(int x, int y, Block block, bool enableScriptCallback = false);
void setBlockdata(Blockdata blockdata); void setBlockdata(Blockdata blockdata);
uint16_t getBorderMetatileId(int x, int y);
void setBorderMetatileId(int x, int y, uint16_t metatileId, bool enableScriptCallback = false);
void setBorderBlockData(Blockdata blockdata);
void floodFillCollisionElevation(int x, int y, uint16_t collision, uint16_t elevation); void floodFillCollisionElevation(int x, int y, uint16_t collision, uint16_t elevation);
void _floodFillCollisionElevation(int x, int y, uint16_t collision, uint16_t elevation); void _floodFillCollisionElevation(int x, int y, uint16_t collision, uint16_t elevation);
void magicFillCollisionElevation(int x, int y, uint16_t collision, uint16_t elevation); void magicFillCollisionElevation(int x, int y, uint16_t collision, uint16_t elevation);
@ -96,6 +103,7 @@ public:
void cacheBorder(); void cacheBorder();
bool hasUnsavedChanges(); bool hasUnsavedChanges();
bool isWithinBounds(int x, int y); bool isWithinBounds(int x, int y);
bool isWithinBorderBounds(int x, int y);
// for memory management // for memory management
QVector<Event *> ownedEvents; QVector<Event *> ownedEvents;

View file

@ -46,6 +46,8 @@ public:
Q_INVOKABLE QJSValue getBlock(int x, int y); Q_INVOKABLE QJSValue getBlock(int x, int y);
void tryRedrawMapArea(bool forceRedraw); void tryRedrawMapArea(bool forceRedraw);
void tryCommitMapChanges(bool commitChanges); void tryCommitMapChanges(bool commitChanges);
void tryRedrawBorder(bool forceRedraw);
void tryCommitBorderChanges(bool commitChanges);
Q_INVOKABLE void setBlock(int x, int y, int tile, int collision, int elevation, bool forceRedraw = true, bool commitChanges = true); Q_INVOKABLE void setBlock(int x, int y, int tile, int collision, int elevation, bool forceRedraw = true, bool commitChanges = true);
Q_INVOKABLE void setBlocksFromSelection(int x, int y, bool forceRedraw = true, bool commitChanges = true); Q_INVOKABLE void setBlocksFromSelection(int x, int y, bool forceRedraw = true, bool commitChanges = true);
Q_INVOKABLE int getMetatileId(int x, int y); Q_INVOKABLE int getMetatileId(int x, int y);

View file

@ -12,10 +12,12 @@ enum CallbackType {
OnProjectOpened, OnProjectOpened,
OnProjectClosed, OnProjectClosed,
OnBlockChanged, OnBlockChanged,
OnBorderMetatileChanged,
OnBlockHoverChanged, OnBlockHoverChanged,
OnBlockHoverCleared, OnBlockHoverCleared,
OnMapOpened, OnMapOpened,
OnMapResized, OnMapResized,
OnBorderResized,
OnMapShifted, OnMapShifted,
OnTilesetUpdated, OnTilesetUpdated,
OnMainTabChanged, OnMainTabChanged,
@ -40,10 +42,12 @@ public:
static void cb_ProjectOpened(QString projectPath); static void cb_ProjectOpened(QString projectPath);
static void cb_ProjectClosed(QString projectPath); static void cb_ProjectClosed(QString projectPath);
static void cb_MetatileChanged(int x, int y, Block prevBlock, Block newBlock); static void cb_MetatileChanged(int x, int y, Block prevBlock, Block newBlock);
static void cb_BorderMetatileChanged(int x, int y, uint16_t prevMetatileId, uint16_t newMetatileId);
static void cb_BlockHoverChanged(int x, int y); static void cb_BlockHoverChanged(int x, int y);
static void cb_BlockHoverCleared(); static void cb_BlockHoverCleared();
static void cb_MapOpened(QString mapName); static void cb_MapOpened(QString mapName);
static void cb_MapResized(int oldWidth, int oldHeight, int newWidth, int newHeight); static void cb_MapResized(int oldWidth, int oldHeight, int newWidth, int newHeight);
static void cb_BorderResized(int oldWidth, int oldHeight, int newWidth, int newHeight);
static void cb_MapShifted(int xDelta, int yDelta); static void cb_MapShifted(int xDelta, int yDelta);
static void cb_TilesetUpdated(QString tilesetName); static void cb_TilesetUpdated(QString tilesetName);
static void cb_MainTabChanged(int oldTab, int newTab); static void cb_MainTabChanged(int oldTab, int newTab);

View file

@ -101,7 +101,7 @@ void PaintBorder::redo() {
if (!map) return; if (!map) return;
map->layout->border = newBorder; map->setBorderBlockData(newBorder);
map->borderItem->draw(); map->borderItem->draw();
} }
@ -109,7 +109,7 @@ void PaintBorder::redo() {
void PaintBorder::undo() { void PaintBorder::undo() {
if (!map) return; if (!map) return;
map->layout->border = oldBorder; map->setBorderBlockData(oldBorder);
map->borderItem->draw(); map->borderItem->draw();

View file

@ -328,9 +328,15 @@ void Map::setBorderDimensions(int newWidth, int newHeight, bool setNewBlockdata)
setNewBorderDimensionsBlockdata(newWidth, newHeight); setNewBorderDimensionsBlockdata(newWidth, newHeight);
} }
int oldWidth = layout->border_width.toInt();
int oldHeight = layout->border_height.toInt();
layout->border_width = QString::number(newWidth); layout->border_width = QString::number(newWidth);
layout->border_height = QString::number(newHeight); layout->border_height = QString::number(newHeight);
if (oldWidth != newWidth || oldHeight != newHeight) {
Scripting::cb_BorderResized(oldWidth, oldHeight, newWidth, newHeight);
}
emit mapChanged(this); emit mapChanged(this);
} }
@ -367,6 +373,35 @@ void Map::setBlockdata(Blockdata blockdata) {
} }
} }
uint16_t Map::getBorderMetatileId(int x, int y) {
int i = y * getBorderWidth() + x;
return layout->border[i].metatileId;
}
void Map::setBorderMetatileId(int x, int y, uint16_t metatileId, bool enableScriptCallback) {
int i = y * getBorderWidth() + x;
if (i < layout->border.size()) {
uint16_t prevMetatileId = layout->border[i].metatileId;
layout->border[i].metatileId = metatileId;
if (prevMetatileId != metatileId && enableScriptCallback) {
Scripting::cb_BorderMetatileChanged(x, y, prevMetatileId, metatileId);
}
}
}
void Map::setBorderBlockData(Blockdata blockdata) {
int width = getBorderWidth();
int size = qMin(blockdata.size(), layout->border.size());
for (int i = 0; i < size; i++) {
Block prevBlock = layout->border.at(i);
Block newBlock = blockdata.at(i);
if (prevBlock != newBlock) {
layout->border.replace(i, newBlock);
Scripting::cb_BorderMetatileChanged(i % width, i / width, prevBlock.metatileId, newBlock.metatileId);
}
}
}
void Map::_floodFillCollisionElevation(int x, int y, uint16_t collision, uint16_t elevation) { void Map::_floodFillCollisionElevation(int x, int y, uint16_t collision, uint16_t elevation) {
QList<QPoint> todo; QList<QPoint> todo;
todo.append(QPoint(x, y)); todo.append(QPoint(x, y));
@ -474,3 +509,7 @@ bool Map::hasUnsavedChanges() {
bool Map::isWithinBounds(int x, int y) { bool Map::isWithinBounds(int x, int y) {
return (x >= 0 && x < this->getWidth() && y >= 0 && y < this->getHeight()); return (x >= 0 && x < this->getWidth() && y >= 0 && y < this->getHeight());
} }
bool Map::isWithinBorderBounds(int x, int y) {
return (x >= 0 && x < this->getBorderWidth() && y >= 0 && y < this->getBorderHeight());
}

View file

@ -2906,9 +2906,8 @@ void MainWindow::on_pushButton_ChangeDimensions_clicked()
bheightSpinBox->setMinimum(1); bheightSpinBox->setMinimum(1);
widthSpinBox->setMaximum(editor->project->getMaxMapWidth()); widthSpinBox->setMaximum(editor->project->getMaxMapWidth());
heightSpinBox->setMaximum(editor->project->getMaxMapHeight()); heightSpinBox->setMaximum(editor->project->getMaxMapHeight());
// Maximum based only on data type (u8) of map border width/height bwidthSpinBox->setMaximum(MAX_BORDER_WIDTH);
bwidthSpinBox->setMaximum(255); bheightSpinBox->setMaximum(MAX_BORDER_HEIGHT);
bheightSpinBox->setMaximum(255);
widthSpinBox->setValue(editor->map->getWidth()); widthSpinBox->setValue(editor->map->getWidth());
heightSpinBox->setValue(editor->map->getHeight()); heightSpinBox->setValue(editor->map->getHeight());
bwidthSpinBox->setValue(editor->map->getBorderWidth()); bwidthSpinBox->setValue(editor->map->getBorderWidth());

View file

@ -50,6 +50,16 @@ void MainWindow::tryCommitMapChanges(bool commitChanges) {
} }
} }
void MainWindow::tryRedrawBorder(bool forceRedraw) {
if (!forceRedraw) return;
// TODO
}
void MainWindow::tryCommitBorderChanges(bool commitChanges) {
if (!commitChanges) return;
// TODO
}
void MainWindow::setBlock(int x, int y, int tile, int collision, int elevation, bool forceRedraw, bool commitChanges) { void MainWindow::setBlock(int x, int y, int tile, int collision, int elevation, bool forceRedraw, bool commitChanges) {
if (!this->editor || !this->editor->map) if (!this->editor || !this->editor->map)
return; return;
@ -91,13 +101,19 @@ void MainWindow::setMetatileId(int x, int y, int metatileId, bool forceRedraw, b
int MainWindow::getBorderMetatileId(int x, int y) { int MainWindow::getBorderMetatileId(int x, int y) {
if (!this->editor || !this->editor->map) if (!this->editor || !this->editor->map)
return 0; return 0;
// TODO if (!this->editor->map->isWithinBorderBounds(x, y))
return 0;
return this->editor->map->getBorderMetatileId(x, y);
} }
void MainWindow::setBorderMetatileId(int x, int y, int metatileId, bool forceRedraw, bool commitChanges) { void MainWindow::setBorderMetatileId(int x, int y, int metatileId, bool forceRedraw, bool commitChanges) {
if (!this->editor || !this->editor->map) if (!this->editor || !this->editor->map)
return; return;
// TODO if (!this->editor->map->isWithinBorderBounds(x, y))
return;
this->editor->map->setBorderMetatileId(x, y, metatileId);
this->tryCommitBorderChanges(commitChanges);
this->tryRedrawBorder(forceRedraw);
} }
int MainWindow::getCollision(int x, int y) { int MainWindow::getCollision(int x, int y) {
@ -213,19 +229,19 @@ int MainWindow::getHeight() {
QJSValue MainWindow::getBorderDimensions() { QJSValue MainWindow::getBorderDimensions() {
if (!this->editor || !this->editor->map) if (!this->editor || !this->editor->map)
return QJSValue(); return QJSValue();
// TODO return Scripting::dimensions(this->editor->map->getBorderWidth(), this->editor->map->getBorderHeight());
} }
int MainWindow::getBorderWidth() { int MainWindow::getBorderWidth() {
if (!this->editor || !this->editor->map) if (!this->editor || !this->editor->map)
return 0; return 0;
// TODO return this->editor->map->getBorderWidth();
} }
int MainWindow::getBorderHeight() { int MainWindow::getBorderHeight() {
if (!this->editor || !this->editor->map) if (!this->editor || !this->editor->map)
return 0; return 0;
// TODO return this->editor->map->getBorderHeight();
} }
void MainWindow::setDimensions(int width, int height) { void MainWindow::setDimensions(int width, int height) {
@ -259,20 +275,32 @@ void MainWindow::setHeight(int height) {
} }
void MainWindow::setBorderDimensions(int width, int height) { void MainWindow::setBorderDimensions(int width, int height) {
if (!this->editor || !this->editor->map) if (!this->editor || !this->editor->map || !projectConfig.getUseCustomBorderSize())
return; return;
if (width < 1 || height < 1 || width > MAX_BORDER_WIDTH || height > MAX_BORDER_HEIGHT)
return;
this->editor->map->setBorderDimensions(width, height);
this->tryCommitBorderChanges(true);
// TODO // TODO
} }
void MainWindow::setBorderWidth(int width) { void MainWindow::setBorderWidth(int width) {
if (!this->editor || !this->editor->map) if (!this->editor || !this->editor->map || !projectConfig.getUseCustomBorderSize())
return; return;
if (width < 1 || width > MAX_BORDER_WIDTH)
return;
this->editor->map->setBorderDimensions(width, this->editor->map->getBorderHeight());
this->tryCommitBorderChanges(true);
// TODO // TODO
} }
void MainWindow::setBorderHeight(int height) { void MainWindow::setBorderHeight(int height) {
if (!this->editor || !this->editor->map) if (!this->editor || !this->editor->map || !projectConfig.getUseCustomBorderSize())
return; return;
if (height < 1 || height > MAX_BORDER_HEIGHT)
return;
this->editor->map->setBorderDimensions(this->editor->map->getBorderWidth(), height);
this->tryCommitBorderChanges(true);
// TODO // TODO
} }

View file

@ -5,10 +5,12 @@ QMap<CallbackType, QString> callbackFunctions = {
{OnProjectOpened, "onProjectOpened"}, {OnProjectOpened, "onProjectOpened"},
{OnProjectClosed, "onProjectClosed"}, {OnProjectClosed, "onProjectClosed"},
{OnBlockChanged, "onBlockChanged"}, {OnBlockChanged, "onBlockChanged"},
{OnBorderMetatileChanged, "onBorderMetatileChanged"},
{OnBlockHoverChanged, "onBlockHoverChanged"}, {OnBlockHoverChanged, "onBlockHoverChanged"},
{OnBlockHoverCleared, "onBlockHoverCleared"}, {OnBlockHoverCleared, "onBlockHoverCleared"},
{OnMapOpened, "onMapOpened"}, {OnMapOpened, "onMapOpened"},
{OnMapResized, "onMapResized"}, {OnMapResized, "onMapResized"},
{OnBorderResized, "onBorderResized"},
{OnMapShifted, "onMapShifted"}, {OnMapShifted, "onMapShifted"},
{OnTilesetUpdated, "onTilesetUpdated"}, {OnTilesetUpdated, "onTilesetUpdated"},
{OnMainTabChanged, "onMainTabChanged"}, {OnMainTabChanged, "onMainTabChanged"},
@ -140,6 +142,18 @@ void Scripting::cb_MetatileChanged(int x, int y, Block prevBlock, Block newBlock
instance->invokeCallback(OnBlockChanged, args); instance->invokeCallback(OnBlockChanged, args);
} }
void Scripting::cb_BorderMetatileChanged(int x, int y, uint16_t prevMetatileId, uint16_t newMetatileId) {
if (!instance) return;
QJSValueList args {
x,
y,
prevMetatileId,
newMetatileId,
};
instance->invokeCallback(OnBorderMetatileChanged, args);
}
void Scripting::cb_BlockHoverChanged(int x, int y) { void Scripting::cb_BlockHoverChanged(int x, int y) {
if (!instance) return; if (!instance) return;
@ -176,6 +190,18 @@ void Scripting::cb_MapResized(int oldWidth, int oldHeight, int newWidth, int new
instance->invokeCallback(OnMapResized, args); instance->invokeCallback(OnMapResized, args);
} }
void Scripting::cb_BorderResized(int oldWidth, int oldHeight, int newWidth, int newHeight) {
if (!instance) return;
QJSValueList args {
oldWidth,
oldHeight,
newWidth,
newHeight,
};
instance->invokeCallback(OnBorderResized, args);
}
void Scripting::cb_MapShifted(int xDelta, int yDelta) { void Scripting::cb_MapShifted(int xDelta, int yDelta) {
if (!instance) return; if (!instance) return;

View file

@ -15,9 +15,8 @@ void BorderMetatilesPixmapItem::mousePressEvent(QGraphicsSceneMouseEvent *event)
for (int i = 0; i < selectionDimensions.x() && (i + pos.x()) < width; i++) { for (int i = 0; i < selectionDimensions.x() && (i + pos.x()) < width; i++) {
for (int j = 0; j < selectionDimensions.y() && (j + pos.y()) < height; j++) { for (int j = 0; j < selectionDimensions.y() && (j + pos.y()) < height; j++) {
int blockIndex = (j + pos.y()) * width + (i + pos.x());
uint16_t metatileId = selectedMetatiles->at(j * selectionDimensions.x() + i); uint16_t metatileId = selectedMetatiles->at(j * selectionDimensions.x() + i);
map->layout->border[blockIndex].metatileId = metatileId; map->setBorderMetatileId(pos.x() + i, pos.y() + j, metatileId, true);
} }
} }
@ -40,9 +39,8 @@ void BorderMetatilesPixmapItem::draw() {
for (int j = 0; j < height; j++) { for (int j = 0; j < height; j++) {
int x = i * 16; int x = i * 16;
int y = j * 16; int y = j * 16;
int index = j * width + i;
QImage metatile_image = getMetatileImage( QImage metatile_image = getMetatileImage(
map->layout->border.value(index).metatileId, map->getBorderMetatileId(i, j),
map->layout->tileset_primary, map->layout->tileset_primary,
map->layout->tileset_secondary, map->layout->tileset_secondary,
map->metatileLayerOrder, map->metatileLayerOrder,