ck3_history_extractor/display/
timeline.rs1use std::path::{Path, PathBuf};
2
3use serde::Serialize;
4
5use super::{
6 super::{
7 game_data::GameData,
8 jinja_env::TIMELINE_TEMPLATE_NAME,
9 parser::{GameRef, GameState},
10 structures::{Character, Culture, EntityRef, Faith, GameObjectDerived, Title},
11 types::GameString,
12 },
13 graph::{create_timeline_graph, Grapher},
14 renderer::{GetPath, Renderable},
15};
16
17pub enum RealmDifference {
19 Faith(GameRef<Faith>),
20 Culture(GameRef<Culture>),
21}
22
23impl Serialize for RealmDifference {
24 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
25 where
26 S: serde::Serializer,
27 {
28 match self {
29 RealmDifference::Faith(f) => f.serialize(serializer),
30 RealmDifference::Culture(c) => c.serialize(serializer),
31 }
32 }
33}
34
35#[derive(Serialize)]
37pub struct Timeline {
38 lifespans: Vec<(GameRef<Title>, Vec<(i16, i16)>)>,
39 latest_event: i16,
40 events: Vec<(
41 i16,
42 GameRef<Character>,
43 GameRef<Title>,
44 GameString,
45 RealmDifference,
46 )>, }
48
49impl Timeline {
50 pub fn new(
52 lifespans: Vec<(GameRef<Title>, Vec<(i16, i16)>)>,
53 latest_event: i16,
54 events: Vec<(
55 i16,
56 GameRef<Character>,
57 GameRef<Title>,
58 GameString,
59 RealmDifference,
60 )>,
61 ) -> Self {
62 Self {
63 lifespans,
64 latest_event,
65 events,
66 }
67 }
68}
69
70impl GameObjectDerived for Timeline {
71 fn get_name(&self) -> GameString {
72 GameString::from("Timeline")
73 }
74
75 fn get_references<E: From<EntityRef>, C: Extend<E>>(&self, collection: &mut C) {
76 for (title, _) in &self.lifespans {
77 collection.extend([E::from(title.clone().into())]);
78 }
79
80 for (_, char, _, _, difference) in &self.events {
81 collection.extend([E::from(char.clone().into())]);
82 match difference {
83 RealmDifference::Faith(f) => collection.extend([E::from(f.clone().into())]),
84 RealmDifference::Culture(c) => collection.extend([E::from(c.clone().into())]),
85 }
86 }
87 }
88}
89
90impl GetPath for Timeline {
91 fn get_path(&self, path: &Path) -> PathBuf {
92 path.join("timeline.html")
93 }
94}
95
96impl Renderable for Timeline {
97 fn get_template() -> &'static str {
98 TIMELINE_TEMPLATE_NAME
99 }
100
101 fn render(&self, path: &Path, _: &GameState, grapher: Option<&Grapher>, _: &GameData) {
102 if grapher.is_some() {
103 create_timeline_graph(
104 &self.lifespans,
105 self.latest_event,
106 path.join("timeline.svg"),
107 );
108 }
109 }
110}