Terrafier/core/src/ops/layers/terrain/biome.rs
loki5512344 bdd4564240 Refactor structure, implement layers, add Erode/Fill/layer panel
- Restructure folder hierarchy: max 4 .rs per dir using subfolders
  (ops/operations -> brush/ + shaping/, model/ -> world/, io/* -> subtypes, etc.)
- Fix golden_test.rs comment, extract BrushApply helper, add World::with_heightmap
- Implement 6 layer data generators (Caves, River, Frost, Trees, Biome, Resources)
  with noise-based (OpenSimplex) and terrain-derived algorithms
- Fix clippy warnings, dead code cleanup, import path fixes
- GUI: add Erode&Fill tool modes with radio buttons/sliders/apply_tool
- GUI: add Layers panel with 6 checkboxes + CPU viewport overlay rendering
2026-06-24 12:27:55 +02:00

59 lines
1.7 KiB
Rust

use crate::coords::TILE_SIZE;
use crate::model::layers::{DataSize, LAYER_BIOME};
use crate::model::tile::Tile;
use crate::ops::layers::LayerGenerator;
pub struct BiomeGenerator;
impl LayerGenerator for BiomeGenerator {
fn layer_id(&self) -> u32 {
LAYER_BIOME
}
fn generate(&self, tile: &mut Tile, _seed: u64) {
let data = from_terrain(&tile.terrain);
let buf = tile.ensure_layer(LAYER_BIOME, DataSize::Byte);
if let crate::model::tile::LayerBuffer::Byte(bytes) = buf {
bytes.copy_from_slice(&data);
}
}
}
/// Map terrain types to biome indices used by BiomeLayerExport.
/// Biome index → MC biome ID mapping (from biome_res.rs):
/// 0 → 1 (Plains), 1 → 2 (Desert), 2 → 4 (Forest),
/// 3 → 5 (Taiga), 4 → 6 (Swamp), 8 → 0 (Ocean)
const TERRAIN_TO_BIOME: [u8; 7] = [
0, // Desert → Plains (index 0)
0, // Grass → Plains (index 0)
2, // Forest → Forest (index 2)
3, // Rock → Taiga (index 3)
1, // Sand → Desert (index 1)
4, // Swamp → Swamp (index 4)
8, // Water → Ocean (index 8)
];
pub fn from_terrain(terrain: &[u8]) -> Vec<u8> {
terrain
.iter()
.map(|&t| {
let idx = t as usize;
if idx < TERRAIN_TO_BIOME.len() {
TERRAIN_TO_BIOME[idx]
} else {
0
}
})
.collect()
}
#[allow(dead_code)]
pub fn biome_at(tile: &Tile, local_x: usize, local_z: usize) -> u8 {
let idx = local_z * TILE_SIZE + local_x;
let terrain = tile.terrain[idx] as usize;
if terrain < TERRAIN_TO_BIOME.len() {
TERRAIN_TO_BIOME[terrain]
} else {
0
}
}