Compare commits

...

11 Commits
0.9.8 ... 0.9.9

Author SHA1 Message Date
Vikeo
e6e562a0c6 fix types 2024-05-22 00:14:25 +02:00
Vikeo
3e38332a68 check version using semver 2024-05-22 00:10:16 +02:00
Vikeo
c23509ae26 icon tweak 2024-05-21 23:48:25 +02:00
Vikeo
9f1cc35eab new logo by elin 2024-05-21 21:06:43 +02:00
Vikeo
fe43e464de pnpm 9 2024-05-21 20:13:36 +02:00
Viktor Rådberg
b074499c1f small settings menu tweak 2024-05-15 18:25:45 +02:00
Viktor Rådberg
5953cf6b49 debump 2024-05-15 18:06:18 +02:00
Viktor Rådberg
acefbb8846 fix start menu width 2024-05-15 18:05:02 +02:00
Viktor Rådberg
adb79bf0e8 fix width 2024-05-10 23:23:32 +02:00
Viktor Rådberg
92be2e56d4 bump 2024-05-05 20:52:51 +02:00
Viktor Rådberg
854ca81a40 fix width 2024-05-05 20:52:30 +02:00
13 changed files with 6414 additions and 5188 deletions

View File

@@ -1,10 +1,10 @@
{
"name": "life-trinket",
"private": true,
"version": "0.9.8",
"version": "0.9.9",
"type": "commonjs",
"engines": {
"node": ">=18",
"node": ">=20",
"yarn": "use pnpm",
"npm": "please use pnpm"
},
@@ -24,6 +24,7 @@
"react-screen-wake-lock": "^3.0.2",
"react-swipeable": "^7.0.1",
"react-twc": "^1.3.0",
"semver": "^7.6.2",
"zod": "^3.22.4"
},
"devDependencies": {
@@ -33,6 +34,7 @@
"@svgr/cli": "^8.1.0",
"@types/react": "^18.3.1",
"@types/react-dom": "^18.3.0",
"@types/semver": "^7.5.8",
"@typescript-eslint/eslint-plugin": "^7.8.0",
"@typescript-eslint/parser": "^7.8.0",
"@vitejs/plugin-react-swc": "^3.6.0",

11091
pnpm-lock.yaml generated

File diff suppressed because it is too large Load Diff

Binary file not shown.

Before

Width:  |  Height:  |  Size: 25 KiB

After

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 18 KiB

After

Width:  |  Height:  |  Size: 9.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 56 KiB

After

Width:  |  Height:  |  Size: 43 KiB

View File

@@ -48,10 +48,12 @@ export const Dialog: React.FC<{
</button>
<div className="bg-background-default rounded-2xl max-w-[548px] max-h-[80vh] flex flex-col">
<div className="text-2xl text-center text-text-primary px-8 pt-4">
<h2 className="">{title}</h2>
<Separator height="1px" />
</div>
{title && (
<div className="text-2xl text-center text-text-primary px-8 pt-4">
<h2 className="">{title}</h2>
<Separator height="1px" />
</div>
)}
<div className="h-full overflow-auto text-text-primary show-scrollbar px-8 pb-8">
{children}

View File

@@ -1,5 +1,6 @@
import { useAnalytics } from '../../Hooks/useAnalytics';
import { BuyMeCoffee } from '../../Icons/generated/Support';
import { Separator } from '../Misc/Separator';
import { Paragraph } from '../Misc/TextComponents';
import { Dialog } from './Dialog';
@@ -10,57 +11,72 @@ export const InfoDialog = ({
}) => {
const analytics = useAnalytics();
return (
<Dialog id="info" title="📋 Usage Guide" dialogRef={dialogRef}>
<div className="text-text-primary">
<Paragraph className="my-4">
There are some controls that you might not know about, so here's a
short list of them.
</Paragraph>
<h3 className="text-lg font-bold mb-2">Life counter</h3>
<ul className="list-disc ml-6 mb-4">
<li>
<strong>Tap</strong> on a player's + or - button to add or subtract{' '}
<strong>1 life</strong>.
</li>
<li>
<strong>Long press</strong> on a player's + or - button to add or
subtract <strong>10 life</strong>.
</li>
</ul>
<h3 className="text-lg font-bold mb-2">
Commander damage and other counters
</h3>
<ul className="list-disc ml-6 mb-4">
<li>
<strong>Tap</strong> on the counter to add{' '}
<strong>1 counter</strong>.
</li>
<li>
<strong>Long press</strong> on the counter to subtract{' '}
<strong>1 counter</strong>.
</li>
</ul>
<h3 className="text-lg font-bold mb-2">Other functionality</h3>
<ul className="list-disc ml-6">
<li>
<Paragraph className="mb-1">
When a player is <strong>at or below 0 life</strong>, has taken{' '}
<strong>21 or more Commander Damage</strong> or has{' '}
<strong>10 or more poison counters</strong>, a button with a skull
will appear on that player's card. Tapping it will dim the
player's card.
</Paragraph>
</li>
<li>
<Paragraph className="mb-4">
Swiping <strong>down</strong> on a player's card will show that
player's settings menu.
</Paragraph>
</li>
</ul>
<Dialog id="info" title="Info" dialogRef={dialogRef}>
<div className=" text-text-primary">
<h2 className="text-md underline">Contributors</h2>
<div className="flex flex-row items-center gap-1 text-sm">
{/* <Trinket className="size-4" /> */}
<a href="#">Elin:</a> Icon design
</div>
<Separator height="1px" />
</div>
<div className="text-text-primary mt-4">
<div className="text">
<h2 className="text-xl">📋 Usage Guide</h2>
<Separator height="1px" />
</div>
<div className="text-text-primary">
<Paragraph className="mb-4">
There are some controls that you might not know about, so here's a
short list of them.
</Paragraph>
<h3 className="text-lg font-bold mb-2">Life counter</h3>
<ul className="list-disc ml-6 mb-4">
<li>
<strong>Tap</strong> on a player's + or - button to add or
subtract <strong>1 life</strong>.
</li>
<li>
<strong>Long press</strong> on a player's + or - button to add or
subtract <strong>10 life</strong>.
</li>
</ul>
<h3 className="text-lg font-bold mb-2">
Commander damage and other counters
</h3>
<ul className="list-disc ml-6 mb-4">
<li>
<strong>Tap</strong> on the counter to add{' '}
<strong>1 counter</strong>.
</li>
<li>
<strong>Long press</strong> on the counter to subtract{' '}
<strong>1 counter</strong>.
</li>
</ul>
<h3 className="text-lg font-bold mb-2">Other functionality</h3>
<ul className="list-disc ml-6">
<li>
<Paragraph className="mb-1">
When a player is <strong>at or below 0 life</strong>, has taken{' '}
<strong>21 or more Commander Damage</strong> or has{' '}
<strong>10 or more poison counters</strong>, a button with a
skull will appear on that player's card. Tapping it will dim the
player's card.
</Paragraph>
</li>
<li>
<Paragraph className="mb-4">
Swiping <strong>down</strong> on a player's card will show that
player's settings menu.
</Paragraph>
</li>
</ul>
</div>
</div>
<div className="text-center mt-4 text-text-primary">
Visit my{' '}
<a
@@ -72,7 +88,6 @@ export const InfoDialog = ({
</a>{' '}
for more info about this web app.
</div>
<div className="flex justify-center mt-4">
<a
className="flex flex-row items-center self-center border-none cursor-pointer bg-primary-main rounded-md mx-4 pr-4 pl-3 py-2 transition-colors duration-200 ease-in-out shadow-[1px_2px_4px_0px_rgba(0,0,0,0.3)] hover:bg-primary-dark"

View File

@@ -61,6 +61,7 @@ const ButtonsSections = twc.div`
justify-evenly
items-center
flex-wrap
h-full
mt-0
px-2
`;

View File

@@ -4,7 +4,7 @@ import { createInitialPlayers } from '../../../Data/getInitialPlayers';
import { useAnalytics } from '../../../Hooks/useAnalytics';
import { useGlobalSettings } from '../../../Hooks/useGlobalSettings';
import { usePlayers } from '../../../Hooks/usePlayers';
import { Cog, Info } from '../../../Icons/generated';
import { Cog, Info, Trinket } from '../../../Icons/generated';
import {
InitialGameSettings,
Orientation,
@@ -35,7 +35,7 @@ const standardSettings: Pick<
orientation: Orientation.Landscape,
};
const MainWrapper = twc.div`w-[100dvw] h-fit pb-24 overflow-hidden items-center flex flex-col min-[349px]:pb-10`;
const MainWrapper = twc.div`h-fit w-full pb-24 overflow-hidden items-center flex flex-col min-[349px]:pb-10`;
const StartButtonFooter = twc.div`w-full max-w-[548px] fixed bottom-4 z-1 items-center flex flex-row flex-wrap px-4 z-10 gap-4`;
@@ -173,177 +173,181 @@ const Start = () => {
<InfoDialog dialogRef={infoDialogRef} />
<SettingsDialog dialogRef={settingsDialogRef} />
<div className="flex justify-center items-center w-screen">
<MainWrapper>
<Info
className="size-8 absolute top-7 left-4 text-primary-main"
onClick={() => {
openInfo();
}}
/>
<a href="https://lifetrinket.com/">
<Trinket className="absolute w-12 h-12 top-4 right-4" />
</a>
<MainWrapper>
<Info
className="size-8 absolute top-4 left-4 text-primary-main"
onClick={() => {
openInfo();
}}
/>
<h1 className="relative flex flex-col text-3xl font-bold mt-6 mb-6 text-text-primary justify-center items-center">
<div className="flex flex-row items-center">Life Trinket</div>
<div className="h-[1px] w-[120%] bg-common-white opacity-50" />
<div className="flex absolute text-xs font-medium -bottom-4">
v{version.installedVersion}
</div>
</h1>
<h1 className="relative flex flex-col text-3xl font-bold mt-6 mb-6 text-text-primary justify-center items-center">
Life Trinket
<div className="h-[1px] w-[120%] bg-common-white opacity-50" />
<div className="flex absolute text-xs font-medium -bottom-4">
v{version.installedVersion}
</div>
</h1>
<div className="overflow-hidden items-center flex flex-col max-w-[548px] w-full mb-8 px-4">
<div className="w-full">
<ToggleButtonsWrapper className="mt-4">
<ToggleButton
label="Commander"
checked={
playerOptions.useCommanderDamage ??
initialGameSettings?.useCommanderDamage ??
true
}
onChange={(e) => {
if (e.target.checked) {
<div className="overflow-hidden items-center flex flex-col max-w-[548px] w-full mb-8 px-4">
<div className="w-full">
<ToggleButtonsWrapper className="mt-4">
<ToggleButton
label="Commander"
checked={
playerOptions.useCommanderDamage ??
initialGameSettings?.useCommanderDamage ??
true
}
onChange={(e) => {
if (e.target.checked) {
setPlayerOptions({
...playerOptions,
useCommanderDamage: e.target.checked,
...commanderSettings,
});
return;
}
setPlayerOptions({
...playerOptions,
useCommanderDamage: e.target.checked,
...commanderSettings,
...standardSettings,
});
return;
}
setPlayerOptions({
...playerOptions,
useCommanderDamage: e.target.checked,
...standardSettings,
});
}}
/>
}}
/>
<div className="flex flex-nowrap text-nowrap relative justify-center items-start">
<button
className="flex justify-center self-center items-center mt-1 mb-1 bg-primary-main px-3 py-2 rounded-md transition-colors duration-200 ease-in-out shadow-[1px_2px_4px_0px_rgba(0,0,0,0.3)] hover:bg-primary-dark"
onClick={openSettings}
>
<span className="text-sm flex flex-row items-center text-text-primary">
<Cog />
&nbsp;Game Settings
</span>
</button>
<div className="flex flex-nowrap text-nowrap relative justify-center items-start">
<button
className="flex justify-center self-center items-center mt-1 mb-1 bg-primary-main px-3 py-2 rounded-md transition-colors duration-200 ease-in-out shadow-[1px_2px_4px_0px_rgba(0,0,0,0.3)] hover:bg-primary-dark"
onClick={openSettings}
>
<span className="text-sm flex flex-row items-center text-text-primary">
<Cog />
&nbsp;Game Settings
</span>
</button>
<div
data-not-latest-version={
!version.isLatest && !!version.remoteVersion
}
className="absolute flex justify-center text-text-primary text-xxs -bottom-5 bg-primary-dark px-2 rounded-md
<div
data-not-latest-version={
!version.isLatest && !!version.remoteVersion
}
className="absolute flex justify-center text-text-primary text-xxs -bottom-5 bg-primary-dark px-2 rounded-md
opacity-0 transition-all duration-200 delay-500
data-[not-latest-version=true]:opacity-100
"
>
<div className="absolute bg-primary-dark rotate-45 size-2 -top-[2px] z-0" />
<span className="z-10">
v{version.remoteVersion} available!
</span>
>
<div className="absolute bg-primary-dark rotate-45 size-2 -top-[2px] z-0" />
<span className="z-10">
v{version.remoteVersion} available!
</span>
</div>
</div>
</div>
</ToggleButtonsWrapper>
<LabelText className="mt-4">Number of Players</LabelText>
<SliderWrapper>
<input
className="accent-primary-main text-primary-dark w-full h-3 rounded-lg cursor-pointer"
title="Number of Players"
type="range"
max={6}
min={1}
value={playerOptions?.numberOfPlayers ?? 4}
onChange={(e) => {
</ToggleButtonsWrapper>
<LabelText className="mt-4">Number of Players</LabelText>
<SliderWrapper>
<input
className="accent-primary-main text-primary-dark w-full h-3 rounded-lg cursor-pointer"
title="Number of Players"
type="range"
max={6}
min={1}
value={playerOptions?.numberOfPlayers ?? 4}
onChange={(e) => {
setPlayerOptions({
...playerOptions,
numberOfPlayers: Number.parseInt(e.target.value),
orientation: Orientation.Landscape,
});
}}
/>
<div className="flex w-full justify-between px-1 text-text-primary pointer-events-none">
<div>1</div>
<div>2</div>
<div>3</div>
<div>4</div>
<div>5</div>
<div>6</div>
</div>
</SliderWrapper>
<LabelText className="mt-4">Starting Health</LabelText>
<SliderWrapper>
<input
className="accent-primary-main text-primary-dark w-full h-3 rounded-lg cursor-pointer"
title="Starting Health"
type="range"
max={60}
min={20}
aria-label="Custom marks"
value={playerOptions?.startingLifeTotal ?? 40}
step={10}
onChange={(e) =>
setPlayerOptions({
...playerOptions,
startingLifeTotal: Number.parseInt(e.target.value),
orientation: Orientation.Landscape,
})
}
/>
<div className="flex w-full justify-between px-1 text-text-primary pointer-events-none">
<div>20</div>
<div>30</div>
<div>40</div>
<div>50</div>
<div>60</div>
</div>
</SliderWrapper>
<LabelText className="mt-4">Layout</LabelText>
<LayoutOptions
numberOfPlayers={playerOptions.numberOfPlayers}
selectedOrientation={playerOptions.orientation}
onChange={(orientation) => {
setPlayerOptions({
...playerOptions,
numberOfPlayers: Number.parseInt(e.target.value),
orientation: Orientation.Landscape,
orientation,
});
}}
/>
<div className="flex w-full justify-between px-1 text-text-primary pointer-events-none">
<div>1</div>
<div>2</div>
<div>3</div>
<div>4</div>
<div>5</div>
<div>6</div>
</div>
</SliderWrapper>
<LabelText className="mt-4">Starting Health</LabelText>
<SliderWrapper>
<input
className="accent-primary-main text-primary-dark w-full h-3 rounded-lg cursor-pointer"
title="Starting Health"
type="range"
max={60}
min={20}
aria-label="Custom marks"
value={playerOptions?.startingLifeTotal ?? 40}
step={10}
onChange={(e) =>
setPlayerOptions({
...playerOptions,
startingLifeTotal: Number.parseInt(e.target.value),
orientation: Orientation.Landscape,
})
}
/>
<div className="flex w-full justify-between px-1 text-text-primary pointer-events-none">
<div>20</div>
<div>30</div>
<div>40</div>
<div>50</div>
<div>60</div>
</div>
</SliderWrapper>
<LabelText className="mt-4">Layout</LabelText>
<LayoutOptions
numberOfPlayers={playerOptions.numberOfPlayers}
selectedOrientation={playerOptions.orientation}
onChange={(orientation) => {
setPlayerOptions({
...playerOptions,
orientation,
});
}}
/>
</div>
{!isPWA && (
<p className="text-center text-xs text-text-primary w-11/12 mt-4">
If you're on iOS, this page works better if you{' '}
<strong>hide the toolbar</strong> or{' '}
<strong>add the app to your home screen</strong>.
</p>
)}
</div>
{!isPWA && (
<p className="text-center text-xs text-text-primary w-11/12 mt-4">
If you're on iOS, this page works better if you{' '}
<strong>hide the toolbar</strong> or{' '}
<strong>add the app to your home screen</strong>.
</p>
)}
</div>
<StartButtonFooter>
<button
className="flex flex-grow basis-0 justify-center self-center items-center bg-primary-main px-3 py-2 rounded-md text-text-primary min-w-[150px] duration-200 ease-in-out shadow-[1px_2px_4px_0px_rgba(0,0,0,0.3)] hover:bg-primary-dark"
onClick={doStartNewGame}
>
NEW GAME
</button>
{savedGame && (
<StartButtonFooter>
<button
className="flex flex-grow basis-0 justify-center self-center items-center bg-secondary-main px-3 py-2 rounded-md text-text-primary min-w-[150px]
className="flex flex-grow basis-0 justify-center self-center items-center bg-primary-main px-3 py-2 rounded-md text-text-primary min-w-[150px] duration-200 ease-in-out shadow-[1px_2px_4px_0px_rgba(0,0,0,0.3)] hover:bg-primary-dark"
onClick={doStartNewGame}
>
NEW GAME
</button>
{savedGame && (
<button
className="flex flex-grow basis-0 justify-center self-center items-center bg-secondary-main px-3 py-2 rounded-md text-text-primary min-w-[150px]
duration-200 ease-in-out shadow-[1px_2px_4px_0px_rgba(0,0,0,0.3)] hover:bg-secondary-dark"
onClick={doResumeGame}
>
RESUME&nbsp;
<span className="text-xs">
({savedGame.players.length}&nbsp;
{savedGame.players.length > 1 ? 'players' : 'player'})
</span>
</button>
)}
</StartButtonFooter>
</MainWrapper>
onClick={doResumeGame}
>
RESUME&nbsp;
<span className="text-xs">
({savedGame.players.length}&nbsp;
{savedGame.players.length > 1 ? 'players' : 'player'})
</span>
</button>
)}
</StartButtonFooter>
</MainWrapper>
</div>
</>
);
};

View File

@@ -0,0 +1,51 @@
import PropTypes from 'prop-types';
import { SVGProps } from 'react';
interface SVGRProps {
title?: string;
titleId?: string;
size?: string;
}
const Trinket = ({
title,
titleId,
...props
}: SVGProps<SVGSVGElement> & SVGRProps) => {
return (
<svg
xmlns="http://www.w3.org/2000/svg"
width={props.size || 16}
height={props.size || 16}
fill="none"
viewBox="0 0 364 472"
aria-labelledby={titleId}
{...props}
>
{title ? <title id={titleId}>{title}</title> : null}
<path
fill="#78A083"
d="M40.536 302.159c-6.366-1.843-13.102 1.822-14.118 8.371-1.599 10.309-1.49 20.912.345 31.493 2.538 14.638 8.327 28.947 17.037 42.11s18.895 21.898 32.45 31.582 32.017 14.639 48.355 19.37 34.674 9.982 51.306 9.04c16.633-.942 29.437-2.571 43.833-9.043s26.935-15.473 36.901-26.49c7.205-7.964 12.964-16.868 17.121-26.436 2.641-6.078-1.095-12.775-7.461-14.619L153.42 334.848zM323.254 168.504c6.37 1.832 13.099-1.846 14.102-8.397 1.579-10.312 1.449-20.915-.405-31.493-2.566-14.633-8.382-28.93-17.117-42.077s-18.937-21.862-32.511-31.52-32.044-14.578-48.391-19.278-34.693-9.916-51.324-8.942-29.432 2.626-43.815 9.126-26.905 15.525-36.851 26.56c-7.19 7.978-12.93 16.893-17.07 26.468-2.629 6.084 1.12 12.774 7.489 14.605l112.946 32.474z"
/>
<path
fill="url(#a)"
d="M75.577 127.413c2.38-5.473 3.57-8.209 5.537-9.963a12 12 0 0 1 6.168-2.906c2.604-.399 5.472.425 11.207 2.074l216.593 62.274c5.73 1.648 8.595 2.471 10.588 4.191a12 12 0 0 1 3.683 5.732c.736 2.528.295 5.476-.588 11.372l-10.644 71.096c-.14.937-.211 1.405-.317 1.865q-.141.614-.347 1.209c-.154.446-.343.881-.721 1.749l-28.861 66.269c-2.382 5.469-3.573 8.204-5.538 9.956a12 12 0 0 1-6.168 2.904c-2.603.398-5.469-.426-11.202-2.074L48.371 290.886c-5.732-1.648-8.597-2.472-10.59-4.191a12 12 0 0 1-3.684-5.735c-.735-2.527-.293-5.476.592-11.374l10.654-71.027c.14-.934.21-1.401.316-1.86q.142-.612.346-1.206c.153-.445.342-.878.718-1.744z"
/>
<defs>
<radialGradient
id="a"
cx={0}
cy={0}
r={1}
gradientTransform="matrix(-25.05324 87.13566 -130.70377 -37.57994 181.959 234.953)"
gradientUnits="userSpaceOnUse"
>
<stop stopColor="#FFF4BE" />
<stop offset={1} stopColor="#FFC374" />
</radialGradient>
</defs>
</svg>
);
};
Trinket.propTypes = {
title: PropTypes.string,
};
export default Trinket;

View File

@@ -13,3 +13,4 @@ export { default as PartnerTax } from './PartnerTax';
export { default as Poison } from './Poison';
export { default as ResetGame } from './ResetGame';
export { default as Skull } from './Skull';
export { default as Trinket } from './Trinket';

View File

@@ -0,0 +1,11 @@
<svg width="364" height="472" viewBox="0 0 364 472" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M40.5356 302.159C34.1697 300.316 27.4337 303.981 26.418 310.53C24.8192 320.839 24.9288 331.442 26.7633 342.023C29.3011 356.661 35.0901 370.97 43.7998 384.133C52.5096 397.296 62.695 406.031 76.2507 415.715C89.8064 425.399 108.267 430.354 124.605 435.085C140.943 439.816 159.279 445.067 175.911 444.125C192.544 443.183 205.348 441.554 219.744 435.082C234.14 428.61 246.679 419.609 256.645 408.592C263.85 400.628 269.609 391.724 273.766 382.156C276.407 376.078 272.671 369.381 266.305 367.537L153.42 334.848L40.5356 302.159Z" fill="#78A083"/>
<path d="M323.254 168.504C329.624 170.336 336.353 166.658 337.356 160.107C338.935 149.795 338.805 139.192 336.951 128.614C334.385 113.981 328.569 99.6837 319.834 86.5374C311.099 73.3911 300.897 64.6755 287.323 55.0171C273.749 45.3588 255.279 40.4391 238.932 35.7391C222.585 31.0391 204.239 25.8229 187.608 26.7968C170.977 27.7707 158.176 29.4234 143.793 35.923C129.41 42.4225 116.888 51.4477 106.942 62.4834C99.7528 70.4607 94.0113 79.3756 89.8724 88.9514C87.2431 95.035 90.9911 101.725 97.3605 103.556L210.307 136.03L323.254 168.504Z" fill="#78A083"/>
<path d="M75.5773 127.413C77.9577 121.94 79.1479 119.204 81.1136 117.45C82.8455 115.905 84.9883 114.896 87.2823 114.544C89.8859 114.145 92.7537 114.969 98.4892 116.618L315.082 178.892C320.812 180.54 323.677 181.363 325.67 183.083C327.426 184.597 328.705 186.589 329.353 188.815C330.089 191.343 329.648 194.291 328.765 200.187L318.121 271.283C317.981 272.22 317.91 272.688 317.804 273.148C317.71 273.557 317.594 273.961 317.457 274.357C317.303 274.803 317.114 275.238 316.736 276.106L287.875 342.375C285.493 347.844 284.302 350.579 282.337 352.331C280.605 353.875 278.462 354.883 276.169 355.235C273.566 355.633 270.7 354.809 264.967 353.161L48.371 290.886C42.6395 289.238 39.7737 288.414 37.7805 286.695C36.0242 285.179 34.7448 283.188 34.097 280.96C33.3618 278.433 33.8042 275.484 34.6888 269.586L45.3425 198.559C45.4826 197.625 45.5527 197.158 45.6588 196.699C45.753 196.291 45.8686 195.889 46.0048 195.493C46.1582 195.048 46.3466 194.615 46.7235 193.749L75.5773 127.413Z" fill="url(#paint0_radial_14799_77884)"/>
<defs>
<radialGradient id="paint0_radial_14799_77884" cx="0" cy="0" r="1" gradientUnits="userSpaceOnUse" gradientTransform="translate(181.959 234.953) rotate(106.041) scale(90.6658 135.999)">
<stop stop-color="#FFF4BE"/>
<stop offset="1" stop-color="#FFC374"/>
</radialGradient>
</defs>
</svg>

After

Width:  |  Height:  |  Size: 2.5 KiB

View File

@@ -14,6 +14,7 @@ import {
initialGameSettingsSchema,
settingsSchema,
} from '../Types/Settings';
import { gte as semverGreaterThanOrEqual } from 'semver';
export const GlobalSettingsProvider = ({
children,
@@ -244,7 +245,12 @@ export const GlobalSettingsProvider = ({
setRemoteVersion(data.name);
if (data.name === import.meta.env.VITE_APP_VERSION) {
const isLatest = semverGreaterThanOrEqual(
import.meta.env.VITE_APP_VERSION,
data.name
);
if (isLatest) {
setIsLatestVersion(true);
return;
}