1use std::rc::Rc;
2use std::collections::HashMap;
3
4use dioxus::prelude::Callback;
5use dioxus::prelude::Element;
6use dioxus_signals::{Memo, ReadSignal, Signal};
7use indexmap::IndexMap;
8
9use hyle::{Blueprint, Field, FieldType, MutateInput, Outcome, Primitive, Query, Source, Value};
10use crate::adapter::{HyleDataState, FieldChange};
11pub(crate) const FORMA_MODEL: &str = "forma";
13pub type HyleFilterField = crate::adapter::HyleFilterField<Rc<dyn Fn(HyleFilterFieldProps) -> Element>>;
18
19pub type DioxusFieldChangeFn = Rc<dyn Fn(&Field) -> Option<FieldChange<Rc<dyn Fn(HyleFilterFieldProps) -> Element>>>>;
21
22pub type DioxusFieldChangeMap = HashMap<String, DioxusFieldChangeFn>;
24
25#[derive(Default)]
29pub struct UseFiltersOptions {
30 pub initial_committed: IndexMap<String, String>,
31 pub change: Option<DioxusFieldChangeMap>,
33}
34
35#[derive(Default)]
37pub struct UseFormOptions {
38 pub initial_committed: IndexMap<String, String>,
39 pub change: Option<DioxusFieldChangeMap>,
41}
42
43impl UseFormOptions {
44 pub fn with_change(
50 mut self,
51 key: &str,
52 f: impl Fn(&Field) -> Option<FieldChange> + 'static,
53 ) -> Self {
54 self.change
55 .get_or_insert_with(HashMap::new)
56 .insert(
57 key.to_owned(),
58 Rc::new(move |field: &Field| {
59 f(field).map(|fc| FieldChange {
60 field: fc.field,
61 render: None,
62 })
63 }),
64 );
65 self
66 }
67}
68
69#[derive(Clone, PartialEq)]
73pub enum HyleSourceState {
74 Loading,
75 Ready(Source),
76 Error(String),
77}
78
79pub type UseSource = ReadSignal<HyleSourceState>;
81
82#[derive(Clone, Copy, PartialEq)]
88pub struct HyleAdapter {
89 pub source: UseSource,
90 pub create: HyleMutation,
91 pub update: HyleMutation,
92 pub delete: HyleMutation,
93}
94
95#[derive(Clone, Copy, PartialEq)]
99pub struct HyleListState {
100 pub data: Memo<HyleDataState>,
101 pub query: Memo<Query>,
102 pub page: Signal<usize>,
103 pub per_page: Signal<usize>,
104 pub sort_field: Signal<Option<String>>,
105 pub sort_ascending: Signal<bool>,
106}
107
108#[derive(Clone)]
112pub struct HyleFilterFieldProps {
113 pub key: String,
114 pub label: String,
115 pub field: Field,
116 pub options: Option<Vec<(String, String)>>,
117 pub value: String,
118 pub set: Callback<String>,
119}
120
121#[derive(Clone, Copy, PartialEq)]
125pub struct HyleMutation {
126 pub mutate: Callback<MutateInput>,
127 pub reset: Callback<()>,
128 pub is_pending: Signal<bool>,
129 pub is_success: Signal<bool>,
130 pub error: Signal<Option<String>>,
131}
132
133#[derive(Clone, Default)]
137pub struct BoundMutateInput {
138 pub id: Option<Value>,
139 pub data: IndexMap<String, String>,
140}
141
142#[derive(Clone, Copy)]
144pub struct BoundMutation {
145 pub mutate: Callback<BoundMutateInput>,
146 pub is_pending: Signal<bool>,
147 pub is_success: Signal<bool>,
148 pub error: Signal<Option<String>>,
149}
150
151#[derive(Clone, Copy)]
153pub struct BoundMutations {
154 pub create: BoundMutation,
155 pub update: BoundMutation,
156 pub delete: BoundMutation,
157}
158
159#[derive(Clone, Copy, PartialEq)]
163pub struct HyleFiltersState {
164 pub query: Memo<Query>,
165 pub fields: Memo<Vec<HyleFilterField>>,
166 pub form_data: Signal<IndexMap<String, String>>,
167 pub set_field: Callback<(String, String)>,
168 pub filter_apply: Callback<()>,
169 pub filter_clear: Callback<()>,
170 pub filter_reset_key: Signal<u32>,
171}
172
173#[derive(Clone)]
177pub struct HyleValueProps {
178 pub key: String,
179 pub field: Field,
180 pub value: Value,
181 pub outcome: Outcome,
182 pub model_name: String,
183 pub blueprint: Blueprint,
184 pub components: Option<HyleComponents>,
185}
186
187#[derive(Clone, Default)]
189pub struct HyleComponents {
190 pub values: indexmap::IndexMap<String, fn(HyleValueProps) -> Element>,
191 pub filters: indexmap::IndexMap<String, fn(HyleFilterFieldProps) -> Element>,
192}
193
194pub fn field_type_key(field_type: &FieldType) -> &'static str {
196 match field_type {
197 FieldType::Primitive { primitive } => match primitive {
198 Primitive::String => "string",
199 Primitive::Number => "number",
200 Primitive::Boolean => "boolean",
201 Primitive::File => "file",
202 },
203 FieldType::Reference { .. } => "reference",
204 FieldType::Array { .. } => "array",
205 FieldType::Shape { .. } => "shape",
206 }
207}
208
209#[derive(Clone, Copy, PartialEq)]
213pub struct HyleFormState {
214 pub filters: HyleFiltersState,
215 pub is_edit: bool,
216 pub is_valid: bool,
217 pub on_submit: Callback<()>,
218 pub mutation: HyleMutation,
219}