1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
|
import { ButtonItem, Field, Focusable, PanelSection, PanelSectionRow } from "@decky/ui";
import { useEffect, useRef, useState } from "react";
import { ConfigurationData } from "../config/configSchema";
import { GameTarget } from "../hooks/useGameConfiguration";
import { GameConfigurationControls } from "./GameConfigurationControls";
import { GameConfigurationSelector } from "./GameConfigurationSelector";
interface ConfigurationTabProps {
config: ConfigurationData;
targets: GameTarget[];
runningGame: GameTarget | null;
onSelect: (appid: string) => void;
onConfigChange: (fieldName: keyof ConfigurationData, value: boolean | number | string | string[]) => Promise<void>;
onEnable: (appid: string) => Promise<boolean>;
onReset: () => Promise<void>;
onResetAll: () => Promise<void>;
}
export function ConfigurationTab({
config,
targets,
runningGame,
onSelect,
onConfigChange,
onEnable,
onReset,
onResetAll,
}: ConfigurationTabProps) {
const [detailAppId, setDetailAppId] = useState<string | null>(null);
const promptedRunningAppId = useRef<string | null>(null);
useEffect(() => {
if (!runningGame || runningGame.configured) {
promptedRunningAppId.current = null;
return;
}
if (promptedRunningAppId.current !== runningGame.appid && detailAppId === null) {
promptedRunningAppId.current = runningGame.appid;
setDetailAppId(runningGame.appid);
}
}, [detailAppId, runningGame?.appid, runningGame?.configured]);
const selectedTarget = detailAppId ? targets.find((target) => target.appid === detailAppId) : null;
if (detailAppId === null) {
return (
<PanelSection title="Games">
<GameConfigurationSelector
targets={targets}
runningGame={runningGame}
onSelect={(appid) => {
onSelect(appid);
setDetailAppId(appid);
}}
onResetAll={onResetAll}
/>
</PanelSection>
);
}
const profileLabel = selectedTarget?.name || "Game profile";
const running = selectedTarget?.appid === runningGame?.appid;
const profileDescription = selectedTarget
? `${selectedTarget.nonSteam ? "Non-Steam" : "Steam"} · App ID ${selectedTarget.appid} · ${selectedTarget.configured ? running && !runningGame?.configured ? "Profile saved · applies next launch" : "Profile active" : "Not configured · changes apply next launch"}`
: "Game is no longer available";
return (
<Focusable onCancelButton={() => setDetailAppId(null)}>
<PanelSection title="Game Profile">
<PanelSectionRow>
<Field label={profileLabel} description={profileDescription} />
</PanelSectionRow>
<PanelSectionRow>
<ButtonItem layout="below" onClick={() => setDetailAppId(null)}>Back to games</ButtonItem>
</PanelSectionRow>
</PanelSection>
<GameConfigurationControls config={config} onConfigChange={onConfigChange} />
<PanelSectionRow>
<ButtonItem
layout="below"
onClick={async () => {
if (selectedTarget?.configured) {
promptedRunningAppId.current = detailAppId;
await onReset();
setDetailAppId(null);
} else if (detailAppId) {
await onEnable(detailAppId);
}
}}
>
{selectedTarget?.configured ? "Remove profile" : "Enable for next launch"}
</ButtonItem>
</PanelSectionRow>
</Focusable>
);
}
|