Prevent castles being assailable from above.

This commit is contained in:
Tormod G. Hellen 2022-02-21 00:33:58 +01:00
parent 609b26ce20
commit 5df1ee6382
2 changed files with 30 additions and 3 deletions

View File

@ -12,7 +12,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
### Changed ### Changed
- Improved town placement - Improved site placement
### Removed ### Removed

View File

@ -15,7 +15,7 @@ use common::{
path::Path, path::Path,
spiral::Spiral2d, spiral::Spiral2d,
store::{Id, Store}, store::{Id, Store},
terrain::{uniform_idx_as_vec2, MapSizeLg, TerrainChunkSize}, terrain::{uniform_idx_as_vec2, MapSizeLg, TerrainChunkSize, TERRAIN_CHUNK_BLOCKS_LG},
vol::RectVolSize, vol::RectVolSize,
}; };
use core::{fmt, hash::BuildHasherDefault, ops::Range}; use core::{fmt, hash::BuildHasherDefault, ops::Range};
@ -1065,7 +1065,7 @@ fn find_site_loc(
size: i32, size: i32,
site_kind: SiteKind, site_kind: SiteKind,
) -> Option<Vec2<i32>> { ) -> Option<Vec2<i32>> {
const MAX_ATTEMPTS: usize = 1000; const MAX_ATTEMPTS: usize = 10000;
let mut loc = None; let mut loc = None;
let (avoid_locs, distance) = avoid; let (avoid_locs, distance) = avoid;
for _ in 0..MAX_ATTEMPTS { for _ in 0..MAX_ATTEMPTS {
@ -1096,6 +1096,7 @@ fn find_site_loc(
) )
}); });
} }
warn!("Failed to place site {:?}.", site_kind);
None None
} }
@ -1158,6 +1159,32 @@ impl SiteKind {
sim.get(loc).map_or(false, |chunk| match self { sim.get(loc).map_or(false, |chunk| match self {
SiteKind::Gnarling => (-0.3..0.4).contains(&chunk.temp) && chunk.tree_density > 0.75, SiteKind::Gnarling => (-0.3..0.4).contains(&chunk.temp) && chunk.tree_density > 0.75,
SiteKind::GiantTree | SiteKind::Tree => chunk.tree_density > 0.4, SiteKind::GiantTree | SiteKind::Tree => chunk.tree_density > 0.4,
SiteKind::Castle => {
if chunk.tree_density > 0.4 || chunk.river.near_water() || chunk.near_cliffs() {
return false;
}
const HILL_RADIUS: i32 = 3 * TERRAIN_CHUNK_BLOCKS_LG as i32;
for x in (-HILL_RADIUS)..HILL_RADIUS {
for y in (-HILL_RADIUS)..HILL_RADIUS {
let check_loc = loc + Vec2::new(x, y);
if let Some(true) = sim
.get_alt_approx(check_loc)
.map(|surrounding_alt| surrounding_alt > chunk.alt + 1.0)
{
return false;
}
// Castles are really big, so to avoid parts of them ending up underwater or
// in other awkward positions we have to do this
if sim
.get(check_loc)
.map_or(true, |c| c.is_underwater() || c.near_cliffs())
{
return false;
}
}
}
true
},
SiteKind::Refactor | SiteKind::Settlement => { SiteKind::Refactor | SiteKind::Settlement => {
const RESOURCE_RADIUS: i32 = 1; const RESOURCE_RADIUS: i32 = 1;
let mut river_chunks = 0; let mut river_chunks = 0;