diff --git a/src/renderer/src/components/context-menu/context-menu.scss b/src/renderer/src/components/context-menu/context-menu.scss index 673fa2da..e292b22d 100644 --- a/src/renderer/src/components/context-menu/context-menu.scss +++ b/src/renderer/src/components/context-menu/context-menu.scss @@ -19,7 +19,6 @@ &__item-container { position: relative; - padding-right: 8px; } &__item { @@ -97,7 +96,7 @@ &__submenu { position: absolute; - left: calc(100% - 2px); + left: 100%; top: 0; background-color: globals.$background-color; border: 1px solid globals.$border-color; diff --git a/src/renderer/src/components/context-menu/context-menu.tsx b/src/renderer/src/components/context-menu/context-menu.tsx index cb9e0347..34431728 100644 --- a/src/renderer/src/components/context-menu/context-menu.tsx +++ b/src/renderer/src/components/context-menu/context-menu.tsx @@ -144,9 +144,9 @@ export function ContextMenu({ if (parentRect.right + submenuWidth > viewportWidth - 8) { styles.left = "auto"; - styles.right = "calc(100% - 2px)"; + styles.right = "100%"; } else { - styles.left = "calc(100% - 2px)"; + styles.left = "100%"; styles.right = undefined; } diff --git a/src/renderer/src/components/game-context-menu/game-context-menu.tsx b/src/renderer/src/components/game-context-menu/game-context-menu.tsx index e424dac7..694012b7 100644 --- a/src/renderer/src/components/game-context-menu/game-context-menu.tsx +++ b/src/renderer/src/components/game-context-menu/game-context-menu.tsx @@ -40,9 +40,11 @@ export function GameContextMenu({ canPlay, isDeleting, isGameDownloading, + isGameRunning, hasRepacks, shouldShowCreateStartMenuShortcut, handlePlayGame, + handleCloseGame, handleToggleFavorite, handleCreateShortcut, handleCreateSteamShortcut, @@ -57,10 +59,20 @@ export function GameContextMenu({ const items: ContextMenuItemData[] = [ { id: "play", - label: canPlay ? t("play") : t("download"), - icon: canPlay ? : , + label: isGameRunning ? t("close") : canPlay ? t("play") : t("download"), + icon: isGameRunning ? ( + + ) : canPlay ? ( + + ) : ( + + ), onClick: () => { - void handlePlayGame(); + if (isGameRunning) { + void handleCloseGame(); + } else { + void handlePlayGame(); + } }, disabled: isDeleting, }, diff --git a/src/renderer/src/components/game-context-menu/use-game-actions.ts b/src/renderer/src/components/game-context-menu/use-game-actions.ts index 042b796b..c7224225 100644 --- a/src/renderer/src/components/game-context-menu/use-game-actions.ts +++ b/src/renderer/src/components/game-context-menu/use-game-actions.ts @@ -1,4 +1,4 @@ -import { useState } from "react"; +import { useState, useEffect } from "react"; import { useTranslation } from "react-i18next"; import { LibraryGame, ShortcutLocation } from "@types"; import { useDownload, useLibrary, useToast } from "@renderer/hooks"; @@ -21,6 +21,7 @@ export function useGameActions(game: LibraryGame) { } = useDownload(); const [creatingSteamShortcut, setCreatingSteamShortcut] = useState(false); + const [isGameRunning, setIsGameRunning] = useState(false); const canPlay = Boolean(game.executablePath); const isDeleting = isGameDeleting(game.id); @@ -30,6 +31,20 @@ export function useGameActions(game: LibraryGame) { const shouldShowCreateStartMenuShortcut = window.electron.platform === "win32"; + useEffect(() => { + const unsubscribe = window.electron.onGamesRunning((gamesIds) => { + const updatedIsGameRunning = + !!game?.id && + !!gamesIds.find((gameRunning) => gameRunning.id == game.id); + + setIsGameRunning(updatedIsGameRunning); + }); + + return () => { + unsubscribe(); + }; + }, [game?.id]); + const handlePlayGame = async () => { if (!canPlay) { const path = buildGameDetailsPath({ @@ -75,6 +90,15 @@ export function useGameActions(game: LibraryGame) { } }; + const handleCloseGame = async () => { + try { + await window.electron.closeGame(game.shop, game.objectId); + } catch (error) { + showErrorToast("Failed to close game"); + logger.error("Failed to close game", error); + } + }; + const handleToggleFavorite = async () => { try { if (game.favorite) { @@ -239,10 +263,12 @@ export function useGameActions(game: LibraryGame) { canPlay, isDeleting, isGameDownloading, + isGameRunning, hasRepacks, shouldShowCreateStartMenuShortcut, creatingSteamShortcut, handlePlayGame, + handleCloseGame, handleToggleFavorite, handleCreateShortcut, handleCreateSteamShortcut, diff --git a/src/renderer/src/pages/game-details/modals/repacks-modal.tsx b/src/renderer/src/pages/game-details/modals/repacks-modal.tsx index 97b8b1b5..f2d1f974 100644 --- a/src/renderer/src/pages/game-details/modals/repacks-modal.tsx +++ b/src/renderer/src/pages/game-details/modals/repacks-modal.tsx @@ -161,6 +161,14 @@ export function RepacksModal({ const [isFilterDrawerOpen, setIsFilterDrawerOpen] = useState(false); + useEffect(() => { + if (!visible) { + setFilterTerm(""); + setSelectedFingerprints([]); + setIsFilterDrawerOpen(false); + } + }, [visible]); + return ( <> - + {downloadSources.length > 0 && (