import { Router, Route, Switch, Link, useLocation } from "wouter-preact";
import { useHashLocation } from "wouter-preact/use-hash-location";
import { HomePage } from "./pages/Home.jsx";
import { TerminalPage } from "./pages/Terminal.jsx";
import { SettingsPage, SettingsSubPage, SUB_PAGES } from "./pages/Settings.jsx";
import { SettingsHeader, useSettingsNav } from "./components/settings/ui.jsx";
import { InstallPage } from "./pages/Install.jsx";
import { ErrorPage } from "./components/ErrorPage.jsx";
import { fatalError } from "./lib/fatalError.js";
export function App() {
if (fatalError.value) {
return <ErrorPage error={fatalError.value} />;
}
return (
<Router hook={useHashLocation}>
<Switch>
{}
<Route path="/s/:node/:name">
{(params) => <TerminalPage node={params.node} name={params.name} />}
</Route>
<Route path="/s/:name">
{(params) => <TerminalPage name={params.name} />}
</Route>
{}
<Route>
<Shell>
<Switch>
<Route path="/" component={HomePage} />
<Route path="/settings" component={SettingsPage} />
<Route path="/settings/:section">
{(params) => <SettingsSubPage section={params.section} />}
</Route>
<Route path="/install" component={InstallPage} />
<Route>
<div class="settings-group">
<h2>Not found</h2>
<p>
No SPA route here yet. <Link href="/">Home</Link>
</p>
</div>
</Route>
</Switch>
</Shell>
</Route>
</Switch>
</Router>
);
}
function HomeHeader() {
const [, navigate] = useLocation();
const { push } = useSettingsNav();
return (
<header class="app-header">
<h1
class="app-wordmark"
role="link"
tabindex="0"
onClick={() => navigate("/")}
onKeyDown={(e) => {
if (e.key === "Enter" || e.key === " ") navigate("/");
}}
>
mobux
</h1>
<ReloadButton />
<button
class="header-icon header-icon-btn"
type="button"
aria-label="Settings"
onClick={() => push("/settings")}
>
⚙
</button>
</header>
);
}
function ReloadButton() {
return (
<button
class="header-icon header-icon-btn"
type="button"
aria-label="Reload"
title="Reload app"
onClick={() => location.reload()}
>
⟳
</button>
);
}
function settingsHeaderFor(location) {
if (location === "/settings")
return <SettingsHeader title="Settings" fallback="/" />;
const m = location.match(/^\/settings\/([^/]+)$/);
if (!m) return null;
const sub = SUB_PAGES[m[1]];
return (
<SettingsHeader title={sub ? sub.title : "Settings"} fallback="/settings" />
);
}
function Shell({ children }) {
const [location] = useLocation();
return (
<div class="spa-shell">
{settingsHeaderFor(location) || <HomeHeader />}
<main class="spa-main">{children}</main>
</div>
);
}