mirror of https://github.com/mgba-emu/mgba.git
Qt: Make clicking tiles work
This commit is contained in:
parent
a7ee79ff45
commit
405eafb969
|
@ -66,6 +66,8 @@ void mMapCacheConfigureSystem(struct mMapCache* cache, mMapCacheSystemInfo confi
|
||||||
void mMapCacheConfigureMap(struct mMapCache* cache, uint32_t mapStart);
|
void mMapCacheConfigureMap(struct mMapCache* cache, uint32_t mapStart);
|
||||||
void mMapCacheWriteVRAM(struct mMapCache* cache, uint32_t address);
|
void mMapCacheWriteVRAM(struct mMapCache* cache, uint32_t address);
|
||||||
|
|
||||||
|
uint32_t mMapCacheTileId(struct mMapCache* cache, unsigned x, unsigned y);
|
||||||
|
|
||||||
bool mMapCacheCheckTile(struct mMapCache* cache, const struct mMapCacheEntry* entry, unsigned x, unsigned y);
|
bool mMapCacheCheckTile(struct mMapCache* cache, const struct mMapCacheEntry* entry, unsigned x, unsigned y);
|
||||||
void mMapCacheCleanTile(struct mMapCache* cache, struct mMapCacheEntry* entry, unsigned x, unsigned y);
|
void mMapCacheCleanTile(struct mMapCache* cache, struct mMapCacheEntry* entry, unsigned x, unsigned y);
|
||||||
|
|
||||||
|
|
|
@ -114,7 +114,7 @@ static inline void _cleanTile(struct mMapCache* cache, const color_t* tile, colo
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline size_t _tileId(struct mMapCache* cache, unsigned x, unsigned y) {
|
uint32_t mMapCacheTileId(struct mMapCache* cache, unsigned x, unsigned y) {
|
||||||
int tilesWide = mMapCacheSystemInfoGetTilesWide(cache->sysConfig);
|
int tilesWide = mMapCacheSystemInfoGetTilesWide(cache->sysConfig);
|
||||||
int tilesHigh = mMapCacheSystemInfoGetTilesHigh(cache->sysConfig);
|
int tilesHigh = mMapCacheSystemInfoGetTilesHigh(cache->sysConfig);
|
||||||
int stride = 1 << mMapCacheSystemInfoGetMacroTileSize(cache->sysConfig);
|
int stride = 1 << mMapCacheSystemInfoGetMacroTileSize(cache->sysConfig);
|
||||||
|
@ -130,7 +130,7 @@ static inline size_t _tileId(struct mMapCache* cache, unsigned x, unsigned y) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void mMapCacheCleanTile(struct mMapCache* cache, struct mMapCacheEntry* entry, unsigned x, unsigned y) {
|
void mMapCacheCleanTile(struct mMapCache* cache, struct mMapCacheEntry* entry, unsigned x, unsigned y) {
|
||||||
size_t location = _tileId(cache, x, y);
|
size_t location = mMapCacheTileId(cache, x, y);
|
||||||
struct mMapCacheEntry* status = &cache->status[location];
|
struct mMapCacheEntry* status = &cache->status[location];
|
||||||
const color_t* tile = NULL;
|
const color_t* tile = NULL;
|
||||||
if (!mMapCacheEntryFlagsIsVramClean(status->flags)) {
|
if (!mMapCacheEntryFlagsIsVramClean(status->flags)) {
|
||||||
|
@ -156,7 +156,7 @@ void mMapCacheCleanTile(struct mMapCache* cache, struct mMapCacheEntry* entry, u
|
||||||
}
|
}
|
||||||
|
|
||||||
bool mMapCacheCheckTile(struct mMapCache* cache, const struct mMapCacheEntry* entry, unsigned x, unsigned y) {
|
bool mMapCacheCheckTile(struct mMapCache* cache, const struct mMapCacheEntry* entry, unsigned x, unsigned y) {
|
||||||
size_t location = _tileId(cache, x, y);
|
size_t location = mMapCacheTileId(cache, x, y);
|
||||||
struct mMapCacheEntry* status = &cache->status[location];
|
struct mMapCacheEntry* status = &cache->status[location];
|
||||||
int paletteId = mMapCacheEntryFlagsGetPaletteId(status->flags);
|
int paletteId = mMapCacheEntryFlagsGetPaletteId(status->flags);
|
||||||
const color_t* tile = NULL;
|
const color_t* tile = NULL;
|
||||||
|
|
|
@ -9,6 +9,7 @@
|
||||||
#include "GBAApp.h"
|
#include "GBAApp.h"
|
||||||
|
|
||||||
#include <QFontDatabase>
|
#include <QFontDatabase>
|
||||||
|
#include <QHBoxLayout>
|
||||||
|
|
||||||
#include <mgba/core/interface.h>
|
#include <mgba/core/interface.h>
|
||||||
#ifdef M_CORE_GBA
|
#ifdef M_CORE_GBA
|
||||||
|
@ -34,12 +35,25 @@ AssetTile::AssetTile(QWidget* parent)
|
||||||
const QFont font = QFontDatabase::systemFont(QFontDatabase::FixedFont);
|
const QFont font = QFontDatabase::systemFont(QFontDatabase::FixedFont);
|
||||||
|
|
||||||
m_ui.tileId->setFont(font);
|
m_ui.tileId->setFont(font);
|
||||||
|
m_ui.paletteId->setFont(font);
|
||||||
m_ui.address->setFont(font);
|
m_ui.address->setFont(font);
|
||||||
m_ui.r->setFont(font);
|
m_ui.r->setFont(font);
|
||||||
m_ui.g->setFont(font);
|
m_ui.g->setFont(font);
|
||||||
m_ui.b->setFont(font);
|
m_ui.b->setFont(font);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void AssetTile::addCustomProperty(const QString& id, const QString& visibleName) {
|
||||||
|
QHBoxLayout* newLayout = new QHBoxLayout;
|
||||||
|
newLayout->addWidget(new QLabel(visibleName));
|
||||||
|
QLabel* value = new QLabel;
|
||||||
|
value->setFont(QFontDatabase::systemFont(QFontDatabase::FixedFont));
|
||||||
|
value->setAlignment(Qt::AlignRight);
|
||||||
|
newLayout->addWidget(value);
|
||||||
|
m_customProperties[id] = value;
|
||||||
|
int index = layout()->indexOf(m_ui.line);
|
||||||
|
static_cast<QBoxLayout*>(layout())->insertLayout(index, newLayout);
|
||||||
|
}
|
||||||
|
|
||||||
void AssetTile::setController(std::shared_ptr<CoreController> controller) {
|
void AssetTile::setController(std::shared_ptr<CoreController> controller) {
|
||||||
m_cacheSet = controller->graphicCaches();
|
m_cacheSet = controller->graphicCaches();
|
||||||
switch (controller->platform()) {
|
switch (controller->platform()) {
|
||||||
|
@ -94,16 +108,30 @@ void AssetTile::selectIndex(int index) {
|
||||||
}
|
}
|
||||||
data = mTileCacheGetTile(tileCache, index, paletteId);
|
data = mTileCacheGetTile(tileCache, index, paletteId);
|
||||||
m_ui.tileId->setText(QString::number(dispIndex));
|
m_ui.tileId->setText(QString::number(dispIndex));
|
||||||
|
m_ui.paletteId->setText(QString::number(paletteId));
|
||||||
m_ui.address->setText(tr("%0%1%2")
|
m_ui.address->setText(tr("%0%1%2")
|
||||||
.arg(m_addressWidth == 4 ? index >= m_boundary / 2 : 0)
|
.arg(m_addressWidth == 4 ? index >= m_boundary / 2 : 0)
|
||||||
.arg(m_addressWidth == 4 ? ":" : "x")
|
.arg(m_addressWidth == 4 ? ":" : "x")
|
||||||
.arg(dispIndex * bpp | base, m_addressWidth, 16, QChar('0')));
|
.arg(dispIndex * bpp | base, m_addressWidth, 16, QChar('0')));
|
||||||
|
int flip = 0;
|
||||||
|
if (m_flipH) {
|
||||||
|
flip |= 007;
|
||||||
|
}
|
||||||
|
if (m_flipV) {
|
||||||
|
flip |= 070;
|
||||||
|
}
|
||||||
for (int i = 0; i < 64; ++i) {
|
for (int i = 0; i < 64; ++i) {
|
||||||
m_ui.preview->setColor(i, data[i]);
|
m_ui.preview->setColor(i ^ flip, data[i]);
|
||||||
}
|
}
|
||||||
m_ui.preview->update();
|
m_ui.preview->update();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void AssetTile::setFlip(bool h, bool v) {
|
||||||
|
m_flipH = h;
|
||||||
|
m_flipV = v;
|
||||||
|
selectIndex(m_index);
|
||||||
|
}
|
||||||
|
|
||||||
void AssetTile::selectColor(int index) {
|
void AssetTile::selectColor(int index) {
|
||||||
const color_t* data;
|
const color_t* data;
|
||||||
mTileCache* tileCache = m_tileCaches[m_index >= m_boundary];
|
mTileCache* tileCache = m_tileCaches[m_index >= m_boundary];
|
||||||
|
@ -122,3 +150,10 @@ void AssetTile::selectColor(int index) {
|
||||||
m_ui.b->setText(tr("0x%0 (%1)").arg(b, 2, 16, QChar('0')).arg(b, 2, 10, QChar('0')));
|
m_ui.b->setText(tr("0x%0 (%1)").arg(b, 2, 16, QChar('0')).arg(b, 2, 10, QChar('0')));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void AssetTile::setCustomProperty(const QString& id, const QVariant& value) {
|
||||||
|
QLabel* label = m_customProperties[id];
|
||||||
|
if (!label) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
label->setText(value.toString());
|
||||||
|
}
|
||||||
|
|
|
@ -21,12 +21,15 @@ Q_OBJECT
|
||||||
public:
|
public:
|
||||||
AssetTile(QWidget* parent = nullptr);
|
AssetTile(QWidget* parent = nullptr);
|
||||||
void setController(std::shared_ptr<CoreController>);
|
void setController(std::shared_ptr<CoreController>);
|
||||||
|
void addCustomProperty(const QString& id, const QString& visibleName);
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
void setPalette(int);
|
void setPalette(int);
|
||||||
void setBoundary(int boundary, int set0, int set1);
|
void setBoundary(int boundary, int set0, int set1);
|
||||||
void selectIndex(int);
|
void selectIndex(int);
|
||||||
|
void setFlip(bool h, bool v);
|
||||||
void selectColor(int);
|
void selectColor(int);
|
||||||
|
void setCustomProperty(const QString& id, const QVariant& value);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
Ui::AssetTile m_ui;
|
Ui::AssetTile m_ui;
|
||||||
|
@ -40,6 +43,10 @@ private:
|
||||||
int m_addressBase;
|
int m_addressBase;
|
||||||
int m_boundary;
|
int m_boundary;
|
||||||
int m_boundaryBase;
|
int m_boundaryBase;
|
||||||
|
bool m_flipH = false;
|
||||||
|
bool m_flipV = false;
|
||||||
|
|
||||||
|
QMap<QString, QLabel*> m_customProperties;
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,6 +2,14 @@
|
||||||
<ui version="4.0">
|
<ui version="4.0">
|
||||||
<class>AssetTile</class>
|
<class>AssetTile</class>
|
||||||
<widget class="QGroupBox" name="AssetTile">
|
<widget class="QGroupBox" name="AssetTile">
|
||||||
|
<property name="geometry">
|
||||||
|
<rect>
|
||||||
|
<x>0</x>
|
||||||
|
<y>0</y>
|
||||||
|
<width>171</width>
|
||||||
|
<height>355</height>
|
||||||
|
</rect>
|
||||||
|
</property>
|
||||||
<property name="sizePolicy">
|
<property name="sizePolicy">
|
||||||
<sizepolicy hsizetype="Fixed" vsizetype="Preferred">
|
<sizepolicy hsizetype="Fixed" vsizetype="Preferred">
|
||||||
<horstretch>0</horstretch>
|
<horstretch>0</horstretch>
|
||||||
|
@ -46,6 +54,27 @@
|
||||||
</item>
|
</item>
|
||||||
</layout>
|
</layout>
|
||||||
</item>
|
</item>
|
||||||
|
<item>
|
||||||
|
<layout class="QHBoxLayout" name="horizontalLayout_4">
|
||||||
|
<item>
|
||||||
|
<widget class="QLabel" name="label_2">
|
||||||
|
<property name="text">
|
||||||
|
<string>Palette #</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
<item>
|
||||||
|
<widget class="QLabel" name="paletteId">
|
||||||
|
<property name="text">
|
||||||
|
<string>0</string>
|
||||||
|
</property>
|
||||||
|
<property name="alignment">
|
||||||
|
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
|
</layout>
|
||||||
|
</item>
|
||||||
<item>
|
<item>
|
||||||
<layout class="QHBoxLayout" name="horizontalLayout_2">
|
<layout class="QHBoxLayout" name="horizontalLayout_2">
|
||||||
<item>
|
<item>
|
||||||
|
|
|
@ -10,9 +10,16 @@
|
||||||
#include "LogController.h"
|
#include "LogController.h"
|
||||||
|
|
||||||
#include <mgba-util/png-io.h>
|
#include <mgba-util/png-io.h>
|
||||||
|
#ifdef M_CORE_GBA
|
||||||
|
#include <mgba/internal/gba/memory.h>
|
||||||
|
#endif
|
||||||
|
#ifdef M_CORE_GB
|
||||||
|
#include <mgba/internal/gb/memory.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
#include <QButtonGroup>
|
#include <QButtonGroup>
|
||||||
#include <QFontDatabase>
|
#include <QFontDatabase>
|
||||||
|
#include <QMouseEvent>
|
||||||
#include <QRadioButton>
|
#include <QRadioButton>
|
||||||
#include <QTimer>
|
#include <QTimer>
|
||||||
|
|
||||||
|
@ -28,17 +35,22 @@ MapView::MapView(std::shared_ptr<CoreController> controller, QWidget* parent)
|
||||||
switch (m_controller->platform()) {
|
switch (m_controller->platform()) {
|
||||||
#ifdef M_CORE_GBA
|
#ifdef M_CORE_GBA
|
||||||
case PLATFORM_GBA:
|
case PLATFORM_GBA:
|
||||||
m_ui.tile->setBoundary(2048, 0, 2);
|
m_boundary = 2048;
|
||||||
|
m_addressBase = BASE_VRAM;
|
||||||
|
m_addressWidth = 8;
|
||||||
break;
|
break;
|
||||||
#endif
|
#endif
|
||||||
#ifdef M_CORE_GB
|
#ifdef M_CORE_GB
|
||||||
case PLATFORM_GB:
|
case PLATFORM_GB:
|
||||||
m_ui.tile->setBoundary(1024, 0, 0);
|
m_boundary = 1024;
|
||||||
|
m_addressBase = GB_BASE_VRAM;
|
||||||
|
m_addressWidth = 4;
|
||||||
break;
|
break;
|
||||||
#endif
|
#endif
|
||||||
default:
|
default:
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
m_ui.tile->setBoundary(m_boundary, 0, 0);
|
||||||
|
|
||||||
connect(m_ui.magnification, static_cast<void (QSpinBox::*)(int)>(&QSpinBox::valueChanged), [this]() {
|
connect(m_ui.magnification, static_cast<void (QSpinBox::*)(int)>(&QSpinBox::valueChanged), [this]() {
|
||||||
updateTiles(true);
|
updateTiles(true);
|
||||||
|
@ -67,6 +79,10 @@ MapView::MapView(std::shared_ptr<CoreController> controller, QWidget* parent)
|
||||||
#else
|
#else
|
||||||
m_ui.exportButton->setVisible(false);
|
m_ui.exportButton->setVisible(false);
|
||||||
#endif
|
#endif
|
||||||
|
m_ui.map->installEventFilter(this);
|
||||||
|
m_ui.tile->addCustomProperty("mapAddr", tr("Map Addr."));
|
||||||
|
m_ui.tile->addCustomProperty("flip", tr("Mirror"));
|
||||||
|
selectTile(0, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
void MapView::selectMap(int map) {
|
void MapView::selectMap(int map) {
|
||||||
|
@ -80,6 +96,45 @@ void MapView::selectMap(int map) {
|
||||||
updateTiles(true);
|
updateTiles(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void MapView::selectTile(int x, int y) {
|
||||||
|
CoreController::Interrupter interrupter(m_controller);
|
||||||
|
mMapCache* mapCache = mMapCacheSetGetPointer(&m_cacheSet->maps, m_map);
|
||||||
|
size_t tileCache = mTileCacheSetIndex(&m_cacheSet->tiles, mapCache->tileCache);
|
||||||
|
m_ui.tile->setBoundary(m_boundary, tileCache, tileCache);
|
||||||
|
uint32_t location = mMapCacheTileId(mapCache, x, y);
|
||||||
|
mMapCacheEntry* entry = &m_mapStatus[location];
|
||||||
|
m_ui.tile->selectIndex(entry->tileId + mapCache->tileStart);
|
||||||
|
m_ui.tile->setPalette(mMapCacheEntryFlagsGetPaletteId(entry->flags));
|
||||||
|
m_ui.tile->setFlip(mMapCacheEntryFlagsGetHMirror(entry->flags), mMapCacheEntryFlagsGetVMirror(entry->flags));
|
||||||
|
location <<= (mMapCacheSystemInfoGetMapAlign(mapCache->sysConfig));
|
||||||
|
location += m_addressBase + mapCache->mapStart;
|
||||||
|
|
||||||
|
QString flip(tr("None"));
|
||||||
|
if (mMapCacheEntryFlagsGetHMirror(entry->flags) && mMapCacheEntryFlagsGetVMirror(entry->flags)) {
|
||||||
|
flip = tr("Both");
|
||||||
|
} else if (mMapCacheEntryFlagsGetHMirror(entry->flags)) {
|
||||||
|
flip = tr("Horizontal");
|
||||||
|
} else if (mMapCacheEntryFlagsGetVMirror(entry->flags)) {
|
||||||
|
flip = tr("Vertical");
|
||||||
|
}
|
||||||
|
m_ui.tile->setCustomProperty("flip", flip);
|
||||||
|
m_ui.tile->setCustomProperty("mapAddr", QString("%0%1")
|
||||||
|
.arg(m_addressWidth == 8 ? "0x" : "")
|
||||||
|
.arg(location, m_addressWidth, 16, QChar('0')));
|
||||||
|
}
|
||||||
|
|
||||||
|
bool MapView::eventFilter(QObject* obj, QEvent* event) {
|
||||||
|
if (event->type() != QEvent::MouseButtonPress) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
int x = static_cast<QMouseEvent*>(event)->x();
|
||||||
|
int y = static_cast<QMouseEvent*>(event)->y();
|
||||||
|
x /= 8 * m_ui.magnification->value();
|
||||||
|
y /= 8 * m_ui.magnification->value();
|
||||||
|
selectTile(x, y);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
void MapView::updateTilesGBA(bool force) {
|
void MapView::updateTilesGBA(bool force) {
|
||||||
{
|
{
|
||||||
CoreController::Interrupter interrupter(m_controller);
|
CoreController::Interrupter interrupter(m_controller);
|
||||||
|
|
|
@ -28,6 +28,10 @@ public slots:
|
||||||
|
|
||||||
private slots:
|
private slots:
|
||||||
void selectMap(int);
|
void selectMap(int);
|
||||||
|
void selectTile(int x, int y);
|
||||||
|
|
||||||
|
protected:
|
||||||
|
bool eventFilter(QObject*, QEvent*) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
#ifdef M_CORE_GBA
|
#ifdef M_CORE_GBA
|
||||||
|
@ -43,6 +47,9 @@ private:
|
||||||
mMapCacheEntry m_mapStatus[128 * 128] = {}; // TODO: Correct size
|
mMapCacheEntry m_mapStatus[128 * 128] = {}; // TODO: Correct size
|
||||||
int m_map = 0;
|
int m_map = 0;
|
||||||
QImage m_rawMap;
|
QImage m_rawMap;
|
||||||
|
int m_boundary;
|
||||||
|
int m_addressBase;
|
||||||
|
int m_addressWidth;
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,8 +6,8 @@
|
||||||
<rect>
|
<rect>
|
||||||
<x>0</x>
|
<x>0</x>
|
||||||
<y>0</y>
|
<y>0</y>
|
||||||
<width>498</width>
|
<width>641</width>
|
||||||
<height>335</height>
|
<height>489</height>
|
||||||
</rect>
|
</rect>
|
||||||
</property>
|
</property>
|
||||||
<property name="windowTitle">
|
<property name="windowTitle">
|
||||||
|
@ -30,8 +30,8 @@
|
||||||
<rect>
|
<rect>
|
||||||
<x>0</x>
|
<x>0</x>
|
||||||
<y>0</y>
|
<y>0</y>
|
||||||
<width>314</width>
|
<width>457</width>
|
||||||
<height>309</height>
|
<height>463</height>
|
||||||
</rect>
|
</rect>
|
||||||
</property>
|
</property>
|
||||||
<layout class="QVBoxLayout" name="verticalLayout">
|
<layout class="QVBoxLayout" name="verticalLayout">
|
||||||
|
|
Loading…
Reference in New Issue