waterui-form
A comprehensive form building system for WaterUI applications with automatic component generation, validation, and secure data handling.
Overview
waterui-form provides an ergonomic, type-safe approach to building interactive forms in WaterUI applications. The crate centers around the FormBuilder trait, which enables automatic mapping from Rust data structures to platform-native UI components. It includes specialized pickers (color, date, multi-date), secure input handling with automatic memory zeroing, and a flexible validation system.
Key features:
- Automatic form generation via
#[derive(FormBuilder)]macro - Type-to-component mapping - primitives automatically map to appropriate controls
- Field labels from field names -
user_namebecomes "User Name" - Placeholder text from doc comments - documentation becomes UI hints
- Secure data handling - password fields with bcrypt hashing and memory zeroing
- Validation system - composable validators with error messages
- Specialized pickers - color, date/time, and multi-date selection
- Reactive bindings - forms automatically update when data changes
This crate is part of the WaterUI workspace and integrates tightly with waterui-core for reactivity, waterui-controls for base components, and waterui-layout for composition.
Installation
Add to your Cargo.toml:
[]
= "0.1.0"
# Optional: enable serde support
= { = "0.1.0", = ["serde"] }
Quick Start
The most common use case is deriving FormBuilder on a struct:
use *;
use ;
This generates a vertical stack with:
- A text field labeled "Name" with placeholder "Enter your full name"
- A stepper labeled "Age" with placeholder "Your current age"
- A toggle labeled "Active" with placeholder "Account is active"
Core Concepts
FormBuilder Trait
The FormBuilder trait is the foundation of the form system. It maps Rust types to UI components:
| Rust Type | UI Component | Description |
|---|---|---|
String, Str |
TextField |
Single-line text input with optional placeholder |
bool |
Toggle |
Boolean switch/checkbox |
i32 |
Stepper |
Integer stepper with +/- buttons |
f32, f64 |
Slider |
Numeric slider (0.0-1.0 range by default) |
Color |
ColorPicker |
Platform-native color selection |
Date |
DatePicker |
Date/time selection (requires time crate types) |
BTreeSet<Date> |
MultiDatePicker |
Multiple date selection |
Secure |
SecureField |
Masked password input with memory zeroing |
The #[derive(FormBuilder)] Macro
The derive macro automatically implements FormBuilder by:
- Converting field names to labels:
user_name→ "User Name" - Extracting doc comments as placeholders:
/// Enter emailbecomes placeholder text - Mapping field types to components: Uses the table above
- Arranging fields in a VStack: Creates a vertical layout of all fields
The macro requires the struct to have named fields and generates an implementation compatible with the Project trait for field-level reactive bindings.
Reactive Bindings and Project
Forms use Binding<T> from the nami crate for reactive state. The Project trait (auto-derived alongside FormBuilder) allows accessing individual field bindings:
let form_binding = binding;
let projected = form_binding.project;
// Access individual field bindings
projected.name.set;
projected.age.set;
// Read entire form state
let profile = form_binding.get;
Examples
Pre-filled Form Data
Initialize a form with existing data instead of defaults:
use *;
use ;
Displaying Form Values Reactively
Use projected bindings to display live form data:
use *;
use ;
Secure Password Input
Use SecureField for sensitive data with automatic memory zeroing:
use *;
use ;
The Secure type:
- Implements
Zeroizeto clear memory on drop - Has
Debugimpl that printsSecure(****)instead of the actual value - Provides
hash()method using bcrypt with default cost - Use
expose()to access the underlying string when needed
Form Validation
Compose validators to enforce rules on form fields:
use *;
use ;
use Regex;
Validators can be combined:
.and(other)- both must succeed.or(other)- at least one must succeed
Built-in validators:
Range<T>- validates value is within rangeRegex- validates string matches patternRequired- validatesOption<T>isSomeor string is non-empty
Date Picker
Use DatePicker for date and time selection:
use *;
use ;
use Date;
Available picker types:
DatePickerType::Date- Date onlyDatePickerType::HourAndMinute- Time only (hour:minute)DatePickerType::HourMinuteAndSecond- Time with secondsDatePickerType::DateHourAndMinute- Date and time (default)DatePickerType::DateHourMinuteAndSecond- Date and time with seconds
Color Picker
Use ColorPicker for platform-native color selection:
use *;
use ColorPicker;
use Color;
Multi-Date Selection
Use MultiDatePicker for selecting multiple dates:
use *;
use MultiDatePicker;
use BTreeSet;
use Date;
Manual FormBuilder Implementation
For custom layouts or specialized behavior, implement FormBuilder manually:
use *;
use FormBuilder;
API Overview
Core Types
FormBuilder- Trait for types that can render as form UIform()- Function to create a form view from aBinding<T: FormBuilder>
Secure Module
Secure- Wrapper type for sensitive strings with automatic memory zeroingSecureField- Password input componentsecure()- Helper function to create aSecureField
Picker Module
Picker- Generic picker for selecting from a listColorPicker- Platform-native color selectionDatePicker- Date and time selection with multiple stylesMultiDatePicker- Multiple date selectionPickerItem<T>- Type alias for picker items (TaggedView<T, Text>)
Validation Module
Validatable- Trait for views that can be validatedValidator<T>- Trait for value validation logicValidatableView<V, T>- Wraps a view with a validatorAnd<A, B>- Combines validators with logical ANDOr<A, B>- Combines validators with logical ORRequired- Validator for required fieldsOutOfRange<T>- Error type for range validationNotMatch- Error type for regex validation
Features
Default Features
None. The crate works out-of-the-box with no feature flags.
Optional Features
serde- EnablesSerializeandDeserializederives on form types= { = "0.1.0", = ["serde"] }
Workspace Dependencies
waterui-core- ProvidesViewtrait,Binding,Environment, andAnyViewwaterui-controls- Base components (TextField,Toggle,Stepper,Slider,Button)waterui-layout- Layout primitives (VStack,HStack,ZStack)waterui-text- Text rendering componentswaterui-color- Color type used byColorPicker
External Dependencies
nami- Fine-grained reactivity system (providesBinding,Computed)time- Date/time types forDatePickerzeroize- Secure memory zeroing forSecuretypebcrypt- Password hashing forSecure::hash()regex- Pattern matching for validation
Derive Macros
The FormBuilder derive macro is provided by waterui-macros, which is automatically included when using waterui::prelude::*.
Notes
- This crate is
#![no_std]compatible (usesextern crate alloc) - All code examples in this README are extracted from actual source code or documentation
- The crate follows WaterUI's layout contract system - see component source for detailed layout behavior
- Forms are rendered to native platform widgets (UIKit/AppKit on Apple, Android View on Android)