Merge branch 'master' of github.com:huderlem/porymap
This commit is contained in:
commit
54a9d8b23b
27 changed files with 3458 additions and 287 deletions
1536
forms/paletteeditor.ui
Normal file
1536
forms/paletteeditor.ui
Normal file
File diff suppressed because it is too large
Load diff
|
@ -1,119 +1,22 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<ui version="4.0">
|
||||
<class>TilesetEditor</class>
|
||||
<widget class="QDialog" name="TilesetEditor">
|
||||
<widget class="QMainWindow" name="TilesetEditor">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>1022</width>
|
||||
<height>386</height>
|
||||
<width>800</width>
|
||||
<height>600</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
<string>Dialog</string>
|
||||
</property>
|
||||
<layout class="QGridLayout" name="gridLayout">
|
||||
<item row="1" column="0" colspan="3">
|
||||
<widget class="QDialogButtonBox" name="buttonBox">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="standardButtons">
|
||||
<set>QDialogButtonBox::Cancel|QDialogButtonBox::Ok</set>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="0">
|
||||
<widget class="QScrollArea" name="scrollArea">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Expanding">
|
||||
<horstretch>1</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="widgetResizable">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<widget class="QWidget" name="scrollAreaWidgetContents">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>329</width>
|
||||
<height>339</height>
|
||||
</rect>
|
||||
</property>
|
||||
<layout class="QGridLayout" name="gridLayout_2">
|
||||
<item row="0" column="0">
|
||||
<spacer name="horizontalSpacer">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>26</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="0" column="1">
|
||||
<widget class="QGraphicsView" name="graphicsView"/>
|
||||
</item>
|
||||
<item row="0" column="2">
|
||||
<spacer name="horizontalSpacer_2">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>26</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="1" column="1">
|
||||
<spacer name="verticalSpacer">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Vertical</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>20</width>
|
||||
<height>120</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="1">
|
||||
<widget class="QFrame" name="frame_2">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>2</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="frameShape">
|
||||
<enum>QFrame::StyledPanel</enum>
|
||||
</property>
|
||||
<property name="frameShadow">
|
||||
<enum>QFrame::Raised</enum>
|
||||
<string>MainWindow</string>
|
||||
</property>
|
||||
<widget class="QWidget" name="centralwidget">
|
||||
<layout class="QHBoxLayout" name="horizontalLayout">
|
||||
<item>
|
||||
<widget class="QScrollArea" name="scrollArea_2">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Expanding">
|
||||
<horstretch>1</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<widget class="QScrollArea" name="scrollArea_Metatiles">
|
||||
<property name="widgetResizable">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
|
@ -122,41 +25,61 @@
|
|||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>316</width>
|
||||
<height>319</height>
|
||||
<width>386</width>
|
||||
<height>539</height>
|
||||
</rect>
|
||||
</property>
|
||||
<layout class="QGridLayout" name="gridLayout_3">
|
||||
<item row="0" column="0">
|
||||
<spacer name="horizontalSpacer_3">
|
||||
<layout class="QGridLayout" name="gridLayout">
|
||||
<item row="1" column="2">
|
||||
<spacer name="horizontalSpacer">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>21</width>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="0" column="1">
|
||||
<widget class="QGraphicsView" name="graphicsView_2"/>
|
||||
</item>
|
||||
<item row="0" column="2">
|
||||
<spacer name="horizontalSpacer_4">
|
||||
<item row="1" column="0">
|
||||
<spacer name="horizontalSpacer_2">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>21</width>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="2" column="1">
|
||||
<spacer name="verticalSpacer">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Vertical</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>20</width>
|
||||
<height>40</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="1" column="1">
|
||||
<widget class="QGraphicsView" name="graphicsView_Metatiles">
|
||||
<property name="verticalScrollBarPolicy">
|
||||
<enum>Qt::ScrollBarAlwaysOff</enum>
|
||||
</property>
|
||||
<property name="horizontalScrollBarPolicy">
|
||||
<enum>Qt::ScrollBarAlwaysOff</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="1">
|
||||
<spacer name="verticalSpacer_2">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Vertical</enum>
|
||||
|
@ -164,7 +87,7 @@
|
|||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>20</width>
|
||||
<height>100</height>
|
||||
<height>40</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
|
@ -174,19 +97,284 @@
|
|||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QFrame" name="frame">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>1</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<widget class="QFrame" name="frame_2">
|
||||
<property name="frameShape">
|
||||
<enum>QFrame::StyledPanel</enum>
|
||||
<enum>QFrame::NoFrame</enum>
|
||||
</property>
|
||||
<property name="frameShadow">
|
||||
<enum>QFrame::Raised</enum>
|
||||
</property>
|
||||
<layout class="QVBoxLayout" name="verticalLayout">
|
||||
<property name="leftMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<item alignment="Qt::AlignTop">
|
||||
<widget class="QFrame" name="frame_4">
|
||||
<property name="frameShape">
|
||||
<enum>QFrame::NoFrame</enum>
|
||||
</property>
|
||||
<property name="frameShadow">
|
||||
<enum>QFrame::Raised</enum>
|
||||
</property>
|
||||
<layout class="QHBoxLayout" name="horizontalLayout_4">
|
||||
<property name="leftMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<item>
|
||||
<widget class="QGroupBox" name="groupBox">
|
||||
<property name="title">
|
||||
<string>Tile Properties</string>
|
||||
</property>
|
||||
<property name="flat">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<layout class="QFormLayout" name="formLayout">
|
||||
<item row="0" column="0">
|
||||
<widget class="QLabel" name="label">
|
||||
<property name="text">
|
||||
<string>Palette</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="1">
|
||||
<widget class="QSpinBox" name="spinBox_paletteSelector"/>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="QLabel" name="label_2">
|
||||
<property name="text">
|
||||
<string>X Flip</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="0">
|
||||
<widget class="QLabel" name="label_3">
|
||||
<property name="text">
|
||||
<string>Y Flip</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="0">
|
||||
<widget class="QLabel" name="label_7">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Fixed" vsizetype="Fixed">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Selection</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="1">
|
||||
<widget class="QCheckBox" name="checkBox_xFlip">
|
||||
<property name="layoutDirection">
|
||||
<enum>Qt::LeftToRight</enum>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string/>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="1">
|
||||
<widget class="QCheckBox" name="checkBox_yFlip">
|
||||
<property name="text">
|
||||
<string/>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="1">
|
||||
<widget class="QGraphicsView" name="graphicsView_selectedTile">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>16</width>
|
||||
<height>16</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="maximumSize">
|
||||
<size>
|
||||
<width>32</width>
|
||||
<height>32</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="frameShape">
|
||||
<enum>QFrame::StyledPanel</enum>
|
||||
</property>
|
||||
<property name="verticalScrollBarPolicy">
|
||||
<enum>Qt::ScrollBarAlwaysOff</enum>
|
||||
</property>
|
||||
<property name="horizontalScrollBarPolicy">
|
||||
<enum>Qt::ScrollBarAlwaysOff</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QGroupBox" name="groupBox_2">
|
||||
<property name="title">
|
||||
<string>Metatile Properties</string>
|
||||
</property>
|
||||
<property name="flat">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<property name="checkable">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<layout class="QFormLayout" name="formLayout_2">
|
||||
<item row="0" column="0">
|
||||
<widget class="QLabel" name="label_4">
|
||||
<property name="text">
|
||||
<string>Bottom/Top</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="QGraphicsView" name="graphicsView_metatileLayers">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>64</width>
|
||||
<height>32</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="maximumSize">
|
||||
<size>
|
||||
<width>64</width>
|
||||
<height>32</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="verticalScrollBarPolicy">
|
||||
<enum>Qt::ScrollBarAlwaysOff</enum>
|
||||
</property>
|
||||
<property name="horizontalScrollBarPolicy">
|
||||
<enum>Qt::ScrollBarAlwaysOff</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="0">
|
||||
<widget class="QLabel" name="label_5">
|
||||
<property name="text">
|
||||
<string>Metatile Behavior</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="0">
|
||||
<widget class="QComboBox" name="comboBox_metatileBehaviors"/>
|
||||
</item>
|
||||
<item row="4" column="0">
|
||||
<widget class="QLabel" name="label_6">
|
||||
<property name="text">
|
||||
<string>Layer Type</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="5" column="0">
|
||||
<widget class="QComboBox" name="comboBox_layerType"/>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QScrollArea" name="scrollArea_Tiles">
|
||||
<property name="widgetResizable">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<widget class="QWidget" name="scrollAreaWidgetContents">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>386</width>
|
||||
<height>359</height>
|
||||
</rect>
|
||||
</property>
|
||||
<layout class="QGridLayout" name="gridLayout_2">
|
||||
<item row="1" column="2">
|
||||
<spacer name="horizontalSpacer_4">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="0" column="1">
|
||||
<spacer name="verticalSpacer_3">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Vertical</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>20</width>
|
||||
<height>40</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="1" column="1">
|
||||
<widget class="QGraphicsView" name="graphicsView_Tiles">
|
||||
<property name="verticalScrollBarPolicy">
|
||||
<enum>Qt::ScrollBarAlwaysOff</enum>
|
||||
</property>
|
||||
<property name="horizontalScrollBarPolicy">
|
||||
<enum>Qt::ScrollBarAlwaysOff</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="1">
|
||||
<spacer name="verticalSpacer_4">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Vertical</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>20</width>
|
||||
<height>40</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<spacer name="horizontalSpacer_3">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
|
@ -194,39 +382,64 @@
|
|||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<widget class="QMenuBar" name="menubar">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>800</width>
|
||||
<height>21</height>
|
||||
</rect>
|
||||
</property>
|
||||
<widget class="QMenu" name="menuFile">
|
||||
<property name="title">
|
||||
<string>File</string>
|
||||
</property>
|
||||
<addaction name="actionSave_Tileset"/>
|
||||
<addaction name="separator"/>
|
||||
</widget>
|
||||
<widget class="QMenu" name="menuTools">
|
||||
<property name="title">
|
||||
<string>Tools</string>
|
||||
</property>
|
||||
<addaction name="actionImport_Primary_Tiles"/>
|
||||
<addaction name="actionImport_Secondary_Tiles"/>
|
||||
<addaction name="actionChange_Metatiles_Count"/>
|
||||
<addaction name="actionChange_Palettes"/>
|
||||
</widget>
|
||||
<addaction name="menuFile"/>
|
||||
<addaction name="menuTools"/>
|
||||
</widget>
|
||||
<widget class="QStatusBar" name="statusbar"/>
|
||||
<action name="actionSave_Tileset">
|
||||
<property name="text">
|
||||
<string>Save Tileset</string>
|
||||
</property>
|
||||
<property name="shortcut">
|
||||
<string>Ctrl+S</string>
|
||||
</property>
|
||||
</action>
|
||||
<action name="actionImport_Primary_Tiles">
|
||||
<property name="text">
|
||||
<string>Import Primary Tiles</string>
|
||||
</property>
|
||||
</action>
|
||||
<action name="actionImport_Secondary_Tiles">
|
||||
<property name="text">
|
||||
<string>Import Secondary Tiles</string>
|
||||
</property>
|
||||
</action>
|
||||
<action name="actionChange_Metatiles_Count">
|
||||
<property name="text">
|
||||
<string>Change Number of Metatiles</string>
|
||||
</property>
|
||||
</action>
|
||||
<action name="actionChange_Palettes">
|
||||
<property name="text">
|
||||
<string>Change Palettes</string>
|
||||
</property>
|
||||
</action>
|
||||
</widget>
|
||||
<resources/>
|
||||
<connections>
|
||||
<connection>
|
||||
<sender>buttonBox</sender>
|
||||
<signal>accepted()</signal>
|
||||
<receiver>TilesetEditor</receiver>
|
||||
<slot>accept()</slot>
|
||||
<hints>
|
||||
<hint type="sourcelabel">
|
||||
<x>248</x>
|
||||
<y>254</y>
|
||||
</hint>
|
||||
<hint type="destinationlabel">
|
||||
<x>157</x>
|
||||
<y>274</y>
|
||||
</hint>
|
||||
</hints>
|
||||
</connection>
|
||||
<connection>
|
||||
<sender>buttonBox</sender>
|
||||
<signal>rejected()</signal>
|
||||
<receiver>TilesetEditor</receiver>
|
||||
<slot>reject()</slot>
|
||||
<hints>
|
||||
<hint type="sourcelabel">
|
||||
<x>316</x>
|
||||
<y>260</y>
|
||||
</hint>
|
||||
<hint type="destinationlabel">
|
||||
<x>286</x>
|
||||
<y>274</y>
|
||||
</hint>
|
||||
</hints>
|
||||
</connection>
|
||||
</connections>
|
||||
<connections/>
|
||||
</ui>
|
||||
|
|
|
@ -10,7 +10,10 @@ public:
|
|||
Metatile();
|
||||
public:
|
||||
QList<Tile> *tiles = nullptr;
|
||||
uint8_t behavior;
|
||||
uint8_t layerType;
|
||||
|
||||
Metatile *copy();
|
||||
static int getBlockIndex(int);
|
||||
};
|
||||
|
||||
|
|
|
@ -17,16 +17,24 @@ public:
|
|||
QString tiles_label;
|
||||
QString palettes_label;
|
||||
QString metatiles_label;
|
||||
QString metatiles_path;
|
||||
QString callback_label;
|
||||
QString metatile_attrs_label;
|
||||
QString metatile_attrs_path;
|
||||
QString tilesImagePath;
|
||||
QImage tilesImage;
|
||||
QList<QString> palettePaths;
|
||||
|
||||
QList<QImage> *tiles = nullptr;
|
||||
QList<Metatile*> *metatiles = nullptr;
|
||||
QList<QList<QRgb>> *palettes = nullptr;
|
||||
|
||||
Tileset* copy();
|
||||
|
||||
static Tileset* getBlockTileset(int, Tileset*, Tileset*);
|
||||
static Metatile* getMetatile(int, Tileset*, Tileset*);
|
||||
static QList<QList<QRgb>> getBlockPalettes(Tileset*, Tileset*);
|
||||
static QList<QRgb> getPalette(int, Tileset*, Tileset*);
|
||||
};
|
||||
|
||||
#endif // TILESET_H
|
||||
|
|
|
@ -68,9 +68,10 @@ public:
|
|||
void updateDiveMap(QString mapName);
|
||||
void updateEmergeMap(QString mapName);
|
||||
void setSelectedConnectionFromMap(QString mapName);
|
||||
void updatePrimaryTileset(QString tilesetLabel);
|
||||
void updateSecondaryTileset(QString tilesetLabel);
|
||||
void updatePrimaryTileset(QString tilesetLabel, bool forceLoad = false);
|
||||
void updateSecondaryTileset(QString tilesetLabel, bool forceLoad = false);
|
||||
void toggleBorderVisibility(bool visible);
|
||||
Tileset *getCurrentMapPrimaryTileset();
|
||||
|
||||
DraggablePixmapItem *addMapEvent(Event *event);
|
||||
void selectMapEvent(DraggablePixmapItem *object);
|
||||
|
|
|
@ -12,6 +12,7 @@
|
|||
#include "project.h"
|
||||
#include "map.h"
|
||||
#include "editor.h"
|
||||
#include "tileseteditor.h"
|
||||
|
||||
namespace Ui {
|
||||
class MainWindow;
|
||||
|
@ -42,6 +43,7 @@ private slots:
|
|||
void onLoadMapRequested(QString, QString);
|
||||
void onMapChanged(Map *map);
|
||||
void onMapNeedsRedrawing();
|
||||
void onTilesetsSaved(QString, QString);
|
||||
|
||||
void on_action_Save_triggered();
|
||||
void on_tabWidget_2_currentChanged(int index);
|
||||
|
@ -92,6 +94,7 @@ private slots:
|
|||
void onAddNewMapToGroupClick(QAction* triggeredAction);
|
||||
void onTilesetChanged(QString);
|
||||
void currentMetatilesSelectionChanged();
|
||||
void onTilesetEditorClosed();
|
||||
|
||||
void on_action_Export_Map_Image_triggered();
|
||||
|
||||
|
@ -123,8 +126,11 @@ private slots:
|
|||
|
||||
void resetMapViewScale();
|
||||
|
||||
void on_actionTileset_Editor_triggered();
|
||||
|
||||
private:
|
||||
Ui::MainWindow *ui;
|
||||
TilesetEditor *tilesetEditor = nullptr;
|
||||
QStandardItemModel *mapListModel;
|
||||
QList<QStandardItem*> *mapGroupsModel;
|
||||
QMap<QString, QModelIndex> mapListIndexes;
|
||||
|
@ -153,6 +159,7 @@ private:
|
|||
void initEditor();
|
||||
void loadUserSettings();
|
||||
void openRecentProject();
|
||||
void updateTilesetEditor();
|
||||
};
|
||||
|
||||
enum MapListUserRoles {
|
||||
|
|
|
@ -40,14 +40,16 @@ public:
|
|||
QStringList *secretBaseIds = nullptr;
|
||||
QStringList *bgEventFacingDirections = nullptr;
|
||||
QStringList mapsWithConnections;
|
||||
QMap<QString, int> metatileBehaviorMap;
|
||||
QMap<int, QString> metatileBehaviorMapInverse;
|
||||
|
||||
QMap<QString, Map*> *map_cache;
|
||||
Map* loadMap(QString);
|
||||
Map* getMap(QString);
|
||||
|
||||
QMap<QString, Tileset*> *tileset_cache = nullptr;
|
||||
Tileset* loadTileset(QString);
|
||||
Tileset* getTileset(QString);
|
||||
Tileset* loadTileset(QString, Tileset *tileset = nullptr);
|
||||
Tileset* getTileset(QString, bool forceLoad = false);
|
||||
|
||||
Blockdata* readBlockdata(QString);
|
||||
void loadBlockdata(Map*);
|
||||
|
@ -72,6 +74,8 @@ public:
|
|||
void readMapsWithConnections();
|
||||
void loadMapTilesets(Map*);
|
||||
void loadTilesetAssets(Tileset*);
|
||||
void loadTilesetTiles(Tileset*, QImage);
|
||||
void loadTilesetMetatiles(Tileset*);
|
||||
|
||||
void saveBlockdata(Map*);
|
||||
void saveMapBorder(Map*);
|
||||
|
@ -83,6 +87,7 @@ public:
|
|||
void saveMapGroupsTable();
|
||||
void saveMapConstantsHeader();
|
||||
void saveHealLocationStruct(Map*);
|
||||
void saveTilesets(Tileset*, Tileset*);
|
||||
|
||||
QList<QStringList>* parseAsm(QString text);
|
||||
QStringList getSongNames();
|
||||
|
@ -100,9 +105,11 @@ public:
|
|||
void readCoordEventWeatherNames();
|
||||
void readSecretBaseIds();
|
||||
void readBgEventFacingDirections();
|
||||
void readMetatileBehaviors();
|
||||
|
||||
void loadEventPixmaps(QList<Event*> objects);
|
||||
QMap<QString, int> getEventObjGfxConstants();
|
||||
QString fixPalettePath(QString path);
|
||||
QString fixGraphicPath(QString path);
|
||||
|
||||
void readMapEvents(Map *map);
|
||||
|
@ -127,6 +134,10 @@ private:
|
|||
QString getMapLayoutFilepath(QString);
|
||||
void saveMapHeader(Map*);
|
||||
void saveMapConnections(Map*);
|
||||
void saveTilesetMetatileAttributes(Tileset*);
|
||||
void saveTilesetMetatiles(Tileset*);
|
||||
void saveTilesetTilesImage(Tileset*);
|
||||
void saveTilesetPalettes(Tileset*, bool);
|
||||
void updateMapsWithConnections(Map*);
|
||||
void saveMapsWithConnections();
|
||||
void saveMapLayoutsTable();
|
||||
|
|
|
@ -8,7 +8,8 @@
|
|||
|
||||
QImage getCollisionMetatileImage(Block);
|
||||
QImage getCollisionMetatileImage(int, int);
|
||||
QImage getMetatileImage(int, Tileset*, Tileset*);
|
||||
QImage getTileImage(int, Tileset*, Tileset*);
|
||||
QImage getMetatileImage(uint16_t, Tileset*, Tileset*);
|
||||
QImage getTileImage(uint16_t, Tileset*, Tileset*);
|
||||
QImage getColoredTileImage(uint16_t, Tileset*, Tileset*, int);
|
||||
|
||||
#endif // IMAGEPROVIDERS_H
|
||||
|
|
29
include/ui/metatilelayersitem.h
Normal file
29
include/ui/metatilelayersitem.h
Normal file
|
@ -0,0 +1,29 @@
|
|||
#ifndef METATILELAYERSITEM_H
|
||||
#define METATILELAYERSITEM_H
|
||||
|
||||
#include "tileset.h"
|
||||
#include <QGraphicsPixmapItem>
|
||||
#include <QGraphicsSceneMouseEvent>
|
||||
|
||||
class MetatileLayersItem : public QObject, public QGraphicsPixmapItem {
|
||||
Q_OBJECT
|
||||
public:
|
||||
MetatileLayersItem(Metatile *metatile, Tileset *primaryTileset, Tileset *secondaryTileset) {
|
||||
this->metatile = metatile;
|
||||
this->primaryTileset = primaryTileset;
|
||||
this->secondaryTileset = secondaryTileset;
|
||||
}
|
||||
void draw();
|
||||
void setTilesets(Tileset*, Tileset*);
|
||||
void setMetatile(Metatile*);
|
||||
private:
|
||||
Metatile* metatile;
|
||||
Tileset *primaryTileset;
|
||||
Tileset *secondaryTileset;
|
||||
signals:
|
||||
void tileChanged(int, int);
|
||||
protected:
|
||||
void mousePressEvent(QGraphicsSceneMouseEvent*);
|
||||
};
|
||||
|
||||
#endif // METATILELAYERSITEM_H
|
43
include/ui/paletteeditor.h
Normal file
43
include/ui/paletteeditor.h
Normal file
|
@ -0,0 +1,43 @@
|
|||
#ifndef PALETTEEDITOR_H
|
||||
#define PALETTEEDITOR_H
|
||||
|
||||
#include <QMainWindow>
|
||||
#include <QSlider>
|
||||
#include <QFrame>
|
||||
#include "project.h"
|
||||
|
||||
namespace Ui {
|
||||
class PaletteEditor;
|
||||
}
|
||||
|
||||
class PaletteEditor : public QMainWindow {
|
||||
Q_OBJECT
|
||||
public:
|
||||
explicit PaletteEditor(Project*, Tileset*, Tileset*, QWidget *parent = nullptr);
|
||||
~PaletteEditor();
|
||||
void setPaletteId(int);
|
||||
|
||||
private:
|
||||
Ui::PaletteEditor *ui;
|
||||
Project *project = nullptr;
|
||||
QList<QList<QSlider*>> sliders;
|
||||
QList<QFrame*> frames;
|
||||
Tileset *primaryTileset;
|
||||
Tileset *secondaryTileset;
|
||||
void disableSliderSignals();
|
||||
void enableSliderSignals();
|
||||
void initColorSliders();
|
||||
void refreshColorSliders();
|
||||
void refreshColors();
|
||||
void refreshColor(int);
|
||||
void setColor(int);
|
||||
|
||||
signals:
|
||||
void closed();
|
||||
void changedPaletteColor();
|
||||
void changedPalette(int);
|
||||
private slots:
|
||||
void on_spinBox_PaletteId_valueChanged(int arg1);
|
||||
};
|
||||
|
||||
#endif // PALETTEEDITOR_H
|
|
@ -1,22 +1,90 @@
|
|||
#ifndef TILESETEDITOR_H
|
||||
#define TILESETEDITOR_H
|
||||
|
||||
#include <QDialog>
|
||||
#include <QMainWindow>
|
||||
#include "project.h"
|
||||
#include "paletteeditor.h"
|
||||
#include "tileseteditormetatileselector.h"
|
||||
#include "tileseteditortileselector.h"
|
||||
#include "metatilelayersitem.h"
|
||||
|
||||
namespace Ui {
|
||||
class TilesetEditor;
|
||||
}
|
||||
|
||||
class TilesetEditor : public QDialog
|
||||
class TilesetEditor : public QMainWindow
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
explicit TilesetEditor(QWidget *parent = nullptr);
|
||||
explicit TilesetEditor(Project*, QString, QString, QWidget *parent = nullptr);
|
||||
~TilesetEditor();
|
||||
void setTilesets(QString, QString);
|
||||
void init(Project*, QString, QString);
|
||||
|
||||
private slots:
|
||||
void onHoveredMetatileChanged(uint16_t);
|
||||
void onHoveredMetatileCleared();
|
||||
void onSelectedMetatileChanged(uint16_t);
|
||||
void onHoveredTileChanged(uint16_t);
|
||||
void onHoveredTileCleared();
|
||||
void onSelectedTilesChanged();
|
||||
void onMetatileLayerTileChanged(int, int);
|
||||
void onPaletteEditorClosed();
|
||||
void onPaletteEditorChangedPaletteColor();
|
||||
void onPaletteEditorChangedPalette(int);
|
||||
|
||||
void on_spinBox_paletteSelector_valueChanged(int arg1);
|
||||
|
||||
void on_checkBox_xFlip_stateChanged(int arg1);
|
||||
|
||||
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();
|
||||
|
||||
void on_actionImport_Secondary_Tiles_triggered();
|
||||
|
||||
void on_actionChange_Metatiles_Count_triggered();
|
||||
|
||||
void on_actionChange_Palettes_triggered();
|
||||
|
||||
private:
|
||||
void closeEvent(QCloseEvent*);
|
||||
void initMetatileSelector();
|
||||
void initTileSelector();
|
||||
void initSelectedTileItem();
|
||||
void initMetatileLayersItem();
|
||||
void drawSelectedTiles();
|
||||
void importTilesetTiles(Tileset*, bool);
|
||||
void refresh();
|
||||
Ui::TilesetEditor *ui;
|
||||
TilesetEditorMetatileSelector *metatileSelector = nullptr;
|
||||
TilesetEditorTileSelector *tileSelector = nullptr;
|
||||
MetatileLayersItem *metatileLayersItem = nullptr;
|
||||
PaletteEditor *paletteEditor = nullptr;
|
||||
Project *project = nullptr;
|
||||
Metatile *metatile = nullptr;
|
||||
int paletteId;
|
||||
bool tileXFlip;
|
||||
bool tileYFlip;
|
||||
bool hasUnsavedChanges;
|
||||
Tileset *primaryTileset = nullptr;
|
||||
Tileset *secondaryTileset = nullptr;
|
||||
QGraphicsScene *metatilesScene = nullptr;
|
||||
QGraphicsScene *tilesScene = nullptr;
|
||||
QGraphicsScene *selectedTileScene = nullptr;
|
||||
QGraphicsPixmapItem *selectedTilePixmapItem = nullptr;
|
||||
QGraphicsScene *metatileLayersScene = nullptr;
|
||||
|
||||
signals:
|
||||
void tilesetsSaved(QString, QString);
|
||||
void closed();
|
||||
};
|
||||
|
||||
#endif // TILESETEDITOR_H
|
||||
|
|
44
include/ui/tileseteditormetatileselector.h
Normal file
44
include/ui/tileseteditormetatileselector.h
Normal file
|
@ -0,0 +1,44 @@
|
|||
#ifndef TILESETEDITORMETATILESELECTOR_H
|
||||
#define TILESETEDITORMETATILESELECTOR_H
|
||||
|
||||
#include "selectablepixmapitem.h"
|
||||
#include "tileset.h"
|
||||
|
||||
class TilesetEditorMetatileSelector: public SelectablePixmapItem {
|
||||
Q_OBJECT
|
||||
public:
|
||||
TilesetEditorMetatileSelector(Tileset *primaryTileset, Tileset *secondaryTileset): SelectablePixmapItem(32, 32, 1, 1) {
|
||||
this->primaryTileset = primaryTileset;
|
||||
this->secondaryTileset = secondaryTileset;
|
||||
this->numMetatilesWide = 8;
|
||||
setAcceptHoverEvents(true);
|
||||
}
|
||||
void draw();
|
||||
void select(uint16_t metatileId);
|
||||
void setTilesets(Tileset*, Tileset*);
|
||||
uint16_t getSelectedMetatile();
|
||||
|
||||
protected:
|
||||
void mousePressEvent(QGraphicsSceneMouseEvent*);
|
||||
void mouseMoveEvent(QGraphicsSceneMouseEvent*);
|
||||
void mouseReleaseEvent(QGraphicsSceneMouseEvent*);
|
||||
void hoverMoveEvent(QGraphicsSceneHoverEvent*);
|
||||
void hoverLeaveEvent(QGraphicsSceneHoverEvent*);
|
||||
|
||||
private:
|
||||
Tileset *primaryTileset = nullptr;
|
||||
Tileset *secondaryTileset = nullptr;
|
||||
uint16_t selectedMetatile;
|
||||
int numMetatilesWide;
|
||||
void updateSelectedMetatile();
|
||||
uint16_t getMetatileId(int x, int y);
|
||||
QPoint getMetatileIdCoords(uint16_t);
|
||||
uint16_t getValidMetatileId(uint16_t);
|
||||
|
||||
signals:
|
||||
void hoveredMetatileChanged(uint16_t);
|
||||
void hoveredMetatileCleared();
|
||||
void selectedMetatileChanged(uint16_t);
|
||||
};
|
||||
|
||||
#endif // TILESETEDITORMETATILESELECTOR_H
|
52
include/ui/tileseteditortileselector.h
Normal file
52
include/ui/tileseteditortileselector.h
Normal file
|
@ -0,0 +1,52 @@
|
|||
#ifndef TILESETEDITORTILESELECTOR_H
|
||||
#define TILESETEDITORTILESELECTOR_H
|
||||
|
||||
#include "selectablepixmapitem.h"
|
||||
#include "tileset.h"
|
||||
|
||||
class TilesetEditorTileSelector: public SelectablePixmapItem {
|
||||
Q_OBJECT
|
||||
public:
|
||||
TilesetEditorTileSelector(Tileset *primaryTileset, Tileset *secondaryTileset): SelectablePixmapItem(16, 16, 2, 2) {
|
||||
this->primaryTileset = primaryTileset;
|
||||
this->secondaryTileset = secondaryTileset;
|
||||
this->numTilesWide = 16;
|
||||
this->paletteId = 0;
|
||||
this->xFlip = false;
|
||||
this->yFlip = false;
|
||||
setAcceptHoverEvents(true);
|
||||
}
|
||||
void draw();
|
||||
void select(uint16_t metatileId);
|
||||
void setTilesets(Tileset*, Tileset*);
|
||||
void setPaletteId(int);
|
||||
void setTileFlips(bool, bool);
|
||||
QList<uint16_t> getSelectedTiles();
|
||||
|
||||
protected:
|
||||
void mousePressEvent(QGraphicsSceneMouseEvent*);
|
||||
void mouseMoveEvent(QGraphicsSceneMouseEvent*);
|
||||
void mouseReleaseEvent(QGraphicsSceneMouseEvent*);
|
||||
void hoverMoveEvent(QGraphicsSceneHoverEvent*);
|
||||
void hoverLeaveEvent(QGraphicsSceneHoverEvent*);
|
||||
|
||||
private:
|
||||
Tileset *primaryTileset;
|
||||
Tileset *secondaryTileset;
|
||||
QList<uint16_t> selectedTiles;
|
||||
int numTilesWide;
|
||||
int paletteId;
|
||||
bool xFlip;
|
||||
bool yFlip;
|
||||
void updateSelectedTiles();
|
||||
uint16_t getTileId(int x, int y);
|
||||
QPoint getTileCoords(uint16_t);
|
||||
QList<QRgb> getCurPaletteTable();
|
||||
|
||||
signals:
|
||||
void hoveredTileChanged(uint16_t);
|
||||
void hoveredTileCleared();
|
||||
void selectedTilesChanged();
|
||||
};
|
||||
|
||||
#endif // TILESETEDITORTILESELECTOR_H
|
11
porymap.pro
11
porymap.pro
|
@ -35,13 +35,17 @@ SOURCES += src/core/block.cpp \
|
|||
src/ui/imageproviders.cpp \
|
||||
src/ui/mappixmapitem.cpp \
|
||||
src/ui/mapsceneeventfilter.cpp \
|
||||
src/ui/metatilelayersitem.cpp \
|
||||
src/ui/metatileselector.cpp \
|
||||
src/ui/movementpermissionsselector.cpp \
|
||||
src/ui/neweventtoolbutton.cpp \
|
||||
src/ui/noscrollcombobox.cpp \
|
||||
src/ui/noscrollspinbox.cpp \
|
||||
src/ui/paletteeditor.cpp \
|
||||
src/ui/selectablepixmapitem.cpp \
|
||||
src/ui/tileseteditor.cpp \
|
||||
src/ui/tileseteditormetatileselector.cpp \
|
||||
src/ui/tileseteditortileselector.cpp \
|
||||
src/editor.cpp \
|
||||
src/main.cpp \
|
||||
src/mainwindow.cpp \
|
||||
|
@ -71,13 +75,17 @@ HEADERS += include/core/block.h \
|
|||
include/ui/imageproviders.h \
|
||||
include/ui/mappixmapitem.h \
|
||||
include/ui/mapsceneeventfilter.h \
|
||||
include/ui/metatilelayersitem.h \
|
||||
include/ui/metatileselector.h \
|
||||
include/ui/movementpermissionsselector.h \
|
||||
include/ui/neweventtoolbutton.h \
|
||||
include/ui/noscrollcombobox.h \
|
||||
include/ui/noscrollspinbox.h \
|
||||
include/ui/paletteeditor.h \
|
||||
include/ui/selectablepixmapitem.h \
|
||||
include/ui/tileseteditor.h \
|
||||
include/ui/tileseteditormetatileselector.h \
|
||||
include/ui/tileseteditortileselector.h \
|
||||
include/editor.h \
|
||||
include/mainwindow.h \
|
||||
include/project.h \
|
||||
|
@ -85,7 +93,8 @@ HEADERS += include/core/block.h \
|
|||
|
||||
FORMS += forms/mainwindow.ui \
|
||||
forms/eventpropertiesframe.ui \
|
||||
forms/tileseteditor.ui
|
||||
forms/tileseteditor.ui \
|
||||
forms/paletteeditor.ui
|
||||
|
||||
RESOURCES += \
|
||||
resources/images.qrc
|
||||
|
|
|
@ -226,7 +226,7 @@ QPixmap Map::renderBorder() {
|
|||
}
|
||||
|
||||
QPixmap Map::renderConnection(MapConnection connection) {
|
||||
render();
|
||||
render(true);
|
||||
int x, y, w, h;
|
||||
if (connection.direction == "up") {
|
||||
x = 0;
|
||||
|
|
|
@ -7,6 +7,17 @@ Metatile::Metatile()
|
|||
tiles = new QList<Tile>;
|
||||
}
|
||||
|
||||
Metatile* Metatile::copy() {
|
||||
Metatile *copy = new Metatile;
|
||||
copy->behavior = this->behavior;
|
||||
copy->layerType = this->layerType;
|
||||
copy->tiles = new QList<Tile>;
|
||||
for (Tile tile : *this->tiles) {
|
||||
copy->tiles->append(tile);
|
||||
}
|
||||
return copy;
|
||||
}
|
||||
|
||||
int Metatile::getBlockIndex(int index) {
|
||||
if (index < Project::getNumMetatilesPrimary()) {
|
||||
return index;
|
||||
|
|
|
@ -11,6 +11,43 @@ Tileset::Tileset()
|
|||
|
||||
}
|
||||
|
||||
Tileset* Tileset::copy() {
|
||||
Tileset *copy = new Tileset;
|
||||
copy->name = this->name;
|
||||
copy->is_compressed = this->is_compressed;
|
||||
copy->is_secondary = this->is_secondary;
|
||||
copy->padding = this->padding;
|
||||
copy->tiles_label = this->tiles_label;
|
||||
copy->palettes_label = this->palettes_label;
|
||||
copy->metatiles_label = this->metatiles_label;
|
||||
copy->metatiles_path = this->metatiles_path;
|
||||
copy->callback_label = this->callback_label;
|
||||
copy->metatile_attrs_label = this->metatile_attrs_label;
|
||||
copy->metatile_attrs_path = this->metatile_attrs_path;
|
||||
copy->tilesImage = this->tilesImage.copy();
|
||||
copy->tilesImagePath = this->tilesImagePath;
|
||||
for (int i = 0; i < this->palettePaths.length(); i++) {
|
||||
copy->palettePaths.append(this->palettePaths.at(i));
|
||||
}
|
||||
copy->tiles = new QList<QImage>;
|
||||
for (QImage tile : *this->tiles) {
|
||||
copy->tiles->append(tile.copy());
|
||||
}
|
||||
copy->metatiles = new QList<Metatile*>;
|
||||
for (Metatile *metatile : *this->metatiles) {
|
||||
copy->metatiles->append(metatile->copy());
|
||||
}
|
||||
copy->palettes = new QList<QList<QRgb>>;
|
||||
for (QList<QRgb> palette : *this->palettes) {
|
||||
QList<QRgb> copyPalette;
|
||||
for (QRgb color : palette) {
|
||||
copyPalette.append(color);
|
||||
}
|
||||
copy->palettes->append(copyPalette);
|
||||
}
|
||||
return copy;
|
||||
}
|
||||
|
||||
Tileset* Tileset::getBlockTileset(int metatile_index, Tileset *primaryTileset, Tileset *secondaryTileset) {
|
||||
if (metatile_index < Project::getNumMetatilesPrimary()) {
|
||||
return primaryTileset;
|
||||
|
@ -39,3 +76,14 @@ QList<QList<QRgb>> Tileset::getBlockPalettes(Tileset *primaryTileset, Tileset *s
|
|||
}
|
||||
return palettes;
|
||||
}
|
||||
|
||||
QList<QRgb> Tileset::getPalette(int paletteId, Tileset *primaryTileset, Tileset *secondaryTileset) {
|
||||
QList<QRgb> paletteTable;
|
||||
Tileset *tileset = paletteId < Project::getNumPalettesPrimary()
|
||||
? primaryTileset
|
||||
: secondaryTileset;
|
||||
for (int i = 0; i < tileset->palettes->at(paletteId).length(); i++) {
|
||||
paletteTable.append(tileset->palettes->at(paletteId).at(i));
|
||||
}
|
||||
return paletteTable;
|
||||
}
|
||||
|
|
|
@ -961,22 +961,22 @@ void Editor::updateDiveEmergeMap(QString mapName, QString direction) {
|
|||
ui->label_NumConnections->setText(QString::number(map->connections.length()));
|
||||
}
|
||||
|
||||
void Editor::updatePrimaryTileset(QString tilesetLabel)
|
||||
void Editor::updatePrimaryTileset(QString tilesetLabel, bool forceLoad)
|
||||
{
|
||||
if (map->layout->tileset_primary_label != tilesetLabel)
|
||||
if (map->layout->tileset_primary_label != tilesetLabel || forceLoad)
|
||||
{
|
||||
map->layout->tileset_primary_label = tilesetLabel;
|
||||
map->layout->tileset_primary = project->getTileset(tilesetLabel);
|
||||
map->layout->tileset_primary = project->getTileset(tilesetLabel, forceLoad);
|
||||
emit tilesetChanged(map->name);
|
||||
}
|
||||
}
|
||||
|
||||
void Editor::updateSecondaryTileset(QString tilesetLabel)
|
||||
void Editor::updateSecondaryTileset(QString tilesetLabel, bool forceLoad)
|
||||
{
|
||||
if (map->layout->tileset_secondary_label != tilesetLabel)
|
||||
if (map->layout->tileset_secondary_label != tilesetLabel || forceLoad)
|
||||
{
|
||||
map->layout->tileset_secondary_label = tilesetLabel;
|
||||
map->layout->tileset_secondary = project->getTileset(tilesetLabel);
|
||||
map->layout->tileset_secondary = project->getTileset(tilesetLabel, forceLoad);
|
||||
emit tilesetChanged(map->name);
|
||||
}
|
||||
}
|
||||
|
@ -987,6 +987,12 @@ void Editor::toggleBorderVisibility(bool visible)
|
|||
this->setConnectionsVisibility(visible);
|
||||
}
|
||||
|
||||
Tileset* Editor::getCurrentMapPrimaryTileset()
|
||||
{
|
||||
QString tilesetLabel = map->layout->tileset_primary_label;
|
||||
return project->getTileset(tilesetLabel);
|
||||
}
|
||||
|
||||
void DraggablePixmapItem::mousePressEvent(QGraphicsSceneMouseEvent *mouse) {
|
||||
active = true;
|
||||
last_x = static_cast<int>(mouse->pos().x() + this->pos().x()) / 16;
|
||||
|
|
|
@ -50,7 +50,7 @@ MainWindow::~MainWindow()
|
|||
}
|
||||
|
||||
void MainWindow::initExtraShortcuts() {
|
||||
new QShortcut(QKeySequence(Qt::CTRL + Qt::SHIFT + Qt::Key_Z), this, SLOT(redo()));
|
||||
new QShortcut(QKeySequence("Ctrl+Shift+Z"), this, SLOT(redo()));
|
||||
new QShortcut(QKeySequence("Ctrl+0"), this, SLOT(resetMapViewScale()));
|
||||
ui->actionZoom_In->setShortcuts({QKeySequence("Ctrl++"), QKeySequence("Ctrl+=")});
|
||||
}
|
||||
|
@ -200,6 +200,7 @@ void MainWindow::setMap(QString map_name, bool scrollTreeView) {
|
|||
|
||||
setRecentMap(map_name);
|
||||
updateMapList();
|
||||
updateTilesetEditor();
|
||||
}
|
||||
|
||||
void MainWindow::redrawMapScene()
|
||||
|
@ -410,6 +411,7 @@ void MainWindow::loadDataStructures() {
|
|||
project->readSecretBaseIds();
|
||||
project->readBgEventFacingDirections();
|
||||
project->readMapsWithConnections();
|
||||
project->readMetatileBehaviors();
|
||||
project->readTilesetProperties();
|
||||
}
|
||||
|
||||
|
@ -525,6 +527,12 @@ void MainWindow::onTilesetChanged(QString mapName)
|
|||
setMap(mapName);
|
||||
}
|
||||
|
||||
void MainWindow::updateTilesetEditor() {
|
||||
if (this->tilesetEditor) {
|
||||
this->tilesetEditor->setTilesets(editor->ui->comboBox_PrimaryTileset->currentText(), editor->ui->comboBox_SecondaryTileset->currentText());
|
||||
}
|
||||
}
|
||||
|
||||
void MainWindow::currentMetatilesSelectionChanged()
|
||||
{
|
||||
ui->graphicsView_currentMetatileSelection->setFixedSize(editor->scene_current_metatile_selection_item->pixmap().width() + 2, editor->scene_current_metatile_selection_item->pixmap().height() + 2);
|
||||
|
@ -1099,6 +1107,11 @@ void MainWindow::onMapNeedsRedrawing() {
|
|||
redrawMapScene();
|
||||
}
|
||||
|
||||
void MainWindow::onTilesetsSaved(QString primaryTilesetLabel, QString secondaryTilesetLabel) {
|
||||
this->editor->updatePrimaryTileset(primaryTilesetLabel, true);
|
||||
this->editor->updateSecondaryTileset(secondaryTilesetLabel, true);
|
||||
}
|
||||
|
||||
void MainWindow::on_action_Export_Map_Image_triggered()
|
||||
{
|
||||
QString defaultFilepath = QString("%1/%2.png").arg(editor->project->root).arg(editor->map->name);
|
||||
|
@ -1223,3 +1236,27 @@ void MainWindow::on_checkBox_ToggleBorder_stateChanged(int selected)
|
|||
bool visible = selected != 0;
|
||||
editor->toggleBorderVisibility(visible);
|
||||
}
|
||||
|
||||
void MainWindow::on_actionTileset_Editor_triggered()
|
||||
{
|
||||
if (!this->tilesetEditor) {
|
||||
this->tilesetEditor = new TilesetEditor(this->editor->project, this->editor->map->layout->tileset_primary_label, this->editor->map->layout->tileset_secondary_label, this);
|
||||
connect(this->tilesetEditor, SIGNAL(tilesetsSaved(QString, QString)), this, SLOT(onTilesetsSaved(QString, QString)));
|
||||
connect(this->tilesetEditor, SIGNAL(closed()), this, SLOT(onTilesetEditorClosed()));
|
||||
}
|
||||
|
||||
if (!this->tilesetEditor->isVisible()) {
|
||||
this->tilesetEditor->show();
|
||||
} else if (this->tilesetEditor->isMinimized()) {
|
||||
this->tilesetEditor->showNormal();
|
||||
} else {
|
||||
this->tilesetEditor->activateWindow();
|
||||
}
|
||||
}
|
||||
|
||||
void MainWindow::onTilesetEditorClosed() {
|
||||
if (this->tilesetEditor) {
|
||||
delete this->tilesetEditor;
|
||||
this->tilesetEditor = nullptr;
|
||||
}
|
||||
}
|
||||
|
|
227
src/project.cpp
227
src/project.cpp
|
@ -576,6 +576,77 @@ void Project::saveHealLocationStruct(Map *map) {
|
|||
saveTextFile(root + "/include/constants/heal_locations.h", constants_text);
|
||||
}
|
||||
|
||||
void Project::saveTilesets(Tileset *primaryTileset, Tileset *secondaryTileset) {
|
||||
saveTilesetMetatileAttributes(primaryTileset);
|
||||
saveTilesetMetatileAttributes(secondaryTileset);
|
||||
saveTilesetMetatiles(primaryTileset);
|
||||
saveTilesetMetatiles(secondaryTileset);
|
||||
saveTilesetTilesImage(primaryTileset);
|
||||
saveTilesetTilesImage(secondaryTileset);
|
||||
saveTilesetPalettes(primaryTileset, true);
|
||||
saveTilesetPalettes(secondaryTileset, false);
|
||||
}
|
||||
|
||||
void Project::saveTilesetMetatileAttributes(Tileset *tileset) {
|
||||
QFile attrs_file(tileset->metatile_attrs_path);
|
||||
if (attrs_file.open(QIODevice::WriteOnly | QIODevice::Truncate)) {
|
||||
QByteArray data;
|
||||
for (Metatile *metatile : *tileset->metatiles) {
|
||||
data.append(static_cast<char>(metatile->behavior));
|
||||
data.append(static_cast<char>((metatile->layerType << 4) & 0xF0));
|
||||
}
|
||||
attrs_file.write(data);
|
||||
} else {
|
||||
qDebug() << QString("Could not save tileset metatile attributes file '%1'").arg(tileset->metatile_attrs_path);
|
||||
}
|
||||
}
|
||||
|
||||
void Project::saveTilesetMetatiles(Tileset *tileset) {
|
||||
QFile metatiles_file(tileset->metatiles_path);
|
||||
if (metatiles_file.open(QIODevice::WriteOnly | QIODevice::Truncate)) {
|
||||
QByteArray data;
|
||||
for (Metatile *metatile : *tileset->metatiles) {
|
||||
for (int i = 0; i < 8; i++) {
|
||||
Tile tile = metatile->tiles->at(i);
|
||||
uint16_t value = static_cast<uint16_t>((tile.tile & 0x3ff)
|
||||
| ((tile.xflip & 1) << 10)
|
||||
| ((tile.yflip & 1) << 11)
|
||||
| ((tile.palette & 0xf) << 12));
|
||||
data.append(static_cast<char>(value & 0xff));
|
||||
data.append(static_cast<char>((value >> 8) & 0xff));
|
||||
}
|
||||
}
|
||||
metatiles_file.write(data);
|
||||
} else {
|
||||
tileset->metatiles = new QList<Metatile*>;
|
||||
qDebug() << QString("Could not open tileset metatiles file '%1'").arg(tileset->metatiles_path);
|
||||
}
|
||||
}
|
||||
|
||||
void Project::saveTilesetTilesImage(Tileset *tileset) {
|
||||
tileset->tilesImage.save(tileset->tilesImagePath);
|
||||
}
|
||||
|
||||
void Project::saveTilesetPalettes(Tileset *tileset, bool primary) {
|
||||
int startPaletteId = primary ? 0 : Project::getNumPalettesPrimary();
|
||||
int endPaletteId = primary ? Project::getNumPalettesPrimary() : Project::getNumPalettesTotal();
|
||||
for (int i = startPaletteId; i < endPaletteId; i++) {
|
||||
QString filepath = tileset->palettePaths.at(i);
|
||||
QString content = "JASC-PAL\r\n";
|
||||
content += "0100\r\n";
|
||||
content += "16\r\n";
|
||||
for (int j = 0; j < 16; j++) {
|
||||
QRgb color = tileset->palettes->at(i).at(j);
|
||||
content += QString("%1 %2 %3\r\n")
|
||||
.arg(qRed(color))
|
||||
.arg(qGreen(color))
|
||||
.arg(qBlue(color));
|
||||
}
|
||||
|
||||
saveTextFile(filepath, content);
|
||||
}
|
||||
}
|
||||
|
||||
void Project::loadMapTilesets(Map* map) {
|
||||
if (map->layout->has_unsaved_changes) {
|
||||
return;
|
||||
|
@ -585,12 +656,14 @@ void Project::loadMapTilesets(Map* map) {
|
|||
map->layout->tileset_secondary = getTileset(map->layout->tileset_secondary_label);
|
||||
}
|
||||
|
||||
Tileset* Project::loadTileset(QString label) {
|
||||
Tileset* Project::loadTileset(QString label, Tileset *tileset) {
|
||||
ParseUtil *parser = new ParseUtil;
|
||||
|
||||
QString headers_text = readTextFile(root + "/data/tilesets/headers.inc");
|
||||
QStringList *values = getLabelValues(parser->parseAsm(headers_text), label);
|
||||
Tileset *tileset = new Tileset;
|
||||
if (tileset == nullptr) {
|
||||
tileset = new Tileset;
|
||||
}
|
||||
tileset->name = label;
|
||||
tileset->is_compressed = values->value(0);
|
||||
tileset->is_secondary = values->value(1);
|
||||
|
@ -750,7 +823,8 @@ void Project::loadTilesetAssets(Tileset* tileset) {
|
|||
if (tileset->name.isNull()) {
|
||||
return;
|
||||
}
|
||||
QString dir_path = root + "/data/tilesets/" + category + "/" + tileset->name.replace("gTileset_", "").toLower();
|
||||
QString tilesetName = tileset->name;
|
||||
QString dir_path = root + "/data/tilesets/" + category + "/" + tilesetName.replace("gTileset_", "").toLower();
|
||||
|
||||
QString graphics_text = readTextFile(root + "/data/tilesets/graphics.inc");
|
||||
QList<QStringList> *graphics = parser->parseAsm(graphics_text);
|
||||
|
@ -767,53 +841,94 @@ void Project::loadTilesetAssets(Tileset* tileset) {
|
|||
}
|
||||
}
|
||||
|
||||
QStringList *palette_paths = new QStringList;
|
||||
if (!palettes_values->isEmpty()) {
|
||||
for (int i = 0; i < palettes_values->length(); i++) {
|
||||
QString value = palettes_values->value(i);
|
||||
palette_paths->append(root + "/" + value.section('"', 1, 1));
|
||||
tileset->palettePaths.append(this->fixPalettePath(root + "/" + value.section('"', 1, 1)));
|
||||
}
|
||||
} else {
|
||||
QString palettes_dir_path = dir_path + "/palettes";
|
||||
for (int i = 0; i < 16; i++) {
|
||||
palette_paths->append(palettes_dir_path + "/" + QString("%1").arg(i, 2, 10, QLatin1Char('0')) + ".gbapal");
|
||||
tileset->palettePaths.append(palettes_dir_path + "/" + QString("%1").arg(i, 2, 10, QLatin1Char('0')) + ".pal");
|
||||
}
|
||||
}
|
||||
|
||||
QString metatiles_path;
|
||||
QString metatile_attrs_path;
|
||||
QString metatiles_text = readTextFile(root + "/data/tilesets/metatiles.inc");
|
||||
QList<QStringList> *metatiles_macros = parser->parseAsm(metatiles_text);
|
||||
QStringList *metatiles_values = getLabelValues(metatiles_macros, tileset->metatiles_label);
|
||||
if (!metatiles_values->isEmpty()) {
|
||||
metatiles_path = root + "/" + metatiles_values->value(0).section('"', 1, 1);
|
||||
tileset->metatiles_path = root + "/" + metatiles_values->value(0).section('"', 1, 1);
|
||||
} else {
|
||||
metatiles_path = dir_path + "/metatiles.bin";
|
||||
tileset->metatiles_path = dir_path + "/metatiles.bin";
|
||||
}
|
||||
QStringList *metatile_attrs_values = getLabelValues(metatiles_macros, tileset->metatile_attrs_label);
|
||||
if (!metatile_attrs_values->isEmpty()) {
|
||||
metatile_attrs_path = root + "/" + metatile_attrs_values->value(0).section('"', 1, 1);
|
||||
tileset->metatile_attrs_path = root + "/" + metatile_attrs_values->value(0).section('"', 1, 1);
|
||||
} else {
|
||||
metatile_attrs_path = dir_path + "/metatile_attributes.bin";
|
||||
tileset->metatile_attrs_path = dir_path + "/metatile_attributes.bin";
|
||||
}
|
||||
|
||||
// tiles
|
||||
tiles_path = fixGraphicPath(tiles_path);
|
||||
QImage *image = new QImage(tiles_path);
|
||||
//image->setColor(0, qRgb(0xff, 0, 0)); // debug
|
||||
tileset->tilesImagePath = tiles_path;
|
||||
QImage image = QImage(tileset->tilesImagePath);
|
||||
this->loadTilesetTiles(tileset, image);
|
||||
this->loadTilesetMetatiles(tileset);
|
||||
|
||||
// palettes
|
||||
QList<QList<QRgb>> *palettes = new QList<QList<QRgb>>;
|
||||
for (int i = 0; i < tileset->palettePaths.length(); i++) {
|
||||
QList<QRgb> palette;
|
||||
QString path = tileset->palettePaths.value(i);
|
||||
QString text = readTextFile(path);
|
||||
if (!text.isNull()) {
|
||||
QStringList lines = text.split(QRegExp("[\r\n]"),QString::SkipEmptyParts);
|
||||
if (lines.length() == 19 && lines[0] == "JASC-PAL" && lines[1] == "0100" && lines[2] == "16") {
|
||||
for (int j = 0; j < 16; j++) {
|
||||
QStringList rgb = lines[j + 3].split(QRegExp(" "), QString::SkipEmptyParts);
|
||||
if (rgb.length() != 3) {
|
||||
qDebug() << QString("Invalid tileset palette RGB value: '%1'").arg(lines[j + 3]);
|
||||
palette.append(qRgb((j - 3) * 16, (j - 3) * 16, (j - 3) * 16));
|
||||
} else {
|
||||
int red = rgb[0].toInt();
|
||||
int green = rgb[1].toInt();
|
||||
int blue = rgb[2].toInt();
|
||||
QRgb color = qRgb(red, green, blue);
|
||||
palette.append(color);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
qDebug() << QString("Invalid JASC-PAL palette file for tileset.");
|
||||
for (int j = 0; j < 16; j++) {
|
||||
palette.append(qRgb(j * 16, j * 16, j * 16));
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (int j = 0; j < 16; j++) {
|
||||
palette.append(qRgb(j * 16, j * 16, j * 16));
|
||||
}
|
||||
qDebug() << QString("Could not open palette path '%1'").arg(path);
|
||||
}
|
||||
|
||||
palettes->append(palette);
|
||||
}
|
||||
tileset->palettes = palettes;
|
||||
}
|
||||
|
||||
void Project::loadTilesetTiles(Tileset *tileset, QImage image) {
|
||||
QList<QImage> *tiles = new QList<QImage>;
|
||||
int w = 8;
|
||||
int h = 8;
|
||||
for (int y = 0; y < image->height(); y += h)
|
||||
for (int x = 0; x < image->width(); x += w) {
|
||||
QImage tile = image->copy(x, y, w, h);
|
||||
for (int y = 0; y < image.height(); y += h)
|
||||
for (int x = 0; x < image.width(); x += w) {
|
||||
QImage tile = image.copy(x, y, w, h);
|
||||
tiles->append(tile);
|
||||
}
|
||||
tileset->tilesImage = image;
|
||||
tileset->tiles = tiles;
|
||||
}
|
||||
|
||||
// metatiles
|
||||
QFile metatiles_file(metatiles_path);
|
||||
void Project::loadTilesetMetatiles(Tileset* tileset) {
|
||||
QFile metatiles_file(tileset->metatiles_path);
|
||||
if (metatiles_file.open(QIODevice::ReadOnly)) {
|
||||
QByteArray data = metatiles_file.readAll();
|
||||
int num_metatiles = data.length() / 16;
|
||||
|
@ -837,11 +952,10 @@ void Project::loadTilesetAssets(Tileset* tileset) {
|
|||
tileset->metatiles = metatiles;
|
||||
} else {
|
||||
tileset->metatiles = new QList<Metatile*>;
|
||||
qDebug() << QString("Could not open '%1'").arg(metatiles_path);
|
||||
qDebug() << QString("Could not open tileset metatiles file '%1'").arg(tileset->metatiles_path);
|
||||
}
|
||||
|
||||
QFile attrs_file(metatile_attrs_path);
|
||||
//qDebug() << metatile_attrs_path;
|
||||
QFile attrs_file(tileset->metatile_attrs_path);
|
||||
if (attrs_file.open(QIODevice::ReadOnly)) {
|
||||
QByteArray data = attrs_file.readAll();
|
||||
int num_metatiles = tileset->metatiles->count();
|
||||
|
@ -851,41 +965,14 @@ void Project::loadTilesetAssets(Tileset* tileset) {
|
|||
if (num_metatiles > num_metatileAttrs)
|
||||
num_metatiles = num_metatileAttrs;
|
||||
}
|
||||
} else {
|
||||
qDebug() << QString("Could not open '%1'").arg(metatile_attrs_path);
|
||||
}
|
||||
|
||||
// palettes
|
||||
QList<QList<QRgb>> *palettes = new QList<QList<QRgb>>;
|
||||
for (int i = 0; i < palette_paths->length(); i++) {
|
||||
QString path = palette_paths->value(i);
|
||||
// the palettes are not compressed. this should never happen. it's only a precaution.
|
||||
path = path.replace(QRegExp("\\.lz$"), "");
|
||||
// TODO default to .pal (JASC-PAL)
|
||||
// just use .gbapal for now
|
||||
QFile file(path);
|
||||
QList<QRgb> palette;
|
||||
if (file.open(QIODevice::ReadOnly)) {
|
||||
QByteArray data = file.readAll();
|
||||
for (int j = 0; j < 16; j++) {
|
||||
uint16_t word = data[j*2] & 0xff;
|
||||
word += (data[j*2 + 1] & 0xff) << 8;
|
||||
int red = word & 0x1f;
|
||||
int green = (word >> 5) & 0x1f;
|
||||
int blue = (word >> 10) & 0x1f;
|
||||
QRgb color = qRgb(red * 8, green * 8, blue * 8);
|
||||
palette.append(color);
|
||||
for (int i = 0; i < num_metatileAttrs; i++) {
|
||||
int value = (static_cast<unsigned char>(data.at(i * 2 + 1)) << 8) | static_cast<unsigned char>(data.at(i * 2));
|
||||
tileset->metatiles->at(i)->behavior = value & 0xFF;
|
||||
tileset->metatiles->at(i)->layerType = (value & 0xF000) >> 12;
|
||||
}
|
||||
} else {
|
||||
for (int j = 0; j < 16; j++) {
|
||||
palette.append(qRgb(j * 16, j * 16, j * 16));
|
||||
qDebug() << QString("Could not open tileset metatile attributes file '%1'").arg(tileset->metatile_attrs_path);
|
||||
}
|
||||
qDebug() << QString("Could not open palette path '%1'").arg(path);
|
||||
}
|
||||
|
||||
palettes->append(palette);
|
||||
}
|
||||
tileset->palettes = palettes;
|
||||
}
|
||||
|
||||
Blockdata* Project::readBlockdata(QString path) {
|
||||
|
@ -913,11 +1000,16 @@ Map* Project::getMap(QString map_name) {
|
|||
}
|
||||
}
|
||||
|
||||
Tileset* Project::getTileset(QString label) {
|
||||
Tileset* Project::getTileset(QString label, bool forceLoad) {
|
||||
Tileset *existingTileset = nullptr;
|
||||
if (tileset_cache->contains(label)) {
|
||||
existingTileset = tileset_cache->value(label);
|
||||
}
|
||||
|
||||
if (existingTileset && !forceLoad) {
|
||||
return tileset_cache->value(label);
|
||||
} else {
|
||||
Tileset *tileset = loadTileset(label);
|
||||
Tileset *tileset = loadTileset(label, existingTileset);
|
||||
return tileset;
|
||||
}
|
||||
}
|
||||
|
@ -1249,6 +1341,22 @@ void Project::readBgEventFacingDirections() {
|
|||
readCDefinesSorted(filepath, prefixes, bgEventFacingDirections);
|
||||
}
|
||||
|
||||
void Project::readMetatileBehaviors() {
|
||||
this->metatileBehaviorMap.clear();
|
||||
this->metatileBehaviorMapInverse.clear();
|
||||
QString filepath = root + "/include/constants/metatile_behaviors.h";
|
||||
QString text = readTextFile(filepath);
|
||||
if (!text.isNull()) {
|
||||
QStringList prefixes = (QStringList() << "MB_");
|
||||
this->metatileBehaviorMap = readCDefines(text, prefixes);
|
||||
for (QString defineName : this->metatileBehaviorMap.keys()) {
|
||||
this->metatileBehaviorMapInverse.insert(this->metatileBehaviorMap[defineName], defineName);
|
||||
}
|
||||
} else {
|
||||
qDebug() << "Failed to read C defines file: " << filepath;
|
||||
}
|
||||
}
|
||||
|
||||
void Project::readCDefinesSorted(QString filepath, QStringList prefixes, QStringList* definesToSet) {
|
||||
QString text = readTextFile(filepath);
|
||||
if (!text.isNull()) {
|
||||
|
@ -1324,6 +1432,11 @@ QMap<QString, int> Project::getEventObjGfxConstants() {
|
|||
return constants;
|
||||
}
|
||||
|
||||
QString Project::fixPalettePath(QString path) {
|
||||
path = path.replace(QRegExp("\\.gbapal$"), ".pal");
|
||||
return path;
|
||||
}
|
||||
|
||||
QString Project::fixGraphicPath(QString path) {
|
||||
path = path.replace(QRegExp("\\.lz$"), "");
|
||||
path = path.replace(QRegExp("\\.[1248]bpp$"), ".png");
|
||||
|
|
|
@ -13,7 +13,7 @@ QImage getCollisionMetatileImage(int collision, int elevation) {
|
|||
return collisionImage.toImage();
|
||||
}
|
||||
|
||||
QImage getMetatileImage(int tile, Tileset *primaryTileset, Tileset *secondaryTileset) {
|
||||
QImage getMetatileImage(uint16_t tile, Tileset *primaryTileset, Tileset *secondaryTileset) {
|
||||
QImage metatile_image(16, 16, QImage::Format_RGBA8888);
|
||||
|
||||
Metatile* metatile = Tileset::getMetatile(tile, primaryTileset, secondaryTileset);
|
||||
|
@ -71,7 +71,7 @@ QImage getMetatileImage(int tile, Tileset *primaryTileset, Tileset *secondaryTil
|
|||
return metatile_image;
|
||||
}
|
||||
|
||||
QImage getTileImage(int tile, Tileset *primaryTileset, Tileset *secondaryTileset) {
|
||||
QImage getTileImage(uint16_t tile, Tileset *primaryTileset, Tileset *secondaryTileset) {
|
||||
Tileset *tileset = Tileset::getBlockTileset(tile, primaryTileset, secondaryTileset);
|
||||
int local_index = Metatile::getBlockIndex(tile);
|
||||
if (!tileset || !tileset->tiles) {
|
||||
|
@ -79,3 +79,19 @@ QImage getTileImage(int tile, Tileset *primaryTileset, Tileset *secondaryTileset
|
|||
}
|
||||
return tileset->tiles->value(local_index, QImage());
|
||||
}
|
||||
|
||||
QImage getColoredTileImage(uint16_t tile, Tileset *primaryTileset, Tileset *secondaryTileset, int paletteId) {
|
||||
QList<QRgb> palette = Tileset::getPalette(paletteId, primaryTileset, secondaryTileset);
|
||||
QImage tileImage = getTileImage(tile, primaryTileset, secondaryTileset);
|
||||
if (tileImage.isNull()) {
|
||||
tileImage = QImage(16, 16, QImage::Format_RGBA8888);
|
||||
QPainter painter(&tileImage);
|
||||
painter.fillRect(0, 0, 16, 16, palette.at(0));
|
||||
} else {
|
||||
for (int i = 0; i < 16; i++) {
|
||||
tileImage.setColor(i, palette.at(i));
|
||||
}
|
||||
}
|
||||
|
||||
return tileImage;
|
||||
}
|
||||
|
|
45
src/ui/metatilelayersitem.cpp
Normal file
45
src/ui/metatilelayersitem.cpp
Normal file
|
@ -0,0 +1,45 @@
|
|||
#include "metatilelayersitem.h"
|
||||
#include "imageproviders.h"
|
||||
#include <QPainter>
|
||||
|
||||
void MetatileLayersItem::draw() {
|
||||
const QList<QPoint> tileCoords = QList<QPoint>{
|
||||
QPoint(0, 0),
|
||||
QPoint(16, 0),
|
||||
QPoint(0, 16),
|
||||
QPoint(16, 16),
|
||||
QPoint(32, 0),
|
||||
QPoint(48, 0),
|
||||
QPoint(32, 16),
|
||||
QPoint(48, 16),
|
||||
};
|
||||
|
||||
QPixmap pixmap(64, 32);
|
||||
QPainter painter(&pixmap);
|
||||
for (int i = 0; i < 8; i++) {
|
||||
Tile tile = this->metatile->tiles->at(i);
|
||||
QImage tileImage = getColoredTileImage(tile.tile, this->primaryTileset, this->secondaryTileset, tile.palette)
|
||||
.mirrored(tile.xflip, tile.yflip)
|
||||
.scaled(16, 16);
|
||||
painter.drawImage(tileCoords.at(i), tileImage);
|
||||
}
|
||||
|
||||
this->setPixmap(pixmap);
|
||||
}
|
||||
|
||||
void MetatileLayersItem::setMetatile(Metatile *metatile) {
|
||||
this->metatile = metatile;
|
||||
}
|
||||
|
||||
void MetatileLayersItem::setTilesets(Tileset *primaryTileset, Tileset *secondaryTileset) {
|
||||
this->primaryTileset = primaryTileset;
|
||||
this->secondaryTileset = secondaryTileset;
|
||||
this->draw();
|
||||
}
|
||||
|
||||
void MetatileLayersItem::mousePressEvent(QGraphicsSceneMouseEvent *event) {
|
||||
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);
|
||||
}
|
176
src/ui/paletteeditor.cpp
Normal file
176
src/ui/paletteeditor.cpp
Normal file
|
@ -0,0 +1,176 @@
|
|||
#include "paletteeditor.h"
|
||||
#include "ui_paletteeditor.h"
|
||||
|
||||
PaletteEditor::PaletteEditor(Project *project, Tileset *primaryTileset, Tileset *secondaryTileset, QWidget *parent) :
|
||||
QMainWindow(parent),
|
||||
ui(new Ui::PaletteEditor)
|
||||
{
|
||||
this->project = project;
|
||||
this->primaryTileset = primaryTileset;
|
||||
this->secondaryTileset = secondaryTileset;
|
||||
this->ui->setupUi(this);
|
||||
this->ui->spinBox_PaletteId->setMinimum(0);
|
||||
this->ui->spinBox_PaletteId->setMaximum(Project::getNumPalettesTotal() - 1);
|
||||
this->sliders.clear();
|
||||
for (int i = 0; i < 16; i++) {
|
||||
this->sliders.append(QList<QSlider*>());
|
||||
}
|
||||
this->sliders[0].append(this->ui->horizontalSlider);
|
||||
this->sliders[0].append(this->ui->horizontalSlider_2);
|
||||
this->sliders[0].append(this->ui->horizontalSlider_3);
|
||||
this->sliders[1].append(this->ui->horizontalSlider_4);
|
||||
this->sliders[1].append(this->ui->horizontalSlider_5);
|
||||
this->sliders[1].append(this->ui->horizontalSlider_6);
|
||||
this->sliders[2].append(this->ui->horizontalSlider_7);
|
||||
this->sliders[2].append(this->ui->horizontalSlider_8);
|
||||
this->sliders[2].append(this->ui->horizontalSlider_9);
|
||||
this->sliders[3].append(this->ui->horizontalSlider_10);
|
||||
this->sliders[3].append(this->ui->horizontalSlider_11);
|
||||
this->sliders[3].append(this->ui->horizontalSlider_12);
|
||||
this->sliders[4].append(this->ui->horizontalSlider_13);
|
||||
this->sliders[4].append(this->ui->horizontalSlider_14);
|
||||
this->sliders[4].append(this->ui->horizontalSlider_15);
|
||||
this->sliders[5].append(this->ui->horizontalSlider_16);
|
||||
this->sliders[5].append(this->ui->horizontalSlider_17);
|
||||
this->sliders[5].append(this->ui->horizontalSlider_18);
|
||||
this->sliders[6].append(this->ui->horizontalSlider_19);
|
||||
this->sliders[6].append(this->ui->horizontalSlider_20);
|
||||
this->sliders[6].append(this->ui->horizontalSlider_21);
|
||||
this->sliders[7].append(this->ui->horizontalSlider_22);
|
||||
this->sliders[7].append(this->ui->horizontalSlider_23);
|
||||
this->sliders[7].append(this->ui->horizontalSlider_24);
|
||||
this->sliders[8].append(this->ui->horizontalSlider_25);
|
||||
this->sliders[8].append(this->ui->horizontalSlider_26);
|
||||
this->sliders[8].append(this->ui->horizontalSlider_27);
|
||||
this->sliders[9].append(this->ui->horizontalSlider_28);
|
||||
this->sliders[9].append(this->ui->horizontalSlider_29);
|
||||
this->sliders[9].append(this->ui->horizontalSlider_30);
|
||||
this->sliders[10].append(this->ui->horizontalSlider_31);
|
||||
this->sliders[10].append(this->ui->horizontalSlider_32);
|
||||
this->sliders[10].append(this->ui->horizontalSlider_33);
|
||||
this->sliders[11].append(this->ui->horizontalSlider_34);
|
||||
this->sliders[11].append(this->ui->horizontalSlider_35);
|
||||
this->sliders[11].append(this->ui->horizontalSlider_36);
|
||||
this->sliders[12].append(this->ui->horizontalSlider_37);
|
||||
this->sliders[12].append(this->ui->horizontalSlider_38);
|
||||
this->sliders[12].append(this->ui->horizontalSlider_39);
|
||||
this->sliders[13].append(this->ui->horizontalSlider_40);
|
||||
this->sliders[13].append(this->ui->horizontalSlider_41);
|
||||
this->sliders[13].append(this->ui->horizontalSlider_42);
|
||||
this->sliders[14].append(this->ui->horizontalSlider_43);
|
||||
this->sliders[14].append(this->ui->horizontalSlider_44);
|
||||
this->sliders[14].append(this->ui->horizontalSlider_45);
|
||||
this->sliders[15].append(this->ui->horizontalSlider_46);
|
||||
this->sliders[15].append(this->ui->horizontalSlider_47);
|
||||
this->sliders[15].append(this->ui->horizontalSlider_48);
|
||||
|
||||
this->frames.clear();
|
||||
this->frames.append(this->ui->frame);
|
||||
this->frames.append(this->ui->frame_2);
|
||||
this->frames.append(this->ui->frame_3);
|
||||
this->frames.append(this->ui->frame_4);
|
||||
this->frames.append(this->ui->frame_5);
|
||||
this->frames.append(this->ui->frame_6);
|
||||
this->frames.append(this->ui->frame_7);
|
||||
this->frames.append(this->ui->frame_8);
|
||||
this->frames.append(this->ui->frame_9);
|
||||
this->frames.append(this->ui->frame_10);
|
||||
this->frames.append(this->ui->frame_11);
|
||||
this->frames.append(this->ui->frame_12);
|
||||
this->frames.append(this->ui->frame_13);
|
||||
this->frames.append(this->ui->frame_14);
|
||||
this->frames.append(this->ui->frame_15);
|
||||
this->frames.append(this->ui->frame_16);
|
||||
|
||||
this->initColorSliders();
|
||||
this->refreshColorSliders();
|
||||
this->refreshColors();
|
||||
}
|
||||
|
||||
PaletteEditor::~PaletteEditor()
|
||||
{
|
||||
delete ui;
|
||||
}
|
||||
|
||||
void PaletteEditor::disableSliderSignals() {
|
||||
for (int i = 0; i < this->sliders.length(); i++) {
|
||||
this->sliders.at(i).at(0)->blockSignals(true);
|
||||
this->sliders.at(i).at(1)->blockSignals(true);
|
||||
this->sliders.at(i).at(2)->blockSignals(true);
|
||||
}
|
||||
}
|
||||
|
||||
void PaletteEditor::enableSliderSignals() {
|
||||
for (int i = 0; i < this->sliders.length(); i++) {
|
||||
this->sliders.at(i).at(0)->blockSignals(false);
|
||||
this->sliders.at(i).at(1)->blockSignals(false);
|
||||
this->sliders.at(i).at(2)->blockSignals(false);
|
||||
}
|
||||
}
|
||||
|
||||
void PaletteEditor::initColorSliders() {
|
||||
for (int i = 0; i < 16; i++) {
|
||||
connect(this->sliders[i][0], &QSlider::valueChanged, [=](int) { this->setColor(i); });
|
||||
connect(this->sliders[i][1], &QSlider::valueChanged, [=](int) { this->setColor(i); });
|
||||
connect(this->sliders[i][2], &QSlider::valueChanged, [=](int) { this->setColor(i); });
|
||||
}
|
||||
}
|
||||
|
||||
void PaletteEditor::refreshColorSliders() {
|
||||
disableSliderSignals();
|
||||
int paletteNum = this->ui->spinBox_PaletteId->value();
|
||||
for (int i = 0; i < 16; i++) {
|
||||
QRgb color;
|
||||
if (paletteNum < Project::getNumPalettesPrimary()) {
|
||||
color = this->primaryTileset->palettes->at(paletteNum).at(i);
|
||||
} else {
|
||||
color = this->secondaryTileset->palettes->at(paletteNum).at(i);
|
||||
}
|
||||
|
||||
this->sliders[i][0]->setValue(qRed(color) / 8);
|
||||
this->sliders[i][1]->setValue(qGreen(color) / 8);
|
||||
this->sliders[i][2]->setValue(qBlue(color) / 8);
|
||||
}
|
||||
enableSliderSignals();
|
||||
}
|
||||
|
||||
void PaletteEditor::refreshColors() {
|
||||
for (int i = 0; i < 16; i++) {
|
||||
this->refreshColor(i);
|
||||
}
|
||||
}
|
||||
|
||||
void PaletteEditor::refreshColor(int colorIndex) {
|
||||
QString stylesheet = QString("background-color: rgb(%1, %2, %3);")
|
||||
.arg(this->sliders[colorIndex][0]->value() * 8)
|
||||
.arg(this->sliders[colorIndex][1]->value() * 8)
|
||||
.arg(this->sliders[colorIndex][2]->value() * 8);
|
||||
this->frames[colorIndex]->setStyleSheet(stylesheet);
|
||||
}
|
||||
|
||||
void PaletteEditor::setPaletteId(int paletteId) {
|
||||
this->ui->spinBox_PaletteId->blockSignals(true);
|
||||
this->ui->spinBox_PaletteId->setValue(paletteId);
|
||||
this->refreshColorSliders();
|
||||
this->refreshColors();
|
||||
this->ui->spinBox_PaletteId->blockSignals(false);
|
||||
}
|
||||
|
||||
void PaletteEditor::setColor(int colorIndex) {
|
||||
int paletteNum = this->ui->spinBox_PaletteId->value();
|
||||
int red = this->sliders[colorIndex][0]->value() * 8;
|
||||
int green = this->sliders[colorIndex][1]->value() * 8;
|
||||
int blue = this->sliders[colorIndex][2]->value() * 8;
|
||||
Tileset *tileset = paletteNum < Project::getNumPalettesPrimary()
|
||||
? this->primaryTileset
|
||||
: this->secondaryTileset;
|
||||
(*tileset->palettes)[paletteNum][colorIndex] = qRgb(red, green, blue);
|
||||
this->refreshColor(colorIndex);
|
||||
emit this->changedPaletteColor();
|
||||
}
|
||||
|
||||
void PaletteEditor::on_spinBox_PaletteId_valueChanged(int paletteId) {
|
||||
this->refreshColorSliders();
|
||||
this->refreshColors();
|
||||
emit this->changedPalette(paletteId);
|
||||
}
|
|
@ -80,6 +80,10 @@ void SelectablePixmapItem::updateSelection(int x, int y)
|
|||
|
||||
QPoint SelectablePixmapItem::getCellPos(QPointF pos)
|
||||
{
|
||||
if (pos.x() < 0) pos.setX(0);
|
||||
if (pos.y() < 0) pos.setY(0);
|
||||
if (pos.x() >= this->pixmap().width()) pos.setX(this->pixmap().width() - 1);
|
||||
if (pos.y() >= this->pixmap().height()) pos.setY(this->pixmap().height() - 1);
|
||||
return QPoint(static_cast<int>(pos.x()) / this->cellWidth,
|
||||
static_cast<int>(pos.y()) / this->cellHeight);
|
||||
}
|
||||
|
|
|
@ -1,14 +1,460 @@
|
|||
#include "tileseteditor.h"
|
||||
#include "ui_tileseteditor.h"
|
||||
#include "imageproviders.h"
|
||||
#include <QFileDialog>
|
||||
#include <QDebug>
|
||||
#include <QMessageBox>
|
||||
#include <QDialogButtonBox>
|
||||
|
||||
TilesetEditor::TilesetEditor(QWidget *parent) :
|
||||
QDialog(parent),
|
||||
TilesetEditor::TilesetEditor(Project *project, QString primaryTilesetLabel, QString secondaryTilesetLabel, QWidget *parent) :
|
||||
QMainWindow(parent),
|
||||
ui(new Ui::TilesetEditor)
|
||||
{
|
||||
ui->setupUi(this);
|
||||
this->init(project, primaryTilesetLabel, secondaryTilesetLabel);
|
||||
}
|
||||
|
||||
TilesetEditor::~TilesetEditor()
|
||||
{
|
||||
delete ui;
|
||||
}
|
||||
|
||||
void TilesetEditor::init(Project *project, QString primaryTilesetLabel, QString secondaryTilesetLabel) {
|
||||
ui->setupUi(this);
|
||||
this->project = project;
|
||||
|
||||
this->hasUnsavedChanges = false;
|
||||
this->tileXFlip = ui->checkBox_xFlip->isChecked();
|
||||
this->tileYFlip = ui->checkBox_yFlip->isChecked();
|
||||
this->paletteId = ui->spinBox_paletteSelector->value();
|
||||
|
||||
Tileset *primaryTileset = project->getTileset(primaryTilesetLabel);
|
||||
Tileset *secondaryTileset = project->getTileset(secondaryTilesetLabel);
|
||||
if (this->primaryTileset) delete this->primaryTileset;
|
||||
if (this->secondaryTileset) delete this->secondaryTileset;
|
||||
this->primaryTileset = primaryTileset->copy();
|
||||
this->secondaryTileset = secondaryTileset->copy();
|
||||
|
||||
QList<QString> sortedBehaviors;
|
||||
for (int num : project->metatileBehaviorMapInverse.keys()) {
|
||||
this->ui->comboBox_metatileBehaviors->addItem(project->metatileBehaviorMapInverse[num], num);
|
||||
}
|
||||
this->ui->comboBox_layerType->addItem("Normal - Middle/Top", 0);
|
||||
this->ui->comboBox_layerType->addItem("Covered - Bottom/Middle", 1);
|
||||
this->ui->comboBox_layerType->addItem("Split - Bottom/Top", 2);
|
||||
this->ui->spinBox_paletteSelector->setMinimum(0);
|
||||
this->ui->spinBox_paletteSelector->setMaximum(Project::getNumPalettesTotal() - 1);
|
||||
|
||||
this->initMetatileSelector();
|
||||
this->initMetatileLayersItem();
|
||||
this->initTileSelector();
|
||||
this->initSelectedTileItem();
|
||||
this->metatileSelector->select(0);
|
||||
}
|
||||
|
||||
void TilesetEditor::setTilesets(QString primaryTilesetLabel, QString secondaryTilesetLabel) {
|
||||
delete this->primaryTileset;
|
||||
delete this->secondaryTileset;
|
||||
Tileset *primaryTileset = project->getTileset(primaryTilesetLabel);
|
||||
Tileset *secondaryTileset = project->getTileset(secondaryTilesetLabel);
|
||||
this->primaryTileset = primaryTileset->copy();
|
||||
this->secondaryTileset = secondaryTileset->copy();
|
||||
this->refresh();
|
||||
}
|
||||
|
||||
void TilesetEditor::refresh() {
|
||||
this->metatileSelector->setTilesets(this->primaryTileset, this->secondaryTileset);
|
||||
this->tileSelector->setTilesets(this->primaryTileset, this->secondaryTileset);
|
||||
this->metatileLayersItem->setTilesets(this->primaryTileset, this->secondaryTileset);
|
||||
this->metatileSelector->select(this->metatileSelector->getSelectedMetatile());
|
||||
this->drawSelectedTiles();
|
||||
|
||||
this->ui->graphicsView_Tiles->setSceneRect(0, 0, this->tileSelector->pixmap().width() + 2, this->tileSelector->pixmap().height() + 2);
|
||||
this->ui->graphicsView_Tiles->setFixedSize(this->tileSelector->pixmap().width() + 2, this->tileSelector->pixmap().height() + 2);
|
||||
this->ui->graphicsView_Metatiles->setSceneRect(0, 0, this->metatileSelector->pixmap().width() + 2, this->metatileSelector->pixmap().height() + 2);
|
||||
this->ui->graphicsView_Metatiles->setFixedSize(this->metatileSelector->pixmap().width() + 2, this->metatileSelector->pixmap().height() + 2);
|
||||
this->ui->graphicsView_selectedTile->setFixedSize(this->selectedTilePixmapItem->pixmap().width(), this->selectedTilePixmapItem->pixmap().height());
|
||||
}
|
||||
|
||||
void TilesetEditor::initMetatileSelector()
|
||||
{
|
||||
this->metatileSelector = new TilesetEditorMetatileSelector(this->primaryTileset, this->secondaryTileset);
|
||||
connect(this->metatileSelector, SIGNAL(hoveredMetatileChanged(uint16_t)),
|
||||
this, SLOT(onHoveredMetatileChanged(uint16_t)));
|
||||
connect(this->metatileSelector, SIGNAL(hoveredMetatileCleared()),
|
||||
this, SLOT(onHoveredMetatileCleared()));
|
||||
connect(this->metatileSelector, SIGNAL(selectedMetatileChanged(uint16_t)),
|
||||
this, SLOT(onSelectedMetatileChanged(uint16_t)));
|
||||
|
||||
this->metatilesScene = new QGraphicsScene;
|
||||
this->metatilesScene->addItem(this->metatileSelector);
|
||||
this->metatileSelector->draw();
|
||||
|
||||
this->ui->graphicsView_Metatiles->setScene(this->metatilesScene);
|
||||
this->ui->graphicsView_Metatiles->setFixedSize(this->metatileSelector->pixmap().width() + 2, this->metatileSelector->pixmap().height() + 2);
|
||||
}
|
||||
|
||||
void TilesetEditor::initTileSelector()
|
||||
{
|
||||
this->tileSelector = new TilesetEditorTileSelector(this->primaryTileset, this->secondaryTileset);
|
||||
connect(this->tileSelector, SIGNAL(hoveredTileChanged(uint16_t)),
|
||||
this, SLOT(onHoveredTileChanged(uint16_t)));
|
||||
connect(this->tileSelector, SIGNAL(hoveredTileCleared()),
|
||||
this, SLOT(onHoveredTileCleared()));
|
||||
connect(this->tileSelector, SIGNAL(selectedTilesChanged()),
|
||||
this, SLOT(onSelectedTilesChanged()));
|
||||
|
||||
this->tilesScene = new QGraphicsScene;
|
||||
this->tilesScene->addItem(this->tileSelector);
|
||||
this->tileSelector->select(0);
|
||||
this->tileSelector->draw();
|
||||
|
||||
this->ui->graphicsView_Tiles->setScene(this->tilesScene);
|
||||
this->ui->graphicsView_Tiles->setFixedSize(this->tileSelector->pixmap().width() + 2, this->tileSelector->pixmap().height() + 2);
|
||||
}
|
||||
|
||||
void TilesetEditor::initSelectedTileItem() {
|
||||
this->selectedTileScene = new QGraphicsScene;
|
||||
this->drawSelectedTiles();
|
||||
this->ui->graphicsView_selectedTile->setScene(this->selectedTileScene);
|
||||
this->ui->graphicsView_selectedTile->setFixedSize(this->selectedTilePixmapItem->pixmap().width(), this->selectedTilePixmapItem->pixmap().height());
|
||||
}
|
||||
|
||||
void TilesetEditor::drawSelectedTiles() {
|
||||
if (!this->selectedTileScene) {
|
||||
return;
|
||||
}
|
||||
|
||||
this->selectedTileScene->clear();
|
||||
QList<uint16_t> tiles = this->tileSelector->getSelectedTiles();
|
||||
QPoint dimensions = this->tileSelector->getSelectionDimensions();
|
||||
QImage selectionImage(16 * dimensions.x(), 16 * dimensions.y(), QImage::Format_RGBA8888);
|
||||
QPainter painter(&selectionImage);
|
||||
int tileIndex = 0;
|
||||
for (int j = 0; j < dimensions.y(); j++) {
|
||||
for (int i = 0; i < dimensions.x(); i++) {
|
||||
QImage tileImage = getColoredTileImage(tiles.at(tileIndex), this->primaryTileset, this->secondaryTileset, this->paletteId)
|
||||
.mirrored(this->tileXFlip, this->tileYFlip)
|
||||
.scaled(16, 16);
|
||||
tileIndex++;
|
||||
painter.drawImage(i * 16, j * 16, tileImage);
|
||||
}
|
||||
}
|
||||
|
||||
this->selectedTilePixmapItem = new QGraphicsPixmapItem(QPixmap::fromImage(selectionImage));
|
||||
this->selectedTileScene->addItem(this->selectedTilePixmapItem);
|
||||
this->ui->graphicsView_selectedTile->setFixedSize(this->selectedTilePixmapItem->pixmap().width(), this->selectedTilePixmapItem->pixmap().height());
|
||||
}
|
||||
|
||||
void TilesetEditor::initMetatileLayersItem() {
|
||||
Metatile *metatile = Tileset::getMetatile(this->metatileSelector->getSelectedMetatile(), this->primaryTileset, this->secondaryTileset);
|
||||
this->metatileLayersItem = new MetatileLayersItem(metatile, this->primaryTileset, this->secondaryTileset);
|
||||
connect(this->metatileLayersItem, SIGNAL(tileChanged(int, int)),
|
||||
this, SLOT(onMetatileLayerTileChanged(int, int)));
|
||||
|
||||
this->metatileLayersScene = new QGraphicsScene;
|
||||
this->metatileLayersScene->addItem(this->metatileLayersItem);
|
||||
this->ui->graphicsView_metatileLayers->setScene(this->metatileLayersScene);
|
||||
}
|
||||
|
||||
void TilesetEditor::onHoveredMetatileChanged(uint16_t metatileId) {
|
||||
QString message = QString("Metatile: 0x%1")
|
||||
.arg(QString("%1").arg(metatileId, 3, 16, QChar('0')).toUpper());
|
||||
this->ui->statusbar->showMessage(message);
|
||||
}
|
||||
|
||||
void TilesetEditor::onHoveredMetatileCleared() {
|
||||
this->ui->statusbar->clearMessage();
|
||||
}
|
||||
|
||||
void TilesetEditor::onSelectedMetatileChanged(uint16_t metatileId) {
|
||||
this->metatile = Tileset::getMetatile(metatileId, this->primaryTileset, this->secondaryTileset);
|
||||
this->metatileLayersItem->setMetatile(metatile);
|
||||
this->metatileLayersItem->draw();
|
||||
this->ui->comboBox_metatileBehaviors->setCurrentIndex(this->ui->comboBox_metatileBehaviors->findData(this->metatile->behavior));
|
||||
this->ui->comboBox_layerType->setCurrentIndex(this->ui->comboBox_layerType->findData(this->metatile->layerType));
|
||||
}
|
||||
|
||||
void TilesetEditor::onHoveredTileChanged(uint16_t tile) {
|
||||
QString message = QString("Tile: 0x%1")
|
||||
.arg(QString("%1").arg(tile, 3, 16, QChar('0')).toUpper());
|
||||
this->ui->statusbar->showMessage(message);
|
||||
}
|
||||
|
||||
void TilesetEditor::onHoveredTileCleared() {
|
||||
this->ui->statusbar->clearMessage();
|
||||
}
|
||||
|
||||
void TilesetEditor::onSelectedTilesChanged() {
|
||||
this->drawSelectedTiles();
|
||||
}
|
||||
|
||||
void TilesetEditor::onMetatileLayerTileChanged(int x, int y) {
|
||||
int maxTileIndex = x < 2 ? 3 : 7;
|
||||
QPoint dimensions = this->tileSelector->getSelectionDimensions();
|
||||
QList<uint16_t> tiles = this->tileSelector->getSelectedTiles();
|
||||
int selectedTileIndex = 0;
|
||||
for (int j = 0; j < dimensions.y(); j++) {
|
||||
for (int i = 0; i < dimensions.x(); i++) {
|
||||
int tileIndex = ((x + i) / 2 * 4) + ((y + j) * 2) + ((x + i) % 2);
|
||||
if (tileIndex <= maxTileIndex) {
|
||||
Tile tile = this->metatile->tiles->at(tileIndex);
|
||||
tile.tile = tiles.at(selectedTileIndex);
|
||||
tile.xflip = this->tileXFlip;
|
||||
tile.yflip = this->tileYFlip;
|
||||
tile.palette = this->paletteId;
|
||||
(*this->metatile->tiles)[tileIndex] = tile;
|
||||
}
|
||||
selectedTileIndex++;
|
||||
}
|
||||
}
|
||||
|
||||
this->metatileSelector->draw();
|
||||
this->metatileLayersItem->draw();
|
||||
this->hasUnsavedChanges = true;
|
||||
}
|
||||
|
||||
void TilesetEditor::on_spinBox_paletteSelector_valueChanged(int paletteId)
|
||||
{
|
||||
this->ui->spinBox_paletteSelector->blockSignals(true);
|
||||
this->ui->spinBox_paletteSelector->setValue(paletteId);
|
||||
this->ui->spinBox_paletteSelector->blockSignals(false);
|
||||
this->paletteId = paletteId;
|
||||
this->tileSelector->setPaletteId(paletteId);
|
||||
this->drawSelectedTiles();
|
||||
if (this->paletteEditor) {
|
||||
this->paletteEditor->setPaletteId(paletteId);
|
||||
}
|
||||
}
|
||||
|
||||
void TilesetEditor::on_checkBox_xFlip_stateChanged(int checked)
|
||||
{
|
||||
this->tileXFlip = checked;
|
||||
this->tileSelector->setTileFlips(this->tileXFlip, this->tileYFlip);
|
||||
this->drawSelectedTiles();
|
||||
}
|
||||
|
||||
void TilesetEditor::on_checkBox_yFlip_stateChanged(int checked)
|
||||
{
|
||||
this->tileYFlip = checked;
|
||||
this->tileSelector->setTileFlips(this->tileXFlip, this->tileYFlip);
|
||||
this->drawSelectedTiles();
|
||||
}
|
||||
|
||||
void TilesetEditor::on_comboBox_metatileBehaviors_currentIndexChanged(const QString &metatileBehavior)
|
||||
{
|
||||
if (this->metatile) {
|
||||
this->metatile->behavior = static_cast<uint8_t>(project->metatileBehaviorMap[metatileBehavior]);
|
||||
}
|
||||
}
|
||||
|
||||
void TilesetEditor::on_comboBox_layerType_currentIndexChanged(int layerType)
|
||||
{
|
||||
if (this->metatile) {
|
||||
this->metatile->layerType = static_cast<uint8_t>(layerType);
|
||||
}
|
||||
}
|
||||
|
||||
void TilesetEditor::on_actionSave_Tileset_triggered()
|
||||
{
|
||||
this->project->saveTilesets(this->primaryTileset, this->secondaryTileset);
|
||||
emit this->tilesetsSaved(this->primaryTileset->name, this->secondaryTileset->name);
|
||||
this->ui->statusbar->showMessage(QString("Saved primary and secondary Tilesets!"), 5000);
|
||||
this->hasUnsavedChanges = false;
|
||||
}
|
||||
|
||||
void TilesetEditor::on_actionImport_Primary_Tiles_triggered()
|
||||
{
|
||||
this->importTilesetTiles(this->primaryTileset, true);
|
||||
}
|
||||
|
||||
void TilesetEditor::on_actionImport_Secondary_Tiles_triggered()
|
||||
{
|
||||
this->importTilesetTiles(this->secondaryTileset, false);
|
||||
}
|
||||
|
||||
void TilesetEditor::importTilesetTiles(Tileset *tileset, bool primary) {
|
||||
QString descriptor = primary ? "primary" : "secondary";
|
||||
QString descriptorCaps = primary ? "Primary" : "Secondary";
|
||||
|
||||
QString filepath = QFileDialog::getOpenFileName(
|
||||
this,
|
||||
QString("Import %1 Tileset Tiles Image").arg(descriptorCaps),
|
||||
this->project->root,
|
||||
"Image Files (*.png)");
|
||||
if (filepath.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
qDebug() << QString("Importing %1 tileset tiles '%2'").arg(descriptor).arg(filepath);
|
||||
|
||||
// Validate image dimensions.
|
||||
QImage image = QImage(filepath);
|
||||
if (image.width() == 0 || image.height() == 0 || image.width() % 8 != 0 || image.height() % 8 != 0) {
|
||||
QMessageBox msgBox(this);
|
||||
msgBox.setText("Failed to import tiles.");
|
||||
msgBox.setInformativeText(QString("The image dimensions (%1 x %2) are invalid. Width and height must be multiples of 8 pixels.")
|
||||
.arg(image.width())
|
||||
.arg(image.height()));
|
||||
msgBox.setDefaultButton(QMessageBox::Ok);
|
||||
msgBox.setIcon(QMessageBox::Icon::Critical);
|
||||
msgBox.exec();
|
||||
return;
|
||||
}
|
||||
|
||||
// Validate image is properly indexed to 16 colors.
|
||||
if (image.colorCount() != 16) {
|
||||
QMessageBox msgBox(this);
|
||||
msgBox.setText("Failed to import tiles.");
|
||||
msgBox.setInformativeText(QString("The image must be indexed and contain 16 total colors. The provided image has %1 indexed colors.")
|
||||
.arg(image.colorCount()));
|
||||
msgBox.setDefaultButton(QMessageBox::Ok);
|
||||
msgBox.setIcon(QMessageBox::Icon::Critical);
|
||||
msgBox.exec();
|
||||
return;
|
||||
}
|
||||
|
||||
// Validate total number of tiles in image.
|
||||
int numTilesWide = image.width() / 16;
|
||||
int numTilesHigh = image.height() / 16;
|
||||
int totalTiles = numTilesHigh * numTilesWide;
|
||||
int maxAllowedTiles = primary ? Project::getNumTilesPrimary() : Project::getNumTilesTotal() - Project::getNumTilesPrimary();
|
||||
if (totalTiles > maxAllowedTiles) {
|
||||
QMessageBox msgBox(this);
|
||||
msgBox.setText("Failed to import tiles.");
|
||||
msgBox.setInformativeText(QString("The maximum number of tiles allowed in the %1 tileset is %2, but the provided image contains %3 total tiles.")
|
||||
.arg(descriptor)
|
||||
.arg(maxAllowedTiles)
|
||||
.arg(totalTiles));
|
||||
msgBox.setDefaultButton(QMessageBox::Ok);
|
||||
msgBox.setIcon(QMessageBox::Icon::Critical);
|
||||
msgBox.exec();
|
||||
return;
|
||||
}
|
||||
|
||||
this->project->loadTilesetTiles(tileset, image);
|
||||
this->project->loadTilesetMetatiles(tileset);
|
||||
this->refresh();
|
||||
this->hasUnsavedChanges = true;
|
||||
}
|
||||
|
||||
void TilesetEditor::closeEvent(QCloseEvent *event)
|
||||
{
|
||||
bool close = true;
|
||||
if (this->hasUnsavedChanges) {
|
||||
QMessageBox::StandardButton result = QMessageBox::question(this, "porymap",
|
||||
"Discard unsaved Tileset changes?",
|
||||
QMessageBox::No | QMessageBox::Yes,
|
||||
QMessageBox::Yes);
|
||||
close = result == QMessageBox::Yes;
|
||||
}
|
||||
|
||||
if (close) {
|
||||
event->accept();
|
||||
emit closed();
|
||||
} else {
|
||||
event->ignore();
|
||||
}
|
||||
}
|
||||
|
||||
void TilesetEditor::on_actionChange_Metatiles_Count_triggered()
|
||||
{
|
||||
QDialog dialog(this, Qt::WindowTitleHint | Qt::WindowCloseButtonHint);
|
||||
dialog.setWindowTitle("Change Number of Metatiles");
|
||||
dialog.setWindowModality(Qt::NonModal);
|
||||
|
||||
QFormLayout form(&dialog);
|
||||
|
||||
QSpinBox *primarySpinBox = new QSpinBox();
|
||||
QSpinBox *secondarySpinBox = new QSpinBox();
|
||||
primarySpinBox->setMinimum(1);
|
||||
secondarySpinBox->setMinimum(1);
|
||||
primarySpinBox->setMaximum(Project::getNumMetatilesPrimary());
|
||||
secondarySpinBox->setMaximum(Project::getNumMetatilesTotal() - Project::getNumMetatilesPrimary());
|
||||
primarySpinBox->setValue(this->primaryTileset->metatiles->length());
|
||||
secondarySpinBox->setValue(this->secondaryTileset->metatiles->length());
|
||||
form.addRow(new QLabel("Primary Tileset"), primarySpinBox);
|
||||
form.addRow(new QLabel("Secondary Tileset"), secondarySpinBox);
|
||||
|
||||
QDialogButtonBox buttonBox(QDialogButtonBox::Ok | QDialogButtonBox::Cancel, Qt::Horizontal, &dialog);
|
||||
connect(&buttonBox, SIGNAL(accepted()), &dialog, SLOT(accept()));
|
||||
connect(&buttonBox, SIGNAL(rejected()), &dialog, SLOT(reject()));
|
||||
form.addRow(&buttonBox);
|
||||
|
||||
if (dialog.exec() == QDialog::Accepted) {
|
||||
int numPrimaryMetatiles = primarySpinBox->value();
|
||||
int numSecondaryMetatiles = secondarySpinBox->value();
|
||||
while (this->primaryTileset->metatiles->length() > numPrimaryMetatiles) {
|
||||
Metatile *metatile = this->primaryTileset->metatiles->takeLast();
|
||||
delete metatile;
|
||||
}
|
||||
while (this->primaryTileset->metatiles->length() < numPrimaryMetatiles) {
|
||||
Tile tile;
|
||||
tile.palette = 0;
|
||||
tile.tile = 0;
|
||||
tile.xflip = 0;
|
||||
tile.yflip = 0;
|
||||
Metatile *metatile = new Metatile;
|
||||
metatile->behavior = 0;
|
||||
metatile->layerType = 0;
|
||||
for (int i = 0; i < 8; i++) {
|
||||
metatile->tiles->append(tile);
|
||||
}
|
||||
this->primaryTileset->metatiles->append(metatile);
|
||||
}
|
||||
while (this->secondaryTileset->metatiles->length() > numSecondaryMetatiles) {
|
||||
Metatile *metatile = this->secondaryTileset->metatiles->takeLast();
|
||||
delete metatile;
|
||||
}
|
||||
while (this->secondaryTileset->metatiles->length() < numSecondaryMetatiles) {
|
||||
Tile tile;
|
||||
tile.palette = 0;
|
||||
tile.tile = 0;
|
||||
tile.xflip = 0;
|
||||
tile.yflip = 0;
|
||||
Metatile *metatile = new Metatile;
|
||||
metatile->behavior = 0;
|
||||
metatile->layerType = 0;
|
||||
for (int i = 0; i < 8; i++) {
|
||||
metatile->tiles->append(tile);
|
||||
}
|
||||
this->secondaryTileset->metatiles->append(metatile);
|
||||
}
|
||||
|
||||
this->refresh();
|
||||
this->hasUnsavedChanges = true;
|
||||
}
|
||||
}
|
||||
|
||||
void TilesetEditor::onPaletteEditorClosed() {
|
||||
if (this->paletteEditor) {
|
||||
delete this->paletteEditor;
|
||||
this->paletteEditor = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
void TilesetEditor::on_actionChange_Palettes_triggered()
|
||||
{
|
||||
if (!this->paletteEditor) {
|
||||
this->paletteEditor = new PaletteEditor(this->project, this->primaryTileset, this->secondaryTileset, this);
|
||||
connect(this->paletteEditor, SIGNAL(closed()), this, SLOT(onPaletteEditorClosed()));
|
||||
connect(this->paletteEditor, SIGNAL(changedPaletteColor()), this, SLOT(onPaletteEditorChangedPaletteColor()));
|
||||
connect(this->paletteEditor, SIGNAL(changedPalette(int)), this, SLOT(onPaletteEditorChangedPalette(int)));
|
||||
}
|
||||
|
||||
if (!this->paletteEditor->isVisible()) {
|
||||
this->paletteEditor->show();
|
||||
} else if (this->paletteEditor->isMinimized()) {
|
||||
this->paletteEditor->showNormal();
|
||||
} else {
|
||||
this->paletteEditor->activateWindow();
|
||||
}
|
||||
}
|
||||
|
||||
void TilesetEditor::onPaletteEditorChangedPaletteColor() {
|
||||
this->refresh();
|
||||
this->hasUnsavedChanges = true;
|
||||
}
|
||||
|
||||
void TilesetEditor::onPaletteEditorChangedPalette(int paletteId) {
|
||||
this->on_spinBox_paletteSelector_valueChanged(paletteId);
|
||||
}
|
||||
|
|
114
src/ui/tileseteditormetatileselector.cpp
Normal file
114
src/ui/tileseteditormetatileselector.cpp
Normal file
|
@ -0,0 +1,114 @@
|
|||
#include "tileseteditormetatileselector.h"
|
||||
#include "imageproviders.h"
|
||||
#include "project.h"
|
||||
#include <QPainter>
|
||||
|
||||
void TilesetEditorMetatileSelector::draw() {
|
||||
if (!this->primaryTileset || !this->primaryTileset->metatiles
|
||||
|| !this->secondaryTileset || !this->secondaryTileset->metatiles) {
|
||||
this->setPixmap(QPixmap());
|
||||
}
|
||||
|
||||
int primaryLength = this->primaryTileset->metatiles->length();
|
||||
int length_ = primaryLength + this->secondaryTileset->metatiles->length();
|
||||
int height_ = length_ / this->numMetatilesWide;
|
||||
QImage image(this->numMetatilesWide * 32, height_ * 32, QImage::Format_RGBA8888);
|
||||
QPainter painter(&image);
|
||||
for (int i = 0; i < length_; i++) {
|
||||
int tile = i;
|
||||
if (i >= primaryLength) {
|
||||
tile += Project::getNumMetatilesPrimary() - primaryLength;
|
||||
}
|
||||
QImage metatile_image = getMetatileImage(tile, this->primaryTileset, this->secondaryTileset).scaled(32, 32);
|
||||
int map_y = i / this->numMetatilesWide;
|
||||
int map_x = i % this->numMetatilesWide;
|
||||
QPoint metatile_origin = QPoint(map_x * 32, map_y * 32);
|
||||
painter.drawImage(metatile_origin, metatile_image);
|
||||
}
|
||||
|
||||
painter.end();
|
||||
this->setPixmap(QPixmap::fromImage(image));
|
||||
this->drawSelection();
|
||||
}
|
||||
|
||||
void TilesetEditorMetatileSelector::select(uint16_t metatileId) {
|
||||
metatileId = this->getValidMetatileId(metatileId);
|
||||
QPoint coords = this->getMetatileIdCoords(metatileId);
|
||||
SelectablePixmapItem::select(coords.x(), coords.y(), 0, 0);
|
||||
this->selectedMetatile = metatileId;
|
||||
emit selectedMetatileChanged(metatileId);
|
||||
}
|
||||
|
||||
void TilesetEditorMetatileSelector::setTilesets(Tileset *primaryTileset, Tileset *secondaryTileset) {
|
||||
this->primaryTileset = primaryTileset;
|
||||
this->secondaryTileset = secondaryTileset;
|
||||
this->draw();
|
||||
}
|
||||
|
||||
void TilesetEditorMetatileSelector::updateSelectedMetatile() {
|
||||
QPoint origin = this->getSelectionStart();
|
||||
this->selectedMetatile = this->getMetatileId(origin.x(), origin.y());
|
||||
}
|
||||
|
||||
uint16_t TilesetEditorMetatileSelector::getSelectedMetatile() {
|
||||
return this->selectedMetatile;
|
||||
}
|
||||
|
||||
uint16_t TilesetEditorMetatileSelector::getMetatileId(int x, int y) {
|
||||
int index = y * this->numMetatilesWide + x;
|
||||
if (index < this->primaryTileset->metatiles->length()) {
|
||||
return static_cast<uint16_t>(index);
|
||||
} else {
|
||||
return static_cast<uint16_t>(Project::getNumMetatilesPrimary() + index - this->primaryTileset->metatiles->length());
|
||||
}
|
||||
}
|
||||
|
||||
void TilesetEditorMetatileSelector::mousePressEvent(QGraphicsSceneMouseEvent *event) {
|
||||
SelectablePixmapItem::mousePressEvent(event);
|
||||
this->updateSelectedMetatile();
|
||||
emit selectedMetatileChanged(this->selectedMetatile);
|
||||
}
|
||||
|
||||
void TilesetEditorMetatileSelector::mouseMoveEvent(QGraphicsSceneMouseEvent *event) {
|
||||
SelectablePixmapItem::mouseMoveEvent(event);
|
||||
this->updateSelectedMetatile();
|
||||
|
||||
QPoint pos = this->getCellPos(event->pos());
|
||||
uint16_t metatileId = this->getMetatileId(pos.x(), pos.y());
|
||||
emit hoveredMetatileChanged(metatileId);
|
||||
emit selectedMetatileChanged(metatileId);
|
||||
}
|
||||
|
||||
void TilesetEditorMetatileSelector::mouseReleaseEvent(QGraphicsSceneMouseEvent *event) {
|
||||
SelectablePixmapItem::mouseReleaseEvent(event);
|
||||
this->updateSelectedMetatile();
|
||||
emit selectedMetatileChanged(this->selectedMetatile);
|
||||
}
|
||||
|
||||
void TilesetEditorMetatileSelector::hoverMoveEvent(QGraphicsSceneHoverEvent *event) {
|
||||
QPoint pos = this->getCellPos(event->pos());
|
||||
uint16_t metatileId = this->getMetatileId(pos.x(), pos.y());
|
||||
emit this->hoveredMetatileChanged(metatileId);
|
||||
}
|
||||
|
||||
void TilesetEditorMetatileSelector::hoverLeaveEvent(QGraphicsSceneHoverEvent*) {
|
||||
emit this->hoveredMetatileCleared();
|
||||
}
|
||||
|
||||
QPoint TilesetEditorMetatileSelector::getMetatileIdCoords(uint16_t metatileId) {
|
||||
int index = metatileId < Project::getNumMetatilesPrimary()
|
||||
? metatileId
|
||||
: metatileId - Project::getNumMetatilesPrimary() + this->primaryTileset->metatiles->length();
|
||||
return QPoint(index % this->numMetatilesWide, index / this->numMetatilesWide);
|
||||
}
|
||||
|
||||
uint16_t TilesetEditorMetatileSelector::getValidMetatileId(uint16_t metatileId) {
|
||||
if (metatileId >= Project::getNumMetatilesTotal()
|
||||
|| (metatileId < Project::getNumMetatilesPrimary() && metatileId >= this->primaryTileset->metatiles->length())
|
||||
|| (metatileId < Project::getNumMetatilesTotal() && metatileId >= Project::getNumMetatilesPrimary() + this->secondaryTileset->metatiles->length()))
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
return metatileId;
|
||||
}
|
||||
|
130
src/ui/tileseteditortileselector.cpp
Normal file
130
src/ui/tileseteditortileselector.cpp
Normal file
|
@ -0,0 +1,130 @@
|
|||
#include "tileseteditortileselector.h"
|
||||
#include "imageproviders.h"
|
||||
#include "project.h"
|
||||
#include <QPainter>
|
||||
|
||||
void TilesetEditorTileSelector::draw() {
|
||||
if (!this->primaryTileset || !this->primaryTileset->tiles
|
||||
|| !this->secondaryTileset || !this->secondaryTileset->tiles) {
|
||||
this->setPixmap(QPixmap());
|
||||
}
|
||||
|
||||
int totalTiles = Project::getNumTilesTotal();
|
||||
int primaryLength = this->primaryTileset->tiles->length();
|
||||
int secondaryLength = this->secondaryTileset->tiles->length();
|
||||
int height = totalTiles / this->numTilesWide;
|
||||
QList<QRgb> palette = Tileset::getPalette(this->paletteId, this->primaryTileset, this->secondaryTileset);
|
||||
QImage image(this->numTilesWide * 16, height * 16, QImage::Format_RGBA8888);
|
||||
|
||||
QPainter painter(&image);
|
||||
for (uint16_t tile = 0; tile < totalTiles; tile++) {
|
||||
QImage tileImage;
|
||||
if (tile < primaryLength) {
|
||||
tileImage = getColoredTileImage(tile, this->primaryTileset, this->secondaryTileset, this->paletteId).scaled(16, 16);
|
||||
} else if (tile < Project::getNumTilesPrimary()) {
|
||||
tileImage = QImage(16, 16, QImage::Format_RGBA8888);
|
||||
tileImage.fill(palette.at(0));
|
||||
} else if (tile < Project::getNumTilesPrimary() + secondaryLength) {
|
||||
tileImage = getColoredTileImage(tile, this->primaryTileset, this->secondaryTileset, this->paletteId).scaled(16, 16);
|
||||
} else {
|
||||
tileImage = QImage(16, 16, QImage::Format_RGBA8888);
|
||||
QPainter painter(&tileImage);
|
||||
painter.fillRect(0, 0, 16, 16, palette.at(0));
|
||||
}
|
||||
|
||||
int y = tile / this->numTilesWide;
|
||||
int x = tile % this->numTilesWide;
|
||||
QPoint origin = QPoint(x * 16, y * 16);
|
||||
painter.drawImage(origin, tileImage.mirrored(this->xFlip, this->yFlip));
|
||||
}
|
||||
|
||||
painter.end();
|
||||
this->setPixmap(QPixmap::fromImage(image));
|
||||
this->drawSelection();
|
||||
}
|
||||
|
||||
void TilesetEditorTileSelector::select(uint16_t tile) {
|
||||
QPoint coords = this->getTileCoords(tile);
|
||||
SelectablePixmapItem::select(coords.x(), coords.y(), 0, 0);
|
||||
this->updateSelectedTiles();
|
||||
emit selectedTilesChanged();
|
||||
}
|
||||
|
||||
void TilesetEditorTileSelector::setTilesets(Tileset *primaryTileset, Tileset *secondaryTileset) {
|
||||
this->primaryTileset = primaryTileset;
|
||||
this->secondaryTileset = secondaryTileset;
|
||||
this->draw();
|
||||
}
|
||||
|
||||
void TilesetEditorTileSelector::setPaletteId(int paletteId) {
|
||||
this->paletteId = paletteId;
|
||||
this->draw();
|
||||
}
|
||||
|
||||
void TilesetEditorTileSelector::setTileFlips(bool xFlip, bool yFlip) {
|
||||
this->xFlip = xFlip;
|
||||
this->yFlip = yFlip;
|
||||
this->draw();
|
||||
}
|
||||
|
||||
void TilesetEditorTileSelector::updateSelectedTiles() {
|
||||
this->selectedTiles.clear();
|
||||
QPoint origin = this->getSelectionStart();
|
||||
QPoint dimensions = this->getSelectionDimensions();
|
||||
for (int j = 0; j < dimensions.y(); j++) {
|
||||
for (int i = 0; i < dimensions.x(); i++) {
|
||||
uint16_t metatileId = this->getTileId(origin.x() + i, origin.y() + j);
|
||||
this->selectedTiles.append(metatileId);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
QList<uint16_t> TilesetEditorTileSelector::getSelectedTiles() {
|
||||
return this->selectedTiles;
|
||||
}
|
||||
|
||||
uint16_t TilesetEditorTileSelector::getTileId(int x, int y) {
|
||||
return static_cast<uint16_t>(y * this->numTilesWide + x);
|
||||
}
|
||||
|
||||
void TilesetEditorTileSelector::mousePressEvent(QGraphicsSceneMouseEvent *event) {
|
||||
SelectablePixmapItem::mousePressEvent(event);
|
||||
this->updateSelectedTiles();
|
||||
emit selectedTilesChanged();
|
||||
}
|
||||
|
||||
void TilesetEditorTileSelector::mouseMoveEvent(QGraphicsSceneMouseEvent *event) {
|
||||
SelectablePixmapItem::mouseMoveEvent(event);
|
||||
this->updateSelectedTiles();
|
||||
|
||||
QPoint pos = this->getCellPos(event->pos());
|
||||
uint16_t tile = this->getTileId(pos.x(), pos.y());
|
||||
emit hoveredTileChanged(tile);
|
||||
emit selectedTilesChanged();
|
||||
}
|
||||
|
||||
void TilesetEditorTileSelector::mouseReleaseEvent(QGraphicsSceneMouseEvent *event) {
|
||||
SelectablePixmapItem::mouseReleaseEvent(event);
|
||||
this->updateSelectedTiles();
|
||||
emit selectedTilesChanged();
|
||||
}
|
||||
|
||||
void TilesetEditorTileSelector::hoverMoveEvent(QGraphicsSceneHoverEvent *event) {
|
||||
QPoint pos = this->getCellPos(event->pos());
|
||||
uint16_t tile = this->getTileId(pos.x(), pos.y());
|
||||
emit this->hoveredTileChanged(tile);
|
||||
}
|
||||
|
||||
void TilesetEditorTileSelector::hoverLeaveEvent(QGraphicsSceneHoverEvent*) {
|
||||
emit this->hoveredTileCleared();
|
||||
}
|
||||
|
||||
QPoint TilesetEditorTileSelector::getTileCoords(uint16_t tile) {
|
||||
if (tile >= Project::getNumTilesTotal())
|
||||
{
|
||||
// Invalid tile.
|
||||
return QPoint(0, 0);
|
||||
}
|
||||
|
||||
return QPoint(tile % this->numTilesWide, tile / this->numTilesWide);
|
||||
}
|
Loading…
Reference in a new issue