2026-10-30 12:28:48 +01:00
|
|
|
// Generated, do not edit. sha256:c74d68370e5fcfc4f6009b2cf9bbe65c4f4f227eb216c413ea6ff5daeae0f4fa
|
2026-10-29 11:57:29 +01:00
|
|
|
import { t } from '../i18n/index.js';
|
|
|
|
|
import { getPref, setPref } from '../data/preferences.js';
|
|
|
|
|
import { SYSTEM_PAGE, targetHash } from '../../shared/config.js';
|
|
|
|
|
import { create as createTabs } from '../ui/tabs.js';
|
|
|
|
|
import { attentionForRoute, attentionDotHtml } from '../ui/attention.js';
|
|
|
|
|
import { registerSystemTab, systemTabs } from './system-tabs.js';
|
|
|
|
|
import * as settings from './settings.js';
|
|
|
|
|
import * as accountsPage from './accounts.js';
|
|
|
|
|
import * as assetsPage from './assets.js';
|
|
|
|
|
import * as connections from './connections.js';
|
|
|
|
|
import * as aiPage from './ai.js';
|
|
|
|
|
import * as licensePage from './license.js';
|
2026-10-30 12:28:48 +01:00
|
|
|
import * as portfoliosPage from './portfolios.js';
|
2026-10-29 11:57:29 +01:00
|
|
|
|
|
|
|
|
export const title = () => t('nav.system');
|
|
|
|
|
|
|
|
|
|
const ROUTE = SYSTEM_PAGE.ROUTE;
|
|
|
|
|
const TABS = SYSTEM_PAGE.TABS;
|
|
|
|
|
const PREF_SCOPE = ROUTE;
|
|
|
|
|
|
2026-10-30 12:28:48 +01:00
|
|
|
registerSystemTab({ id: TABS.PORTFOLIOS, render: panel => portfoliosPage.render(panel) });
|
2026-10-29 11:57:29 +01:00
|
|
|
registerSystemTab({ id: TABS.SETTINGS, render: panel => settings.render(panel) });
|
|
|
|
|
registerSystemTab({ id: TABS.ASSETS, render: panel => assetsPage.render(panel) });
|
|
|
|
|
registerSystemTab({ id: TABS.ACCOUNTS, render: panel => accountsPage.render(panel) });
|
|
|
|
|
registerSystemTab({ id: TABS.INTEGRATIONS, label: 'nav.connections', subs: ['connections'], render: panel => connections.render(panel) });
|
|
|
|
|
registerSystemTab({ id: TABS.AI, render: panel => aiPage.render(panel) });
|
|
|
|
|
registerSystemTab({ id: TABS.LICENSE, render: panel => licensePage.render(panel) });
|
|
|
|
|
|
|
|
|
|
function parseHash() {
|
|
|
|
|
const parts = (location.hash || '').replace(/^#\/?/, '').split('/');
|
|
|
|
|
return { tab: parts[1] || null, sub: parts[2] || null };
|
|
|
|
|
}
|
|
|
|
|
const hashFor = tab => targetHash({ route: ROUTE, tab });
|
|
|
|
|
|
|
|
|
|
function tabDot(tabId) {
|
|
|
|
|
return attentionDotHtml(attentionForRoute(ROUTE).filter(a => (a.tab || '').split('/')[0] === tabId));
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
export async function render(el) {
|
|
|
|
|
const tabs = systemTabs();
|
|
|
|
|
const TAB_IDS = tabs.map(x => x.id);
|
|
|
|
|
const { tab: hashTab, sub } = parseHash();
|
|
|
|
|
let tab = TAB_IDS.includes(hashTab) ? hashTab : null;
|
|
|
|
|
if (!tab) {
|
|
|
|
|
const att = attentionForRoute(ROUTE).find(a => TAB_IDS.includes((a.tab || '').split('/')[0]));
|
|
|
|
|
tab = att ? att.tab.split('/')[0] : await getPref(PREF_SCOPE, 'tab', TAB_IDS[0]);
|
|
|
|
|
if (!TAB_IDS.includes(tab)) tab = TAB_IDS[0];
|
|
|
|
|
history.replaceState(null, '', hashFor(tab));
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
el.innerHTML = '<div data-tabs></div>';
|
|
|
|
|
let firstSub = sub;
|
|
|
|
|
createTabs(el.querySelector('[data-tabs]'), {
|
|
|
|
|
size: 'lg',
|
|
|
|
|
active: tab,
|
|
|
|
|
items: tabs.map(x => ({ id: x.id, label: t(x.label), dot: () => tabDot(x.id) })),
|
|
|
|
|
render: (id, panel) => { tabs.find(x => x.id === id).render(panel, firstSub); firstSub = null; },
|
|
|
|
|
onChange: (id) => {
|
|
|
|
|
setPref(PREF_SCOPE, 'tab', id).catch(() => { });
|
|
|
|
|
if (location.hash !== hashFor(id)) history.pushState(null, '', hashFor(id));
|
|
|
|
|
},
|
|
|
|
|
syncOn: ['attention-changed'],
|
|
|
|
|
});
|
|
|
|
|
}
|