mf_model/
mark_type.rs

1use serde::Serialize;
2use serde_json::Value;
3use std::collections::HashMap;
4
5use crate::attrs::Attrs;
6
7use super::mark::Mark;
8use super::schema::{Attribute, AttributeSpec, compute_attrs};
9#[derive(Clone, PartialEq, Debug, Eq)]
10pub struct MarkType {
11    pub name: String,
12    pub rank: usize,
13    pub spec: MarkSpec,
14    pub attrs: HashMap<String, Attribute>,
15    pub excluded: Option<Vec<MarkType>>,
16}
17
18impl MarkType {
19    pub(crate) fn compile(
20        marks: HashMap<String, MarkSpec>
21    ) -> HashMap<String, MarkType> {
22        let mut result = HashMap::new();
23
24        for (rank, (name, spec)) in marks.into_iter().enumerate() {
25            result.insert(
26                name.clone(),
27                MarkType::new(name.clone(), rank, spec.clone()),
28            );
29        }
30
31        result
32    }
33
34    fn new(
35        name: String,
36        rank: usize,
37        spec: MarkSpec,
38    ) -> Self {
39        let attrs = spec.attrs.as_ref().map_or_else(HashMap::new, |attrs| {
40            attrs
41                .iter()
42                .map(|(name, spec)| {
43                    (name.clone(), Attribute::new(spec.clone()))
44                })
45                .collect()
46        });
47
48        MarkType { name, rank, spec, attrs, excluded: None }
49    }
50
51    pub fn create(
52        &self,
53        attrs: Option<&HashMap<String, Value>>,
54    ) -> Mark {
55        Mark { r#type: self.name.clone(), attrs: self.compute_attrs(attrs) }
56    }
57    pub fn compute_attrs(
58        &self,
59        attrs: Option<&HashMap<String, Value>>,
60    ) -> Attrs {
61        match attrs {
62            Some(attr) => compute_attrs(&self.attrs, Some(attr)),
63            None => compute_attrs(&self.attrs, None),
64        }
65    }
66
67    // 其他方法...
68}
69
70#[derive(Clone, PartialEq, Eq, Debug, Serialize, Default)]
71pub struct MarkSpec {
72    pub attrs: Option<HashMap<String, AttributeSpec>>,
73    pub excludes: Option<String>,
74    pub group: Option<String>,
75    pub spanning: Option<bool>,
76    pub desc: Option<String>,
77}