blastmud/blastmud_game/src/models/item.rs

275 lines
7.1 KiB
Rust
Raw Normal View History

2022-12-26 01:30:59 +11:00
use serde::{Serialize, Deserialize};
use std::collections::BTreeMap;
2023-01-15 17:30:23 +11:00
use crate::language;
2023-01-15 23:16:02 +11:00
use super::session::Session;
2022-12-26 01:30:59 +11:00
2022-12-31 19:33:31 +11:00
#[derive(Serialize, Deserialize, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
2022-12-26 01:30:59 +11:00
pub enum BuffCause {
WaitingTask { task_code: String, task_type: String },
ByItem { item_code: String, item_type: String }
}
#[derive(Serialize, Deserialize, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
pub enum BuffImpact {
ChangeStat { stat: StatType, magnitude: i16 },
ChangeSkill { stat: StatType, magnitude: i16 }
}
2022-12-31 19:33:31 +11:00
#[derive(Serialize, Deserialize, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
2022-12-26 01:30:59 +11:00
pub struct Buff {
description: String,
cause: BuffCause,
impacts: Vec<BuffImpact>
}
2023-01-15 23:16:02 +11:00
#[derive(Serialize, Deserialize, Clone, Debug, PartialEq, Eq, PartialOrd, Ord)]
pub enum SkillType {
Apraise,
Blades,
Bombs,
Chemistry,
Climb,
Clubs,
Craft,
Dodge,
Fish,
Fists,
Flails,
Fuck,
Hack,
Locksmith,
Medic,
Persuade,
Pilot,
Pistols,
Quickdraw,
Repair,
Ride,
Rifles,
Scavenge,
Science,
Sneak,
Spears,
Swim,
Teach,
Throw,
Track,
Wrestle,
Whips
}
#[derive(Serialize, Deserialize, Clone, Debug, PartialEq, Eq, PartialOrd, Ord)]
pub enum StatType {
Brains,
Senses,
Brawn,
Reflexes,
Endurance,
Cool
}
#[derive(Serialize, Deserialize, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
pub struct Pronouns {
pub subject: String,
pub object: String,
pub intensive: String,
pub possessive: String,
// And some miscellaneous details to determine context
pub is_plural: bool, // ... are instead of ... is
pub is_proper: bool, // When naming, just ... instead of The ...
}
impl Pronouns {
pub fn default_inanimate() -> Pronouns {
Pronouns {
subject: "it".to_owned(),
object: "it".to_owned(),
intensive: "itself".to_owned(),
possessive: "its".to_owned(),
is_plural: false,
is_proper: true,
}
}
pub fn default_animate() -> Pronouns {
Pronouns {
subject: "they".to_owned(),
object: "them".to_owned(),
intensive: "themselves".to_owned(),
possessive: "their".to_owned(),
is_plural: true,
is_proper: true,
}
}
#[allow(dead_code)]
pub fn default_male() -> Pronouns {
Pronouns {
subject: "he".to_owned(),
object: "him".to_owned(),
intensive: "himself".to_owned(),
possessive: "his".to_owned(),
is_plural: false,
is_proper: true,
}
}
#[allow(dead_code)]
pub fn default_female() -> Pronouns {
Pronouns {
subject: "she".to_owned(),
object: "her".to_owned(),
intensive: "herself".to_owned(),
possessive: "her".to_owned(),
is_plural: false,
is_proper: true,
}
}
}
2022-12-26 01:30:59 +11:00
#[derive(Serialize, Deserialize, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
pub enum Subattack {
Normal,
Powerattacking,
Feinting,
Grabbing,
Wrestling
}
2022-12-31 19:33:31 +11:00
#[derive(Serialize, Deserialize, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
2022-12-26 01:30:59 +11:00
pub enum LocationActionType {
Normal,
Sitting,
Reclining,
Worn, // Clothing etc...
Wielded,
2023-01-15 17:30:23 +11:00
Attacking(Subattack)
2022-12-26 01:30:59 +11:00
}
2022-12-31 19:33:31 +11:00
#[derive(Serialize, Deserialize, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
pub enum Sex {
Male,
Female,
}
2022-12-31 19:33:31 +11:00
#[derive(Serialize, Deserialize, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
pub enum ItemFlag {
2023-01-08 00:18:56 +11:00
NoSay,
NoSeeContents
}
2023-01-15 17:30:23 +11:00
#[derive(Serialize, Deserialize, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
#[serde(default)]
pub struct ActiveCombat {
pub attacking: Option<String>,
pub attacked_by: Vec<String>
}
impl Default for ActiveCombat {
fn default() -> Self {
Self {
attacking: None,
attacked_by: vec!()
}
}
}
#[derive(Serialize, Deserialize, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
#[serde(default)]
2022-12-26 01:30:59 +11:00
pub struct Item {
pub item_code: String,
pub item_type: String,
pub display: String,
pub display_less_explicit: Option<String>,
2022-12-29 18:44:50 +11:00
pub details: Option<String>,
pub details_less_explicit: Option<String>,
2022-12-26 01:30:59 +11:00
pub location: String, // Item reference as item_type/item_code.
pub action_type: LocationActionType,
pub presence_target: Option<String>, // e.g. what are they sitting on.
pub is_static: bool,
2023-01-15 17:30:23 +11:00
pub is_dead: bool,
pub is_challenge_attack_only: bool,
2022-12-26 01:30:59 +11:00
pub total_xp: u64,
pub total_stats: BTreeMap<StatType, u16>,
pub total_skills: BTreeMap<SkillType, u16>,
2022-12-26 01:30:59 +11:00
pub temporary_buffs: Vec<Buff>,
pub pronouns: Pronouns,
pub flags: Vec<ItemFlag>,
pub sex: Option<Sex>,
2023-01-15 17:30:23 +11:00
pub active_combat: Option<ActiveCombat>,
}
impl Item {
2023-01-15 17:30:23 +11:00
pub fn display_for_sentence(&self, explicit_ok: bool, pluralise: usize, caps: bool) -> String {
let mut buf = String::new();
if self.is_dead {
if pluralise > 1 {
buf.push_str("the bodies of ");
} else {
buf.push_str("the body of ");
}
}
if !self.pronouns.is_proper && pluralise == 1 {
buf.push_str("a ");
}
if pluralise > 1 {
buf.push_str(&format!("{} ", pluralise));
}
let singular = if explicit_ok { &self.display } else {
self.display_less_explicit.as_ref().unwrap_or(&self.display) };
if pluralise > 1 {
buf.push_str(&language::pluralise(singular));
} else {
buf.push_str(singular);
}
if caps {
language::caps_first(&buf)
} else {
buf
}
}
pub fn display_for_session<'l>(self: &'l Self, session: &Session) -> String {
self.display_for_sentence(!session.less_explicit_mode, 1, false)
}
pub fn details_for_session<'l>(self: &'l Self, session: &Session) -> Option<&'l str>{
self.details.as_ref()
.map(|dets|
session.explicit_if_allowed(
dets.as_str(),
self.details_less_explicit.as_ref().map(String::as_str)
)
)
}
2022-12-26 01:30:59 +11:00
}
impl Default for Item {
fn default() -> Self {
2023-01-15 17:30:23 +11:00
Self {
item_code: "unset".to_owned(),
item_type: "unset".to_owned(),
display: "Item".to_owned(),
display_less_explicit: None,
2022-12-29 18:44:50 +11:00
details: None,
details_less_explicit: None,
location: "room/storage".to_owned(),
action_type: LocationActionType::Normal,
presence_target: None,
is_static: false,
2023-01-15 17:30:23 +11:00
is_dead: false,
is_challenge_attack_only: true,
total_xp: 0,
total_stats: BTreeMap::new(),
total_skills: BTreeMap::new(),
temporary_buffs: Vec::new(),
pronouns: Pronouns::default_inanimate(),
flags: vec!(),
2023-01-15 17:30:23 +11:00
sex: None,
active_combat: Some(Default::default()),
}
}
}