Skip to main content

rustial_engine/layers/
mod.rs

1//! Layer system for the map engine.
2
3mod background_layer;
4mod dynamic_image_overlay_layer;
5mod hillshade_layer;
6mod image_overlay_layer;
7mod model_layer;
8mod tile_layer;
9mod vector_layer;
10
11pub use background_layer::BackgroundLayer;
12pub use dynamic_image_overlay_layer::{
13    CallbackFrameProvider, DynamicImageOverlayLayer, FrameData, FrameProvider, FrameProviderFactory,
14};
15pub use hillshade_layer::{HillshadeLayer, HillshadeParams};
16pub use image_overlay_layer::{ImageOverlayData, ImageOverlayLayer};
17pub use model_layer::ModelLayer;
18pub use tile_layer::TileLayer;
19pub use vector_layer::{
20    CircleInstanceData, FeatureProvenance, LineCap, LineJoin, PatternImage, VectorLayer,
21    VectorMeshData, VectorRenderMode, VectorStyle,
22};
23
24/// An ordered stack of map layers, rendered bottom-to-top.
25pub struct LayerStack {
26    layers: Vec<Box<dyn crate::layer::Layer>>,
27}
28
29impl LayerStack {
30    /// Create an empty layer stack.
31    pub fn new() -> Self {
32        Self { layers: Vec::new() }
33    }
34
35    /// Create a layer stack from an existing vector of layers.
36    pub fn from_vec(layers: Vec<Box<dyn crate::layer::Layer>>) -> Self {
37        Self { layers }
38    }
39
40    /// Add a layer on top of the stack.
41    pub fn push(&mut self, layer: Box<dyn crate::layer::Layer>) {
42        self.layers.push(layer);
43    }
44
45    /// Insert a layer at a specific index (0 = bottom).
46    pub fn insert(&mut self, index: usize, layer: Box<dyn crate::layer::Layer>) {
47        let idx = index.min(self.layers.len());
48        self.layers.insert(idx, layer);
49    }
50
51    /// Remove a layer by index. Returns it if valid.
52    pub fn remove(&mut self, index: usize) -> Option<Box<dyn crate::layer::Layer>> {
53        if index < self.layers.len() {
54            Some(self.layers.remove(index))
55        } else {
56            None
57        }
58    }
59
60    /// Remove a layer by name. Returns it if found.
61    pub fn remove_by_name(&mut self, name: &str) -> Option<Box<dyn crate::layer::Layer>> {
62        if let Some(idx) = self.layers.iter().position(|l| l.name() == name) {
63            Some(self.layers.remove(idx))
64        } else {
65            None
66        }
67    }
68
69    /// Move a layer up (toward the top of the stack / rendered last).
70    ///
71    /// Returns `true` if the layer was moved.
72    pub fn move_up(&mut self, index: usize) -> bool {
73        if index + 1 < self.layers.len() {
74            self.layers.swap(index, index + 1);
75            true
76        } else {
77            false
78        }
79    }
80
81    /// Move a layer down (toward the bottom of the stack / rendered first).
82    ///
83    /// Returns `true` if the layer was moved.
84    pub fn move_down(&mut self, index: usize) -> bool {
85        if index > 0 && index < self.layers.len() {
86            self.layers.swap(index, index - 1);
87            true
88        } else {
89            false
90        }
91    }
92
93    /// Find a layer by name and return its index.
94    pub fn index_of(&self, name: &str) -> Option<usize> {
95        self.layers.iter().position(|l| l.name() == name)
96    }
97
98    /// Get a layer by index.
99    pub fn get(&self, index: usize) -> Option<&dyn crate::layer::Layer> {
100        self.layers.get(index).map(|l| l.as_ref())
101    }
102
103    /// Get a layer mutably by index.
104    pub fn get_mut(&mut self, index: usize) -> Option<&mut Box<dyn crate::layer::Layer>> {
105        self.layers.get_mut(index)
106    }
107
108    /// Number of layers.
109    pub fn len(&self) -> usize {
110        self.layers.len()
111    }
112
113    /// Whether there are no layers.
114    pub fn is_empty(&self) -> bool {
115        self.layers.is_empty()
116    }
117
118    /// Iterate layers bottom-to-top.
119    pub fn iter(&self) -> impl Iterator<Item = &dyn crate::layer::Layer> + '_ {
120        self.layers.iter().map(|l| l.as_ref())
121    }
122
123    /// Iterate layers mutably.
124    pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, Box<dyn crate::layer::Layer>> {
125        self.layers.iter_mut()
126    }
127}
128
129impl Default for LayerStack {
130    fn default() -> Self {
131        Self::new()
132    }
133}