Skip to main content

workflow_html/
interface.rs

1use crate::WebElement;
2use crate::render::{Render, Renderables};
3pub use crate::utils::{Element, ElementResult, document};
4use std::collections::BTreeMap;
5/// Map of `@name`-tagged element bindings keyed by their declared name.
6pub type Hooks = BTreeMap<String, Element>;
7//use workflow_log::log_trace;
8
9/// The result of rendering an HTML template: the live DOM root elements, the
10/// map of `@name`-tagged hook elements, and the retained Rust renderables that
11/// keep elements and callbacks alive for the lifetime of this structure.
12#[derive(Clone)]
13pub struct Html {
14    /// The top-level DOM elements produced by the template.
15    pub roots: Vec<Element>,
16    /// Map of `@name`-tagged elements available for external binding.
17    pub hooks: Hooks,
18    /// Retained renderables that keep DOM elements and Rust state alive.
19    pub renderables: Renderables,
20}
21
22impl Html {
23    /// Constructs an [`Html`] from its rendered root elements, hooks map and
24    /// retained renderables.
25    pub fn new(roots: Vec<Element>, hooks: Hooks, renderables: Renderables) -> ElementResult<Html> {
26        let html = Html {
27            roots,
28            hooks,
29            renderables,
30        };
31        Ok(html)
32    }
33
34    /// Returns the top-level DOM elements produced by the template.
35    pub fn roots(&self) -> &Vec<Element> {
36        &self.roots
37    }
38
39    /// Returns the map of `@name`-tagged elements available for external binding.
40    pub fn hooks(&self) -> &Hooks {
41        &self.hooks
42    }
43
44    /// Appends each root element into the given parent DOM `element`.
45    pub fn inject_into(&self, element: &Element) -> ElementResult<()> {
46        for root in self.roots.iter() {
47            element.append_child(root)?;
48        }
49        Ok(())
50    }
51    /// Removes all event listeners from every retained renderable, releasing
52    /// their closures.
53    pub fn remove_event_listeners(&self) -> ElementResult<()> {
54        for root in &self.renderables {
55            root.remove_event_listeners()?;
56        }
57        Ok(())
58    }
59}
60
61impl Render for Html {
62    fn render_node(
63        mut self,
64        parent: &mut WebElement,
65        map: &mut Hooks,
66        renderables: &mut Renderables,
67    ) -> ElementResult<()> {
68        renderables.append(self.renderables.as_mut());
69        let mut hooks = self.hooks().clone();
70        map.append(&mut hooks);
71        self.inject_into(parent)?;
72        Ok(())
73    }
74
75    fn render(&self, _w: &mut Vec<String>) -> ElementResult<()> {
76        Ok(())
77    }
78
79    fn remove_event_listeners(&self) -> ElementResult<()> {
80        for root in &self.renderables {
81            root.remove_event_listeners()?;
82        }
83        Ok(())
84    }
85}
86
87/*
88impl Drop for Html{
89    fn drop(&mut self) {
90        log_trace!("HTML Drop: {:?}", self.roots[0].get_attribute("class"));
91    }
92}
93*/