feat(feed): 1D — content-type chips + sort in a toolbar above the cards
Move content type and ordering out of the filter sidebar into a feed toolbar (approved proposal 2): a prominent content-type chip row (Normal/Shorts/Live toggle chips) with the sort control + count + reshuffle in a quieter row beneath it. The toolbar renders even on 'no matches' so content-type can be turned back on after it filtered everything out. The sidebar keeps Show / Upload date / Language / Topic; 'sort' and 'content' widgets removed from the layout (normalizeLayout drops them from any saved layout). New feed.sortLabel string (HU/EN/DE).
This commit is contained in:
parent
f6efe44e37
commit
d96b47ae5d
6 changed files with 95 additions and 84 deletions
|
|
@ -215,9 +215,7 @@ export default function Sidebar({
|
|||
|
||||
const available: Record<WidgetId, boolean> = {
|
||||
show: true,
|
||||
sort: true,
|
||||
date: true,
|
||||
content: true,
|
||||
language: languages.length > 0,
|
||||
topic: topics.length > 0,
|
||||
};
|
||||
|
|
@ -257,41 +255,6 @@ export default function Sidebar({
|
|||
))}
|
||||
</div>
|
||||
);
|
||||
case "sort":
|
||||
return (
|
||||
<div className="flex items-center gap-1.5">
|
||||
<select
|
||||
value={filters.sort}
|
||||
onChange={(e) => {
|
||||
const sort = e.target.value;
|
||||
// Seed shuffle on selection so it lands on a fresh order, not the
|
||||
// deterministic seed-0 one every time.
|
||||
setFilters({
|
||||
...filters,
|
||||
sort,
|
||||
seed: sort === "shuffle" ? rollSeed() : undefined,
|
||||
});
|
||||
}}
|
||||
className="w-full bg-card border border-border rounded-lg px-2 py-1.5 text-sm outline-none focus:border-accent"
|
||||
>
|
||||
{SORT_IDS.map((id) => (
|
||||
<option key={id} value={id}>
|
||||
{t("sidebar.sort." + id)}
|
||||
</option>
|
||||
))}
|
||||
</select>
|
||||
{filters.sort === "shuffle" && (
|
||||
<button
|
||||
onClick={() => setFilters({ ...filters, seed: rollSeed() })}
|
||||
title={t("sidebar.reshuffle")}
|
||||
aria-label={t("sidebar.reshuffle")}
|
||||
className="shrink-0 p-1.5 rounded-lg border border-border bg-card text-fg shadow-sm hover:border-accent hover:text-accent active:translate-y-px transition"
|
||||
>
|
||||
<RefreshCw className="w-4 h-4" />
|
||||
</button>
|
||||
)}
|
||||
</div>
|
||||
);
|
||||
case "date":
|
||||
return (
|
||||
<>
|
||||
|
|
@ -381,26 +344,6 @@ export default function Sidebar({
|
|||
)}
|
||||
</>
|
||||
);
|
||||
case "content":
|
||||
return (
|
||||
<>
|
||||
<Toggle
|
||||
label={t("sidebar.content.normal")}
|
||||
checked={filters.includeNormal}
|
||||
onChange={(v) => setFilters({ ...filters, includeNormal: v })}
|
||||
/>
|
||||
<Toggle
|
||||
label={t("sidebar.content.shorts")}
|
||||
checked={filters.includeShorts}
|
||||
onChange={(v) => setFilters({ ...filters, includeShorts: v })}
|
||||
/>
|
||||
<Toggle
|
||||
label={t("sidebar.content.live")}
|
||||
checked={filters.includeLive}
|
||||
onChange={(v) => setFilters({ ...filters, includeLive: v })}
|
||||
/>
|
||||
</>
|
||||
);
|
||||
case "language": {
|
||||
const chips = visibleChips(languages);
|
||||
return (
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue