feat: create new header component

This component is now required for forms.
This commit is contained in:
alphafetus committed 2026-01-12 16:14:24 -05:00
1 parent 5d72a8f949
commit 14d89fc696
7 files changed
+76 -13

No files matched your search

+40
View File
@@ -0,0 +1,40 @@
use leptos::prelude::*;
/// # Header Component
///
/// A simple header that may also contain a description. Should be used to annotate sections and
/// forms, with extra information about how that section/form will work.
///
/// Example usage:
/// ```
/// view! {
/// <Header
/// title: "Example header"
/// description: "Example description"
/// />
/// }
/// ```
#[component]
pub fn Header(
/// The title of the header. Must always be present.
#[prop(into)] title: Signal<String>,
/// The description of the header. Hidden when nothing i s
#[prop(optional, into)] description: Signal<String>,
) -> impl IntoView {
let show_description = Signal::derive(move || {
!description.get().is_empty()
});
view! {
<div class="m-1.5 mb-5">
<div class="text-3xl font-bold">
{title}
</div>
<Show when=move || show_description.get()>
<div>
{description}
</div>
</Show>
</div>
}
}
+2 -1
View File
@@ -10,9 +10,10 @@ mod utils;
mod validated_form; mod validated_form;
mod lists; mod lists;
mod toasts; mod toasts;
mod header;
pub use self::{ pub use self::{
action_button::*, banner::*, dashboard_button::*, lists::*, action_button::*, banner::*, dashboard_button::*, lists::*,
loading::*, multi_entry::*, panel::*, row::*, text_field::*, loading::*, multi_entry::*, panel::*, row::*, text_field::*,
validated_form::*, toasts::* validated_form::*, toasts::*, header::*
}; };
+14 -2
View File
@@ -1,7 +1,7 @@
use leptos::logging::log; use leptos::logging::log;
use leptos::prelude::*; use leptos::prelude::*;
use leptos::web_sys::SubmitEvent; use leptos::web_sys::SubmitEvent;
use crate::components::ActionButton; use crate::components::{ActionButton, Header};
/// Indicates the current state of an input. /// Indicates the current state of an input.
#[derive(Default, Debug, Clone)] #[derive(Default, Debug, Clone)]
@@ -71,7 +71,11 @@ pub fn use_validation_context() -> Option<FormValidationRegistry> {
/// Example usage in the view macro: /// Example usage in the view macro:
/// ``` /// ```
/// view! { /// view! {
/// <ValidatedForm on_submit=Callback::new(move || {/* something here */})> /// <ValidatedForm
/// on_submit=Callback::new(move || {/* something here */})
/// title="Example Title"
/// description="Example description."
/// >
/// {/* As many input components as you want */} /// {/* As many input components as you want */}
/// </ValidatedForm> /// </ValidatedForm>
/// } /// }
@@ -102,6 +106,10 @@ pub fn ValidatedForm(
children: Children, children: Children,
/// A callback that runs when the form successfully validates. /// A callback that runs when the form successfully validates.
#[prop(into)] on_submit: Callback<()>, #[prop(into)] on_submit: Callback<()>,
/// The title of the included header.
#[prop(into)] title: Signal<String>,
/// The description for the included header.
#[prop(optional, into)] description: Signal<String>,
) -> impl IntoView { ) -> impl IntoView {
let validators = RwSignal::new(vec![]); let validators = RwSignal::new(vec![]);
@@ -142,6 +150,10 @@ pub fn ValidatedForm(
view! { view! {
<form novalidate on:submit=submit_success_event> <form novalidate on:submit=submit_success_event>
<Header
title=title
description=description
/>
{children()} {children()}
<ActionButton <ActionButton
on:click=move |_| { on:click=move |_| {
+5 -1
View File
@@ -245,7 +245,11 @@ pub fn HomePage() -> impl IntoView {
<Row> <Row>
<div class="flex flex-col flex-1" /> <div class="flex flex-col flex-1" />
<Panel> <Panel>
<ValidatedForm on_submit=Callback::new(on_submit)> <ValidatedForm
on_submit=Callback::new(on_submit)
title="Home Page Test Form"
description="This really is just a test."
>
<Row> <Row>
<h1 class="text-3xl font-bold"> <h1 class="text-3xl font-bold">
"Region 15 Scholarship Application (DEMO)" "Region 15 Scholarship Application (DEMO)"
+5 -5
View File
@@ -275,11 +275,11 @@ pub fn LoanerBorrowForm() -> impl IntoView {
//#endregion //#endregion
view! { view! {
<ValidatedForm on_submit=Callback::new(on_submit)> <ValidatedForm
<div class="flex flex-col justify-center gap-2 mb-1 py-3 px-2"> on_submit=Callback::new(on_submit)
<h2 class="text-2xl font-bold">"Borrower Information"</h2> title="Borrower Information"
<p class="text-lg">"Please fill out the form below."</p> description="Please fill out the form below."
</div> >
<Row> <Row>
<OutlinedTextField <OutlinedTextField
label="First Name:" label="First Name:"
+5 -1
View File
@@ -144,7 +144,11 @@ pub fn ProviderContactPage() -> impl IntoView {
<div class="flex flex-row"> <div class="flex flex-row">
<div class="flex flex-col flex-1" /> <div class="flex flex-col flex-1" />
<Panel> <Panel>
<ValidatedForm on_submit=on_submit> <ValidatedForm
on_submit=on_submit
title="Contact Form"
description="Enter your contact information and click submit."
>
{move || { {move || {
contact_resource contact_resource
.get() .get()
+5 -3
View File
@@ -505,9 +505,11 @@ fn ScholarshipForm(
} }
> >
<Suspense fallback=Loading> <Suspense fallback=Loading>
<ValidatedForm on_submit=Callback::new( <ValidatedForm
on_submit, on_submit=Callback::new(on_submit)
)> title="Scholarship Info Form"
description="Create or edit a scholarship. Input all information and click Submit."
>
{move || { {move || {
scholarship_info scholarship_info
.get() .get()