Modals
Modals are easy. Let us imagine the following urls:
/seats
- This shows a stadium map of available seats./seats/1
- This shows the status of a single seat as a modal over the mapof seats.
Visually, the only difference between the two pages is the modal. So we model our application as such.
In /seats/index.json.props
# Other index.json.props content here
...
json.seat_details do
json.show false
# empty
end
In /seats/show.json.props
# Other index.json.props content here
...
json.seat_details do
json.show true
# Add additional modal content here.
end
In packs/application.js
, change your component mapping to use your ShowIndex
component as your identifier's component:
const identifierToComponentMapping = {
'seats/index': SeatsIndex,
'seats/show': SeatsIndex,
};
and in Modal
component's render:
if (props.show) {
....render modal with `props.seatDetails`
} else {
return null;
}
and add a UJS visit attribute to get the SPA modal effect with history change and back button support!
In SeatsIndex.js
, change the a
tags like so.
<a
href="/seats/1"
data-bz-visit={true}
> Show Seat Modal </a>
Optimize it!
The above solution will load the entirety of the show.json.props
. That may not be what we want as some parts of the template may be slow.
Instead, we can make it more efficient by loading just the modal contents.
<a
href="/seats/1?bzq=data.seat"
data-bz-visit={true}
data-bz-placeholder="/seats"
> Show Seat Modal </a>
The change above uses Breezy's copy feature to
Copy the current page,
/seats
and use it as a placeholder for/seats/1
Navigate to that page optimistically (as defined in our
identifierToComponentMapping
)Query
show.json.props
and walk to thedata
node, then to theseat
node,and return that.
Immutably graft it to the placeholder in
/seats/1
in the same location.React will render with the modal contents.
Last updated
Was this helpful?