Skip to main content

vertigo_forms/resource_table/
row_from_data_section.rs

1use vertigo::{DomNode, css, dom};
2
3use crate::{
4    form::{DataSection, Field},
5    resource_table::{base_row_css, normal_col_css},
6};
7
8/// Renders a single row in a `ResourceTable` using a `DataSection`.
9///
10/// This function simplifies building editable table rows by leveraging `vertigo_forms::form::DataSection`
11/// to automatically render form fields based on the section's definition.
12///
13/// # Arguments
14///
15/// * `section` - A reference to the `DataSection` containing the row's form fields.
16/// * `buttons` - A `DomNode` containing the action buttons (e.g., Save, Cancel) to render in the last column.
17/// * `grid_template_columns` - A string specifying the CSS `grid-template-columns` property to align the
18///   row's cells with the table header (e.g., `"50px 1fr 100px 150px"`).
19///
20/// # Example
21///
22/// ```rust,ignore
23/// render_row_form: |form: &Rc<DataSection>, buttons| {
24///     row_from_data_section(form, buttons, "50px 1fr 100px 150px")
25/// }
26/// ```
27pub fn row_from_data_section(
28    section: &DataSection,
29    buttons: DomNode,
30    grid_template_columns: &str,
31) -> DomNode {
32    let fields: Vec<DomNode> = section
33        .fields
34        .iter()
35        .map(|field| {
36            dom! { <Field {field} /> }
37        })
38        .collect();
39
40    let error_node = section.error.as_ref().map(|err| {
41        dom! { <span css={css! {"color: red; font-size: 0.8rem;"}}>{err}</span> }
42    });
43
44    dom! {
45        <div css={base_row_css() + css! {"grid-template-columns: {grid_template_columns};"}}>
46            <div css={normal_col_css()}>{section.label.clone()}</div>
47            {..fields}
48            {..error_node}
49            <div>{buttons}</div>
50        </div>
51    }
52}