summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorxXJSONDeruloXx <danielhimebauch@gmail.com>2025-09-17 14:57:02 -0400
committerxXJSONDeruloXx <danielhimebauch@gmail.com>2025-09-17 14:57:02 -0400
commitbac59e55e319d871de5ac70c47199eb209fee66e (patch)
treef2e2ef62d52446ad7789c4c0bb657068ad0504fe /src
parent21b076df45f542fdc02e8b5574abcd91e9d68f89 (diff)
downloaddecky-lsfg-vk-bac59e55e319d871de5ac70c47199eb209fee66e.tar.gz
decky-lsfg-vk-bac59e55e319d871de5ac70c47199eb209fee66e.zip
add deckyfg combo launch option clipboard
Diffstat (limited to 'src')
-rw-r--r--src/api/lsfgApi.ts8
-rw-r--r--src/components/Content.tsx11
-rw-r--r--src/components/FgmodClipboardButton.tsx109
-rw-r--r--src/components/index.ts1
4 files changed, 128 insertions, 1 deletions
diff --git a/src/api/lsfgApi.ts b/src/api/lsfgApi.ts
index 6c535af..8db0c82 100644
--- a/src/api/lsfgApi.ts
+++ b/src/api/lsfgApi.ts
@@ -89,6 +89,13 @@ export interface FileContentResult {
error?: string;
}
+export interface FgmodCheckResult {
+ success: boolean;
+ exists: boolean;
+ path?: string;
+ error?: string;
+}
+
// Profile management interfaces
export interface ProfilesResult {
success: boolean;
@@ -116,6 +123,7 @@ export const getConfigSchema = callable<[], ConfigSchemaResult>("get_config_sche
export const getLaunchOption = callable<[], LaunchOptionResult>("get_launch_option");
export const getConfigFileContent = callable<[], FileContentResult>("get_config_file_content");
export const getLaunchScriptContent = callable<[], FileContentResult>("get_launch_script_content");
+export const checkFgmodDirectory = callable<[], FgmodCheckResult>("check_fgmod_directory");
// Updated config function using object-based configuration (single source of truth)
export const updateLsfgConfig = callable<
diff --git a/src/components/Content.tsx b/src/components/Content.tsx
index e0adf3f..e870dda 100644
--- a/src/components/Content.tsx
+++ b/src/components/Content.tsx
@@ -11,6 +11,7 @@ import { UsageInstructions } from "./UsageInstructions";
import { WikiButton } from "./WikiButton";
import { ClipboardButton } from "./ClipboardButton";
import { SmartClipboardButton } from "./SmartClipboardButton";
+import { FgmodClipboardButton } from "./FgmodClipboardButton";
import { PluginUpdateChecker } from "./PluginUpdateChecker";
import { NerdStuffModal } from "./NerdStuffModal";
import { ConfigurationData } from "../config/configSchema";
@@ -96,7 +97,13 @@ export function Content() {
</>
)}
- <SmartClipboardButton />
+ {/* Clipboard buttons - only show if installed */}
+ {isInstalled && (
+ <>
+ <SmartClipboardButton />
+ <FgmodClipboardButton />
+ </>
+ )}
{/* Profile Management - only show if installed */}
{isInstalled && (
@@ -117,8 +124,10 @@ export function Content() {
/>
)}
+ {/* Usage instructions - always visible for user guidance */}
<UsageInstructions config={config} />
+ {/* Wiki and clipboard buttons - always available for documentation */}
<WikiButton />
<ClipboardButton />
diff --git a/src/components/FgmodClipboardButton.tsx b/src/components/FgmodClipboardButton.tsx
new file mode 100644
index 0000000..6f65955
--- /dev/null
+++ b/src/components/FgmodClipboardButton.tsx
@@ -0,0 +1,109 @@
+import { useState, useEffect } from "react";
+import { PanelSectionRow, ButtonItem } from "@decky/ui";
+import { FaClipboard, FaCheck } from "react-icons/fa";
+import { checkFgmodDirectory } from "../api/lsfgApi";
+import { showClipboardErrorToast } from "../utils/toastUtils";
+import { copyWithVerification } from "../utils/clipboardUtils";
+
+export function FgmodClipboardButton() {
+ const [isLoading, setIsLoading] = useState(false);
+ const [showSuccess, setShowSuccess] = useState(false);
+ const [fgmodExists, setFgmodExists] = useState(false);
+ const [checkingFgmod, setCheckingFgmod] = useState(true);
+
+ // Check for fgmod directory on component mount
+ useEffect(() => {
+ const checkFgmod = async () => {
+ try {
+ const result = await checkFgmodDirectory();
+ setFgmodExists(result.exists);
+ } catch (error) {
+ console.error("Error checking fgmod directory:", error);
+ setFgmodExists(false);
+ } finally {
+ setCheckingFgmod(false);
+ }
+ };
+
+ checkFgmod();
+ }, []);
+
+ // Reset success state after 3 seconds
+ useEffect(() => {
+ if (showSuccess) {
+ const timer = setTimeout(() => {
+ setShowSuccess(false);
+ }, 3000);
+ return () => clearTimeout(timer);
+ }
+ return undefined;
+ }, [showSuccess]);
+
+ const copyToClipboard = async () => {
+ if (isLoading || showSuccess) return;
+
+ setIsLoading(true);
+ try {
+ const text = "~/fgmod/fgmod ~/lsfg %command%";
+ const { success, verified } = await copyWithVerification(text);
+
+ if (success) {
+ // Show success feedback in the button instead of toast
+ setShowSuccess(true);
+ if (!verified) {
+ // Copy worked but verification failed - still show success
+ console.log('Copy verification failed but copy likely worked');
+ }
+ } else {
+ showClipboardErrorToast();
+ }
+ } catch (error) {
+ showClipboardErrorToast();
+ } finally {
+ setIsLoading(false);
+ }
+ };
+
+ // Don't render if fgmod directory doesn't exist or we're still checking
+ if (checkingFgmod || !fgmodExists) {
+ return null;
+ }
+
+ return (
+ <PanelSectionRow>
+ <ButtonItem
+ layout="below"
+ onClick={copyToClipboard}
+ disabled={isLoading || showSuccess}
+ >
+ <div style={{ display: "flex", alignItems: "center", gap: "8px" }}>
+ {showSuccess ? (
+ <FaCheck style={{
+ color: "#4CAF50" // Green color for success
+ }} />
+ ) : isLoading ? (
+ <FaClipboard style={{
+ animation: "pulse 1s ease-in-out infinite",
+ opacity: 0.7
+ }} />
+ ) : (
+ <FaClipboard />
+ )}
+ <div style={{
+ color: showSuccess ? "#4CAF50" : "inherit",
+ fontWeight: showSuccess ? "bold" : "normal"
+ }}>
+ {showSuccess ? "Copied to clipboard" : isLoading ? "Copying..." : "LSFG + DeckyFG"}
+ </div>
+ </div>
+ </ButtonItem>
+ <style>{`
+ @keyframes pulse {
+ 0% { opacity: 0.7; }
+ 50% { opacity: 1; }
+ 100% { opacity: 0.7; }
+ }
+ `}</style>
+ </PanelSectionRow>
+ );
+}
diff --git a/src/components/index.ts b/src/components/index.ts
index bf60423..32bbb31 100644
--- a/src/components/index.ts
+++ b/src/components/index.ts
@@ -6,6 +6,7 @@ export { FpsMultiplierControl } from "./FpsMultiplierControl";
export { UsageInstructions } from "./UsageInstructions";
export { WikiButton } from "./WikiButton";
export { SmartClipboardButton } from "./SmartClipboardButton";
+export { FgmodClipboardButton } from "./FgmodClipboardButton";
export { PluginUpdateChecker } from "./PluginUpdateChecker";
export { NerdStuffModal } from "./NerdStuffModal";
export { ProfileManagement } from "./ProfileManagement";