the bar is gone; the device toggle is the editor's
It sat across the top of the detail panel with Sync, Build and Publish — three things that act on the site, beside one that decides how you are looking at it. The toggle belongs with the settings it scopes: a spacing is chosen per width, so the control saying which width is the first thing in that column. Sync, Build and Publish are unmounted until they have a place of their own. ViewModeProvider stays; it was never the bar's. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
+9
-54
@@ -1,8 +1,6 @@
|
|||||||
import { Navigate } from 'react-router';
|
import { Navigate } from 'react-router';
|
||||||
import { href, useNav } from './routes';
|
import { href, useNav } from './routes';
|
||||||
import { DEFAULT_SECTION } from './sections';
|
import { DEFAULT_SECTION } from './sections';
|
||||||
import { Eye, Monitor, Pencil, Smartphone, Tablet } from 'lucide-react';
|
|
||||||
import { Button } from '@/components/ui/button';
|
|
||||||
import { sectionFor, sectionOpen, type SectionKey } from './sections';
|
import { sectionFor, sectionOpen, type SectionKey } from './sections';
|
||||||
import { AdministrationPanel } from './AdministrationPanel';
|
import { AdministrationPanel } from './AdministrationPanel';
|
||||||
import { MediaPanel } from './MediaPanel';
|
import { MediaPanel } from './MediaPanel';
|
||||||
@@ -10,10 +8,7 @@ import { GalleriesPanel } from './sections/GalleriesPanel';
|
|||||||
import { LayoutPanel } from './sections/LayoutPanel';
|
import { LayoutPanel } from './sections/LayoutPanel';
|
||||||
import { PagesPanel } from './sections/PagesPanel';
|
import { PagesPanel } from './sections/PagesPanel';
|
||||||
import { PageBuilderPanel } from './sections/PageBuilderPanel';
|
import { PageBuilderPanel } from './sections/PageBuilderPanel';
|
||||||
import { PublishButton } from './PublishButton';
|
import { ViewModeProvider } from './ViewMode';
|
||||||
import { SyncButton } from './SyncButton';
|
|
||||||
import { DEVICES, ViewModeProvider, useViewMode } from './ViewMode';
|
|
||||||
import { DeviceToggle } from './DeviceToggle';
|
|
||||||
import { MessagesPanel } from './MessagesPanel';
|
import { MessagesPanel } from './MessagesPanel';
|
||||||
import { PlannedSection } from './PlannedSection';
|
import { PlannedSection } from './PlannedSection';
|
||||||
import { useReady } from './useReady';
|
import { useReady } from './useReady';
|
||||||
@@ -58,16 +53,6 @@ const PANELS: Partial<Record<SectionKey, () => React.JSX.Element>> = {
|
|||||||
media: MediaPanel,
|
media: MediaPanel,
|
||||||
};
|
};
|
||||||
|
|
||||||
/** The width the preview is rendered at. See DEVICES for why these three and not others. */
|
|
||||||
const BarDeviceToggle = () => {
|
|
||||||
const { previewable } = useViewMode();
|
|
||||||
if (!previewable) return null;
|
|
||||||
|
|
||||||
// The same control the editor sections use — see DeviceToggle, which reads `?device=` rather than a
|
|
||||||
// context so every panel on the screen shares one answer.
|
|
||||||
return <DeviceToggle size="bar" />;
|
|
||||||
};
|
|
||||||
|
|
||||||
export const DetailPanel = () => {
|
export const DetailPanel = () => {
|
||||||
/*
|
/*
|
||||||
A page selected inside Pages opens the BUILDER, not the list with a row lit up. By SLUG, so the URL
|
A page selected inside Pages opens the BUILDER, not the list with a row lit up. By SLUG, so the URL
|
||||||
@@ -113,48 +98,18 @@ export const DetailPanel = () => {
|
|||||||
return (
|
return (
|
||||||
<div className="flex size-full flex-col overflow-hidden">
|
<div className="flex size-full flex-col overflow-hidden">
|
||||||
{/*
|
{/*
|
||||||
The site's own actions, pinned above whatever the section is showing.
|
No bar.
|
||||||
|
|
||||||
OUTSIDE the scroll area on purpose. Every panel scrolls its own contents, so anything drawn
|
It held the device toggle and Sync / Build / Publish across the top of this panel. The toggle
|
||||||
inside one leaves the screen as soon as somebody reads to the bottom — and Publish is what you
|
moved to the top of the EDITOR, which is where the settings it scopes already are; the three
|
||||||
reach for AFTER reading to the bottom. It sits here instead, as a sibling of the scrolling
|
actions are out until they have a place that is theirs rather than a corner of the panel that
|
||||||
region rather than the first thing inside it.
|
happens to be pinned. `SyncButton` and `PublishButton` still exist and are still mounted
|
||||||
|
nowhere — see git history for what the bar looked like.
|
||||||
|
|
||||||
Not in the workspace's chrome header either, where it lived for an afternoon. That header is
|
`ViewModeProvider` stays. It is not the bar's: the preview and the two panels with one read
|
||||||
shared furniture drawn the same way by every panel in the app; these two buttons belong to this
|
`device` from it, and `usePreviewable` is how a section says it has a page to show.
|
||||||
plugin and to the site it administers.
|
|
||||||
*/}
|
*/}
|
||||||
<ViewModeProvider>
|
<ViewModeProvider>
|
||||||
{/*
|
|
||||||
Three groups: how you are looking at it, at what width, and what to do with it.
|
|
||||||
|
|
||||||
The middle one is centred against the BAR rather than against what is beside it — the two
|
|
||||||
outer groups change width as sections come and go, and a middle that drifted with them
|
|
||||||
would never be in the same place twice.
|
|
||||||
*/}
|
|
||||||
<div className="flex shrink-0 items-center gap-2 border-b border-border px-4 py-2">
|
|
||||||
{/* Empty, and deliberately still here: the middle group is centred against the BAR, so
|
|
||||||
removing the left group would let Desktop/Tablet/Mobile drift left as the right group
|
|
||||||
changes width. It held Edit/View — see the note in ViewMode about why there is no
|
|
||||||
longer a mode to toggle. */}
|
|
||||||
<div className="flex flex-1 justify-start" />
|
|
||||||
|
|
||||||
<div className="flex justify-center">
|
|
||||||
<BarDeviceToggle />
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div className="flex flex-1 items-center justify-end gap-2">
|
|
||||||
{/* The order is the sequence: make the media web-ready, then make it public. Sync sits
|
|
||||||
left of Build for the same reason Build sits left of Publish — it is what has to have
|
|
||||||
happened first, and a stale `derived/` is a picture missing from the page you just
|
|
||||||
built.
|
|
||||||
|
|
||||||
No Save. Every control writes itself — see useAutosave. */}
|
|
||||||
<SyncButton />
|
|
||||||
<PublishButton />
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div className="min-h-0 flex-1">{Panel ? <Panel /> : <PlannedSection section={current} />}</div>
|
<div className="min-h-0 flex-1">{Panel ? <Panel /> : <PlannedSection section={current} />}</div>
|
||||||
</ViewModeProvider>
|
</ViewModeProvider>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
+35
-13
@@ -1,3 +1,4 @@
|
|||||||
|
import { DeviceToggle } from './DeviceToggle';
|
||||||
import { useEditorSlot } from './useEditorSlot';
|
import { useEditorSlot } from './useEditorSlot';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -8,23 +9,44 @@ import { useEditorSlot } from './useEditorSlot';
|
|||||||
* to a row of two dropdowns. A panel keeps the page whole and puts the controls where a workspace puts
|
* to a row of two dropdowns. A panel keeps the page whole and puts the controls where a workspace puts
|
||||||
* controls.
|
* controls.
|
||||||
*
|
*
|
||||||
* It holds nothing. The panel that owns a selection builds the editor and announces it — see
|
* It holds nothing of its own except the width. The panel that owns a selection builds the editor and
|
||||||
* useEditorSlot for why it carries the element rather than a description of one.
|
* announces it — see useEditorSlot for why it carries the element rather than a description of one.
|
||||||
|
*
|
||||||
|
* ── The device toggle is here, above everything ──
|
||||||
|
*
|
||||||
|
* It was in a bar across the top of the detail panel, which put it beside Sync and Publish — three
|
||||||
|
* things that act on the SITE next to one that decides how you are looking at it. It belongs with the
|
||||||
|
* settings it scopes: a spacing is chosen per width, and the control saying which width should be the
|
||||||
|
* first thing in the column those choices are made in.
|
||||||
|
*
|
||||||
|
* Always drawn, including when nothing is selected. It is not part of the editor — it decides what the
|
||||||
|
* PREVIEW shows, so hiding it until a block is picked would mean selecting something to change the
|
||||||
|
* width and then deselecting it.
|
||||||
|
*
|
||||||
|
* It reads `?device=` rather than a context, which is what lets it live in a panel that is a sibling of
|
||||||
|
* the one holding the preview. See DeviceToggle.
|
||||||
*/
|
*/
|
||||||
export const EditorPanel = () => {
|
export const EditorPanel = () => {
|
||||||
const [editor] = useEditorSlot();
|
const [editor] = useEditorSlot();
|
||||||
|
|
||||||
if (!editor) {
|
return (
|
||||||
return (
|
<div className="flex size-full flex-col overflow-hidden">
|
||||||
<div className="flex size-full items-center justify-center p-6 text-center">
|
{/* Outside the scroll area, so a long editor cannot carry it off the screen. */}
|
||||||
{/* Names what the panel is FOR rather than saying it is empty. "Nothing selected" describes
|
<div className="flex shrink-0 justify-center border-b border-border px-3 py-2">
|
||||||
this component's state; this describes the reader's next move. */}
|
<DeviceToggle size="bar" />
|
||||||
<p className="text-xs text-muted-foreground">
|
|
||||||
Pick a block in the page to edit it, or press Spacing on a band.
|
|
||||||
</p>
|
|
||||||
</div>
|
</div>
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
return <div className="size-full overflow-auto p-3">{editor}</div>;
|
{editor ? (
|
||||||
|
<div className="min-h-0 flex-1 overflow-auto p-3">{editor}</div>
|
||||||
|
) : (
|
||||||
|
<div className="flex min-h-0 flex-1 items-center justify-center p-6 text-center">
|
||||||
|
{/* Names what the panel is FOR rather than saying it is empty. "Nothing selected" describes
|
||||||
|
this component's state; this describes the reader's next move. */}
|
||||||
|
<p className="text-xs text-muted-foreground">
|
||||||
|
Pick a block in the page to edit it, or press Spacing on a band.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
Reference in New Issue
Block a user