ui(sidebar): split editable vs read-only between Edit and Metadata

The Metadata collapsible was hosting two editable widgets (TagsEditor
and TakenAtEditor) buried inside the readonly sub-sections — Tags as
its own Section, taken-at wedged into Basic Info between size/dims
and the filepath. With both top-level collapsibles in place, the
clearer split is editable up top, readonly below.

Moved into the Edit collapsible (in identification → description →
categorization order):
  Filename, Title, Date Taken, Notes, Tags, Rating, Color, Flag

Metadata now holds only readonly sub-sections:
  Basic Info (size, dims, path), Camera, Location

Dropped the now-empty Tags Section from Metadata and the 'tags' key
from the default-expanded set.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
Claudio
2026-05-10 21:49:44 +02:00
parent 1695eae226
commit eeeb16a0f1

View File

@@ -143,7 +143,7 @@ export function PhotoInfoPanel({ photoId, darkTheme = false }: PhotoInfoPanelPro
const queryClient = useQueryClient()
const [expandedSections, setExpandedSections] = useState<Set<string>>(
new Set(['edit', 'metadata', 'basic', 'camera', 'location', 'tags'])
new Set(['edit', 'metadata', 'basic', 'camera', 'location'])
)
const toggleSection = (section: string) => {
const next = new Set(expandedSections)
@@ -447,6 +447,14 @@ export function PhotoInfoPanel({ photoId, darkTheme = false }: PhotoInfoPanelPro
/>
</div>
<TakenAtEditor
photo={photo}
draft={takenAtDraft}
onDraftChange={setTakenAtDraft}
onCommit={commitTakenAt}
darkTheme={darkTheme}
/>
<div>
<label className="mb-1 block text-xs text-text-muted">Notes</label>
<Textarea
@@ -459,6 +467,22 @@ export function PhotoInfoPanel({ photoId, darkTheme = false }: PhotoInfoPanelPro
/>
</div>
<div>
<label className="mb-1 block text-xs text-text-muted">Tags</label>
<TagsEditor
photoTags={photo.tags ?? []}
allTags={allTags}
tagInput={tagInput}
onTagInputChange={setTagInput}
onAttachExisting={(id) => attachExistingTagMutation.mutate(id)}
onCreateAndAttach={(name) => {
addTagMutation.mutate(name)
setTagInput('')
}}
onRemove={(id) => removeTagMutation.mutate(id)}
/>
</div>
{/* Rating */}
<div>
<label className="mb-1 block text-xs text-text-muted">Rating</label>
@@ -581,25 +605,6 @@ export function PhotoInfoPanel({ photoId, darkTheme = false }: PhotoInfoPanelPro
)}
</CollapsibleTrigger>
<CollapsibleContent>
<Section
title="Tags"
expanded={expandedSections.has('tags')}
onToggle={() => toggleSection('tags')}
>
<TagsEditor
photoTags={photo.tags ?? []}
allTags={allTags}
tagInput={tagInput}
onTagInputChange={setTagInput}
onAttachExisting={(id) => attachExistingTagMutation.mutate(id)}
onCreateAndAttach={(name) => {
addTagMutation.mutate(name)
setTagInput('')
}}
onRemove={(id) => removeTagMutation.mutate(id)}
/>
</Section>
<Section
title="Basic Info"
expanded={expandedSections.has('basic')}
@@ -616,13 +621,6 @@ export function PhotoInfoPanel({ photoId, darkTheme = false }: PhotoInfoPanelPro
}
/>
</div>
<TakenAtEditor
photo={photo}
draft={takenAtDraft}
onDraftChange={setTakenAtDraft}
onCommit={commitTakenAt}
darkTheme={darkTheme}
/>
{/* Filepath spans the full sidebar width — most paths are long
* enough that the two-column grid above wraps them painfully.
* Mono so each character lines up under the next, break-all