diff --git a/Makefile b/Makefile index 6f3beb1..b8836cd 100644 --- a/Makefile +++ b/Makefile @@ -5,6 +5,7 @@ run-pi: MESA_GL_VERSION_OVERRIDE=3.0 MESA_GLSL_VERSION_OVERRIDE=330 cargo run clean: + rm -f savegame.json cargo clean check: diff --git a/src/map_builders/town.rs b/src/map_builders/town.rs index 1c930f1..876e6bc 100644 --- a/src/map_builders/town.rs +++ b/src/map_builders/town.rs @@ -17,6 +17,16 @@ pub fn town_builder( chain } +pub struct TownBuilder {} + +impl InitialMapBuilder for TownBuilder { + #[allow(dead_code)] + fn build_map(&mut self, rng: &mut RandomNumberGenerator, build_data: &mut BuilderMap) { + self.build_rooms(rng, build_data); + } +} + +#[derive(Debug)] enum BuildingTag { Pub, Temple, @@ -29,15 +39,6 @@ enum BuildingTag { Unassigned, } -pub struct TownBuilder {} - -impl InitialMapBuilder for TownBuilder { - #[allow(dead_code)] - fn build_map(&mut self, rng: &mut RandomNumberGenerator, build_data: &mut BuilderMap) { - self.build_rooms(rng, build_data); - } -} - impl TownBuilder { pub fn new() -> Box { Box::new(TownBuilder {}) @@ -47,16 +48,9 @@ impl TownBuilder { self.grass_layer(build_data); self.water_and_piers(rng, build_data); - // Make visible for screenshot - for t in build_data.map.visible_tiles.iter_mut() { - *t = true; - } - build_data.take_snapshot(); - let (mut available_building_tiles, wall_gap_y) = self.town_walls(rng, build_data); let mut buildings = self.buildings(rng, build_data, &mut available_building_tiles); let doors = self.add_doors(rng, build_data, &mut buildings, wall_gap_y); - self.add_paths(build_data, &doors); let exit_idx = build_data.map.xy_idx(build_data.width - 5, wall_gap_y); @@ -64,6 +58,12 @@ impl TownBuilder { let building_size = self.sort_buildings(&buildings); self.building_factory(rng, build_data, &buildings, &building_size); + + // Make visible for screenshot + for t in build_data.map.visible_tiles.iter_mut() { + *t = true; + } + build_data.take_snapshot(); } fn grass_layer(&mut self, build_data: &mut BuilderMap) { @@ -305,7 +305,6 @@ impl TownBuilder { &mut self, buildings: &[(i32, i32, i32, i32)], ) -> Vec<(usize, i32, BuildingTag)> { - // Sort buildings by size let mut building_size: Vec<(usize, i32, BuildingTag)> = Vec::new(); for (i, building) in buildings.iter().enumerate() { building_size.push((i, building.2 * building.3, BuildingTag::Unassigned)); @@ -320,7 +319,6 @@ impl TownBuilder { for b in building_size.iter_mut().skip(6) { b.2 = BuildingTag::Hovel; } - let last_index = building_size.len() - 1; building_size[last_index].2 = BuildingTag::Abandoned; @@ -338,11 +336,42 @@ impl TownBuilder { let build_type = &building_index[i].2; match build_type { BuildingTag::Pub => self.build_pub(building, build_data, rng), + BuildingTag::Temple => self.build_temple(building, build_data, rng), + BuildingTag::Blacksmith => self.build_smith(building, build_data, rng), + BuildingTag::Clothier => self.build_clothier(building, build_data, rng), + BuildingTag::Alchemist => self.build_alchemist(building, build_data, rng), + BuildingTag::PlayerHouse => self.build_my_house(building, build_data, rng), + BuildingTag::Hovel => self.build_hovel(building, build_data, rng), + BuildingTag::Abandoned => self.build_abandoned_house(building, build_data, rng), _ => {} } } } + fn random_building_spawn( + &mut self, + building: &(i32, i32, i32, i32), + build_data: &mut BuilderMap, + rng: &mut RandomNumberGenerator, + to_place: &mut Vec<&str>, + player_idx: usize, + ) { + for y in building.1..building.1 + building.3 { + for x in building.0..building.0 + building.2 { + let idx = build_data.map.xy_idx(x, y); + if build_data.map.tiles[idx] == TileType::WoodFloor + && idx != player_idx + && rng.roll_dice(1, 3) == 1 + && !to_place.is_empty() + { + let entity_tag = to_place[0]; + to_place.remove(0); + build_data.spawn_list.push((idx, entity_tag.to_string())); + } + } + } + } + fn build_pub( &mut self, building: &(i32, i32, i32, i32), @@ -359,27 +388,115 @@ impl TownBuilder { .xy_idx(building.0 + (building.2 / 2), building.1 + (building.3 / 2)); // Place other items - let mut to_place: Vec<&str> = vec![ + let mut to_place = vec![ "Barkeep", "Shady Salesman", "Patron", "Patron", + "Keg", "Table", "Chair", "Table", "Chair", ]; + self.random_building_spawn(building, build_data, rng, &mut to_place, player_idx); + } + + fn build_temple( + &mut self, + building: &(i32, i32, i32, i32), + build_data: &mut BuilderMap, + rng: &mut RandomNumberGenerator, + ) { + // Place items + let mut to_place: Vec<&str> = vec![ + "Priest", + "Parishioner", + "Parishioner", + "Chair", + "Chair", + "Candle", + "Candle", + ]; + self.random_building_spawn(building, build_data, rng, &mut to_place, 0); + } + + fn build_smith( + &mut self, + building: &(i32, i32, i32, i32), + build_data: &mut BuilderMap, + rng: &mut RandomNumberGenerator, + ) { + // Place items + let mut to_place: Vec<&str> = vec![ + "Blacksmith", + "Anvil", + "Water Trough", + "Weapon Rack", + "Armor Stand", + ]; + self.random_building_spawn(building, build_data, rng, &mut to_place, 0); + } + + fn build_clothier( + &mut self, + building: &(i32, i32, i32, i32), + build_data: &mut BuilderMap, + rng: &mut RandomNumberGenerator, + ) { + // Place items + let mut to_place: Vec<&str> = vec!["Clothier", "Cabinet", "Table", "Loom", "Hide Rack"]; + self.random_building_spawn(building, build_data, rng, &mut to_place, 0); + } + + fn build_alchemist( + &mut self, + building: &(i32, i32, i32, i32), + build_data: &mut BuilderMap, + rng: &mut RandomNumberGenerator, + ) { + // Place items + let mut to_place: Vec<&str> = + vec!["Alchemist", "Chemistry Set", "Dead Thing", "Chair", "Table"]; + self.random_building_spawn(building, build_data, rng, &mut to_place, 0); + } + + fn build_my_house( + &mut self, + building: &(i32, i32, i32, i32), + build_data: &mut BuilderMap, + rng: &mut RandomNumberGenerator, + ) { + // Place items + let mut to_place: Vec<&str> = vec!["Mom", "Bed", "Cabinet", "Chair", "Table"]; + self.random_building_spawn(building, build_data, rng, &mut to_place, 0); + } + + fn build_hovel( + &mut self, + building: &(i32, i32, i32, i32), + build_data: &mut BuilderMap, + rng: &mut RandomNumberGenerator, + ) { + // Place items + let mut to_place: Vec<&str> = vec!["Peasant", "Bed", "Chair", "Table"]; + self.random_building_spawn(building, build_data, rng, &mut to_place, 0); + } + + fn build_abandoned_house( + &mut self, + building: &(i32, i32, i32, i32), + build_data: &mut BuilderMap, + rng: &mut RandomNumberGenerator, + ) { for y in building.1..building.1 + building.3 { for x in building.0..building.0 + building.2 { let idx = build_data.map.xy_idx(x, y); if build_data.map.tiles[idx] == TileType::WoodFloor - && idx != player_idx - && rng.roll_dice(1, 3) == 1 - && !to_place.is_empty() + && idx != 0 + && rng.roll_dice(1, 2) == 1 { - let entity_tag = to_place[0]; - to_place.remove(0); - build_data.spawn_list.push((idx, entity_tag.to_string())); + build_data.spawn_list.push((idx, "Rat".to_string())); } } }