aboutsummaryrefslogtreecommitdiff
path: root/src/gamedata.rs
diff options
context:
space:
mode:
authorDaniel Schadt <kingdread@gmx.de>2020-09-23 15:22:55 +0200
committerDaniel Schadt <kingdread@gmx.de>2020-09-23 15:23:55 +0200
commit39972d54be41bfc7b8b7f38b1f5a4d60e2453da5 (patch)
tree5ef048c306eca6a67005290859a29699d35978b6 /src/gamedata.rs
parent3b79ad8fa9b4a8c9c535b417129e3f70769074e0 (diff)
downloadevtclib-39972d54be41bfc7b8b7f38b1f5a4d60e2453da5.tar.gz
evtclib-39972d54be41bfc7b8b7f38b1f5a4d60e2453da5.tar.bz2
evtclib-39972d54be41bfc7b8b7f38b1f5a4d60e2453da5.zip
rename Boss to Encounter
This is the first step in differentiating between Encounters and Bosses. It sounds a bit weird at first, but there are some events without any bosses (like the River of Souls), and some events which have multiple bosses (like Twin Largos or the kodan strike mission). If we want to support this better, without relying on extra IDs, special casing and constants (like NIKARE_ID), we should differentiate between Encounters and Bosses.
Diffstat (limited to 'src/gamedata.rs')
-rw-r--r--src/gamedata.rs197
1 files changed, 95 insertions, 102 deletions
diff --git a/src/gamedata.rs b/src/gamedata.rs
index 392bd01..d307802 100644
--- a/src/gamedata.rs
+++ b/src/gamedata.rs
@@ -6,9 +6,17 @@ use std::{
};
use thiserror::Error;
-/// Enum containing all bosses with their IDs.
+/// Enum containing all encounters with their IDs.
+///
+/// An encounter is a fight or event, consisting of no, one or multiple bosses. Most encounters map
+/// 1:1 to a boss (like Vale Guardian), however there are some encounters with multiple bosses
+/// (like Twin Largos), and even encounters without bosses (like the River of Souls).
+///
+/// This enum is non-exhaustive to ensure that future added encounters can be added without
+/// inducing a breaking change.
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash, FromPrimitive)]
-pub enum Boss {
+#[non_exhaustive]
+pub enum Encounter {
// Wing 1
ValeGuardian = 0x3C4E,
Gorseval = 0x3C45,
@@ -20,11 +28,6 @@ pub enum Boss {
// Wing 3
KeepConstruct = 0x3F6B,
- /// Xera ID for phase 1.
- ///
- /// This is only half of Xera's ID, as there will be a second agent for the
- /// second phase. This agent will have another ID, see
- /// [`XERA_PHASE2_ID`](constant.XERA_PHASE2_ID.html).
Xera = 0x3F76,
// Wing 4
@@ -35,15 +38,11 @@ pub enum Boss {
// Wing 5
SoullessHorror = 0x4D37,
- Dhuum = 0x4BFA,
+ VoiceInTheVoid = 0x4BFA,
// Wing 6
ConjuredAmalgamate = 0xABC6,
- /// This is the ID of Nikare, as that is what the Twin Largos logs are identified by.
- ///
- /// If you want Nikare specifically, consider using [`NIKARE_ID`][NIKARE_ID], and similarly, if
- /// you need Kenut, you can use [`KENUT_ID`][KENUT_ID].
- LargosTwins = 0x5271,
+ TwinLargos = 0x5271,
Qadim = 0x51C6,
// Wing 7
@@ -66,110 +65,104 @@ pub enum Boss {
// Strike missions
IcebroodConstruct = 0x568A,
- /// This is the ID of the Voice of the Fallen.
- ///
- /// The strike mission itself contains two bosses, the Voice of the Fallen and the Claw of the
- /// Fallen. Consider using either [`VOICE_OF_THE_FALLEN_ID`][VOICE_OF_THE_FALLEN_ID] or
- /// [`CLAW_OF_THE_FALLEN_ID`][CLAW_OF_THE_FALLEN_ID] if you refer to one of those bosses
- /// specifically.
- VoiceOfTheFallen = 0x5747,
+ SuperKodanBrothers = 0x5747,
FraenirOfJormag = 0x57DC,
Boneskinner = 0x57F9,
WhisperOfJormag = 0x58B7,
}
-/// Error for when converting a string to the boss fails.
+/// Error for when converting a string to an encounter fails.
#[derive(Debug, Clone, Hash, PartialEq, Eq, Error)]
-#[error("Invalid boss identifier: {0}")]
-pub struct ParseBossError(String);
+#[error("Invalid encounter identifier: {0}")]
+pub struct ParseEncounterError(String);
-impl FromStr for Boss {
- type Err = ParseBossError;
+impl FromStr for Encounter {
+ type Err = ParseEncounterError;
fn from_str(s: &str) -> Result<Self, Self::Err> {
let lower = s.to_lowercase();
match &lower as &str {
- "vg" | "vale guardian" => Ok(Boss::ValeGuardian),
- "gorse" | "gorseval" => Ok(Boss::Gorseval),
- "sab" | "sabetha" => Ok(Boss::Sabetha),
+ "vg" | "vale guardian" => Ok(Encounter::ValeGuardian),
+ "gorse" | "gorseval" => Ok(Encounter::Gorseval),
+ "sab" | "sabetha" => Ok(Encounter::Sabetha),
- "sloth" | "slothasor" => Ok(Boss::Slothasor),
- "matthias" => Ok(Boss::Matthias),
+ "sloth" | "slothasor" => Ok(Encounter::Slothasor),
+ "matthias" => Ok(Encounter::Matthias),
- "kc" | "keep construct" => Ok(Boss::KeepConstruct),
- "xera" => Ok(Boss::Xera),
+ "kc" | "keep construct" => Ok(Encounter::KeepConstruct),
+ "xera" => Ok(Encounter::Xera),
- "cairn" => Ok(Boss::Cairn),
- "mo" | "mursaat overseer" => Ok(Boss::MursaatOverseer),
- "sam" | "sama" | "samarog" => Ok(Boss::Samarog),
- "deimos" => Ok(Boss::Deimos),
+ "cairn" => Ok(Encounter::Cairn),
+ "mo" | "mursaat overseer" => Ok(Encounter::MursaatOverseer),
+ "sam" | "sama" | "samarog" => Ok(Encounter::Samarog),
+ "deimos" => Ok(Encounter::Deimos),
- "desmina" | "sh" | "soulless horror" => Ok(Boss::SoullessHorror),
- "dhuum" => Ok(Boss::Dhuum),
+ "desmina" | "sh" | "soulless horror" => Ok(Encounter::SoullessHorror),
+ "dhuum" | "voice in the void" => Ok(Encounter::VoiceInTheVoid),
- "ca" | "conjured amalgamate" => Ok(Boss::ConjuredAmalgamate),
- "largos" | "twins" | "largos twins" => Ok(Boss::LargosTwins),
- "qadim" => Ok(Boss::Qadim),
+ "ca" | "conjured amalgamate" => Ok(Encounter::ConjuredAmalgamate),
+ "largos" | "twins" | "largos twins" => Ok(Encounter::TwinLargos),
+ "qadim" => Ok(Encounter::Qadim),
- "adina" | "cardinal adina" => Ok(Boss::CardinalAdina),
- "sabir" | "cardinal sabir" => Ok(Boss::CardinalSabir),
- "qadimp" | "peerless qadim" | "qadim the peerless" => Ok(Boss::QadimThePeerless),
+ "adina" | "cardinal adina" => Ok(Encounter::CardinalAdina),
+ "sabir" | "cardinal sabir" => Ok(Encounter::CardinalSabir),
+ "qadimp" | "peerless qadim" | "qadim the peerless" => Ok(Encounter::QadimThePeerless),
- "ai" | "ai keeper of the peak" => Ok(Boss::Ai),
+ "ai" | "ai keeper of the peak" => Ok(Encounter::Ai),
- "skorvald" => Ok(Boss::Skorvald),
- "artsariiv" => Ok(Boss::Artsariiv),
- "arkk" => Ok(Boss::Arkk),
+ "skorvald" => Ok(Encounter::Skorvald),
+ "artsariiv" => Ok(Encounter::Artsariiv),
+ "arkk" => Ok(Encounter::Arkk),
- "mama" => Ok(Boss::MAMA),
- "siax" => Ok(Boss::Siax),
- "ensolyss" | "ensolyss of the endless torment" => Ok(Boss::Ensolyss),
+ "mama" => Ok(Encounter::MAMA),
+ "siax" => Ok(Encounter::Siax),
+ "ensolyss" | "ensolyss of the endless torment" => Ok(Encounter::Ensolyss),
- "icebrood" | "icebrood construct" => Ok(Boss::IcebroodConstruct),
- "kodans" | "super kodan brothers" => Ok(Boss::VoiceOfTheFallen),
- "fraenir" | "fraenir of jormag" => Ok(Boss::FraenirOfJormag),
- "boneskinner" => Ok(Boss::Boneskinner),
- "whisper" | "whisper of jormag" => Ok(Boss::WhisperOfJormag),
+ "icebrood" | "icebrood construct" => Ok(Encounter::IcebroodConstruct),
+ "kodans" | "super kodan brothers" => Ok(Encounter::SuperKodanBrothers),
+ "fraenir" | "fraenir of jormag" => Ok(Encounter::FraenirOfJormag),
+ "boneskinner" => Ok(Encounter::Boneskinner),
+ "whisper" | "whisper of jormag" => Ok(Encounter::WhisperOfJormag),
- _ => Err(ParseBossError(s.to_owned())),
+ _ => Err(ParseEncounterError(s.to_owned())),
}
}
}
-impl Display for Boss {
+impl Display for Encounter {
fn fmt(&self, f: &mut Formatter) -> fmt::Result {
let name = match *self {
- Boss::ValeGuardian => "Vale Guardian",
- Boss::Gorseval => "Gorseval",
- Boss::Sabetha => "Sabetha",
- Boss::Slothasor => "Slothasor",
- Boss::Matthias => "Matthias Gabrel",
- Boss::KeepConstruct => "Keep Construct",
- Boss::Xera => "Xera",
- Boss::Cairn => "Cairn the Indomitable",
- Boss::MursaatOverseer => "Mursaat Overseer",
- Boss::Samarog => "Samarog",
- Boss::Deimos => "Deimos",
- Boss::SoullessHorror => "Soulless Horror",
- Boss::Dhuum => "Dhuum",
- Boss::ConjuredAmalgamate => "Conjured Amalgamate",
- Boss::LargosTwins => "Twin Largos",
- Boss::Qadim => "Qadim",
- Boss::CardinalAdina => "Cardinal Adina",
- Boss::CardinalSabir => "Cardinal Sabir",
- Boss::QadimThePeerless => "Qadim the Peerless",
- Boss::Ai => "Ai Keeper of the Peak",
- Boss::Skorvald => "Skorvald the Shattered",
- Boss::Artsariiv => "Artsariiv",
- Boss::Arkk => "Arkk",
- Boss::MAMA => "MAMA",
- Boss::Siax => "Siax the Corrupted",
- Boss::Ensolyss => "Ensolyss of the Endless Torment",
- Boss::IcebroodConstruct => "Icebrood Construct",
- Boss::VoiceOfTheFallen => "Super Kodan Brothers",
- Boss::FraenirOfJormag => "Fraenir of Jormag",
- Boss::Boneskinner => "Boneskinner",
- Boss::WhisperOfJormag => "Whisper of Jormag",
+ Encounter::ValeGuardian => "Vale Guardian",
+ Encounter::Gorseval => "Gorseval",
+ Encounter::Sabetha => "Sabetha",
+ Encounter::Slothasor => "Slothasor",
+ Encounter::Matthias => "Matthias Gabrel",
+ Encounter::KeepConstruct => "Keep Construct",
+ Encounter::Xera => "Xera",
+ Encounter::Cairn => "Cairn the Indomitable",
+ Encounter::MursaatOverseer => "Mursaat Overseer",
+ Encounter::Samarog => "Samarog",
+ Encounter::Deimos => "Deimos",
+ Encounter::SoullessHorror => "Soulless Horror",
+ Encounter::VoiceInTheVoid => "Voice in the Void",
+ Encounter::ConjuredAmalgamate => "Conjured Amalgamate",
+ Encounter::TwinLargos => "Twin Largos",
+ Encounter::Qadim => "Qadim",
+ Encounter::CardinalAdina => "Cardinal Adina",
+ Encounter::CardinalSabir => "Cardinal Sabir",
+ Encounter::QadimThePeerless => "Qadim the Peerless",
+ Encounter::Ai => "Ai Keeper of the Peak",
+ Encounter::Skorvald => "Skorvald the Shattered",
+ Encounter::Artsariiv => "Artsariiv",
+ Encounter::Arkk => "Arkk",
+ Encounter::MAMA => "MAMA",
+ Encounter::Siax => "Siax the Corrupted",
+ Encounter::Ensolyss => "Ensolyss of the Endless Torment",
+ Encounter::IcebroodConstruct => "Icebrood Construct",
+ Encounter::SuperKodanBrothers => "Super Kodan Brothers",
+ Encounter::FraenirOfJormag => "Fraenir of Jormag",
+ Encounter::Boneskinner => "Boneskinner",
+ Encounter::WhisperOfJormag => "Whisper of Jormag",
};
write!(f, "{}", name)
}
@@ -184,12 +177,12 @@ impl Display for Boss {
pub const XERA_PHASE2_ID: u16 = 0x3F9E;
/// The ID of Nikare in the Twin Largos fight.
-pub const NIKARE_ID: u16 = Boss::LargosTwins as u16;
+pub const NIKARE_ID: u16 = Encounter::TwinLargos as u16;
/// The ID of Kenut in the Twin Largos fight.
pub const KENUT_ID: u16 = 21089;
/// The ID of the Voice of the Fallen.
-pub const VOICE_OF_THE_FALLEN_ID: u16 = Boss::VoiceOfTheFallen as u16;
+pub const VOICE_OF_THE_FALLEN_ID: u16 = Encounter::SuperKodanBrothers as u16;
/// The ID of the Claw of the Fallen.
pub const CLAW_OF_THE_FALLEN_ID: u16 = 22481;
@@ -369,9 +362,9 @@ mod tests {
use super::*;
#[test]
- fn test_boss_parsing_ok() {
- use Boss::*;
- let tests: &[(&'static str, Boss)] = &[
+ fn test_encounter_parsing_ok() {
+ use Encounter::*;
+ let tests: &[(&'static str, Encounter)] = &[
("vg", ValeGuardian),
("VG", ValeGuardian),
("vale guardian", ValeGuardian),
@@ -408,14 +401,14 @@ mod tests {
("soulless horror", SoullessHorror),
("desmina", SoullessHorror),
("Desmina", SoullessHorror),
- ("dhuum", Dhuum),
- ("Dhuum", Dhuum),
+ ("dhuum", VoiceInTheVoid),
+ ("Dhuum", VoiceInTheVoid),
("ca", ConjuredAmalgamate),
("conjured amalgamate", ConjuredAmalgamate),
("Conjured Amalgamate", ConjuredAmalgamate),
- ("largos", LargosTwins),
- ("twins", LargosTwins),
- ("largos twins", LargosTwins),
+ ("largos", TwinLargos),
+ ("twins", TwinLargos),
+ ("largos twins", TwinLargos),
("qadim", Qadim),
("Qadim", Qadim),
("adina", CardinalAdina),
@@ -445,7 +438,7 @@ mod tests {
("fraenir", FraenirOfJormag),
("Fraenir of Jormag", FraenirOfJormag),
("boneskinner", Boneskinner),
- ("kodans", VoiceOfTheFallen),
+ ("kodans", SuperKodanBrothers),
("whisper", WhisperOfJormag),
("Whisper of Jormag", WhisperOfJormag),
];
@@ -461,7 +454,7 @@ mod tests {
}
#[test]
- fn test_boss_parsing_err() {
+ fn test_encounter_parsing_err() {
let tests = &[
"",
"vga",
@@ -475,7 +468,7 @@ mod tests {
"cardinal",
];
for test in tests {
- assert!(test.parse::<Boss>().is_err());
+ assert!(test.parse::<Encounter>().is_err());
}
}