diff --git a/src/frontend/App.tsx b/src/frontend/App.tsx index 4608db29d8..fac7c060c5 100644 --- a/src/frontend/App.tsx +++ b/src/frontend/App.tsx @@ -19,6 +19,7 @@ import { ThemeProvider, createTheme } from '@mui/material/styles' import LogFileUploadDialog from './components/UI/LogFileUploadDialog' import UploadedLogFilesList from './screens/Settings/sections/LogSettings/components/UploadedLogFilesList' import { TourProvider } from './state/TourContext' +import { InstallGameWrapper } from './screens/Library/components/InstallModal' function Root() { const { @@ -74,6 +75,7 @@ function Root() { type={isSettingsModalOpen.type} /> )} + diff --git a/src/frontend/screens/Game/GamePage/index.tsx b/src/frontend/screens/Game/GamePage/index.tsx index 3f6e51d50f..25cada9233 100644 --- a/src/frontend/screens/Game/GamePage/index.tsx +++ b/src/frontend/screens/Game/GamePage/index.tsx @@ -32,7 +32,6 @@ import { import GamePicture from '../GamePicture' import TimeContainer from '../TimeContainer' -import { InstallModal } from 'frontend/screens/Library/components' import { install } from 'frontend/helpers/library' import { hasProgress } from 'frontend/hooks/hasProgress' import ErrorComponent from 'frontend/components/UI/ErrorComponent' @@ -65,6 +64,7 @@ import { hasHelp } from 'frontend/hooks/hasHelp' import Genres from './components/Genres' import ReleaseDate from './components/ReleaseDate' import { hasKnownFixes } from 'frontend/hooks/hasKnownFixes' +import { openInstallGameModal } from 'frontend/state/InstallGameModal' export default React.memo(function GamePage(): JSX.Element | null { const { appName, runner } = useParams() as { appName: string; runner: Runner } @@ -76,7 +76,6 @@ export default React.memo(function GamePage(): JSX.Element | null { const { gameInfo: locationGameInfo } = location.state - const [showModal, setShowModal] = useState({ game: '', show: false }) const [showUninstallModal, setShowUninstallModal] = useState(false) const [wikiInfo, setWikiInfo] = useState(null) @@ -256,7 +255,7 @@ export default React.memo(function GamePage(): JSX.Element | null { } function handleModal() { - setShowModal({ game: appName, show: true }) + openInstallGameModal({ appName, runner, gameInfo }) } let hasUpdate = false @@ -366,14 +365,6 @@ export default React.memo(function GamePage(): JSX.Element | null { className="backgroundImage" /> )} - {gameInfo.runner !== 'sideload' && showModal.show && ( - setShowModal({ game: '', show: false })} - gameInfo={gameInfo} - /> - )} {showUninstallModal && ( (false) const [eosOverlayRefresh, setEosOverlayRefresh] = useState(false) - const [showModal, setShowModal] = useState(false) const eosOverlayAppName = '98bc04bc842e4906993fd6d6644ffb8d' const [showUninstallModal, setShowUninstallModal] = useState(false) const [protonDBurl, setProtonDBurl] = useState( @@ -147,7 +146,7 @@ export default function GamesSubmenu({ } function handleEdit() { - setShowModal(true) + openInstallGameModal({ appName, runner, gameInfo }) } async function handleEosOverlay() { @@ -414,13 +413,6 @@ export default function GamesSubmenu({ )} - {showModal && ( - setShowModal(false)} - /> - )} ) } diff --git a/src/frontend/screens/Library/components/InstallModal/index.tsx b/src/frontend/screens/Library/components/InstallModal/index.tsx index 7b99ac2b72..fdcc830149 100644 --- a/src/frontend/screens/Library/components/InstallModal/index.tsx +++ b/src/frontend/screens/Library/components/InstallModal/index.tsx @@ -21,10 +21,13 @@ import { SelectField } from 'frontend/components/UI' import { useTranslation } from 'react-i18next' import ThirdPartyDialog from './ThirdPartyDialog' import { MenuItem } from '@mui/material' +import { + closeInstallGameModal, + useInstallGameModal +} from 'frontend/state/InstallGameModal' type Props = { appName: string - backdropClick: () => void runner: Runner gameInfo?: GameInfo | null } @@ -36,12 +39,7 @@ export type AvailablePlatforms = { icon: IconDefinition }[] -export default React.memo(function InstallModal({ - appName, - backdropClick, - runner, - gameInfo = null -}: Props) { +function InstallModal({ appName, runner, gameInfo = null }: Props) { const { platform } = useContext(ContextProvider) const { t } = useTranslation('gamepage') @@ -155,10 +153,12 @@ export default React.memo(function InstallModal({ const showDownloadDialog = !isSideload && gameInfo const isThirdPartyManagedApp = gameInfo && !!gameInfo.thirdPartyManagedApp + const closeModal = () => closeInstallGameModal() + return (
@@ -169,7 +169,7 @@ export default React.memo(function InstallModal({ winePrefix={winePrefix} wineVersion={wineVersion} availablePlatforms={availablePlatforms} - backdropClick={backdropClick} + backdropClick={closeModal} platformToInstall={platformToInstall} gameInfo={gameInfo} crossoverBottle={crossoverBottle} @@ -197,7 +197,7 @@ export default React.memo(function InstallModal({ winePrefix={winePrefix} wineVersion={wineVersion} availablePlatforms={availablePlatforms} - backdropClick={backdropClick} + backdropClick={closeModal} platformToInstall={platformToInstall} gameInfo={gameInfo} crossoverBottle={crossoverBottle} @@ -223,7 +223,7 @@ export default React.memo(function InstallModal({ winePrefix={winePrefix} wineVersion={wineVersion} availablePlatforms={availablePlatforms} - backdropClick={backdropClick} + backdropClick={closeModal} platformToInstall={platformToInstall} appName={appName} crossoverBottle={crossoverBottle} @@ -246,4 +246,20 @@ export default React.memo(function InstallModal({
) -}) +} + +export function InstallGameWrapper() { + const installGameModalState = useInstallGameModal() + + if (!installGameModalState.isOpen) { + return <> + } + + return ( + + ) +} diff --git a/src/frontend/screens/Library/components/index.tsx b/src/frontend/screens/Library/components/index.tsx deleted file mode 100644 index 914f9d9bf4..0000000000 --- a/src/frontend/screens/Library/components/index.tsx +++ /dev/null @@ -1 +0,0 @@ -export { default as InstallModal } from './InstallModal' diff --git a/src/frontend/screens/Library/index.tsx b/src/frontend/screens/Library/index.tsx index ebfdb205eb..0ad38f8676 100644 --- a/src/frontend/screens/Library/index.tsx +++ b/src/frontend/screens/Library/index.tsx @@ -27,7 +27,6 @@ import { sideloadedCategories } from 'frontend/helpers/library' import RecentlyPlayed from './components/RecentlyPlayed' -import { InstallModal } from './components' import LibraryContext from './LibraryContext' import { Category, PlatformsFilters, StoresFilters } from 'frontend/types' import { hasHelp } from 'frontend/hooks/hasHelp' @@ -35,16 +34,10 @@ import EmptyLibraryMessage from './components/EmptyLibrary' import CategoriesManager from './components/CategoriesManager' import LibraryTour from './components/LibraryTour' import AlphabetFilter from './components/AlphabetFilter' +import { openInstallGameModal } from 'frontend/state/InstallGameModal' const storage = window.localStorage -type ModalState = { - game: string - show: boolean - runner: Runner - gameInfo: GameInfo | null -} - export default React.memo(function Library(): JSX.Element { const { t } = useTranslation() @@ -202,12 +195,6 @@ export default React.memo(function Library(): JSX.Element { string | null >(null) - const [showModal, setShowModal] = useState({ - game: '', - show: false, - runner: 'legendary', - gameInfo: null - }) const [sortDescending, setSortDescending] = useState( JSON.parse(storage?.getItem('sortDescending') || 'false') ) @@ -267,7 +254,7 @@ export default React.memo(function Library(): JSX.Element { runner: Runner, gameInfo: GameInfo | null ) { - setShowModal({ game: appName, show: true, runner, gameInfo }) + openInstallGameModal({ appName, runner, gameInfo }) } // cache list of games being installed @@ -735,22 +722,6 @@ export default React.memo(function Library(): JSX.Element { - {showModal.show && ( - - setShowModal({ - game: '', - show: false, - runner: 'legendary', - gameInfo: null - }) - } - /> - )} - {showCategories && } ) diff --git a/src/frontend/state/GlobalState.tsx b/src/frontend/state/GlobalState.tsx index 807eacee31..f2c9248843 100644 --- a/src/frontend/state/GlobalState.tsx +++ b/src/frontend/state/GlobalState.tsx @@ -23,7 +23,6 @@ import { getGameInfo, getLegendaryConfig, notify } from '../helpers' import { i18n, t, TFunction } from 'i18next' import ContextProvider from './ContextProvider' -import { InstallModal } from 'frontend/screens/Library/components' import { configStore, @@ -978,7 +977,6 @@ class GlobalState extends PureComponent { render() { const { - showInstallModal, language, epic, gog, @@ -1074,18 +1072,6 @@ class GlobalState extends PureComponent { }} > {this.props.children} - {showInstallModal.show && ( - - this.setState({ - showInstallModal: { ...showInstallModal, show: false } - }) - } - /> - )} ) } diff --git a/src/frontend/state/InstallGameModal.ts b/src/frontend/state/InstallGameModal.ts new file mode 100644 index 0000000000..dff21758ae --- /dev/null +++ b/src/frontend/state/InstallGameModal.ts @@ -0,0 +1,38 @@ +import { GameInfo, Runner } from 'common/types' +import { create } from 'zustand' + +interface InstallGameModalState { + isOpen: boolean + appName?: string + runner?: Runner + gameInfo: GameInfo | null +} + +export const useInstallGameModal = create()(() => ({ + isOpen: false, + gameInfo: null +})) + +interface OpenInstallGameModalParams { + appName: string + runner: Runner + gameInfo: GameInfo | null +} +export const openInstallGameModal = ({ + appName, + runner, + gameInfo +}: OpenInstallGameModalParams) => { + useInstallGameModal.setState({ + isOpen: true, + appName, + runner, + gameInfo + }) +} + +export const closeInstallGameModal = () => { + useInstallGameModal.setState({ + isOpen: false + }) +}