From afdb45a1d2d0313010da5baea19e52803a1c7575 Mon Sep 17 00:00:00 2001 From: MathieuG-P Date: Fri, 15 Jul 2022 20:25:06 +0200 Subject: [PATCH] add double click to quick launch --- .../nav-bar/bs-version-item.component.tsx | 16 ++- .../available-versions-list.components.tsx | 22 +--- .../pages/version-viewer.component.tsx | 33 +---- .../services/bs-downloader.service.ts | 114 ++++++++++-------- src/renderer/services/bs-launcher.service.ts | 52 +++++--- 5 files changed, 125 insertions(+), 112 deletions(-) diff --git a/src/renderer/components/nav-bar/bs-version-item.component.tsx b/src/renderer/components/nav-bar/bs-version-item.component.tsx index 5311cf7f..ed4aac8e 100644 --- a/src/renderer/components/nav-bar/bs-version-item.component.tsx +++ b/src/renderer/components/nav-bar/bs-version-item.component.tsx @@ -5,6 +5,8 @@ import { SteamIcon } from "../svgs/steam-icon.component"; import { BsDownloaderService } from "renderer/services/bs-downloader.service"; import { useEffect, useState } from "react"; import { combineLatest } from "rxjs"; +import { BSLauncherService, LaunchMods } from "renderer/services/bs-launcher.service"; +import { ConfigurationService } from "renderer/services/configuration.service"; export default function BsVersionItem(props: {version: BSVersion}) { @@ -14,11 +16,23 @@ export default function BsVersionItem(props: {version: BSVersion}) { const [downloadPercent, setDownloadPercent] = useState(0); const downloaderService = BsDownloaderService.getInstance(); + const launcherService = BSLauncherService.getInstance(); + const configService = ConfigurationService.getInstance(); const isActive = (): boolean => { return props.version?.BSVersion === state?.BSVersion && props?.version.steam === state?.steam; } + const handleDoubleClick = () => { + if(state.steam){ return; } + launcherService.launch( + state, + !!configService.get(LaunchMods.OCULUS_MOD), + !!configService.get(LaunchMods.DESKTOP_MOD), + !!configService.get(LaunchMods.DEBUG_MOD) + ) + } + useEffect(() => { combineLatest([downloaderService.currentBsVersionDownload$, downloaderService.downloadProgress$]).subscribe(vals => { if(vals[0]?.BSVersion === props.version.BSVersion && vals[0]?.steam === props.version.steam){ @@ -36,7 +50,7 @@ export default function BsVersionItem(props: {version: BSVersion}) { return (
- + {props.version.steam && } {!props.version.steam && } {props.version.BSVersion} diff --git a/src/renderer/pages/available-versions-list.components.tsx b/src/renderer/pages/available-versions-list.components.tsx index a97aaa72..bc786551 100644 --- a/src/renderer/pages/available-versions-list.components.tsx +++ b/src/renderer/pages/available-versions-list.components.tsx @@ -3,10 +3,8 @@ import { BsDownloaderService } from "../services/bs-downloader.service"; import { Slideshow } from "renderer/components/slideshow/slideshow.component"; import { useEffect, useState } from "react"; import { BSVersion } from "main/services/bs-version-manager.service"; -import { ProgressBarService } from "renderer/services/progress-bar.service"; import { BsmButton } from "renderer/components/shared/bsm-button.component"; import { AnimatePresence, motion } from "framer-motion"; -import { NotificationService } from "renderer/services/notification.service"; import { useTranslation } from "renderer/hooks/use-translation.hook"; import { BSVersionManagerService } from "renderer/services/bs-version-manager.service"; import { useObservable } from "renderer/hooks/use-observable.hook"; @@ -23,25 +21,15 @@ export function AvailableVersionsList() { require('../../../assets/images/slideshow-images/image-7-blur.png'), ]; const bsDownloaderService: BsDownloaderService = BsDownloaderService.getInstance(); - const progressBarService: ProgressBarService = ProgressBarService.getInstance(); - const notificationService: NotificationService = NotificationService.getInstance(); const versionManagerService: BSVersionManagerService = BSVersionManagerService.getInstance(); const [versionSelected, setVersionSelected] = useState(null as BSVersion); - const progressBarVisible = useObservable(progressBarService.visible$); + const currentVersionDownloading = useObservable(bsDownloaderService.currentBsVersionDownload$); const t = useTranslation(); - const startDownload = () => { - if(progressBarService.visible$.value){ return; } - progressBarService.show(bsDownloaderService.downloadProgress$); - bsDownloaderService.download(versionSelected).then(res => { - progressBarService.hide(true); - - if(res.success){ - notificationService.notifySuccess({title: "notifications.bs-download.success.titles.download-success", duration: 3000}); - } - }); - } + const startDownload = () => { + bsDownloaderService.download(versionSelected, versionManagerService.isVersionInstalled(versionSelected)); + } useEffect(() => { const versionSelectedSub = bsDownloaderService.selectedBsVersion$.subscribe(version => { @@ -61,7 +49,7 @@ export function AvailableVersionsList() { - { versionSelected && !progressBarVisible && ( + { versionSelected && !currentVersionDownloading && ( diff --git a/src/renderer/pages/version-viewer.component.tsx b/src/renderer/pages/version-viewer.component.tsx index 8dc772b8..52b7fb54 100644 --- a/src/renderer/pages/version-viewer.component.tsx +++ b/src/renderer/pages/version-viewer.component.tsx @@ -14,9 +14,7 @@ import { BSUninstallerService } from '../services/bs-uninstaller.service'; import { BSVersionManagerService } from '../services/bs-version-manager.service'; import { ModalExitCode, ModalService, ModalType } from '../services/modale.service'; import DefautVersionImage from "../../../assets/images/default-version-img.jpg"; -import { NotificationService } from 'renderer/services/notification.service'; import { BsDownloaderService } from 'renderer/services/bs-downloader.service'; -import { ProgressBarService } from 'renderer/services/progress-bar.service'; import { useTranslation } from 'renderer/hooks/use-translation.hook'; export function VersionViewer() { @@ -34,9 +32,7 @@ export function VersionViewer() { const bsUninstallerService = BSUninstallerService.getInstance(); const bsVersionManagerService = BSVersionManagerService.getInstance(); const modalService = ModalService.getInsance(); - const notificationService = NotificationService.getInstance(); const bsDownloaderService = BsDownloaderService.getInstance(); - const progressService = ProgressBarService.getInstance(); useEffect(() => { setOculusMode(!!configService.get(LaunchMods.OCULUS_MOD)); @@ -81,30 +77,13 @@ export function VersionViewer() { } } - const verifyFiles = () => { - progressService.show(bsDownloaderService.downloadProgress$); - bsDownloaderService.download(state).then(res => { - progressService.hide(true); - if(!res.success){ notificationService.notifyError({title: "notifications.bs-download.errors.titles.verification-failed", desc: "notifications.bs-download.errors.msg.verification-failed"}); } - else(notificationService.notifySuccess({title: "notifications.bs-download.success.titles.verification-finished"})); - }) - } + const verifyFiles = () => { + bsDownloaderService.download(state, true); + } - const launchBs = () => { - bsLauncherService.launch(state, oculusMode, desktopMode, debugMode).then(res => { - if(!res.success){ notificationService.notifyError({title: "notifications.bs-launch.errors.titles.UNABLE_TO_LAUNCH", desc: res.error.title}); } - else if(res.data === "STEAM_NOT_RUNNING"){ notificationService.notifyError({title: "notifications.bs-launch.errors.titles.STEAM_NOT_RUNNING", desc: "notifications.bs-launch.errors.msg.STEAM_NOT_RUNNING"}); } - else if(res.data === "BS_ALREADY_RUNNING"){ notificationService.notifyError({title: "notifications.bs-launch.errors.titles.UNABLE_TO_LAUNCH", desc: "notifications.bs-launch.errors.msg.UNABLE_TO_LAUNCH"}); } - else if(res.data === "EXE_NOT_FINDED"){ - notificationService.notifyError({title: "notifications.bs-launch.errors.titles.EXE_NOT_FINDED", desc: "notifications.bs-launch.errors.msg.EXE_NOT_FINDED", actions: [{id: "0", title:"misc.verify"}]}).then(res => { - if(res !== "0"){ return; } - verifyFiles(); - }); - } - else if(res.data === "LAUNCHED"){ notificationService.notifySuccess({title: "notifications.bs-launch.success.titles.launching"}) } - else(notificationService.notifyError({title: res.data || res.error.title})); - }); - } + const launchBs = () => { + bsLauncherService.launch(state, oculusMode, desktopMode, debugMode); + } return ( <> diff --git a/src/renderer/services/bs-downloader.service.ts b/src/renderer/services/bs-downloader.service.ts index ff16eeb6..c50085a6 100644 --- a/src/renderer/services/bs-downloader.service.ts +++ b/src/renderer/services/bs-downloader.service.ts @@ -1,11 +1,13 @@ import { DownloadEvent } from 'main/services/bs-installer.service'; -import { BehaviorSubject, distinctUntilChanged } from 'rxjs'; +import { BehaviorSubject, distinctUntilChanged, filter, debounceTime } from 'rxjs'; import { IpcResponse } from 'shared/models/ipc-models.model'; import { BSVersion } from '../../main/services/bs-version-manager.service' import { AuthUserService } from './auth-user.service'; import { BSVersionManagerService } from './bs-version-manager.service'; import { IpcService } from './ipc.service'; import { ModalExitCode, ModalService, ModalType } from './modale.service'; +import { NotificationService } from './notification.service'; +import { ProgressBarService } from './progress-bar.service'; export class BsDownloaderService{ @@ -15,6 +17,8 @@ export class BsDownloaderService{ private readonly ipcService: IpcService; private readonly bsVersionManager: BSVersionManagerService; private readonly authService: AuthUserService; + private readonly progressBarService: ProgressBarService; + private readonly notificationService: NotificationService; public readonly currentBsVersionDownload$: BehaviorSubject = new BehaviorSubject(null); @@ -34,30 +38,35 @@ export class BsDownloaderService{ this.modalService = ModalService.getInsance(); this.bsVersionManager = BSVersionManagerService.getInstance(); this.authService = AuthUserService.getInstance(); + this.progressBarService = ProgressBarService.getInstance(); + this.notificationService = NotificationService.getInstance(); this.asignListerners(); } - private asignListerners(): void{ - - this.ipcService.watch("bs-download.[Progress]").pipe(distinctUntilChanged()).subscribe(response => this.downloadProgress$.next(response.data)); + private asignListerners(): void{ + this.ipcService.watch("bs-download.[Progress]").pipe(distinctUntilChanged()).subscribe(response => this.downloadProgress$.next(response.data)); - this.ipcService.watch("bs-download.[SteamID]").subscribe(response => response.success && this.authService.setSteamID(response.data)); + this.ipcService.watch("bs-download.[SteamID]").pipe(filter(r => r.success && !!r.data)).subscribe(response => this.authService.setSteamID(response.data)); - this.ipcService.watch("bs-download.[Warning]").subscribe(response => this.downloadWarning$.next(response.data)); + this.ipcService.watch("bs-download.[Warning]").pipe(filter(v => !!v && !!v.data), distinctUntilChanged(), debounceTime(1000)).subscribe(warning => { + this.notificationService.notifyWarning({title: "notifications.types.warning", desc: `notifications.bs-download.warnings.msg.${warning.data}`}); + }); - this.ipcService.watch("bs-download.[Error]").subscribe(response => this.downloadError$.next(response.data)); + this.ipcService.watch("bs-download.[Error]").pipe(filter(v => !!v && !!v.data), distinctUntilChanged(), debounceTime(1000)).subscribe(err => { + this.notificationService.notifyError({title: "notifications.types.error", desc: `notifications.bs-download.errors.msg.${err.data}`}); + }); - this.ipcService.watch("bs-download.[2FA]").subscribe(async response => { - if(!response.success){ return; } - const res = await this.modalService.openModal(ModalType.GUARD_CODE); - if(res.exitCode !== ModalExitCode.COMPLETED){ return; } - this.ipcService.sendLazy('bs-download.[2FA]', {args: res.data}); - }); + this.ipcService.watch("bs-download.[2FA]").subscribe(async response => { + if(!response.success){ return; } + const res = await this.modalService.openModal(ModalType.GUARD_CODE); + if(res.exitCode !== ModalExitCode.COMPLETED){ return; } + this.ipcService.sendLazy('bs-download.[2FA]', {args: res.data}); + }); - this.currentBsVersionDownload$.subscribe(version => { - if(version){ this.bsVersionManager.setInstalledVersions([...this.bsVersionManager.installedVersions$.value, version]); } - else{ this.bsVersionManager.askInstalledVersions(); } - }); + this.currentBsVersionDownload$.subscribe(version => { + if(version){ this.bsVersionManager.setInstalledVersions([...this.bsVersionManager.installedVersions$.value, version]); } + else{ this.bsVersionManager.askInstalledVersions(); } + }); } private resetDownload(): void{ @@ -66,44 +75,51 @@ export class BsDownloaderService{ this.selectedBsVersion$.next(null); } - public async download(bsVersion: BSVersion): Promise>{ - let promise; - if(!this.authService.sessionExist()){ - const res = await this.modalService.openModal(ModalType.STEAM_LOGIN); - if(res.exitCode !== ModalExitCode.COMPLETED){ return {success: false}; } - this.authService.setSteamSession(res.data.username, res.data.stay); - promise = this.ipcService.send('bs-download.start', {args: {bsVersion: bsVersion, username: res.data.username, password: res.data.password, stay: res.data.stay}}); - } - else{ - promise = this.ipcService.send('bs-download.start', {args: {bsVersion: bsVersion, username: this.authService.getSteamUsername()}}); - } + public async download(bsVersion: BSVersion, isVerification?: boolean): Promise>{ + if(this.progressBarService.visible$.value){ + this.notificationService.notifyError({title: "notifications.bs-download.errors.titles.already-downloading"}); + return {success: false}; + } - this.currentBsVersionDownload$.next(bsVersion); + this.progressBarService.show(this.downloadProgress$); - let res = await promise; + let promise; + if(!this.authService.sessionExist()){ + const res = await this.modalService.openModal(ModalType.STEAM_LOGIN); + if(res.exitCode !== ModalExitCode.COMPLETED){ return {success: false}; } + this.authService.setSteamSession(res.data.username, res.data.stay); + promise = this.ipcService.send('bs-download.start', {args: {bsVersion: bsVersion, username: res.data.username, password: res.data.password, stay: res.data.stay}}); + } + else{ + promise = this.ipcService.send('bs-download.start', {args: {bsVersion: bsVersion, username: this.authService.getSteamUsername()}}); + } - if(!res.success){ return res; } + this.currentBsVersionDownload$.next(bsVersion); + + let res = await promise; - if(res.data.type === "[Password]"){ - this.authService.deleteSteamSession(); - res = await this.download(bsVersion); - } - - this.resetDownload(); - return res; - } + if(res.data.type === "[Password]"){ + this.authService.deleteSteamSession(); + res = await this.download(bsVersion); + } + + this.progressBarService.hide(true); + this.resetDownload(); + res.success && this.notificationService.notifySuccess({title: `notifications.bs-download.success.titles.${isVerification ? "verification-finished" : "download-success"}`, duration: 3000}); + return res; + } - public get isDownloading(): boolean{ - return !!this.currentBsVersionDownload$.value; - } + public get isDownloading(): boolean{ + return !!this.currentBsVersionDownload$.value; + } - public async getInstallationFolder(): Promise{ - const res = await this.ipcService.send("bs-download.installation-folder"); - return res.success ? res.data : ""; - } + public async getInstallationFolder(): Promise{ + const res = await this.ipcService.send("bs-download.installation-folder"); + return res.success ? res.data : ""; + } - public setInstallationFolder(path: string): Promise>{ - return this.ipcService.send("bs-download.set-installation-folder", {args: path}); - } + public setInstallationFolder(path: string): Promise>{ + return this.ipcService.send("bs-download.set-installation-folder", {args: path}); + } } diff --git a/src/renderer/services/bs-launcher.service.ts b/src/renderer/services/bs-launcher.service.ts index 04cc43e5..e3d36e98 100644 --- a/src/renderer/services/bs-launcher.service.ts +++ b/src/renderer/services/bs-launcher.service.ts @@ -2,32 +2,48 @@ import { LauchOption } from "../../shared/models/launch-models.model"; import { BSVersion } from "../../main/services/bs-version-manager.service"; import { IpcService } from "./ipc.service"; import { BsLaunchResult } from "../../shared/models/launch-models.model"; -import { IpcResponse } from "shared/models/ipc-models.model"; +import { NotificationResult, NotificationService } from "./notification.service"; +import { BsDownloaderService } from "./bs-downloader.service"; export class BSLauncherService{ - private static instance: BSLauncherService; + private static instance: BSLauncherService; - private readonly ipcService: IpcService; + private readonly ipcService: IpcService; + private readonly notificationService: NotificationService; + private readonly bsDownloaderService: BsDownloaderService; + + public static getInstance(){ + if(!BSLauncherService.instance){ BSLauncherService.instance = new BSLauncherService(); } + return BSLauncherService.instance; + } - public static getInstance(){ - if(!BSLauncherService.instance){ BSLauncherService.instance = new BSLauncherService(); } - return BSLauncherService.instance; - } + private constructor(){ + this.ipcService = IpcService.getInstance(); + this.notificationService = NotificationService.getInstance(); + this.bsDownloaderService = BsDownloaderService.getInstance(); + } - private constructor(){ - this.ipcService = IpcService.getInstance(); - } - - public launch(version: BSVersion, oculus: boolean, desktop: boolean, debug: boolean): Promise>{ - const lauchOption: LauchOption = {debug, oculus, desktop, version}; - return this.ipcService.send("bs-launch.launch", {args: lauchOption}); - } + public launch(version: BSVersion, oculus: boolean, desktop: boolean, debug: boolean): Promise{ + const lauchOption: LauchOption = {debug, oculus, desktop, version}; + return this.ipcService.send("bs-launch.launch", {args: lauchOption}).then(res => { + if(!res.success){ return this.notificationService.notifyError({title: "notifications.bs-launch.errors.titles.UNABLE_TO_LAUNCH", desc: res.error.title}); } + if(res.data === "EXE_NOT_FINDED"){ + this.notificationService.notifyError({title: "notifications.bs-launch.errors.titles.EXE_NOT_FINDED", desc: "notifications.bs-launch.errors.msg.EXE_NOT_FINDED", actions: [{id: "0", title:"misc.verify"}]}).then(res => { + if(res === "0"){ this.bsDownloaderService.download(version, true); } + return res; + }); + } + if(res.data === "LAUNCHED"){ return this.notificationService.notifySuccess({title: "notifications.bs-launch.success.titles.launching"}); } + if(res.data){ return this.notificationService.notifyError({title: `notifications.bs-launch.errors.titles.${res.data}`}); } + return this.notificationService.notifyError({title: res.data || res.error.title}); + }); + } } export enum LaunchMods{ - OCULUS_MOD = "LAUNCH_OCULUS_MOD", - DESKTOP_MOD = "LAUNCH_DESKTOP_MOD", - DEBUG_MOD ="LAUNCH_DEBUG_MOD" + OCULUS_MOD = "LAUNCH_OCULUS_MOD", + DESKTOP_MOD = "LAUNCH_DESKTOP_MOD", + DEBUG_MOD ="LAUNCH_DEBUG_MOD" }