aoe2_probe/tweak/
effect.rs

1use crate::{
2    parse::{Censor, Token},
3    prebuilt::{ver1_46, EffectConfig, EFFECT_SCHEME},
4    AttrTweak, Scenario,
5};
6
7pub struct EffectTweak;
8
9impl EffectTweak {
10    pub fn translate(
11        scenario: &Scenario,
12        effect: &Token,
13    ) -> Result<(String, String), &'static str> {
14        let version = scenario.version();
15        match version {
16            "1.46" | "1.47" => {
17                Self::is_effect(effect, version)?;
18
19                let type_id = *effect.get_by_path("/effect_type").try_i32();
20                if type_id >= 0 && type_id < EFFECT_SCHEME.len() as i32 {
21                    let scheme = &EFFECT_SCHEME[type_id as usize];
22                    let name = scheme.name.to_string();
23                    let attrs: Vec<String> = scheme
24                        .attrs
25                        .iter()
26                        .map(|&path| match path {
27                            "message" | "sound_name" => {
28                                format!(
29                                    "{}: {}",
30                                    path,
31                                    effect.get_by_path(path).try_str32().content()
32                                )
33                            }
34                            "class" | "quantity" => {
35                                format!("{}: {}", path, effect.get_by_path(path).try_i16())
36                            }
37                            "selected_object_ids" => {
38                                format!("{}: {:?}", path, effect.get_by_path(path).try_vec())
39                            }
40                            "object_attributes" => {
41                                let attr_id = effect.get_by_path(path).try_i32();
42                                let content = AttrTweak::translate(attr_id, version).unwrap();
43                                format!("{}: {}", path, content)
44                            }
45                            _ => {
46                                format!("{}: {}", path, effect.get_by_path(path).try_i32())
47                            }
48                        })
49                        .collect();
50
51                    Ok((name, attrs.join(" ")))
52                } else {
53                    Ok(("Unknown Effect!".to_string(), "".to_string()))
54                }
55            }
56            _ => Err("Incompatible version!"),
57        }
58    }
59
60    pub fn scheme(version: &str, effect: &Token) -> Result<&'static EffectConfig, &'static str> {
61        match version {
62            "1.46" | "1.47" => {
63                Self::is_effect(effect, version)?;
64
65                let type_id = *effect.get_by_path("/effect_type").try_i32();
66                if type_id >= 0 && type_id < EFFECT_SCHEME.len() as i32 {
67                    let scheme = &EFFECT_SCHEME[type_id as usize];
68
69                    Ok(scheme)
70                } else {
71                    Err("Unknown Effect!")
72                }
73            }
74            _ => Err("Incompatible version!"),
75        }
76    }
77
78    pub fn is_effect(effect: &Token, version: &str) -> Result<(), &'static str> {
79        match version {
80            "1.46" | "1.47" => {
81                let template = ver1_46::Effect::template();
82                let res = Censor::is_template(effect, &template, 2);
83
84                if res {
85                    Ok(())
86                } else {
87                    Err("Not a effect!")
88                }
89            }
90            _ => Err("Incompatible version!"),
91        }
92    }
93}