Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

AutoMapping: Removed the "touched layers" optimization #4168

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 1 addition & 9 deletions src/tiled/automapper.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -155,16 +155,11 @@ AutoMapper::AutoMapper(std::unique_ptr<Map> rulesMap)

AutoMapper::~AutoMapper() = default;

QString AutoMapper::rulesMapFileName() const
const QString &AutoMapper::rulesMapFileName() const
{
return mRulesMap->fileName;
}

bool AutoMapper::ruleLayerNameUsed(const QString &ruleLayerName) const
{
return mRuleMapSetup.mInputLayerNames.contains(ruleLayerName);
}

template<typename Type>
bool checkOption(const QString &propertyName,
const QVariant &propertyValue,
Expand Down Expand Up @@ -1366,9 +1361,6 @@ void AutoMapper::copyMapRegion(const Rule &rule, QPoint offset,
if (!rule.options.ignoreLock && !toTileLayer->isUnlocked())
continue;

if (!context.touchedTileLayers.isEmpty())
appendUnique<const TileLayer*>(context.touchedTileLayers, toTileLayer);

for (const QRect &rect : rule.outputRegion) {
copyTileRegion(tileOutput.tileLayer, rect, toTileLayer,
rect.x() + offset.x(), rect.y() + offset.y(),
Expand Down
11 changes: 1 addition & 10 deletions src/tiled/automapper.h
Original file line number Diff line number Diff line change
Expand Up @@ -256,9 +256,6 @@ struct TILED_EDITOR_EXPORT AutoMappingContext
// Clones of existing tile layers that might have been changed in AutoMapper::autoMap
std::unordered_map<TileLayer*, std::unique_ptr<TileLayer>> originalToOutputLayerMapping;

// Used to keep track of touched tile layers (only when initially non-empty)
QVector<const TileLayer*> touchedTileLayers;

private:
friend class AutoMapper;

Expand Down Expand Up @@ -335,13 +332,7 @@ class TILED_EDITOR_EXPORT AutoMapper
explicit AutoMapper(std::unique_ptr<Map> rulesMap);
~AutoMapper();

QString rulesMapFileName() const;

/**
* Checks if the passed \a ruleLayerName is used as input layer in this
* instance of AutoMapper.
*/
bool ruleLayerNameUsed(const QString &ruleLayerName) const;
const QString &rulesMapFileName() const;

/**
* This needs to be called directly before the autoMap call.
Expand Down
15 changes: 1 addition & 14 deletions src/tiled/automapperwrapper.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -37,20 +37,14 @@ using namespace Tiled;

AutoMapperWrapper::AutoMapperWrapper(MapDocument *mapDocument,
const QVector<const AutoMapper *> &autoMappers,
const QRegion &where,
const TileLayer *touchedLayer)
const QRegion &where)
: PaintTileLayer(mapDocument)
{
AutoMappingContext context(mapDocument);

for (const auto autoMapper : autoMappers)
autoMapper->prepareAutoMap(context);

// During "AutoMap while drawing", keep track of the touched layers, so we
// can skip any rule maps that doesn't have these layers as input entirely.
if (touchedLayer)
context.touchedTileLayers.append(touchedLayer);

// use a copy of the region, so each AutoMapper can manipulate it and the
// following AutoMappers do see the impact
QRegion region(where);
Expand All @@ -64,13 +58,6 @@ AutoMapperWrapper::AutoMapperWrapper(MapDocument *mapDocument,
if (appliedRegionPtr && (!map->infinite() && (mapRect - region).isEmpty()))
appliedRegionPtr = nullptr;

if (touchedLayer) {
if (std::none_of(context.touchedTileLayers.cbegin(),
context.touchedTileLayers.cend(),
[&] (const TileLayer *tileLayer) { return autoMapper->ruleLayerNameUsed(tileLayer->name()); }))
continue;
}

autoMapper->autoMap(region, appliedRegionPtr, context);

if (appliedRegionPtr) {
Expand Down
3 changes: 1 addition & 2 deletions src/tiled/automapperwrapper.h
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,7 @@ class AutoMapperWrapper : public PaintTileLayer
public:
AutoMapperWrapper(MapDocument *mapDocument,
const QVector<const AutoMapper *> &autoMappers,
const QRegion &where,
const TileLayer *touchedLayer = nullptr);
const QRegion &where);
};

} // namespace Tiled
29 changes: 9 additions & 20 deletions src/tiled/automappingmanager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -78,18 +78,18 @@ void AutomappingManager::autoMap()
}
}

autoMapInternal(region, nullptr);
autoMapInternal(region, false);
}

void AutomappingManager::autoMapRegion(const QRegion &region)
{
autoMapInternal(region, nullptr);
autoMapInternal(region, false);
}

void AutomappingManager::onRegionEdited(const QRegion &where, TileLayer *touchedLayer)
void AutomappingManager::onRegionEdited(const QRegion &where)
{
if (automappingWhileDrawing)
autoMapInternal(where, touchedLayer);
autoMapInternal(where, true);
}

void AutomappingManager::onMapFileNameChanged()
Expand All @@ -99,25 +99,23 @@ void AutomappingManager::onMapFileNameChanged()
}

void AutomappingManager::autoMapInternal(const QRegion &where,
const TileLayer *touchedLayer)
bool whileDrawing)
{
mError.clear();
mWarning.clear();

if (!mMapDocument)
return;

const bool automatic = touchedLayer != nullptr;

// Even if no AutoMapper instance will be executed, we still want to report
// any warnings or errors that might have been reported while interpreting
// the rule maps.
auto reportErrors = qScopeGuard([=] {
if (!mWarning.isEmpty())
emit warningsOccurred(automatic);
emit warningsOccurred(whileDrawing);

if (!mError.isEmpty())
emit errorsOccurred(automatic);
emit errorsOccurred(whileDrawing);
});

if (!mLoaded) {
Expand Down Expand Up @@ -148,17 +146,8 @@ void AutomappingManager::autoMapInternal(const QRegion &where,
if (autoMappers.isEmpty())
return;

// Skip this AutoMapping run if none of the loaded rule maps actually use
// the touched layer.
if (touchedLayer) {
if (std::none_of(autoMappers.cbegin(),
autoMappers.cend(),
[=] (const AutoMapper *autoMapper) { return autoMapper->ruleLayerNameUsed(touchedLayer->name()); }))
return;
}

AutoMapperWrapper *aw = new AutoMapperWrapper(mMapDocument, autoMappers, where, touchedLayer);
aw->setMergeable(automatic);
AutoMapperWrapper *aw = new AutoMapperWrapper(mMapDocument, autoMappers, where);
aw->setMergeable(whileDrawing);
aw->setText(tr("Apply AutoMap rules"));

mMapDocument->undoStack()->push(aw);
Expand Down
8 changes: 4 additions & 4 deletions src/tiled/automappingmanager.h
Original file line number Diff line number Diff line change
Expand Up @@ -86,7 +86,7 @@ class AutomappingManager : public QObject
void warningsOccurred(bool automatic);

private:
void onRegionEdited(const QRegion &where, TileLayer *touchedLayer);
void onRegionEdited(const QRegion &where);
void onMapFileNameChanged();
void onFileChanged(const QString &path);

Expand All @@ -99,10 +99,10 @@ class AutomappingManager : public QObject
/**
* Applies automapping to the region \a where.
*
* If a \a touchedLayer is given, only those AutoMappers will be used which
* have a rule layer matching the \a touchedLayer.
* If \a whileDrawing is true, the changes made through AutoMapping will
* merge with the previous undo operation when possible.
*/
void autoMapInternal(const QRegion &where, const TileLayer *touchedLayer);
void autoMapInternal(const QRegion &where, bool whileDrawing);

/**
* deletes all its data structures
Expand Down