use std::time::Instant; use cgmath::Vector3; use noise::{Perlin, NoiseFn}; use rand::{Rng, prelude::ThreadRng}; use crate::game::world::{block, block::WorldBlock}; const SCALE: f64 = 150.0; pub struct WorldGen { } impl WorldGen { /* * Generate height map for given block position */ fn gen_height_map(x: i32, z: i32, rand: &mut ThreadRng, noise: &Perlin) -> ([[usize;block::SIZE]; block::SIZE], usize) { let size = block::SIZE as i32; let x = x * size; let z = z * size; // Generate map let mut max: usize = 0; let mut map = [[0_usize; block::SIZE]; block::SIZE]; for lx in 0..size { for lz in 0..size { let value = (noise.get([(x + lx) as f64 / SCALE, (z + lz) as f64 /SCALE]) + 1.0) / 2.0; let mut h = (value * 30.0) as usize; h += (rand.gen::() * 2.0) as usize; if h == 0 { h = 1; } if h > max { max = h; } map[lx as usize][lz as usize] = h; } } (map, max) } /* * Generate block */ pub fn generate(block_pos: &Vector3, block: &mut WorldBlock) { let mut rng = rand::thread_rng(); let noise = Perlin::new(); // Generate height map let (map, _max) = WorldGen::gen_height_map(block_pos.x, block_pos.z, &mut rng, &noise); // Fill for x in 0..block::SIZE { for z in 0..block::SIZE { let mut h = map[x][z]; let mut t = 2; if block_pos.x == 8 && block_pos.z == 8 { h = 32; t = 3; } //let h = 16; // testing for y in 0..h { block.set(Vector3{x, y, z}, t); } } } } }