Update widgets
This commit is contained in:
@@ -0,0 +1,30 @@
|
||||
import type React from "react";
|
||||
|
||||
import { BoltIcon } from "@heroicons/react/24/outline";
|
||||
|
||||
import { Card } from "../Card.js";
|
||||
|
||||
export interface BatteryWidgetProps {
|
||||
batteryLevel: number;
|
||||
voltage: number;
|
||||
}
|
||||
|
||||
export const BatteryWidget = ({
|
||||
batteryLevel,
|
||||
voltage,
|
||||
}: BatteryWidgetProps): JSX.Element => {
|
||||
return (
|
||||
<Card>
|
||||
<div className="flex w-20 bg-slate-700 p-3">
|
||||
<BoltIcon className="m-auto h-12 text-white" />
|
||||
</div>
|
||||
<div className="w-full">
|
||||
<div className="flex h-8 bg-slate-100">
|
||||
<span className="m-auto text-lg font-medium">Power</span>
|
||||
</div>
|
||||
<span>{batteryLevel}</span>
|
||||
<span>{voltage}</span>
|
||||
</div>
|
||||
</Card>
|
||||
);
|
||||
};
|
||||
@@ -2,6 +2,9 @@ import React, { useEffect } from "react";
|
||||
|
||||
import { useDevice } from "@core/providers/useDevice.js";
|
||||
|
||||
import { Button } from "../Button.js";
|
||||
import { Card } from "../Card.js";
|
||||
|
||||
export const ConfiguringWidget = (): JSX.Element => {
|
||||
const {
|
||||
hardware,
|
||||
@@ -32,40 +35,45 @@ export const ConfiguringWidget = (): JSX.Element => {
|
||||
]);
|
||||
|
||||
return (
|
||||
<div className="mb-4 flex flex-col space-y-3 rounded-2xl bg-[#f9e3aa] p-6 text-sm text-black">
|
||||
<p className="text-xl font-bold">Connecting to device</p>
|
||||
<ol className="flex flex-col gap-3 overflow-hidden">
|
||||
<StatusIndicator
|
||||
title="Device Info"
|
||||
current={hardware.myNodeNum ? 1 : 0}
|
||||
total={0}
|
||||
/>
|
||||
<StatusIndicator title="Peers" current={nodes.length} total={0} />
|
||||
<StatusIndicator
|
||||
title="Device Config"
|
||||
current={Object.keys(config).length - 1}
|
||||
total={6}
|
||||
/>
|
||||
<StatusIndicator
|
||||
title="Module Config"
|
||||
current={Object.keys(moduleConfig).length - 1}
|
||||
total={6}
|
||||
/>
|
||||
<StatusIndicator
|
||||
title="Channels"
|
||||
current={channels.length}
|
||||
total={hardware.maxChannels ?? 0}
|
||||
/>
|
||||
</ol>
|
||||
<div
|
||||
className="mt-2 cursor-pointer rounded-md bg-[#dabb6b] p-1 text-center ring-[#f9e3aa]"
|
||||
onClick={() => {
|
||||
void connection?.configure();
|
||||
}}
|
||||
>
|
||||
Retry
|
||||
<Card className="flex-col">
|
||||
<div className="flex h-8 bg-slate-100">
|
||||
<span className="m-auto text-lg font-medium">Power</span>
|
||||
</div>
|
||||
</div>
|
||||
<div className="flex flex-col gap-2 p-3">
|
||||
<ol className="flex flex-col gap-3 overflow-hidden">
|
||||
<StatusIndicator
|
||||
title="Device Info"
|
||||
current={hardware.myNodeNum ? 1 : 0}
|
||||
total={0}
|
||||
/>
|
||||
<StatusIndicator title="Peers" current={nodes.length} total={0} />
|
||||
<StatusIndicator
|
||||
title="Device Config"
|
||||
current={Object.keys(config).length - 1}
|
||||
total={6}
|
||||
/>
|
||||
<StatusIndicator
|
||||
title="Module Config"
|
||||
current={Object.keys(moduleConfig).length - 1}
|
||||
total={6}
|
||||
/>
|
||||
<StatusIndicator
|
||||
title="Channels"
|
||||
current={channels.length}
|
||||
total={hardware.maxChannels ?? 0}
|
||||
/>
|
||||
</ol>
|
||||
<Button
|
||||
variant="secondary"
|
||||
size="sm"
|
||||
onClick={() => {
|
||||
void connection?.configure();
|
||||
}}
|
||||
>
|
||||
Retry
|
||||
</Button>
|
||||
</div>
|
||||
</Card>
|
||||
);
|
||||
};
|
||||
|
||||
|
||||
@@ -4,6 +4,7 @@ import { Hashicon } from "@emeraldpay/hashicon-react";
|
||||
import { XCircleIcon } from "@heroicons/react/24/outline";
|
||||
|
||||
import { Button } from "../Button.js";
|
||||
import { Card } from "../Card.js";
|
||||
|
||||
export interface DeviceWidgetProps {
|
||||
name: string;
|
||||
@@ -21,7 +22,7 @@ export const DeviceWidget = ({
|
||||
reconnect,
|
||||
}: DeviceWidgetProps): JSX.Element => {
|
||||
return (
|
||||
<div className="relative overflow-hidden rounded-xl bg-emerald-400">
|
||||
<Card className="relative flex-col">
|
||||
<div className="absolute bottom-20 h-full w-full">
|
||||
<Hashicon size={350} value={nodeNum} />
|
||||
</div>
|
||||
@@ -45,6 +46,6 @@ export const DeviceWidget = ({
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</Card>
|
||||
);
|
||||
};
|
||||
|
||||
@@ -1,11 +1,38 @@
|
||||
import type React from "react";
|
||||
|
||||
export interface NodeInfoWidgetProps {}
|
||||
import type { Protobuf } from "@meshtastic/meshtasticjs";
|
||||
|
||||
export const NodeInfoWidget = ({}: NodeInfoWidgetProps): JSX.Element => {
|
||||
import { Card } from "../Card.js";
|
||||
|
||||
export interface NodeInfoWidgetProps {
|
||||
hardware: Protobuf.MyNodeInfo;
|
||||
}
|
||||
|
||||
export const NodeInfoWidget = ({
|
||||
hardware,
|
||||
}: NodeInfoWidgetProps): JSX.Element => {
|
||||
return (
|
||||
<div className="mb-4 flex flex-col space-y-3 rounded-2xl bg-[#f9e3aa] p-6 text-sm text-black">
|
||||
node info
|
||||
</div>
|
||||
<Card className="flex-col">
|
||||
<div className="flex h-8 bg-slate-100">
|
||||
<span className="m-auto text-lg font-medium">Information</span>
|
||||
</div>
|
||||
<div className="flex flex-col gap-2 p-3">
|
||||
<dl className="mt-2 border-b border-gray-200">
|
||||
<div className="flex justify-between py-1 text-sm font-medium">
|
||||
<dt className="text-gray-500">Firmware version</dt>
|
||||
<dd className="cursor-pointer whitespace-nowrap text-gray-900 hover:text-orange-400 hover:underline">
|
||||
{hardware.firmwareVersion}
|
||||
</dd>
|
||||
</div>
|
||||
</dl>
|
||||
<div className="flex justify-between py-1 text-sm font-medium">
|
||||
<dt className="text-gray-500">Bitrate</dt>
|
||||
<dd className="whitespace-nowrap text-gray-900">
|
||||
{hardware.bitrate.toFixed(2)}
|
||||
<span className="font-mono text-sm text-slate-500 ">bps</span>
|
||||
</dd>
|
||||
</div>
|
||||
</div>
|
||||
</Card>
|
||||
);
|
||||
};
|
||||
|
||||
@@ -1,11 +1,55 @@
|
||||
import type React from "react";
|
||||
|
||||
export interface PeersWidgetProps {}
|
||||
import { base16 } from "rfc4648";
|
||||
|
||||
export const PeersWidget = ({}: PeersWidgetProps): JSX.Element => {
|
||||
import { Hashicon } from "@emeraldpay/hashicon-react";
|
||||
import { EllipsisHorizontalCircleIcon } from "@heroicons/react/24/outline";
|
||||
import type { Protobuf } from "@meshtastic/meshtasticjs";
|
||||
|
||||
import { Card } from "../Card.js";
|
||||
import { IconButton } from "../IconButton.js";
|
||||
import { Mono } from "../Mono.js";
|
||||
|
||||
export interface PeersWidgetProps {
|
||||
peers: Protobuf.NodeInfo[];
|
||||
}
|
||||
|
||||
export const PeersWidget = ({ peers }: PeersWidgetProps): JSX.Element => {
|
||||
return (
|
||||
<div className="mb-4 flex flex-col space-y-3 rounded-2xl bg-[#f9e3aa] p-6 text-sm text-black">
|
||||
Peers
|
||||
</div>
|
||||
<Card>
|
||||
<div className="flex w-full flex-col gap-1">
|
||||
<div className="flex h-8 bg-slate-100">
|
||||
<span className="m-auto text-lg font-medium">Peers</span>
|
||||
</div>
|
||||
<div className="p-4">
|
||||
{peers.map((peer) => (
|
||||
<div
|
||||
className="flex gap-2 rounded-md p-2 hover:bg-slate-100"
|
||||
key={peer.num}
|
||||
>
|
||||
<span className="my-auto shrink-0">
|
||||
<Hashicon value={peer.num.toString()} size={28} />
|
||||
</span>
|
||||
<div className="flex flex-col">
|
||||
<span className="font-medium">{peer.user?.longName}</span>
|
||||
<Mono>
|
||||
{base16
|
||||
.stringify(peer.user?.macaddr ?? [])
|
||||
.match(/.{1,2}/g)
|
||||
?.join(":") ?? ""}
|
||||
</Mono>
|
||||
</div>
|
||||
<div className="my-auto ml-auto">
|
||||
<IconButton
|
||||
variant="secondary"
|
||||
size="sm"
|
||||
icon={<EllipsisHorizontalCircleIcon className="h-4" />}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
</Card>
|
||||
);
|
||||
};
|
||||
|
||||
@@ -1,11 +1,25 @@
|
||||
import type React from "react";
|
||||
|
||||
export interface PositionWidgetProps {}
|
||||
import { MapPinIcon } from "@heroicons/react/24/outline";
|
||||
|
||||
export const PositionWidget = ({}: PositionWidgetProps): JSX.Element => {
|
||||
import { Card } from "../Card.js";
|
||||
|
||||
export interface PositionWidgetProps {
|
||||
grid: string;
|
||||
}
|
||||
|
||||
export const PositionWidget = ({ grid }: PositionWidgetProps): JSX.Element => {
|
||||
return (
|
||||
<div className="mb-4 flex flex-col space-y-3 rounded-2xl bg-[#f9e3aa] p-6 text-sm text-black">
|
||||
position
|
||||
</div>
|
||||
<Card>
|
||||
<div className="flex w-20 bg-teal-600 p-3">
|
||||
<MapPinIcon className="m-auto h-12 text-white" />
|
||||
</div>
|
||||
<div className="flex w-full flex-col">
|
||||
<div className="flex h-8 bg-slate-100">
|
||||
<span className="m-auto text-lg font-medium">Position</span>
|
||||
</div>
|
||||
<span className="m-auto text-lg">{grid}</span>
|
||||
</div>
|
||||
</Card>
|
||||
);
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user