Skip to content

Commit

Permalink
refactor: decouple components
Browse files Browse the repository at this point in the history
Signed-off-by: eXhumer <[email protected]>
  • Loading branch information
eXhumer committed Oct 26, 2024
1 parent e00c4be commit 4cea9c0
Show file tree
Hide file tree
Showing 3 changed files with 80 additions and 64 deletions.
50 changes: 50 additions & 0 deletions src/components/ControllersView.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
import { gamepadDialogClasses, joinClassNames, PanelSectionRow } from "@decky/ui";
import { IController } from "../types";
import { IconContext } from "react-icons";
import { BiBluetooth, BiUsb } from "react-icons/bi";
import VendorIcon from "./VendorIcon";
import BatteryIcon from "./BatteryIcon";

const FieldWithSeparator = joinClassNames(gamepadDialogClasses.Field, gamepadDialogClasses.WithBottomSeparatorStandard);

type ControllersViewProps = {
controllers: IController[];
};

const ControllersView = ({ controllers }: ControllersViewProps) => {
return (
controllers.sort((a, b) => a.name.localeCompare(b.name)).map((controller) => (
<PanelSectionRow key={controller.productId}>
<div className={FieldWithSeparator}>
<div className={gamepadDialogClasses.FieldLabelRow}>
<div className={gamepadDialogClasses.FieldLabel}>
<IconContext.Provider value={{ style: { verticalAlign: 'middle', marginRight: '10px' } }}>
{controller.bluetooth ? <BiBluetooth /> : <BiUsb />}
</IconContext.Provider>
<IconContext.Provider value={{ style: { verticalAlign: 'middle', marginRight: '5px' } }}>
<VendorIcon controller={controller}/>
</IconContext.Provider>
{controller.name}
</div>
{
(controller.capacity > 0 || controller.status !== "unknown") &&
<div className={gamepadDialogClasses.FieldChildrenInner}>
{
// only show battery capacity for non-MS vendors unless capacity is > 0 and over BT
// since we don't have the battery capacity yet for Xbox over USB
(controller.vendorId != 0x045E || (controller.capacity > 0 && controller.bluetooth)) &&
<span style={{ display: "inline-block", textAlign: "right", }}>{controller.capacity}%</span>
}
<IconContext.Provider value={{ style: { verticalAlign: 'middle', marginLeft: "6px" }, size: '2em' }}>
<BatteryIcon controller={controller}/>
</IconContext.Provider>
</div>
}
</div>
</div>
</PanelSectionRow>
))
);
};

export default ControllersView;
23 changes: 23 additions & 0 deletions src/components/NoControllersView.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
import { gamepadDialogClasses, joinClassNames, PanelSectionRow } from "@decky/ui";

const FieldWithSeparator = joinClassNames(gamepadDialogClasses.Field, gamepadDialogClasses.WithBottomSeparatorStandard);

type NoControllersViewProps = {
loading: boolean;
};

const NoControllersView = ({ loading }: NoControllersViewProps) => {
return (
<PanelSectionRow>
<div className={FieldWithSeparator}>
<div className={gamepadDialogClasses.FieldLabelRow}>
<div className={gamepadDialogClasses.FieldLabel}>
{loading ? 'Loading...' : 'No controllers found'}
</div>
</div>
</div>
</PanelSectionRow>
);
};

export default NoControllersView;
71 changes: 7 additions & 64 deletions src/components/PluginContent.tsx
Original file line number Diff line number Diff line change
@@ -1,21 +1,14 @@
import {
gamepadDialogClasses,
joinClassNames,
PanelSection,
PanelSectionRow,
} from "@decky/ui";
import { PanelSection } from "@decky/ui";

import { useEffect, useState } from "react";
import { IconContext } from "react-icons";
import { BiBluetooth, BiUsb } from "react-icons/bi";

import BatteryIcon from "./BatteryIcon";
import NoControllersView from "./NoControllersView";
import RefreshButton from "./RefreshButton";
import SettingsMenu from "./SettingsMenu";
import VendorIcon from "./VendorIcon";

import * as backend from "../backend";
import { IController } from "../types";
import ControllersView from "./ControllersView";

const delayPromise = <T,>(value: T) => {
return new Promise<T>(resolve => {
Expand All @@ -28,7 +21,6 @@ const PluginContent = () => {
const [notifications, setNotifications] = useState<boolean>(true);
const [loading, setLoading] = useState<boolean>(false);
const [controllers, setControllers] = useState<IController[]>([]);
const FieldWithSeparator = joinClassNames(gamepadDialogClasses.Field, gamepadDialogClasses.WithBottomSeparatorStandard);

// For fetching controller & settings data on render
useEffect(() => {
Expand Down Expand Up @@ -65,68 +57,19 @@ const PluginContent = () => {
});
};

if (controllers.length === 0) {
return <PanelSection title="Controllers">
<PanelSectionRow>
<div className={FieldWithSeparator}>
<div className={gamepadDialogClasses.FieldLabelRow}>
<div className={gamepadDialogClasses.FieldLabel}>
{loading ? 'Loading...' : 'No controllers found'}
</div>
</div>
</div>
</PanelSectionRow>
<RefreshButton onClick={onRefresh}/>
<SettingsMenu
debug={debug}
notifications={notifications}
onDebugChange={onDebugChange}
onNotificationsChange={onNotificationsChange}
/>
</PanelSection>;
}

return (
<PanelSection title="Controllers">
{controllers.sort((a, b) => a.name.localeCompare(b.name)).map((controller) => (
<PanelSectionRow key={controller.productId}>
<div className={FieldWithSeparator}>
<div className={gamepadDialogClasses.FieldLabelRow}>
<div className={gamepadDialogClasses.FieldLabel}>
<IconContext.Provider value={{ style: { verticalAlign: 'middle', marginRight: '10px' } }}>
{controller.bluetooth ? <BiBluetooth /> : <BiUsb />}
</IconContext.Provider>
<IconContext.Provider value={{ style: { verticalAlign: 'middle', marginRight: '5px' } }}>
<VendorIcon controller={controller}/>
</IconContext.Provider>
{controller.name}
</div>
{
(controller.capacity > 0 || controller.status !== "unknown") &&
<div className={gamepadDialogClasses.FieldChildrenInner}>
{
// only show battery capacity for non-MS vendors unless capacity is > 0 and over BT
// since we don't have the battery capacity yet for Xbox over USB
(controller.vendorId != 1118 || (controller.capacity > 0 && controller.bluetooth)) &&
<span style={{ display: "inline-block", textAlign: "right", }}>{controller.capacity}%</span>
}
<IconContext.Provider value={{ style: { verticalAlign: 'middle', marginLeft: "6px" }, size: '2em' }}>
<BatteryIcon controller={controller}/>
</IconContext.Provider>
</div>
}
</div>
</div>
</PanelSectionRow>
))}
{controllers.length === 0 ?
<NoControllersView loading={loading}/> :
<ControllersView controllers={controllers}/>}
<RefreshButton onClick={onRefresh}/>
<SettingsMenu
debug={debug}
notifications={notifications}
onDebugChange={onDebugChange}
onNotificationsChange={onNotificationsChange}
/>
</PanelSection >
</PanelSection>
);
};

Expand Down

0 comments on commit 4cea9c0

Please sign in to comment.