State Management
Relevant source files
The following files were used as context for generating this wiki page:
State management in the AVP Supercars application is primarily handled through React's local state hooks (useState), memoization hooks (useMemo), and side-effect hooks (useEffect). The architecture follows a decentralized approach where state is managed close to the components that require it, such as form handling, UI toggles, and data filtering.
The application leverages the "lifting state up" pattern in certain modules, such as the fleet gallery, where a parent container manages the list of displayed vehicles while a child component handles the filtering logic. Interactive elements also utilize Framer Motion's internal state management for parallax effects and scroll-based animations.
Component-Level State
Most functional components manage their own local state to handle user interactions and UI transitions.
UI and Navigation State
The Navbar component manages the visibility of the mobile menu and the styling of the header based on the user's scroll position.
- Scrolled State: A boolean tracking if the user has scrolled beyond a specific threshold (12px) to transition the header from transparent to a blurred background.
- Menu Toggle: Controls the
AnimatePresencefor the mobile navigation overlay. - Body Overflow: A side effect synchronizes the
document.body.style.overflowwith the menu state to prevent background scrolling when the menu is open.
Sources: components/Navbar.tsx:24-34
Request Form State
The RequestForm component utilizes a complex object-based state to track multiple input fields for car rental requests. It uses a FormState type to ensure type safety across the application.
| Field | Type | Description |
|---|---|---|
name | string | Full name of the requester |
phone | string | Contact phone number |
email | string | User email address |
car | string | Selected car model (defaults from props) |
startDate | string | Rental start date |
endDate | string | Rental end date |
location | string | Delivery destination |
message | string | Additional request details |
Sources: components/RequestForm.tsx:5-26
Filtering and Data Flow
The Fleet module implements a reactive filtering system where user input dynamically updates the displayed list of vehicles. This involves a parent-child relationship between FleetPage and FleetFilters.
Data Flow Diagram
The following diagram illustrates how filtering state flows from user input through the filter component back to the main page display.
The diagram shows the unidirectional data flow where the child component calculates the filtered set and notifies the parent.
Sources: app/fleet/page.tsx:16-21, components/FleetFilters.tsx:32-35
Filtering Logic
The FleetFilters component maintains local state for the search query (q) and category selection (cat). It uses useMemo to perform the filtering operation whenever these states or the base items change, preventing unnecessary recalculations during unrelated re-renders.
const filtered = useMemo(() => {
const query = q.trim().toLowerCase();
return items.filter((c) => {
const matchesCat = cat === "All" ? true : c.category === cat;
const matchesQ = !query || `${c.brand} ${c.model} ${c.tagline}`.toLowerCase().includes(query);
return matchesCat && matchesQ;
});
}, [items, q, cat]);
Sources: components/FleetFilters.tsx:18-30
Visual and Motion State
The application utilizes framer-motion to manage state related to scroll progress and animations. This is particularly evident in the Hero sections of various pages.
Scroll-Linked State
Pages like the Home and Locations views use useScroll to create a scrollYProgress value (0 to 1). This value is then mapped to CSS properties via useTransform.
- Parallax: Maps scroll progress to vertical displacement (
y) and scale. - Opacity: Gradually fades out hero content as the user scrolls down the page.
- Accessibility: Utilizes
useReducedMotionto conditionally disable or simplify these state-driven transforms for users with motion sensitivities.
Sources: app/page.tsx:18-32, app/locations/page.tsx:14-25
Communication State
Communication with external services (WhatsApp and Email) is handled through derived state rather than persistent storage. The RequestForm uses useMemo to generate URI-encoded strings based on the current form state.
This flow ensures that the generated links always reflect the most recent data entered by the user.
Sources: components/RequestForm.tsx:36-63
Summary
State management in the project is lightweight and component-centric. By utilizing React's built-in hooks and Framer Motion's motion values, the application maintains a responsive UI without the overhead of global state libraries. Key logic is encapsulated within specific functional areas: navigation toggles in Navbar, complex user input in RequestForm, and data transformation in FleetFilters.