implement CLI write-attribute and write-modifier

This commit is contained in:
mykola2312 2023-09-10 22:06:33 +03:00
parent ff7ada6fc7
commit fb6c39ffd7

View file

@ -5,9 +5,9 @@ use std::io::{stdout, BufWriter, Write};
use std::path::Path; use std::path::Path;
mod fot; mod fot;
use fot::attributes::Attributes;
use fot::entity::Entity; use fot::entity::Entity;
use fot::entitylist::EntityList; use fot::entitylist::EntityList;
use fot::attributes::Attributes;
use fot::save::Save; use fot::save::Save;
#[derive(Parser)] #[derive(Parser)]
@ -53,7 +53,19 @@ enum Commands {
/// List entity attributes (like special stats and skills) /// List entity attributes (like special stats and skills)
ListAttributes, ListAttributes,
/// List entity modifiers (buffs/debuffs for attributes) /// List entity modifiers (buffs/debuffs for attributes)
ListModifiers ListModifiers,
/// Write attribute value where group is stats/traits/derived/skills/skill_tags/opt_traits/perks/addictions
WriteAttribute {
group: String,
name: String,
value: String,
},
/// Write modifier value where group is stats/traits/derived/skills/skill_tags/opt_traits/perks/addictions
WriteModifier {
group: String,
name: String,
value: String,
},
} }
fn log_entities<'a>(entlist: &EntityList, iter: impl IntoIterator<Item = (usize, &'a Entity)>) { fn log_entities<'a>(entlist: &EntityList, iter: impl IntoIterator<Item = (usize, &'a Entity)>) {
@ -86,6 +98,22 @@ fn from_ids(entlist: &EntityList, line: String) -> HashMap<usize, &Entity> {
.collect::<HashMap<usize, &Entity>>() .collect::<HashMap<usize, &Entity>>()
} }
fn from_ids_mut(entlist: &mut EntityList, line: String) -> HashMap<usize, &mut Entity> {
let mut entities: HashMap<usize, &mut Entity> = HashMap::new();
let ids: Vec<usize> = line
.split(",")
.map(|id| id.parse().expect("id parse"))
.collect();
for (id, ent) in entlist {
if ids.contains(&id) {
entities.insert(id, ent);
}
}
entities
}
fn find_entities(entlist: &EntityList, line: String) -> HashMap<usize, &Entity> { fn find_entities(entlist: &EntityList, line: String) -> HashMap<usize, &Entity> {
let kv = parse_kv(&line); let kv = parse_kv(&line);
let mut entities: HashMap<usize, &Entity> = HashMap::new(); let mut entities: HashMap<usize, &Entity> = HashMap::new();
@ -109,6 +137,30 @@ fn find_entities(entlist: &EntityList, line: String) -> HashMap<usize, &Entity>
entities entities
} }
fn find_entities_mut(entlist: &mut EntityList, line: String) -> HashMap<usize, &mut Entity> {
let kv = parse_kv(&line);
let mut entities: HashMap<usize, &mut Entity> = HashMap::new();
for (id, ent) in entlist {
let esh = match &ent.esh {
Some(esh) => esh,
None => continue,
};
'check: for (name, value) in &esh.props {
let key = name.str.as_str();
let svalue = value.to_string();
for (k, v) in &kv {
if key == *k && svalue == *v {
entities.insert(id, ent);
break 'check;
}
}
}
}
entities
}
fn get_entities( fn get_entities(
entlist: &EntityList, entlist: &EntityList,
ids: Option<String>, ids: Option<String>,
@ -123,6 +175,20 @@ fn get_entities(
} }
} }
fn get_entities_mut(
entlist: &mut EntityList,
ids: Option<String>,
find: Option<String>,
) -> HashMap<usize, &mut Entity> {
if let Some(ids) = ids {
from_ids_mut(entlist, ids)
} else if let Some(find) = find {
find_entities_mut(entlist, find)
} else {
panic!("No entity selector provided!")
}
}
fn list_values(ent: &Entity) { fn list_values(ent: &Entity) {
let mut bf = BufWriter::new(stdout().lock()); let mut bf = BufWriter::new(stdout().lock());
let esh = match ent.esh.as_ref() { let esh = match ent.esh.as_ref() {
@ -179,17 +245,43 @@ fn log_attributes(attrs: Attributes) {
fn list_attributes(ent: &Entity) { fn list_attributes(ent: &Entity) {
match ent.get_attributes() { match ent.get_attributes() {
Ok(attrs) => log_attributes(attrs), Ok(attrs) => log_attributes(attrs),
Err(e) => panic!("Fatal Error {}", e) Err(e) => panic!("Fatal Error {}", e),
} }
} }
fn list_modifiers(ent: &Entity) { fn list_modifiers(ent: &Entity) {
match ent.get_modifiers() { match ent.get_modifiers() {
Ok(attrs) => log_attributes(attrs), Ok(attrs) => log_attributes(attrs),
Err(e) => panic!("Fatal Error {}", e) Err(e) => panic!("Fatal Error {}", e),
} }
} }
fn write_attribute_value(attrs: &mut Attributes, group: &str, name: &str, value: &str) {
match group {
"stats" => attrs.stats[name] = value.parse().expect("parse"),
"traits" => attrs.traits[name] = value.parse().expect("parse"),
"derived" => attrs.derived[name] = value.parse().expect("parse"),
"skills" => attrs.skills[name] = value.parse().expect("parse"),
"skill_tags" => attrs.skill_tags[name] = value.parse().expect("parse"),
"opt_traits" => attrs.opt_traits[name] = value.parse().expect("parse"),
"perks" => attrs.perks[name] = value.parse().expect("parse"),
"addictions" => attrs.addictions[name] = value.parse().expect("parse"),
_ => panic!("invalid group specified"),
}
}
fn write_attribute(ent: &mut Entity, group: &str, name: &str, value: &str) {
let mut attrs = ent.get_attributes().expect("get_attributes");
write_attribute_value(&mut attrs, group, name, value);
ent.set_attributes(attrs).expect("set_attributes");
}
fn write_modifier(ent: &mut Entity, group: &str, name: &str, value: &str) {
let mut attrs = ent.get_modifiers().expect("modifiers");
write_attribute_value(&mut attrs, group, name, value);
ent.set_modifiers(attrs).expect("set_modifiers");
}
fn do_save(cli: Cli) { fn do_save(cli: Cli) {
let mut save = match Save::load(Path::new(cli.input.as_str())) { let mut save = match Save::load(Path::new(cli.input.as_str())) {
Ok(save) => save, Ok(save) => save,
@ -219,6 +311,18 @@ fn do_save(cli: Cli) {
list_modifiers(ent); list_modifiers(ent);
} }
} }
Commands::WriteAttribute { group, name, value } => {
for (_, ent) in get_entities_mut(&mut save.world.entlist, cli.ids, cli.find) {
write_attribute(ent, group.as_str(), name.as_str(), value.as_str())
}
save.save(Path::new(&cli.output)).expect("failed to save");
}
Commands::WriteModifier { group, name, value } => {
for (_, ent) in get_entities_mut(&mut save.world.entlist, cli.ids, cli.find) {
write_modifier(ent, group.as_str(), name.as_str(), value.as_str())
}
save.save(Path::new(&cli.output)).expect("failed to save");
}
} }
} }