This commit is contained in:
Mitchell Marino 2024-06-12 16:46:03 -05:00
parent 1e2709dc8c
commit 079c9bde53
4 changed files with 26 additions and 30 deletions

View File

@ -4,10 +4,12 @@ use leptos::RwSignal;
use std::rc::Rc;
use web_sys::MouseEvent;
type ButtonAction<FD> = dyn Fn(MouseEvent, &mut FD);
#[derive(Clone)]
pub struct ButtonData<FD: FormToolData> {
pub(crate) text: String,
pub(crate) action: Option<Rc<dyn Fn(MouseEvent, &mut FD)>>,
pub(crate) action: Option<Rc<ButtonAction<FD>>>,
}
impl<FD: FormToolData> Default for ButtonData<FD> {
fn default() -> Self {

View File

@ -15,7 +15,7 @@ impl<FD: FormToolData, FS: FormStyle> FormBuilder<FD, FS> {
let (views, validation_cbs): (Vec<_>, Vec<_>) = group_builder
.render_fns
.into_iter()
.map(|r_fn| r_fn(&fs, fd))
.map(|r_fn| r_fn(fs, fd))
.unzip();
let view = fs.group(super::ControlRenderData {

View File

@ -1,8 +1,8 @@
use crate::{
controls::{
BuiltControlData, BuiltVanityControlData, ControlBuilder, ControlData, ControlRenderData,
FieldGetter, FieldSetter, ParseFn, RenderFn, UnparseFn, ValidationCb, ValidationFn,
VanityControlBuilder, VanityControlData,
FieldSetter, ParseFn, RenderFn, ValidationCb, ValidationFn, VanityControlBuilder,
VanityControlData,
},
form::{Form, FormToolData, FormValidator},
styles::FormStyle,
@ -87,33 +87,17 @@ impl<FD: FormToolData, FS: FormStyle> FormBuilder<FD, FS> {
&mut self,
control: ControlBuilder<FD, FS, C, FDT>,
) {
let BuiltControlData {
render_data,
getter,
setter,
parse_fn,
unparse_fn,
validation_fn,
} = match control.build() {
let built_control_data = match control.build() {
Ok(c) => c,
Err(e) => panic!("Invalid Component: {}", e),
};
if let Some(ref validation_fn) = validation_fn {
if let Some(ref validation_fn) = built_control_data.validation_fn {
self.validations.push(validation_fn.clone());
}
let render_fn = move |fs: &FS, fd: RwSignal<FD>| {
let (view, cb) = Self::build_control_view(
fd,
fs,
getter,
setter,
unparse_fn,
parse_fn,
validation_fn,
render_data,
);
let (view, cb) = Self::build_control_view(fd, fs, built_control_data);
(view, Some(cb))
};
@ -123,13 +107,17 @@ impl<FD: FormToolData, FS: FormStyle> FormBuilder<FD, FS> {
fn build_control_view<C: ControlData, FDT: 'static>(
fd: RwSignal<FD>,
fs: &FS,
getter: Rc<dyn FieldGetter<FD, FDT>>,
setter: Rc<dyn FieldSetter<FD, FDT>>,
unparse_fn: Box<dyn UnparseFn<<C as ControlData>::ReturnType, FDT>>,
parse_fn: Box<dyn ParseFn<<C as ControlData>::ReturnType, FDT>>,
validation_fn: Option<Rc<dyn ValidationFn<FD>>>,
render_data: crate::controls::ControlRenderData<FS, C>,
control_data: BuiltControlData<FD, FS, C, FDT>,
) -> (View, Box<dyn ValidationCb>) {
let BuiltControlData {
render_data,
getter,
setter,
parse_fn,
unparse_fn,
validation_fn,
} = control_data;
let (validation_signal, validation_signal_set) = create_signal(Ok(()));
let validation_fn_clone = validation_fn.clone();
let value_getter = move || {

View File

@ -1,6 +1,12 @@
use crate::{controls::ValidationFn, FormToolData};
use std::fmt::Display;
/// A function that validates a field.
///
/// This is similar to [`ValidationFn`](crate::controls::ValidationFn)
/// but takes a &str for the name of the field for improved error messages.
type ValidationBuilderFn<T> = dyn Fn(&str, &T) -> Result<(), String> + 'static;
/// A helper builder that allows you to specify a validation function
/// declaritivly
///
@ -14,7 +20,7 @@ pub struct ValidationBuilder<FD: FormToolData, T: 'static> {
/// The getter function for the field to validate.
field_fn: Box<dyn Fn(&FD) -> &T + 'static>,
/// The functions to be called when validating.
functions: Vec<Box<dyn Fn(&str, &T) -> Result<(), String> + 'static>>,
functions: Vec<Box<ValidationBuilderFn<T>>>,
}
impl<FD: FormToolData, T: 'static> ValidationBuilder<FD, T> {