mirror of
https://gitlab.com/veloren/veloren.git
synced 2024-08-30 18:12:32 +00:00
Lowered path priority
This commit is contained in:
parent
41916d4594
commit
6a41f6aa88
@ -28,7 +28,7 @@ pub fn structure_gen<'a>(
|
||||
|| st_sample.alt < st_sample.water_level
|
||||
|| st_sample.spawn_rate < 0.5
|
||||
|| st_sample.water_dist.map(|d| d < 8.0).unwrap_or(false)
|
||||
|| st_sample.path.map(|(d, _)| d < 12.0).unwrap_or(false)
|
||||
|| st_sample.path.map(|(d, _, _, _)| d < 12.0).unwrap_or(false)
|
||||
{
|
||||
return None;
|
||||
}
|
||||
|
@ -1,7 +1,7 @@
|
||||
use crate::{
|
||||
all::ForestKind,
|
||||
block::StructureMeta,
|
||||
sim::{local_cells, uniform_idx_as_vec2, vec2_as_uniform_idx, RiverKind, SimChunk, WorldSim},
|
||||
sim::{local_cells, uniform_idx_as_vec2, vec2_as_uniform_idx, RiverKind, SimChunk, WorldSim, Path},
|
||||
util::Sampler,
|
||||
Index, CONFIG,
|
||||
};
|
||||
@ -1157,7 +1157,7 @@ pub struct ColumnSample<'a> {
|
||||
pub spawn_rate: f32,
|
||||
pub stone_col: Rgb<u8>,
|
||||
pub water_dist: Option<f32>,
|
||||
pub path: Option<(f32, Vec2<f32>)>,
|
||||
pub path: Option<(f32, Vec2<f32>, Path, Vec2<f32>)>,
|
||||
|
||||
pub chunk: &'a SimChunk,
|
||||
}
|
||||
|
@ -37,7 +37,7 @@ pub fn apply_paths_to<'a>(
|
||||
})
|
||||
};
|
||||
|
||||
if let Some((path_dist, path_nearest)) = col_sample.path.filter(|(dist, _)| *dist < 5.0)
|
||||
if let Some((path_dist, path_nearest, path, _)) = col_sample.path.filter(|(dist, _, path, _)| *dist < path.width)
|
||||
{
|
||||
let inset = 0;
|
||||
|
||||
@ -82,7 +82,7 @@ pub fn apply_paths_to<'a>(
|
||||
},
|
||||
);
|
||||
}
|
||||
let head_space = (8 - (path_dist * 0.25).powf(6.0).round() as i32).max(1);
|
||||
let head_space = path.head_space(path_dist);
|
||||
for z in inset..inset + head_space {
|
||||
let pos = Vec3::new(offs.x, offs.y, surface_z + z);
|
||||
if vol.get(pos).unwrap().kind() != BlockKind::Water {
|
||||
|
@ -175,14 +175,14 @@ impl World {
|
||||
|
||||
let mut rng = rand::thread_rng();
|
||||
|
||||
// Apply paths
|
||||
layer::apply_paths_to(chunk_wpos2d, sample_get, &mut chunk);
|
||||
|
||||
// Apply site generation
|
||||
sim_chunk.sites.iter().for_each(|site| {
|
||||
self.index.sites[*site].apply_to(chunk_wpos2d, sample_get, &mut chunk)
|
||||
});
|
||||
|
||||
// Apply paths
|
||||
layer::apply_paths_to(chunk_wpos2d, sample_get, &mut chunk);
|
||||
|
||||
let gen_entity_pos = || {
|
||||
let lpos2d = TerrainChunkSize::RECT_SIZE
|
||||
.map(|sz| rand::thread_rng().gen::<u32>().rem_euclid(sz) as i32);
|
||||
|
@ -15,7 +15,7 @@ pub use self::{
|
||||
},
|
||||
location::Location,
|
||||
map::{MapConfig, MapDebug},
|
||||
path::PathData,
|
||||
path::{Path, PathData},
|
||||
util::{
|
||||
cdf_irwin_hall, downhill, get_oceans, local_cells, map_edge_factor, neighbors,
|
||||
uniform_idx_as_vec2, uniform_noise, uphill, vec2_as_uniform_idx, InverseCdf, ScaleBias,
|
||||
@ -1699,7 +1699,9 @@ impl WorldSim {
|
||||
Some(z0 + z1 + z2 + z3)
|
||||
}
|
||||
|
||||
pub fn get_nearest_path(&self, wpos: Vec2<i32>) -> Option<(f32, Vec2<f32>)> {
|
||||
/// Return the distance to the nearest path in blocks, along with the closest point on the path
|
||||
/// and the tangent vector of that path.
|
||||
pub fn get_nearest_path(&self, wpos: Vec2<i32>) -> Option<(f32, Vec2<f32>, Path, Vec2<f32>)> {
|
||||
let chunk_pos = wpos.map2(TerrainChunkSize::RECT_SIZE, |e, sz: u32| {
|
||||
e.div_euclid(sz as i32)
|
||||
});
|
||||
@ -1759,13 +1761,13 @@ impl WorldSim {
|
||||
.clamped(0.0, 1.0);
|
||||
let pos = bez.evaluate(nearest_interval);
|
||||
let dist_sqrd = pos.distance_squared(wpos.map(|e| e as f32));
|
||||
Some((dist_sqrd, pos))
|
||||
Some((dist_sqrd, pos, chunk.path.path, move || bez.evaluate_derivative(nearest_interval).normalized()))
|
||||
}),
|
||||
)
|
||||
})
|
||||
.flatten()
|
||||
.min_by_key(|(dist_sqrd, _)| (dist_sqrd * 1024.0) as i32)
|
||||
.map(|(dist, pos)| (dist.sqrt(), pos))
|
||||
.min_by_key(|(dist_sqrd, _, _, _)| (dist_sqrd * 1024.0) as i32)
|
||||
.map(|(dist, pos, path, calc_tangent)| (dist.sqrt(), pos, path, calc_tangent()))
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1,9 +1,15 @@
|
||||
use vek::*;
|
||||
|
||||
#[derive(Copy, Clone, Debug)]
|
||||
pub struct Path {
|
||||
pub width: f32,
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct PathData {
|
||||
pub offset: Vec2<f32>, /* Offset from centre of chunk: must not be more than half chunk
|
||||
* width in any direction */
|
||||
pub path: Path,
|
||||
pub neighbors: u8, // One bit for each neighbor
|
||||
}
|
||||
|
||||
@ -15,7 +21,17 @@ impl Default for PathData {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
offset: Vec2::zero(),
|
||||
path: Path {
|
||||
width: 5.0,
|
||||
},
|
||||
neighbors: 0,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Path {
|
||||
/// Return the number of blocks of headspace required at the given path distance
|
||||
pub fn head_space(&self, dist: f32) -> i32 {
|
||||
(8 - (dist * 0.25).powf(6.0).round() as i32).max(1)
|
||||
}
|
||||
}
|
||||
|
@ -88,7 +88,7 @@ impl Castle {
|
||||
if ctx
|
||||
.sim
|
||||
.and_then(|sim| sim.get_nearest_path(wpos + offset))
|
||||
.map(|(dist, _)| dist > 24.0)
|
||||
.map(|(dist, _, _, _)| dist > 24.0)
|
||||
.unwrap_or(true)
|
||||
{
|
||||
break;
|
||||
@ -202,6 +202,16 @@ impl Castle {
|
||||
})
|
||||
.min_by_key(|x| x.0)
|
||||
.unwrap();
|
||||
let border_pos = (wall_pos - rpos).map(|e| e.abs());
|
||||
let wall_normal = (rpos - wall_pos).map(|e| e as f32);
|
||||
let wall_rpos = if wall_ori == Ori::East {
|
||||
rpos
|
||||
} else {
|
||||
rpos.yx()
|
||||
};
|
||||
let head_space = col_sample.path
|
||||
.map(|(dist, _, path, _)| path.head_space(dist))
|
||||
.unwrap_or(0);
|
||||
|
||||
// Apply the dungeon entrance
|
||||
let wall_sample = if let Some(col) = get_column(offs + wall_pos - rpos) {
|
||||
@ -218,27 +228,26 @@ impl Castle {
|
||||
};
|
||||
|
||||
// Boundary
|
||||
let border_pos = (wall_pos - rpos).map(|e| e.abs());
|
||||
let wall_rpos = if wall_ori == Ori::East {
|
||||
rpos
|
||||
let wall_z = wpos.z - wall_alt;
|
||||
let mut mask = if z < head_space {
|
||||
BlockMask::nothing()
|
||||
} else {
|
||||
rpos.yx()
|
||||
keep.draw(
|
||||
Vec3::from(wall_rpos) + Vec3::unit_z() * wpos.z - wall_alt,
|
||||
wall_dist,
|
||||
Vec2::new(border_pos.reduce_max(), border_pos.reduce_min()),
|
||||
rpos - wall_pos,
|
||||
wall_z,
|
||||
wall_ori,
|
||||
4,
|
||||
0,
|
||||
&Attr {
|
||||
height: 16,
|
||||
is_tower: false,
|
||||
rounded: true,
|
||||
},
|
||||
)
|
||||
};
|
||||
let mut mask = keep.draw(
|
||||
Vec3::from(wall_rpos) + Vec3::unit_z() * wpos.z - wall_alt,
|
||||
wall_dist,
|
||||
Vec2::new(border_pos.reduce_max(), border_pos.reduce_min()),
|
||||
rpos - wall_pos,
|
||||
wpos.z - wall_alt,
|
||||
wall_ori,
|
||||
4,
|
||||
0,
|
||||
&Attr {
|
||||
height: 16,
|
||||
is_tower: false,
|
||||
rounded: true,
|
||||
},
|
||||
);
|
||||
for tower in &self.towers {
|
||||
let tower_wpos = Vec3::new(
|
||||
self.origin.x + tower.offset.x,
|
||||
|
@ -380,7 +380,7 @@ impl Settlement {
|
||||
|| ctx
|
||||
.sim
|
||||
.and_then(|sim| sim.get_nearest_path(self.origin + house_pos))
|
||||
.map(|(dist, _)| dist < 28.0)
|
||||
.map(|(dist, _, _, _)| dist < 28.0)
|
||||
.unwrap_or(false)
|
||||
{
|
||||
continue;
|
||||
@ -590,45 +590,46 @@ impl Settlement {
|
||||
}
|
||||
|
||||
// Paths
|
||||
if let Some((WayKind::Path, dist, nearest)) = sample.way {
|
||||
let inset = -1;
|
||||
// if let Some((WayKind::Path, dist, nearest)) = sample.way {
|
||||
// let inset = -1;
|
||||
|
||||
// Try to use the column at the centre of the path for sampling to make them
|
||||
// flatter
|
||||
let col = get_column(offs + (nearest.floor().map(|e| e as i32) - rpos))
|
||||
.unwrap_or(col_sample);
|
||||
let (bridge_offset, depth) = if let Some(water_dist) = col.water_dist {
|
||||
(
|
||||
((water_dist.max(0.0) * 0.2).min(f32::consts::PI).cos() + 1.0) * 5.0,
|
||||
((1.0 - ((water_dist + 2.0) * 0.3).min(0.0).cos().abs())
|
||||
* (col.riverless_alt + 5.0 - col.alt).max(0.0)
|
||||
* 1.75
|
||||
+ 3.0) as i32,
|
||||
)
|
||||
} else {
|
||||
(0.0, 3)
|
||||
};
|
||||
let surface_z = (col.riverless_alt + bridge_offset).floor() as i32;
|
||||
// // Try to use the column at the centre of the path for sampling to make them
|
||||
// // flatter
|
||||
// let col = get_column(offs + (nearest.floor().map(|e| e as i32) - rpos))
|
||||
// .unwrap_or(col_sample);
|
||||
// let (bridge_offset, depth) = if let Some(water_dist) = col.water_dist {
|
||||
// (
|
||||
// ((water_dist.max(0.0) * 0.2).min(f32::consts::PI).cos() + 1.0) * 5.0,
|
||||
// ((1.0 - ((water_dist + 2.0) * 0.3).min(0.0).cos().abs())
|
||||
// * (col.riverless_alt + 5.0 - col.alt).max(0.0)
|
||||
// * 1.75
|
||||
// + 3.0) as i32,
|
||||
// )
|
||||
// } else {
|
||||
// (0.0, 3)
|
||||
// };
|
||||
// let surface_z = (col.riverless_alt + bridge_offset).floor() as i32;
|
||||
|
||||
for z in inset - depth..inset {
|
||||
let _ = vol.set(
|
||||
Vec3::new(offs.x, offs.y, surface_z + z),
|
||||
if bridge_offset >= 2.0 && dist >= 3.0 || z < inset - 1 {
|
||||
Block::new(BlockKind::Normal, noisy_color(Rgb::new(80, 80, 100), 8))
|
||||
} else {
|
||||
Block::new(BlockKind::Normal, noisy_color(Rgb::new(80, 50, 30), 8))
|
||||
},
|
||||
);
|
||||
}
|
||||
let head_space = (8 - (dist * 0.25).powf(6.0).round() as i32).max(1);
|
||||
for z in inset..inset + head_space {
|
||||
let pos = Vec3::new(offs.x, offs.y, surface_z + z);
|
||||
if vol.get(pos).unwrap().kind() != BlockKind::Water {
|
||||
let _ = vol.set(pos, Block::empty());
|
||||
}
|
||||
}
|
||||
// Ground colour
|
||||
} else {
|
||||
// for z in inset - depth..inset {
|
||||
// let _ = vol.set(
|
||||
// Vec3::new(offs.x, offs.y, surface_z + z),
|
||||
// if bridge_offset >= 2.0 && dist >= 3.0 || z < inset - 1 {
|
||||
// Block::new(BlockKind::Normal, noisy_color(Rgb::new(80, 80, 100), 8))
|
||||
// } else {
|
||||
// Block::new(BlockKind::Normal, noisy_color(Rgb::new(80, 50, 30), 8))
|
||||
// },
|
||||
// );
|
||||
// }
|
||||
// let head_space = (8 - (dist * 0.25).powf(6.0).round() as i32).max(1);
|
||||
// for z in inset..inset + head_space {
|
||||
// let pos = Vec3::new(offs.x, offs.y, surface_z + z);
|
||||
// if vol.get(pos).unwrap().kind() != BlockKind::Water {
|
||||
// let _ = vol.set(pos, Block::empty());
|
||||
// }
|
||||
// }
|
||||
// // Ground colour
|
||||
// } else
|
||||
{
|
||||
let mut surface_block = None;
|
||||
|
||||
let roll =
|
||||
@ -639,7 +640,7 @@ impl Settlement {
|
||||
Some(Plot::Grass) => Some(Rgb::new(100, 200, 0)),
|
||||
Some(Plot::Water) => Some(Rgb::new(100, 150, 250)),
|
||||
Some(Plot::Town { district }) => {
|
||||
if let Some((_, path_nearest)) = col_sample.path {
|
||||
if let Some((_, path_nearest, _, _)) = col_sample.path {
|
||||
let path_dir = (path_nearest - wpos2d.map(|e| e as f32))
|
||||
.rotated_z(f32::consts::PI / 2.0)
|
||||
.normalized();
|
||||
@ -651,8 +652,8 @@ impl Settlement {
|
||||
/ path_dir.dot(Vec2::unit_x()).abs()
|
||||
<= 1.0
|
||||
};
|
||||
if (col_sample.path.map(|(dist, _)| dist > 6.0 && dist < 7.0).unwrap_or(false) && is_lamp) //roll(0, 50) == 0)
|
||||
|| (roll(0, 2000) == 0 && col_sample.path.map(|(dist, _)| dist > 20.0).unwrap_or(true))
|
||||
if (col_sample.path.map(|(dist, _, _, _)| dist > 6.0 && dist < 7.0).unwrap_or(false) && is_lamp) //roll(0, 50) == 0)
|
||||
|| (roll(0, 2000) == 0 && col_sample.path.map(|(dist, _, _, _)| dist > 20.0).unwrap_or(true))
|
||||
{
|
||||
surface_block =
|
||||
Some(Block::new(BlockKind::StreetLamp, Rgb::white()));
|
||||
|
Loading…
Reference in New Issue
Block a user