Merge pull request #544 from James9074/loading-device
Cleaner Device Loading UX
This commit is contained in:
+54
-40
@@ -3,6 +3,8 @@ import { SidebarButton } from "@components/UI/Sidebar/sidebarButton.tsx";
|
|||||||
import { Subtle } from "@components/UI/Typography/Subtle.tsx";
|
import { Subtle } from "@components/UI/Typography/Subtle.tsx";
|
||||||
import { useDevice } from "@core/stores/deviceStore.ts";
|
import { useDevice } from "@core/stores/deviceStore.ts";
|
||||||
import type { Page } from "@core/stores/deviceStore.ts";
|
import type { Page } from "@core/stores/deviceStore.ts";
|
||||||
|
import { Spinner } from "@components/UI/Spinner.tsx";
|
||||||
|
|
||||||
import {
|
import {
|
||||||
BatteryMediumIcon,
|
BatteryMediumIcon,
|
||||||
CpuIcon,
|
CpuIcon,
|
||||||
@@ -67,46 +69,55 @@ export const Sidebar = ({ children }: SidebarProps) => {
|
|||||||
return showSidebar
|
return showSidebar
|
||||||
? (
|
? (
|
||||||
<div className="min-w-[280px] max-w-min flex-col overflow-y-auto border-r-[0.5px] bg-background-primary border-slate-300 dark:border-slate-400">
|
<div className="min-w-[280px] max-w-min flex-col overflow-y-auto border-r-[0.5px] bg-background-primary border-slate-300 dark:border-slate-400">
|
||||||
<div className="flex justify-between px-8 pt-6">
|
{myNode === undefined ? (
|
||||||
<div>
|
<div className="flex flex-col items-center justify-center px-8 py-6">
|
||||||
<span className="text-lg font-medium">
|
<Spinner />
|
||||||
{myNode?.user?.shortName ?? "UNK"}
|
<Subtle className="mt-2">Loading device info...</Subtle>
|
||||||
</span>
|
|
||||||
<Subtle>{myNode?.user?.longName ?? "UNK"}</Subtle>
|
|
||||||
</div>
|
</div>
|
||||||
<button
|
) : (
|
||||||
type="button"
|
<>
|
||||||
className="transition-all hover:text-accent"
|
<div className="flex justify-between px-8 pt-6">
|
||||||
onClick={() => setDialogOpen("deviceName", true)}
|
<div>
|
||||||
>
|
<span className="text-lg font-medium">
|
||||||
<EditIcon size={16} />
|
{myNode.user?.shortName ?? "UNK"}
|
||||||
</button>
|
</span>
|
||||||
<button type="button" onClick={() => setShowSidebar(false)}>
|
<Subtle>{myNode.user?.longName ?? "UNK"}</Subtle>
|
||||||
<SidebarCloseIcon size={24} />
|
</div>
|
||||||
</button>
|
<button
|
||||||
</div>
|
type="button"
|
||||||
<div className="px-8 pb-6">
|
className="transition-all hover:text-accent"
|
||||||
<div className="flex items-center">
|
onClick={() => setDialogOpen("deviceName", true)}
|
||||||
<BatteryMediumIcon size={24} viewBox="0 0 28 24" />
|
>
|
||||||
<Subtle>
|
<EditIcon size={16} />
|
||||||
{myNode?.deviceMetrics?.batteryLevel
|
</button>
|
||||||
? myNode?.deviceMetrics?.batteryLevel > 100
|
<button type="button" onClick={() => setShowSidebar(false)}>
|
||||||
? "Charging"
|
<SidebarCloseIcon size={24} />
|
||||||
: `${myNode?.deviceMetrics?.batteryLevel}%`
|
</button>
|
||||||
: "UNK"}
|
</div>
|
||||||
</Subtle>
|
<div className="px-8 pb-6">
|
||||||
</div>
|
<div className="flex items-center">
|
||||||
<div className="flex items-center">
|
<BatteryMediumIcon size={24} viewBox="0 0 28 24" />
|
||||||
<ZapIcon size={24} viewBox="0 0 36 24" />
|
<Subtle>
|
||||||
<Subtle>
|
{myNode.deviceMetrics?.batteryLevel
|
||||||
{myNode?.deviceMetrics?.voltage?.toPrecision(3) ?? "UNK"} volts
|
? myNode.deviceMetrics.batteryLevel > 100
|
||||||
</Subtle>
|
? "Charging"
|
||||||
</div>
|
: `${myNode.deviceMetrics.batteryLevel}%`
|
||||||
<div className="flex items-center">
|
: "UNK"}
|
||||||
<CpuIcon size={24} viewBox="0 0 36 24" />
|
</Subtle>
|
||||||
<Subtle>v{myMetadata?.firmwareVersion ?? "UNK"}</Subtle>
|
</div>
|
||||||
</div>
|
<div className="flex items-center">
|
||||||
</div>
|
<ZapIcon size={24} viewBox="0 0 36 24" />
|
||||||
|
<Subtle>
|
||||||
|
{myNode.deviceMetrics?.voltage?.toPrecision(3) ?? "UNK"} volts
|
||||||
|
</Subtle>
|
||||||
|
</div>
|
||||||
|
<div className="flex items-center">
|
||||||
|
<CpuIcon size={24} viewBox="0 0 36 24" />
|
||||||
|
<Subtle>v{myMetadata?.firmwareVersion ?? "UNK"}</Subtle>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
|
||||||
<SidebarSection label="Navigation">
|
<SidebarSection label="Navigation">
|
||||||
{pages.map((link) => (
|
{pages.map((link) => (
|
||||||
@@ -115,9 +126,12 @@ export const Sidebar = ({ children }: SidebarProps) => {
|
|||||||
label={link.name}
|
label={link.name}
|
||||||
Icon={link.icon}
|
Icon={link.icon}
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
setActivePage(link.page);
|
if (myNode !== undefined) {
|
||||||
|
setActivePage(link.page);
|
||||||
|
}
|
||||||
}}
|
}}
|
||||||
active={link.page === activePage}
|
active={link.page === activePage}
|
||||||
|
disabled={myNode === undefined}
|
||||||
/>
|
/>
|
||||||
))}
|
))}
|
||||||
</SidebarSection>
|
</SidebarSection>
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ export interface SidebarButtonProps {
|
|||||||
Icon?: LucideIcon;
|
Icon?: LucideIcon;
|
||||||
element?;
|
element?;
|
||||||
onClick?: () => void;
|
onClick?: () => void;
|
||||||
|
disabled?: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export const SidebarButton = ({
|
export const SidebarButton = ({
|
||||||
@@ -15,12 +16,14 @@ export const SidebarButton = ({
|
|||||||
Icon,
|
Icon,
|
||||||
element,
|
element,
|
||||||
onClick,
|
onClick,
|
||||||
|
disabled = false,
|
||||||
}: SidebarButtonProps) => (
|
}: SidebarButtonProps) => (
|
||||||
<Button
|
<Button
|
||||||
onClick={onClick}
|
onClick={onClick}
|
||||||
variant={active ? "subtle" : "ghost"}
|
variant={active ? "subtle" : "ghost"}
|
||||||
size="sm"
|
size="sm"
|
||||||
className="flex gap-2 w-full"
|
className="flex gap-2 w-full"
|
||||||
|
disabled={disabled}
|
||||||
>
|
>
|
||||||
{Icon && <Icon size={16} />}
|
{Icon && <Icon size={16} />}
|
||||||
{element && element}
|
{element && element}
|
||||||
|
|||||||
Reference in New Issue
Block a user