dampen_core/ir/
node.rs

1use crate::ir::layout::{Breakpoint, LayoutConstraints};
2use crate::ir::span::Span;
3use crate::ir::style::StyleProperties;
4use std::collections::HashMap;
5
6/// A node in the widget tree
7#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize, Default)]
8pub struct WidgetNode {
9    pub kind: WidgetKind,
10    pub id: Option<String>,
11    pub attributes: HashMap<String, AttributeValue>,
12    pub events: Vec<EventBinding>,
13    pub children: Vec<WidgetNode>,
14    pub span: Span,
15
16    // Styling extensions
17    pub style: Option<StyleProperties>,
18    pub layout: Option<LayoutConstraints>,
19    pub theme_ref: Option<String>,
20    pub classes: Vec<String>,
21    pub breakpoint_attributes: HashMap<Breakpoint, HashMap<String, AttributeValue>>,
22}
23
24/// Enumeration of all supported widget types
25#[derive(Debug, Clone, PartialEq, Eq, Hash, serde::Serialize, serde::Deserialize, Default)]
26pub enum WidgetKind {
27    #[default]
28    Column,
29    Row,
30    Container,
31    Scrollable,
32    Stack,
33    Text,
34    Image,
35    Svg,
36    Button,
37    TextInput,
38    Checkbox,
39    Slider,
40    PickList,
41    Toggler,
42    Space,
43    Rule,
44    Radio,
45    // Advanced widgets
46    ComboBox,
47    ProgressBar,
48    Tooltip,
49    Grid,
50    Canvas,
51    Float,
52    // Control flow
53    For,
54    Custom(String),
55}
56
57/// A value that can be either static or dynamically bound
58#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
59pub enum AttributeValue {
60    Static(String),
61    Binding(crate::expr::BindingExpr),
62    Interpolated(Vec<InterpolatedPart>),
63}
64
65impl Default for AttributeValue {
66    fn default() -> Self {
67        AttributeValue::Static(String::new())
68    }
69}
70
71/// Part of an interpolated string
72#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
73pub enum InterpolatedPart {
74    Literal(String),
75    Binding(crate::expr::BindingExpr),
76}
77
78impl Default for InterpolatedPart {
79    fn default() -> Self {
80        InterpolatedPart::Literal(String::new())
81    }
82}
83
84/// Attribute structures for advanced widgets
85#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
86pub struct ComboBoxAttributes {
87    pub options: Vec<String>,
88    pub selected: Option<crate::expr::BindingExpr>,
89    pub placeholder: Option<String>,
90    pub on_select: Option<String>,
91}
92
93#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
94pub struct PickListAttributes {
95    pub options: Vec<String>,
96    pub selected: Option<crate::expr::BindingExpr>,
97    pub placeholder: Option<String>,
98    pub on_select: Option<String>,
99}
100
101#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
102pub struct CanvasAttributes {
103    pub width: f32,
104    pub height: f32,
105    pub program: Option<crate::expr::BindingExpr>,
106    pub on_click: Option<String>,
107}
108
109#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
110pub struct ProgressBarAttributes {
111    pub min: Option<f32>,
112    pub max: Option<f32>,
113    pub value: crate::expr::BindingExpr,
114    pub style: Option<ProgressBarStyle>,
115}
116
117#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
118pub enum ProgressBarStyle {
119    Primary,
120    Success,
121    Warning,
122    Danger,
123    Secondary,
124}
125
126#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
127pub struct TooltipAttributes {
128    pub message: String,
129    pub position: Option<TooltipPosition>,
130    pub delay: Option<u64>,
131}
132
133#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
134pub enum TooltipPosition {
135    FollowCursor,
136    Top,
137    Bottom,
138    Left,
139    Right,
140}
141
142#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
143pub struct GridAttributes {
144    pub columns: u32,
145    pub spacing: Option<f32>,
146    pub padding: Option<f32>,
147}
148
149#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
150pub struct FloatAttributes {
151    pub position: Option<FloatPosition>,
152    pub offset_x: Option<f32>,
153    pub offset_y: Option<f32>,
154    pub z_index: Option<u32>,
155}
156
157#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
158pub enum FloatPosition {
159    TopLeft,
160    TopRight,
161    BottomLeft,
162    BottomRight,
163}
164
165/// An event binding from XML to a Rust handler
166#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize, Default)]
167pub struct EventBinding {
168    pub event: EventKind,
169    pub handler: String,
170    /// Optional parameter expression (e.g., for on_click="delete:{item.id}")
171    pub param: Option<crate::expr::BindingExpr>,
172    pub span: Span,
173}
174
175/// Supported event types
176#[derive(Debug, Clone, PartialEq, Eq, Hash, serde::Serialize, serde::Deserialize, Default)]
177pub enum EventKind {
178    #[default]
179    Click,
180    Press,
181    Release,
182    Change,
183    Input,
184    Submit,
185    Select,
186    Toggle,
187    Scroll,
188}