Skip to content

Commit 1c0132e

Browse files
committed
Moved 'Erase Terrain' mode into Terrains list
Instead of being a separate button, the erasing mode is now part of the list of terrains. This may be more intuitive.
1 parent 193b61c commit 1c0132e

File tree

10 files changed

+142
-150
lines changed

10 files changed

+142
-150
lines changed

src/libtiled/wangset.h

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -29,13 +29,13 @@
2929
#pragma once
3030

3131
#include "tile.h"
32-
#include "tileset.h"
3332
#include "tilelayer.h"
33+
#include "tileset.h"
3434

3535
#include <QHash>
36+
#include <QList>
3637
#include <QMultiHash>
3738
#include <QString>
38-
#include <QList>
3939

4040
namespace Tiled {
4141

@@ -79,12 +79,14 @@ class TILEDSHARED_EXPORT WangId
7979

8080
MaskEdges = MaskTop | MaskRight | MaskBottom | MaskLeft,
8181
MaskCorners = MaskTopRight | MaskBottomRight | MaskBottomLeft | MaskTopLeft,
82+
83+
MaskAll = MaskEdges | MaskCorners,
8284
};
8385

8486
constexpr WangId(quint64 id = 0) : mId(id) {}
8587

8688
constexpr operator quint64() const { return mId; }
87-
inline void setId(quint64 id) { mId = id; }
89+
void setId(quint64 id) { mId = id; }
8890

8991
bool isEmpty() const { return mId == 0; }
9092

@@ -256,7 +258,7 @@ class TILEDSHARED_EXPORT WangSet : public Object
256258
const QString &name,
257259
Type type,
258260
int imageTileId = -1);
259-
~WangSet();
261+
~WangSet() override;
260262

261263
Tileset *tileset() const;
262264
void setTileset(Tileset *tileset);

src/tiled/tilesetview.cpp

Lines changed: 26 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -55,28 +55,6 @@ using namespace Tiled;
5555

5656
namespace {
5757

58-
static void setupTilesetGridTransform(const Tileset &tileset, QTransform &transform, QRect &targetRect)
59-
{
60-
if (tileset.orientation() == Tileset::Isometric) {
61-
const QPoint tileCenter = targetRect.center();
62-
targetRect.setHeight(targetRect.width());
63-
targetRect.moveCenter(tileCenter);
64-
65-
const QSize gridSize = tileset.gridSize();
66-
67-
transform.translate(tileCenter.x(), tileCenter.y());
68-
69-
const auto ratio = (qreal) gridSize.height() / gridSize.width();
70-
const auto scaleX = 1.0 / sqrt(2.0);
71-
const auto scaleY = scaleX * ratio;
72-
transform.scale(scaleX, scaleY);
73-
74-
transform.rotate(45.0);
75-
76-
transform.translate(-tileCenter.x(), -tileCenter.y());
77-
}
78-
}
79-
8058
/**
8159
* The delegate for drawing tile items in the tileset view.
8260
*/
@@ -105,11 +83,13 @@ class TileDelegate : public QAbstractItemDelegate
10583
TilesetView *mTilesetView;
10684
};
10785

86+
} // anonymous namespace
87+
10888
void TileDelegate::paint(QPainter *painter,
10989
const QStyleOptionViewItem &option,
11090
const QModelIndex &index) const
11191
{
112-
const TilesetModel *model = static_cast<const TilesetModel*>(index.model());
92+
const auto *model = static_cast<const TilesetModel*>(index.model());
11393
const Tile *tile = model->tileAt(index);
11494
if (!tile)
11595
return;
@@ -245,6 +225,28 @@ void TileDelegate::drawFilmStrip(QPainter *painter, QRect targetRect)
245225
painter->restore();
246226
}
247227

228+
static void setupTilesetGridTransform(const Tileset &tileset, QTransform &transform, QRect &targetRect)
229+
{
230+
if (tileset.orientation() == Tileset::Isometric) {
231+
const QPoint tileCenter = targetRect.center();
232+
targetRect.setHeight(targetRect.width());
233+
targetRect.moveCenter(tileCenter);
234+
235+
const QSize gridSize = tileset.gridSize();
236+
237+
transform.translate(tileCenter.x(), tileCenter.y());
238+
239+
const auto ratio = (qreal) gridSize.height() / gridSize.width();
240+
const auto scaleX = 1.0 / sqrt(2.0);
241+
const auto scaleY = scaleX * ratio;
242+
transform.scale(scaleX, scaleY);
243+
244+
transform.rotate(45.0);
245+
246+
transform.translate(-tileCenter.x(), -tileCenter.y());
247+
}
248+
}
249+
248250
void TileDelegate::drawWangOverlay(QPainter *painter,
249251
const Tile *tile,
250252
QRect targetRect,
@@ -278,7 +280,6 @@ void TileDelegate::drawWangOverlay(QPainter *painter,
278280
painter->restore();
279281
}
280282

281-
} // anonymous namespace
282283

283284
TilesetView::TilesetView(QWidget *parent)
284285
: QTableView(parent)
@@ -932,7 +933,7 @@ void TilesetView::applyWangId()
932933
WangId newWangId = previousWangId;
933934

934935
if (mWangBehavior == AssignWholeId) {
935-
newWangId = mWangId;
936+
newWangId = mWangId & ~mWangId.mask(WangId::INDEX_MASK);
936937
} else {
937938
for (int i = 0; i < WangId::NumIndexes; ++i) {
938939
if (mWangId.indexColor(i))

src/tiled/wangcolormodel.cpp

Lines changed: 29 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -39,23 +39,24 @@ WangColorModel::WangColorModel(TilesetDocument *tilesetDocument,
3939
: QAbstractListModel(parent)
4040
, mTilesetDocument(tilesetDocument)
4141
, mWangSet(wangSet)
42+
, mEraserIcon(QLatin1String(":images/22/stock-tool-eraser.png"))
4243
{
4344
}
4445

45-
QModelIndex WangColorModel::colorIndex(int color) const
46+
QModelIndex WangColorModel::colorModelIndex(int color) const
4647
{
47-
if (!mWangSet || color > mWangSet->colorCount())
48+
if (!mWangSet || color < 0 || color > mWangSet->colorCount())
4849
return QModelIndex();
4950

50-
return createIndex(color - 1, 0);
51+
return createIndex(color, 0);
5152
}
5253

5354
int WangColorModel::rowCount(const QModelIndex &parent) const
5455
{
5556
if (!mWangSet || parent.isValid())
5657
return 0;
5758

58-
return mWangSet->colorCount();
59+
return mWangSet->colorCount() + 1;
5960
}
6061

6162
int WangColorModel::columnCount(const QModelIndex &parent) const
@@ -68,15 +69,25 @@ QVariant WangColorModel::data(const QModelIndex &index, int role) const
6869
if (!mWangSet)
6970
return QVariant();
7071

72+
const int colorIndex = index.row();
73+
7174
switch (role) {
75+
case WangColorIndexRole:
76+
return colorIndex;
7277
case Qt::DisplayRole:
7378
case Qt::EditRole:
79+
if (colorIndex == 0)
80+
return QCoreApplication::translate("Tiled::WangDock", "Erase Terrain");
7481
return wangColorAt(index)->name();
7582
case Qt::DecorationRole:
76-
if (Tile *tile = mWangSet->tileset()->findTile(wangColorAt(index)->imageId()))
83+
if (colorIndex == 0)
84+
return mEraserIcon;
85+
if (Tile *tile = mWangSet->tileset()->findTile(wangColorAt(index)->imageId()))
7786
return tile->image().copy(tile->imageRect());
7887
break;
7988
case ColorRole:
89+
if (colorIndex == 0)
90+
return QVariant();
8091
return wangColorAt(index)->color();
8192
}
8293

@@ -86,10 +97,13 @@ QVariant WangColorModel::data(const QModelIndex &index, int role) const
8697
bool WangColorModel::setData(const QModelIndex &index, const QVariant &value, int role)
8798
{
8899
if (role == Qt::EditRole) {
100+
const auto wangColor = wangColorAt(index);
101+
if (!wangColor)
102+
return false;
103+
89104
const QString newName = value.toString();
90-
WangColor *wangColor = wangColorAt(index).data();
91105
if (wangColor->name() != newName) {
92-
auto command = new ChangeWangColorName(mTilesetDocument, wangColor, newName);
106+
auto command = new ChangeWangColorName(mTilesetDocument, wangColor.data(), newName);
93107
mTilesetDocument->undoStack()->push(command);
94108
}
95109

@@ -101,7 +115,11 @@ bool WangColorModel::setData(const QModelIndex &index, const QVariant &value, in
101115

102116
Qt::ItemFlags WangColorModel::flags(const QModelIndex &index) const
103117
{
104-
return QAbstractItemModel::flags(index) | Qt::ItemIsEditable;
118+
Qt::ItemFlags flags = QAbstractItemModel::flags(index);
119+
if (index.row() == 0)
120+
return flags;
121+
122+
return flags | Qt::ItemIsEditable;
105123
}
106124

107125
void WangColorModel::resetModel()
@@ -110,20 +128,12 @@ void WangColorModel::resetModel()
110128
endResetModel();
111129
}
112130

113-
int WangColorModel::colorAt(const QModelIndex &index) const
114-
{
115-
if (!index.isValid())
116-
return 0;
117-
118-
return index.row() + 1;
119-
}
120-
121131
QSharedPointer<WangColor> WangColorModel::wangColorAt(const QModelIndex &index) const
122132
{
123-
if (!index.isValid())
133+
if (!index.isValid() || index.row() == 0)
124134
return QSharedPointer<WangColor>();
125135

126-
return mWangSet->colorAt(colorAt(index));
136+
return mWangSet->colorAt(index.row());
127137
}
128138

129139
void WangColorModel::setName(WangColor *wangColor, const QString &name)
@@ -156,7 +166,7 @@ void WangColorModel::setProbability(WangColor *wangColor, qreal probability)
156166

157167
void WangColorModel::emitDataChanged(WangColor *wangColor)
158168
{
159-
const QModelIndex i = colorIndex(wangColor->colorIndex());
169+
const QModelIndex i = colorModelIndex(wangColor->colorIndex());
160170
emit dataChanged(i, i);
161171
}
162172

src/tiled/wangcolormodel.h

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@
2323
#include "wangset.h"
2424

2525
#include <QAbstractListModel>
26+
#include <QIcon>
2627

2728
namespace Tiled {
2829

@@ -38,13 +39,14 @@ class WangColorModel : public QAbstractListModel
3839
public:
3940
enum UserRoles {
4041
ColorRole = Qt::UserRole,
42+
WangColorIndexRole,
4143
};
4244

4345
WangColorModel(TilesetDocument *tilesetDocument,
4446
WangSet *wangSet,
4547
QObject *parent = nullptr);
4648

47-
QModelIndex colorIndex(int color) const;
49+
QModelIndex colorModelIndex(int color) const;
4850

4951
int rowCount(const QModelIndex &parent = QModelIndex()) const override;
5052
int columnCount(const QModelIndex &parent = QModelIndex()) const override;
@@ -61,8 +63,7 @@ class WangColorModel : public QAbstractListModel
6163

6264
void resetModel();
6365

64-
int colorAt(const QModelIndex &index) const;
65-
66+
// Returns null for the "No Terrain" entry.
6667
QSharedPointer<WangColor> wangColorAt(const QModelIndex &index) const;
6768

6869
void setName(WangColor *wangColor, const QString &name);
@@ -76,6 +77,7 @@ class WangColorModel : public QAbstractListModel
7677

7778
TilesetDocument *mTilesetDocument;
7879
WangSet *mWangSet;
80+
QIcon mEraserIcon;
7981
};
8082

8183
} // namespace Tiled

src/tiled/wangcolorview.cpp

Lines changed: 21 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -46,10 +46,12 @@ class WangColorDelegate : public QStyledItemDelegate
4646
void initStyleOption(QStyleOptionViewItem *option, const QModelIndex &index) const override;
4747
};
4848

49+
} // anonymous namespace
50+
4951
void WangColorDelegate::initStyleOption(QStyleOptionViewItem *option, const QModelIndex &index) const
5052
{
5153
QSize decorationSize = option->decorationSize;
52-
QPixmap tileImage = index.data(Qt::DecorationRole).value<QPixmap>();
54+
auto tileImage = index.data(Qt::DecorationRole).value<QPixmap>();
5355

5456
QPixmap pixmap(decorationSize);
5557
pixmap.fill(Qt::transparent);
@@ -73,26 +75,28 @@ void WangColorDelegate::initStyleOption(QStyleOptionViewItem *option, const QMod
7375
}
7476

7577
// Draw the Wang color on top
76-
const QColor wangColor = index.data(WangColorModel::ColorRole).value<QColor>();
77-
const QPointF topRight = QPointF(pixmap.width() * 0.75, 0);
78-
const QPointF bottomLeft = QPointF(0, pixmap.height() * 0.75);
79-
painter.setBrush(wangColor);
80-
painter.setPen(Qt::NoPen);
81-
painter.drawPolygon(QVector<QPointF> { QPointF(), topRight, bottomLeft });
82-
QColor border(Qt::black);
83-
border.setAlpha(128);
84-
painter.setPen(QPen(border, 2.0));
85-
painter.drawLine(topRight, bottomLeft);
78+
const auto wangColor = index.data(WangColorModel::ColorRole).value<QColor>();
79+
if (wangColor.isValid()) {
80+
const QPointF topRight = QPointF(pixmap.width() * 0.75, 0);
81+
const QPointF bottomLeft = QPointF(0, pixmap.height() * 0.75);
82+
painter.setBrush(wangColor);
83+
painter.setPen(Qt::NoPen);
84+
painter.drawPolygon(QVector<QPointF> { QPointF(), topRight, bottomLeft });
85+
QColor border(Qt::black);
86+
border.setAlpha(128);
87+
painter.setPen(QPen(border, 2.0));
88+
painter.drawLine(topRight, bottomLeft);
89+
}
8690

8791
QStyledItemDelegate::initStyleOption(option, index);
8892

8993
// Reset the icon
9094
option->features |= QStyleOptionViewItem::HasDecoration;
9195
option->decorationSize = decorationSize;
92-
option->icon = pixmap;
96+
if (wangColor.isValid())
97+
option->icon = pixmap;
9398
}
9499

95-
} // anonymous namespace
96100

97101
WangColorView::WangColorView(QWidget *parent)
98102
: QTreeView(parent)
@@ -105,9 +109,7 @@ WangColorView::WangColorView(QWidget *parent)
105109
setItemDelegate(new WangColorDelegate(this));
106110
}
107111

108-
WangColorView::~WangColorView()
109-
{
110-
}
112+
WangColorView::~WangColorView() = default;
111113

112114
void WangColorView::setTileSize(QSize size)
113115
{
@@ -138,6 +140,8 @@ void WangColorView::contextMenuEvent(QContextMenuEvent *event)
138140

139141
const QModelIndex index = proxyModel->mapToSource(filterModelIndex);
140142
mClickedWangColor = wangColorModel->wangColorAt(index);
143+
if (!mClickedWangColor)
144+
return;
141145

142146
QMenu menu;
143147

@@ -150,7 +154,7 @@ void WangColorView::contextMenuEvent(QContextMenuEvent *event)
150154

151155
void WangColorView::pickColor()
152156
{
153-
QColorDialog *colorPicker = new QColorDialog(this);
157+
auto colorPicker = new QColorDialog(this);
154158
colorPicker->setAttribute(Qt::WA_DeleteOnClose);
155159
colorPicker->setCurrentColor(mClickedWangColor->color());
156160
connect(colorPicker, &QColorDialog::colorSelected,

0 commit comments

Comments
 (0)