GBA: Palette RIFF exporter
Jeffrey Pfau jeffrey@endrift.com
Fri, 29 May 2015 00:03:09 -0700
6 files changed,
165 insertions(+),
3 deletions(-)
M
CHANGES
→
CHANGES
@@ -2,7 +2,7 @@ 0.3.0: (Future)
Features: - Ability to hide individual background layers, or OBJs - Ability to mute individual audio channels - - Palette viewer + - Palette viewer and exporter - Volume control - More shortcuts are editable (e.g. quick save/load) - Rewind now shows the frame after rewinding
A
src/gba/supervisor/export.c
@@ -0,0 +1,57 @@
+/* Copyright (c) 2013-2015 Jeffrey Pfau + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ +#include "export.h" + +#include "gba/video.h" +#include "util/vfs.h" + +bool GBAExportPaletteRIFF(struct VFile* vf, size_t entries, const uint16_t* colors) { + if (entries > 0xFFFF) { + return false; + } + uint32_t chunkSize = 4 + 4 * entries; + uint32_t size = chunkSize + 12; + + // Header + if (vf->write(vf, "RIFF", 4) < 4) { + return false; + } + if (VFileWrite32LE(vf, size) < 4) { + return false; + } + if (vf->write(vf, "PAL ", 4) < 4) { + return false; + } + + // Data chunk + if (vf->write(vf, "data", 4) < 4) { + return false; + } + if (VFileWrite32LE(vf, chunkSize) < 4) { + return false; + } + if (VFileWrite16LE(vf, 0x0300) < 2) { + return false; + } + if (VFileWrite16LE(vf, entries) < 2) { + return false; + } + + size_t i; + for (i = 0; i < entries; ++i) { + uint8_t block[4] = { + GBA_R8(colors[i]), + GBA_G8(colors[i]), + GBA_B8(colors[i]), + 0 + }; + if (vf->write(vf, block, 4) < 4) { + return false; + } + } + + return true; +}
A
src/gba/supervisor/export.h
@@ -0,0 +1,15 @@
+/* Copyright (c) 2013-2015 Jeffrey Pfau + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ +#ifndef GBA_EXPORT_H +#define GBA_EXPORT_H + +#include "util/common.h" + +struct VFile; + +bool GBAExportPaletteRIFF(struct VFile* vf, size_t entries, const uint16_t* colors); + +#endif
M
src/platform/qt/PaletteView.cpp
→
src/platform/qt/PaletteView.cpp
@@ -5,7 +5,13 @@ * License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */ #include "PaletteView.h" +#include <QFileDialog> #include <QFontDatabase> + +extern "C" { +#include "gba/supervisor/export.h" +#include "util/vfs.h" +} using namespace QGBA;@@ -33,6 +39,8 @@ m_ui.b->setFont(font);
connect(m_ui.bgGrid, SIGNAL(indexPressed(int)), this, SLOT(selectIndex(int))); connect(m_ui.objGrid, &Swatch::indexPressed, [this] (int index) { selectIndex(index + 256); }); + connect(m_ui.exportBG, &QAbstractButton::clicked, [this] () { exportPalette(0, 256); }); + connect(m_ui.exportOBJ, &QAbstractButton::clicked, [this] () { exportPalette(256, 256); }); connect(controller, SIGNAL(gameStopped(GBAThread*)), this, SLOT(close())); }@@ -64,3 +72,26 @@ m_ui.r->setText(tr("0x%0 (%1)").arg(r, 2, 16, QChar('0')).arg(r, 2, 10, QChar('0')));
m_ui.g->setText(tr("0x%0 (%1)").arg(g, 2, 16, QChar('0')).arg(g, 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 PaletteView::exportPalette(int start, int length) { + if (start >= 512) { + return; + } + if (start + length > 512) { + length = 512 - start; + } + m_controller->threadInterrupt(); + QString filename = QFileDialog::getSaveFileName(this, tr("Export palette"), QString(), tr("Windows PAL (*.pal)")); + if (filename.isNull()) { + m_controller->threadContinue(); + return; + } + VFile* vf = VFileOpen(filename.toLocal8Bit().constData(), O_WRONLY | O_CREAT | O_TRUNC); + if (!vf) { + m_controller->threadContinue(); + return; + } + GBAExportPaletteRIFF(vf, length, &m_controller->thread()->gba->video.palette[start]); + vf->close(vf); + m_controller->threadContinue(); +}
M
src/platform/qt/PaletteView.h
→
src/platform/qt/PaletteView.h
@@ -32,6 +32,8 @@ private slots:
void selectIndex(int); private: + void exportPalette(int start, int length); + Ui::PaletteView m_ui; GameController* m_controller;
M
src/platform/qt/PaletteView.ui
→
src/platform/qt/PaletteView.ui
@@ -6,8 +6,8 @@ <property name="geometry">
<rect> <x>0</x> <y>0</y> - <width>452</width> - <height>349</height> + <width>440</width> + <height>397</height> </rect> </property> <property name="windowTitle">@@ -291,6 +291,63 @@ </layout>
</item> </layout> </widget> + </item> + <item> + <layout class="QHBoxLayout" name="horizontalLayout_3"> + <item> + <spacer name="horizontalSpacer_4"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="sizeHint" stdset="0"> + <size> + <width>20</width> + <height>0</height> + </size> + </property> + </spacer> + </item> + <item> + <widget class="QPushButton" name="exportBG"> + <property name="text"> + <string>Export BG</string> + </property> + </widget> + </item> + <item> + <spacer name="horizontalSpacer_5"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="sizeHint" stdset="0"> + <size> + <width>40</width> + <height>0</height> + </size> + </property> + </spacer> + </item> + <item> + <widget class="QPushButton" name="exportOBJ"> + <property name="text"> + <string>Export OBJ</string> + </property> + </widget> + </item> + <item> + <spacer name="horizontalSpacer_6"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="sizeHint" stdset="0"> + <size> + <width>20</width> + <height>0</height> + </size> + </property> + </spacer> + </item> + </layout> </item> </layout> </widget>