Implement --exhaustive y mode as another database access optimization

This one works best when you have a wide area with low height (e.g. 10000x200x10000)
This commit is contained in:
sfan5 2020-03-28 00:14:47 +01:00
parent 7ff2288627
commit cb8341aeab
4 changed files with 34 additions and 6 deletions

@ -108,5 +108,6 @@ scales:
Draw scales on specified image edges (letters *t b l r* meaning top, bottom, left and right), e.g. ``--scales tbr``
exhaustive:
Select if database should be traversed exhaustively or using range queries, available: *never*, *y*, *full*, *auto*
Defaults to *auto*. You shouldn't need to change this, but doing so can improve rendering times on large maps.
| Select if database should be traversed exhaustively or using range queries, available: *never*, *y*, *full*, *auto*
| Defaults to *auto*. You shouldn't need to change this, but doing so can improve rendering times on large maps.
| For these optimizations to work it is important that you set ``min-y`` and ``max-y`` when you don't care about the world below e.g. -60 and above 1000 nodes.

@ -353,7 +353,7 @@ void TileGenerator::openDb(const std::string &input)
m_exhaustiveSearch = EXH_NEVER;
else if (blocks < 200000)
m_exhaustiveSearch = EXH_FULL;
else if (y_range < 600)
else if (y_range < 42)
m_exhaustiveSearch = EXH_Y;
else
m_exhaustiveSearch = EXH_NEVER;
@ -364,8 +364,6 @@ void TileGenerator::openDb(const std::string &input)
" in worse performance." << std::endl;
}
}
if (m_exhaustiveSearch == EXH_Y)
m_exhaustiveSearch = EXH_NEVER; // (TODO remove when implemented)
assert(m_exhaustiveSearch != EXH_AUTO);
}
@ -511,6 +509,30 @@ void TileGenerator::renderMap()
}
postRenderRow(zPos);
}
} else if (m_exhaustiveSearch == EXH_Y) {
#ifndef NDEBUG
std::cerr << "Exhaustively searching height of "
<< (yMax - (m_yMin / 16)) << " blocks" << std::endl;
#endif
std::vector<BlockPos> positions;
positions.reserve(yMax - (m_yMin / 16));
for (auto it = m_positions.rbegin(); it != m_positions.rend(); ++it) {
int16_t zPos = it->first;
for (auto it2 = it->second.rbegin(); it2 != it->second.rend(); ++it2) {
int16_t xPos = *it2;
positions.clear();
for (int16_t yPos = m_yMin / 16; yPos < yMax; yPos++)
positions.emplace_back(xPos, yPos, zPos);
BlockList blockStack;
m_db->getBlocksByPos(blockStack, positions);
blockStack.sort();
renderSingle(xPos, zPos, blockStack);
}
postRenderRow(zPos);
}
} else if (m_exhaustiveSearch == EXH_FULL) {
#ifndef NDEBUG
std::cerr << "Exhaustively searching "

@ -25,7 +25,7 @@ enum {
enum {
EXH_NEVER, // Always use range queries
EXH_Y, // Exhaustively search Y space, range queries for X/Z (future TODO)
EXH_Y, // Exhaustively search Y space, range queries for X/Z
EXH_FULL, // Exhaustively search entire requested geometry
EXH_AUTO, // Automatically pick one of the previous modes
};

@ -97,6 +97,11 @@ Draw scales on specified image edges (letters \fIt b l r\fP meaning top, bottom,
Select if database should be traversed exhaustively or using range queries, available: \fInever\fP, \fIy\fP, \fIfull\fP, \fIauto\fP
Defaults to \fIauto\fP. You shouldn't need to change this, but doing so can improve rendering times on large maps.
For these optimizations to work it is important that you set
.B min-y
and
.B max-y
when you don't care about the world below e.g. -60 and above 1000 nodes.
.SH MORE INFORMATION
Website: https://github.com/minetest/minetestmapper