Merge branch 'master' into feat/702-respect-system-proxy-windows

This commit is contained in:
Gold John King
2024-12-24 19:52:46 +08:00
21 changed files with 168 additions and 69 deletions
@@ -2,7 +2,7 @@ import Tippy from "@tippyjs/react";
import { GlowEffect } from "renderer/components/shared/glow-effect.component";
import { BsmIcon } from "renderer/components/svgs/bsm-icon.component";
import { SvgIcon } from "renderer/components/svgs/svg-icon.type";
import { useTranslation } from "renderer/hooks/use-translation.hook";
import { useTranslationV2 } from "renderer/hooks/use-translation.hook";
type Props = {
onClick: (active: boolean) => void;
@@ -13,7 +13,7 @@ type Props = {
};
export function LaunchModToogle({ onClick, active, text, icon: Icon, infoText }: Props) {
const t = useTranslation();
const { text: t } = useTranslationV2();
return (
<button className={`shrink-0 relative rounded-full cursor-pointer group active:scale-95 transition-transform ${!active && "shadow-md shadow-black"}`} onClick={() => onClick(!active)}>
@@ -22,7 +22,7 @@ export function LaunchModToogle({ onClick, active, text, icon: Icon, infoText }:
{Icon && <Icon className="h-7 shrink-0 text-gray-800 dark:text-white" />}
<span className="w-fit min-w-fit text-lg font-bold uppercase tracking-wide italic ">{t(text)}</span>
{infoText && (
<Tippy content={t(infoText)} placement="top" theme="default" delay={[400, 0]}>
<Tippy content={t(infoText)} className="break-words" placement="top" theme="default" delay={[200, 0]}>
<div className="h-[25px] w-[25px] shrink-0 p-1.5 rounded-full cursor-help bg-light-main-color-1 dark:bg-main-color-3 hover:brightness-110">
<BsmIcon className="w-full h-full" icon="info" />
</div>
@@ -52,7 +52,7 @@ export function LaunchModItem({ id, icon: Icon, label, description, active, visi
const { text: t } = useTranslationV2();
return (
<Tippy theme="default" placement="top" content={description}>
<Tippy theme="default" className="break-words" placement="top" content={description}>
<button id={id} className={cn("grow rounded-md bg-theme-1 relative flex justify-center items-center h-10 py-1 px-3", visible === false && "hidden")} onClick={e => { e.preventDefault(); e.stopPropagation(); onChange?.(!active) }}>
<BsmCheckbox className="h-4 aspect-square z-[1] relative mr-1.5" checked={active} onChange={onChange}/>
{Icon && <Icon className="h-full w-fit py-0.5 mr-1.5"/>}
@@ -62,7 +62,22 @@ export function LaunchSlide({ version }: Props) {
}
}, [activeLaunchMods]);
const toggleActiveLaunchMod = (checked: boolean, launchMod: LaunchMod) => checked
? setActiveLaunchMods(prev => [...prev, launchMod])
: setActiveLaunchMods(prev => prev.filter(mod => mod !== launchMod));
const togglePinnedLaunchMod = (pinned: boolean, launchMod: LaunchMod) => pinned
? setPinnedLaunchMods(prev => [...prev, launchMod])
: setPinnedLaunchMods(prev => prev.filter(mod => mod !== launchMod));
useEffect(() => {
let protonLogsPath: string[] = [];
if (window.electron.platform === "linux") {
protonLogsPath = version.steam
? [version.path, "Logs"]
: ["BSInstances", version.name, "Logs"];
}
setLaunchModItems(() => [
{
id: LaunchMods.OCULUS,
@@ -72,8 +87,8 @@ export function LaunchSlide({ version }: Props) {
active: activeLaunchMods.includes(LaunchMods.OCULUS),
visible: !(version.metadata?.store === BsStore.OCULUS),
pinned: pinnedLaunchMods.includes(LaunchMods.OCULUS),
onChange: checked => checked ? setActiveLaunchMods(prev => [...prev, LaunchMods.OCULUS]) : setActiveLaunchMods(prev => prev.filter(mod => mod !== LaunchMods.OCULUS)),
onPinChange: pinned => pinned ? setPinnedLaunchMods(prev => [...prev, LaunchMods.OCULUS]) : setPinnedLaunchMods(prev => prev.filter(mod => mod !== LaunchMods.OCULUS)),
onChange: (checked) => toggleActiveLaunchMod(checked, LaunchMods.OCULUS),
onPinChange: (pinned) => togglePinnedLaunchMod(pinned, LaunchMods.OCULUS),
},
{
id: LaunchMods.FPFC,
@@ -82,8 +97,8 @@ export function LaunchSlide({ version }: Props) {
description: t("pages.version-viewer.launch-mods.desktop-description"),
active: activeLaunchMods.includes(LaunchMods.FPFC),
pinned: pinnedLaunchMods.includes(LaunchMods.FPFC),
onChange: checked => checked ? setActiveLaunchMods(prev => [...prev, LaunchMods.FPFC]) : setActiveLaunchMods(prev => prev.filter(mod => mod !== LaunchMods.FPFC)),
onPinChange: pinned => pinned ? setPinnedLaunchMods(prev => [...prev, LaunchMods.FPFC]) : setPinnedLaunchMods(prev => prev.filter(mod => mod !== LaunchMods.FPFC)),
onChange: (checked) => toggleActiveLaunchMod(checked, LaunchMods.FPFC),
onPinChange: (pinned) => togglePinnedLaunchMod(pinned, LaunchMods.FPFC),
},
{
id: LaunchMods.DEBUG,
@@ -92,8 +107,8 @@ export function LaunchSlide({ version }: Props) {
description: t("pages.version-viewer.launch-mods.debug-description"),
active: activeLaunchMods.includes(LaunchMods.DEBUG),
pinned: pinnedLaunchMods.includes(LaunchMods.DEBUG),
onChange: checked => checked ? setActiveLaunchMods(prev => [...prev, LaunchMods.DEBUG]) : setActiveLaunchMods(prev => prev.filter(mod => mod !== LaunchMods.DEBUG)),
onPinChange: pinned => pinned ? setPinnedLaunchMods(prev => [...prev, LaunchMods.DEBUG]) : setPinnedLaunchMods(prev => prev.filter(mod => mod !== LaunchMods.DEBUG)),
onChange: (checked) => toggleActiveLaunchMod(checked, LaunchMods.DEBUG),
onPinChange: (pinned) => togglePinnedLaunchMod(pinned, LaunchMods.DEBUG),
},
{
id: LaunchMods.SKIP_STEAM,
@@ -101,8 +116,8 @@ export function LaunchSlide({ version }: Props) {
description: t("pages.version-viewer.launch-mods.skipsteam-description"),
active: activeLaunchMods.includes(LaunchMods.SKIP_STEAM),
pinned: pinnedLaunchMods.includes(LaunchMods.SKIP_STEAM),
onChange: checked => checked ? setActiveLaunchMods(prev => [...prev, LaunchMods.SKIP_STEAM]) : setActiveLaunchMods(prev => prev.filter(mod => mod !== LaunchMods.SKIP_STEAM)),
onPinChange: pinned => pinned ? setPinnedLaunchMods(prev => [...prev, LaunchMods.SKIP_STEAM]) : setPinnedLaunchMods(prev => prev.filter(mod => mod !== LaunchMods.SKIP_STEAM)),
onChange: (checked) => toggleActiveLaunchMod(checked, LaunchMods.SKIP_STEAM),
onPinChange: (pinned) => togglePinnedLaunchMod(pinned, LaunchMods.SKIP_STEAM),
},
{
id: LaunchMods.EDITOR,
@@ -112,14 +127,25 @@ export function LaunchSlide({ version }: Props) {
active: activeLaunchMods.includes(LaunchMods.EDITOR),
pinned: pinnedLaunchMods.includes(LaunchMods.EDITOR),
visible: !safeLt(version.BSVersion, "1.23.0"),
onChange: checked => checked ? setActiveLaunchMods(prev => [...prev, LaunchMods.EDITOR]) : setActiveLaunchMods(prev => prev.filter(mod => mod !== LaunchMods.EDITOR)),
onPinChange: pinned => pinned ? setPinnedLaunchMods(prev => [...prev, LaunchMods.EDITOR]) : setPinnedLaunchMods(prev => prev.filter(mod => mod !== LaunchMods.EDITOR)),
}
onChange: (checked) => toggleActiveLaunchMod(checked, LaunchMods.EDITOR),
onPinChange: (pinned) => togglePinnedLaunchMod(pinned, LaunchMods.EDITOR),
},
{
id: LaunchMods.PROTON_LOGS,
label: t("pages.version-viewer.launch-mods.proton-logs"),
description: t("pages.version-viewer.launch-mods.proton-logs-description", {
versionPath: `${window.electron.path.join(...protonLogsPath)}/`
}),
active: activeLaunchMods.includes(LaunchMods.PROTON_LOGS),
pinned: pinnedLaunchMods.includes(LaunchMods.PROTON_LOGS),
visible: window.electron.platform === "linux",
onChange: (checked) => toggleActiveLaunchMod(checked, LaunchMods.PROTON_LOGS),
onPinChange: (pinned) => togglePinnedLaunchMod(pinned, LaunchMods.PROTON_LOGS),
},
]);
}, [activeLaunchMods, pinnedLaunchMods, version]);
const launch = () => {
const launch = async () => {
const additionalArgs = additionalArgsString?.split(";").map(arg => arg.trim()).filter(arg => arg.length > 0);
const launch$ = bsLauncherService.launch({
@@ -193,5 +219,3 @@ export function LaunchSlide({ version }: Props) {
</div>
);
}
+8 -1
View File
@@ -5,6 +5,7 @@ import { ConfigurationService } from "./configuration.service";
import { getProperty } from "dot-prop";
import { i18n } from "dateformat";
import { createElement, Fragment } from "react";
import { logRenderError } from "renderer";
export class I18nService {
private static instance: I18nService;
@@ -79,7 +80,13 @@ export class I18nService {
public translate(translationKey: string, args?: Record<string, string>): string {
let translated = this.cache.get(translationKey);
if (!translated) {
translated = getProperty(this.dictionary, translationKey) ?? translationKey;
try {
translated = getProperty(this.dictionary, translationKey) ?? translationKey;
} catch (error) {
// Invalid translationKey like strings containing "[]"
logRenderError(`Could not get property of ${translationKey}`, error);
translated = translationKey;
}
this.cache.set(translationKey, translated);
}