1
0
Fork 0

Feature: New Trees Placement Algorithm "Forest"

pull/12712/head
Sylvain Devidal 2018-07-04 13:37:37 +02:00 committed by Susan
parent 37f68a65ee
commit 53d2153844
2 changed files with 40 additions and 2 deletions

View File

@ -1586,11 +1586,12 @@ STR_CONFIG_SETTING_RIVER_AMOUNT :River amount: {
STR_CONFIG_SETTING_RIVER_AMOUNT_HELPTEXT :Choose how many rivers to generate
STR_CONFIG_SETTING_TREE_PLACER :Tree placer algorithm: {STRING2}
STR_CONFIG_SETTING_TREE_PLACER_HELPTEXT :Choose the distribution of trees on the map: 'Original' plants trees uniformly scattered, 'Improved' plants them in groups
STR_CONFIG_SETTING_TREE_PLACER_HELPTEXT :Choose the distribution of trees on the map: 'Original' plants trees uniformly scattered, 'Improved' plants them in groups, 'Forest' plants them in forests
###length 3
STR_CONFIG_SETTING_TREE_PLACER_NONE :None
STR_CONFIG_SETTING_TREE_PLACER_ORIGINAL :Original
STR_CONFIG_SETTING_TREE_PLACER_IMPROVED :Improved
STR_CONFIG_SETTING_TREE_PLACER_FOREST :Forest
STR_CONFIG_SETTING_ROAD_SIDE :Road vehicles: {STRING2}
STR_CONFIG_SETTING_ROAD_SIDE_HELPTEXT :Choose the driving side

View File

@ -41,6 +41,7 @@ enum TreePlacer {
TP_NONE, ///< No tree placer algorithm
TP_ORIGINAL, ///< The original algorithm
TP_IMPROVED, ///< A 'improved' algorithm
TP_FOREST, ///< An algorithm trying to make only forests
};
/** Where to place trees while in-game? */
@ -80,6 +81,30 @@ static bool CanPlantTreesOnTile(TileIndex tile, bool allow_desert)
}
}
/**
* Tests if a tile is near an already existing forest.
* Trees won't spread if not placed near some other trees.
*
* @param tile the tile of interest
* @return true if the tile is near a forest
*/
static bool IsNearbyForest(TileIndex tile)
{
uint planted_tile_count = 0;
for (int x = -2; x <= 2; x++) {
for (int y = -2; y <= 2; y++) {
TileIndex vincity = TileAddWrap(tile, x, y);
if (vincity != INVALID_TILE &&
IsTileType(vincity, MP_TREES)) {
planted_tile_count++;
}
}
}
return (planted_tile_count >= 6);
}
/**
* Creates a tree tile
* Ground type and density is preserved.
@ -257,7 +282,10 @@ void PlaceTreesRandomly()
if (CanPlantTreesOnTile(tile, true)) {
PlaceTree(tile, r);
if (_settings_game.game_creation.tree_placer != TP_IMPROVED) continue;
if (_settings_game.game_creation.tree_placer != TP_IMPROVED &&
_settings_game.game_creation.tree_placer != TP_FOREST) {
continue;
}
/* Place a number of trees based on the tile height.
* This gives a cool effect of multiple trees close together.
@ -358,6 +386,7 @@ void GenerateTrees()
switch (_settings_game.game_creation.tree_placer) {
case TP_ORIGINAL: i = _settings_game.game_creation.landscape == LT_ARCTIC ? 15 : 6; break;
case TP_FOREST: /* FALL THROUGH */
case TP_IMPROVED: i = _settings_game.game_creation.landscape == LT_ARCTIC ? 4 : 2; break;
default: NOT_REACHED();
}
@ -371,6 +400,8 @@ void GenerateTrees()
if (num_groups != 0) PlaceTreeGroups(num_groups);
if (_settings_game.game_creation.tree_placer == TP_FOREST) return;
for (; i != 0; i--) {
PlaceTreesRandomly();
}
@ -758,6 +789,9 @@ static void TileLoop_Trees(TileIndex tile)
/* Don't plant trees, if ground was freshly cleared */
if (IsTileType(tile, MP_CLEAR) && GetClearGround(tile) == CLEAR_GRASS && GetClearDensity(tile) != 3) return;
/* Plants trees only near existing forests */
if (_settings_game.game_creation.tree_placer == TP_FOREST && !IsNearbyForest(tile)) return;
PlantTreesOnTile(tile, treetype, 0, 0);
break;
@ -859,6 +893,9 @@ void OnTick_Trees()
r = Random();
tile = RandomTileSeed(r);
if (CanPlantTreesOnTile(tile, false) && (tree = GetRandomTreeType(tile, GB(r, 24, 8))) != TREE_INVALID) {
/* Plants trees only near existing forests */
if (_settings_game.game_creation.tree_placer == TP_FOREST && !IsNearbyForest(tile)) return;
PlantTreesOnTile(tile, tree, 0, 0);
}
}