Move the spawn table to raws

This commit is contained in:
Timothy Warren 2021-12-23 13:07:50 -05:00
parent aaf3fdcc42
commit c1222294d0
4 changed files with 73 additions and 17 deletions

View File

@ -2,6 +2,7 @@ mod item_structs;
mod mob_structs;
mod prop_structs;
mod rawmaster;
mod spawn_table_structs;
use std::sync::Mutex;
@ -10,12 +11,14 @@ use mob_structs::*;
use prop_structs::*;
pub use rawmaster::*;
use serde::Deserialize;
use spawn_table_structs::*;
#[derive(Deserialize, Debug)]
pub struct Raws {
pub items: Vec<Item>,
pub mobs: Vec<Mob>,
pub props: Vec<Prop>,
pub spawn_table: Vec<SpawnTableEntry>,
}
rltk::embedded_resource!(RAW_FILE, "../raws/spawns.json");

View File

@ -1,8 +1,9 @@
use std::collections::HashMap;
use std::collections::{HashMap, HashSet};
use specs::prelude::*;
use crate::components::*;
use crate::random_table::RandomTable;
use crate::raws::Raws;
pub enum SpawnType {
@ -23,6 +24,7 @@ impl RawMaster {
items: Vec::new(),
mobs: Vec::new(),
props: Vec::new(),
spawn_table: Vec::new(),
},
item_index: HashMap::new(),
mob_index: HashMap::new(),
@ -33,15 +35,45 @@ impl RawMaster {
pub fn load(&mut self, raws: Raws) {
self.raws = raws;
self.item_index = HashMap::new();
let mut used_names: HashSet<String> = HashSet::new();
for (i, item) in self.raws.items.iter().enumerate() {
if used_names.contains(&item.name) {
rltk::console::log(format!(
"WARNING - duplicate item name in raws [{}]",
item.name
));
}
self.item_index.insert(item.name.clone(), i);
used_names.insert(item.name.clone());
}
for (i, mob) in self.raws.mobs.iter().enumerate() {
if used_names.contains(&mob.name) {
rltk::console::log(format!(
"WARNING - duplicate mob name in raws [{}]",
mob.name
));
}
self.mob_index.insert(mob.name.clone(), i);
used_names.insert(mob.name.clone());
}
for (i, prop) in self.raws.props.iter().enumerate() {
if used_names.contains(&prop.name) {
rltk::console::log(format!(
"WARNING - duplicate prop name in raws [{}]",
prop.name
));
}
self.prop_index.insert(prop.name.clone(), i);
used_names.insert(prop.name.clone());
}
for spawn in self.raws.spawn_table.iter() {
if !used_names.contains(&spawn.name) {
rltk::console::log(format!(
"WARNING - Spawn tables references unspecified entity {}",
spawn.name
));
}
}
}
}
@ -280,3 +312,25 @@ pub fn spawn_named_entity(
None
}
pub fn get_spawn_table_for_depth(raws: &RawMaster, depth: i32) -> RandomTable {
use super::SpawnTableEntry;
let available_options: Vec<&SpawnTableEntry> = raws
.raws
.spawn_table
.iter()
.filter(|a| depth >= a.min_depth && depth <= a.max_depth)
.collect();
let mut rt = RandomTable::new();
for e in available_options.iter() {
let mut weight = e.weight;
if e.add_map_depth_to_weight.is_some() {
weight += depth;
}
rt = rt.add(e.name.clone(), weight);
}
rt
}

View File

@ -0,0 +1,12 @@
use serde::Deserialize;
use super::Renderable;
#[derive(Deserialize, Debug)]
pub struct SpawnTableEntry {
pub name: String,
pub weight: i32,
pub min_depth: i32,
pub max_depth: i32,
pub add_map_depth_to_weight: Option<bool>,
}

View File

@ -6,7 +6,7 @@ use specs::saveload::{MarkedBuilder, SimpleMarker};
use crate::components::*;
use crate::random_table::RandomTable;
use crate::raws::{spawn_named_entity, SpawnType, RAWS};
use crate::raws::{get_spawn_table_for_depth, spawn_named_entity, SpawnType, RAWS};
use crate::{Map, Rect, TileType};
/// Spawns the player and returns their entity object
@ -42,20 +42,7 @@ pub fn player(ecs: &mut World, player_x: i32, player_y: i32) -> Entity {
const MAX_MONSTERS: i32 = 4;
fn room_table(map_depth: i32) -> RandomTable {
RandomTable::new()
.add("Goblin", 10)
.add("Orc", 1 + map_depth)
.add("Health Potion", 7)
.add("Fireball Scroll", 2 + map_depth)
.add("Confusion Scroll", 2 + map_depth)
.add("Magic Missile Scroll", 4)
.add("Dagger", 3)
.add("Shield", 3)
.add("Longsword", map_depth - 1)
.add("Tower Shield", map_depth - 1)
.add("Rations", 10)
.add("Magic Mapping Scroll", 2)
.add("Bear Trap", 2)
get_spawn_table_for_depth(&RAWS.lock().unwrap(), map_depth)
}
/// fills a room with stuff!