Going Fullscreen
Every camera tile and every Location View panel can go fullscreen — a big view of the camera with a toolbar for switching between the 60° image, the 360° pano, the map, and timelapse playback. Simple feature, but there's one conceptual snag worth learning properly, because it confuses everyone: the app has two different definitions of "fullscreen," and both are true.
The two fullscreen signals
Signal 1: expandedCameraId. One field in mapCameraInteractiveStore — a camera id or
null. Every CameraDetails tile derives its own state from it:
const isImgExpanded = expandedCameraId === cameraDetails.cId;
That single comparison is the one-camera-at-a-time rule: setting a new id implicitly collapses whoever was expanded before, with no bookkeeping.
Signal 2: isLocationViewInFullscreen(visibleLocationViewPanels). The Location View can
also be "fullscreen" in a different sense — showing exactly one of its three panels
(image / map / wide). The helper just counts true flags and returns visibleCount === 1.
Crucially, a map-only view is fullscreen by this definition while expandedCameraId stays
null — there's no camera being expanded, just a panel filling the screen.
Consumers that need "is anything fullscreen right now?" — like MapButtonsFL deciding
whether to show collapse buttons and the view-switching toolbar — must OR the two:
const isCameraDetailsExpanded =
expandedCameraId || isLocationViewInFullscreen(visibleLocationViewPanels);
If you're debugging a stuck expand/collapse button, first ask which signal is active. An expanded tile and an expanded map panel look identical on screen and completely different in state.
Ways in
Expand mode opens from more places than you'd guess: the tile's expand button, the mobile
more-options drawer ("View Full Screen", "See 360 view" — which opens straight into 360
mode — and "View Time Lapse", which opens with playback pre-loaded), a parent passing a
fullscreenRequest prop (how the pinned-cameras section drives it), and Location View's
image panel entering fullscreen (fullscreen === 'image', which sets expandedCameraId via
an effect in CameraImageWrapper).
Inside, ExpandMode shows one of three views — camera, 360, or map (an embedded
FeatureMap) — switched by the toolbar's toggle.
One toolbar, three hosts
ExpandedImageButtons is the bottom toolbar in every expanded view, and it's rendered by
three different parents — ExpandMode, CameraImageWrapper, and MapButtonsFL. It shows the
camera name and last-moved time, a playback button (and scrub slider during playback), the
camera/360/map toggle, an open-in-new link, and a compass readout of the pano scroll offset.
Hosts hide what doesn't apply via btnsToHide, and — the important part — each host wires
the toggle differently:
ExpandMode→ flips localexpandedModestateCameraImageWrapper→ rewritesvisibleLocationViewPanels(a real layout change)MapButtonsFL→ routes to the tile-view or location-view handler depending on context
Same toolbar, three meanings of "switch view." When a toggle behaves oddly, identify the host first.
Ways out
Every close path resolves to one of the two signals: the X inside ExpandMode, the backdrop
click, and exitFullscreenRequest all setExpandedCameraId(null); the map panel's collapse
resets visibleLocationViewPanels to a split layout, which flips
isLocationViewInFullscreen back to false. If fullscreen "won't close," you're clearing the
wrong signal.
Wrapping up
Two orthogonal fullscreen signals — a camera id and a panel count — OR'd together by anything that needs the whole truth; a single toolbar with three hosts that interpret its toggle three ways; and every entrance and exit reducible to writes on those two signals.
Next feature: Timelapse, which you've already seen hiding inside this toolbar.