feat(m5a): channel manager, tabbed settings panel, per-user sync status
Backend: /api/channels (list + PATCH priority/hidden + attach/detach user tags), user-tag CRUD on /api/tags, /api/sync/my-status (per-user channel sync counts). Frontend: feed|channels page nav (URL-synced) from the account menu; a slide-in tabbed Settings panel (Appearance, Notifications=6b sound+duration, Sync status + actions + admin pause/resume, Account); a channel manager with priority, hide, per-channel user tags, sync badges and 'view in feed'. Notifications now honor the configurable sound + auto-dismiss settings.
This commit is contained in:
parent
b8a8605797
commit
a8822d3935
11 changed files with 1063 additions and 45 deletions
|
|
@ -74,9 +74,19 @@ export function hasFilterParams(params: URLSearchParams): boolean {
|
|||
return KEYS.some((k) => params.has(k));
|
||||
}
|
||||
|
||||
/** Reflect the current filters into the address bar without adding history entries. */
|
||||
export function syncUrl(f: FeedFilters): void {
|
||||
const qs = filtersToParams(f).toString();
|
||||
export type Page = "feed" | "channels";
|
||||
|
||||
export function readPage(): Page {
|
||||
return new URLSearchParams(window.location.search).get("page") === "channels"
|
||||
? "channels"
|
||||
: "feed";
|
||||
}
|
||||
|
||||
/** Reflect the current filters + page into the address bar without adding history entries. */
|
||||
export function syncUrl(f: FeedFilters, page: Page = "feed"): void {
|
||||
const params = filtersToParams(f);
|
||||
if (page !== "feed") params.set("page", page);
|
||||
const qs = params.toString();
|
||||
const url = qs ? `${window.location.pathname}?${qs}` : window.location.pathname;
|
||||
window.history.replaceState(null, "", url);
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue