fix: update errors

This commit is contained in:
TrèsAbhi committed 2025-09-27 16:07:45 -05:00
1 parent 4ff9a2ec7f
commit c14efe86cc
34 files changed
+217 -280

No files matched your search

@@ -1,7 +1,8 @@
import type { GroupProps } from '@react-three/fiber';
import { forwardRef } from 'react';
import { Group } from 'three';
import { forwardRef, type ComponentProps } from "react";
import { Group } from "three";
export const ModelTankWrapper = forwardRef<Group, GroupProps>((props, ref) => {
return <group rotation={[-Math.PI / 2, 0, 0]} ref={ref} {...props} />;
});
export const ModelTankWrapper = forwardRef<Group, ComponentProps<"group">>(
(props, ref) => {
return <group rotation={[-Math.PI / 2, 0, 0]} ref={ref} {...props} />;
}
);
@@ -1,19 +1,19 @@
import { memo, useRef } from 'react';
import { Group } from 'three';
import { correctZYTuple } from '../../../core/blitz/correctZYTuple';
import { nameToArmorId } from '../../../core/blitzkit/nameToArmorId';
import { resolveArmor } from '../../../core/blitzkit/resolveThickness';
import { useArmor } from '../../../hooks/useArmor';
import { useTankModelDefinition } from '../../../hooks/useTankModelDefinition';
import { useTankTransform } from '../../../hooks/useTankTransform';
import { Duel } from '../../../stores/duel';
import { ModelTankWrapper } from './ModelTankWrapper';
import { PrimaryArmorSceneComponent } from './PrimaryArmorSceneComponent';
import { memo, useRef } from "react";
import { Group } from "three";
import { correctZYTuple } from "../../../core/blitz/correctZYTuple";
import { nameToArmorId } from "../../../core/blitzkit/nameToArmorId";
import { resolveArmor } from "../../../core/blitzkit/resolveThickness";
import { useArmor } from "../../../hooks/useArmor";
import { useTankModelDefinition } from "../../../hooks/useTankModelDefinition";
import { useTankTransform } from "../../../hooks/useTankTransform";
import { Duel } from "../../../stores/duel";
import { ModelTankWrapper } from "./ModelTankWrapper";
import { PrimaryArmorSceneComponent } from "./PrimaryArmorSceneComponent";
export const PrimaryArmorScene = memo(() => {
const wrapper = useRef<Group>(null);
const turretContainer = useRef<Group>(null);
const gunContainer = useRef<Group>(null);
const turretContainer = useRef<Group>(null!);
const gunContainer = useRef<Group>(null!);
const tank = Duel.use((state) => state.protagonist.tank);
const track = Duel.use((state) => state.protagonist.track);
const turret = Duel.use((state) => state.protagonist.turret);
@@ -28,7 +28,7 @@ export const PrimaryArmorScene = memo(() => {
const turretOrigin = correctZYTuple(tankModelDefinition.turret_origin);
const gunOrigin = correctZYTuple(turretModelDefinition.gun_origin);
const isDynamicArmorActive = Duel.use((state) =>
state.protagonist.consumables.includes(73),
state.protagonist.consumables.includes(73)
);
useTankTransform(track, turret, turretContainer, gunContainer);
@@ -37,20 +37,20 @@ export const PrimaryArmorScene = memo(() => {
<ModelTankWrapper ref={wrapper}>
<group position={hullOrigin}>
{armorNodes.map((node) => {
const isHull = node.name.startsWith('hull_');
const isHull = node.name.startsWith("hull_");
const isVisible = isHull;
const armorId = nameToArmorId(node.name);
const { spaced, thickness } = resolveArmor(
tankModelDefinition.armor,
armorId,
armorId
);
if (
!isVisible ||
spaced ||
thickness === undefined ||
(isDynamicArmorActive && node.name.includes('state_01')) ||
(!isDynamicArmorActive && node.name.includes('state_00'))
(isDynamicArmorActive && node.name.includes("state_01")) ||
(!isDynamicArmorActive && node.name.includes("state_00"))
)
return null;
@@ -67,21 +67,21 @@ export const PrimaryArmorScene = memo(() => {
<group ref={turretContainer}>
{armorNodes.map((node) => {
const isCurrentTurret = node.name.startsWith(
`turret_${turretModelDefinition.model_id.toString().padStart(2, '0')}`,
`turret_${turretModelDefinition.model_id.toString().padStart(2, "0")}`
);
const isVisible = isCurrentTurret;
const armorId = nameToArmorId(node.name);
const { spaced, thickness } = resolveArmor(
turretModelDefinition.armor,
armorId,
armorId
);
if (
!isVisible ||
spaced ||
thickness === undefined ||
(isDynamicArmorActive && node.name.includes('state_01')) ||
(!isDynamicArmorActive && node.name.includes('state_00'))
(isDynamicArmorActive && node.name.includes("state_01")) ||
(!isDynamicArmorActive && node.name.includes("state_00"))
)
return null;
@@ -101,21 +101,21 @@ export const PrimaryArmorScene = memo(() => {
<group ref={gunContainer}>
{armorNodes.map((node) => {
const isCurrentGun = node.name.startsWith(
`gun_${gunModelDefinition.model_id.toString().padStart(2, '0')}`,
`gun_${gunModelDefinition.model_id.toString().padStart(2, "0")}`
);
const isVisible = isCurrentGun;
const armorId = nameToArmorId(node.name);
const { spaced, thickness } = resolveArmor(
gunModelDefinition.armor,
armorId,
armorId
);
if (
!isVisible ||
spaced ||
thickness === undefined ||
(isDynamicArmorActive && node.name.includes('state_01')) ||
(!isDynamicArmorActive && node.name.includes('state_00'))
(isDynamicArmorActive && node.name.includes("state_01")) ||
(!isDynamicArmorActive && node.name.includes("state_00"))
)
return null;
@@ -1,15 +1,15 @@
import { memo, useRef } from 'react';
import { Group, Plane, Scene, Vector3 } from 'three';
import { correctZYTuple } from '../../../core/blitz/correctZYTuple';
import { nameToArmorId } from '../../../core/blitzkit/nameToArmorId';
import { resolveArmor } from '../../../core/blitzkit/resolveThickness';
import { useArmor } from '../../../hooks/useArmor';
import { useModel } from '../../../hooks/useModel';
import { useTankModelDefinition } from '../../../hooks/useTankModelDefinition';
import { useTankTransform } from '../../../hooks/useTankTransform';
import { Duel } from '../../../stores/duel';
import { ModelTankWrapper } from './ModelTankWrapper';
import { SpacedArmorSceneComponent } from './SpacedArmorSceneComponent';
import { memo, useRef } from "react";
import { Group, Plane, Scene, Vector3 } from "three";
import { correctZYTuple } from "../../../core/blitz/correctZYTuple";
import { nameToArmorId } from "../../../core/blitzkit/nameToArmorId";
import { resolveArmor } from "../../../core/blitzkit/resolveThickness";
import { useArmor } from "../../../hooks/useArmor";
import { useModel } from "../../../hooks/useModel";
import { useTankModelDefinition } from "../../../hooks/useTankModelDefinition";
import { useTankTransform } from "../../../hooks/useTankTransform";
import { Duel } from "../../../stores/duel";
import { ModelTankWrapper } from "./ModelTankWrapper";
import { SpacedArmorSceneComponent } from "./SpacedArmorSceneComponent";
export enum ArmorType {
Primary,
@@ -23,8 +23,8 @@ interface SpacedArmorSceneProps {
export const SpacedArmorScene = memo<SpacedArmorSceneProps>(({ scene }) => {
const wrapper = useRef<Group>(null);
const turretContainer = useRef<Group>(null);
const gunContainer = useRef<Group>(null);
const turretContainer = useRef<Group>(null!);
const gunContainer = useRef<Group>(null!);
const tank = Duel.use((state) => state.protagonist.tank);
const track = Duel.use((state) => state.protagonist.track);
const turret = Duel.use((state) => state.protagonist.turret);
@@ -45,7 +45,7 @@ export const SpacedArmorScene = memo<SpacedArmorSceneProps>(({ scene }) => {
? undefined
: gunModelDefinition.mask + hullOrigin.y + turretOrigin.y + gunOrigin.y;
const isDynamicArmorActive = Duel.use((state) =>
state.protagonist.consumables.includes(73),
state.protagonist.consumables.includes(73)
);
useTankTransform(track, turret, turretContainer, gunContainer);
@@ -54,19 +54,19 @@ export const SpacedArmorScene = memo<SpacedArmorSceneProps>(({ scene }) => {
<ModelTankWrapper ref={wrapper}>
<group position={hullOrigin}>
{armorNodes.map((node) => {
const isHull = node.name.startsWith('hull_');
const isHull = node.name.startsWith("hull_");
const isVisible = isHull;
const armorId = nameToArmorId(node.name);
const { spaced, thickness } = resolveArmor(
tankModelDefinition.armor,
armorId,
armorId
);
if (
!isVisible ||
thickness === undefined ||
(isDynamicArmorActive && node.name.includes('state_00')) ||
(!isDynamicArmorActive && node.name.includes('state_01'))
(isDynamicArmorActive && node.name.includes("state_00")) ||
(!isDynamicArmorActive && node.name.includes("state_01"))
)
return null;
@@ -83,8 +83,8 @@ export const SpacedArmorScene = memo<SpacedArmorSceneProps>(({ scene }) => {
</group>
{modelNodes.map((node) => {
const isWheel = node.name.startsWith('chassis_wheel_');
const isTrack = node.name.startsWith('chassis_track_');
const isWheel = node.name.startsWith("chassis_wheel_");
const isTrack = node.name.startsWith("chassis_track_");
const isVisible = isWheel || isTrack;
if (!isVisible) return null;
@@ -104,20 +104,20 @@ export const SpacedArmorScene = memo<SpacedArmorSceneProps>(({ scene }) => {
<group ref={turretContainer}>
{armorNodes.map((node) => {
const isCurrentTurret = node.name.startsWith(
`turret_${turretModelDefinition.model_id.toString().padStart(2, '0')}`,
`turret_${turretModelDefinition.model_id.toString().padStart(2, "0")}`
);
const isVisible = isCurrentTurret;
const armorId = nameToArmorId(node.name);
const { spaced, thickness } = resolveArmor(
turretModelDefinition.armor,
armorId,
armorId
);
if (
!isVisible ||
thickness === undefined ||
(isDynamicArmorActive && node.name.includes('state_00')) ||
(!isDynamicArmorActive && node.name.includes('state_01'))
(isDynamicArmorActive && node.name.includes("state_00")) ||
(!isDynamicArmorActive && node.name.includes("state_01"))
)
return null;
@@ -139,20 +139,20 @@ export const SpacedArmorScene = memo<SpacedArmorSceneProps>(({ scene }) => {
<group ref={gunContainer}>
{armorNodes.map((node) => {
const isCurrentGun = node.name.startsWith(
`gun_${gunModelDefinition.model_id.toString().padStart(2, '0')}`,
`gun_${gunModelDefinition.model_id.toString().padStart(2, "0")}`
);
const isVisible = isCurrentGun;
const armorId = nameToArmorId(node.name);
const { spaced, thickness } = resolveArmor(
gunModelDefinition.armor,
armorId,
armorId
);
if (
!isVisible ||
thickness === undefined ||
(isDynamicArmorActive && node.name.includes('state_00')) ||
(!isDynamicArmorActive && node.name.includes('state_01'))
(isDynamicArmorActive && node.name.includes("state_00")) ||
(!isDynamicArmorActive && node.name.includes("state_01"))
)
return null;
@@ -173,7 +173,7 @@ export const SpacedArmorScene = memo<SpacedArmorSceneProps>(({ scene }) => {
{modelNodes.map((node) => {
const gunString = `gun_${gunModelDefinition.model_id
.toString()
.padStart(2, '0')}`;
.padStart(2, "0")}`;
const isCurrentGun = gunModelDefinition.mask
? node.name.startsWith(gunString)
: node.name === gunString;
@@ -28,8 +28,8 @@ export interface ThicknessRange {
export const StaticArmor = memo<ArmorSceneProps>(({ thicknessRange }) => {
const wrapper = useRef<Group>(null);
const turretContainer = useRef<Group>(null);
const gunContainer = useRef<Group>(null);
const turretContainer = useRef<Group>(null!);
const gunContainer = useRef<Group>(null!);
const tank = Duel.use((state) => state.protagonist.tank);
const track = Duel.use((state) => state.protagonist.track);
const turret = Duel.use((state) => state.protagonist.turret);
@@ -1,8 +1,8 @@
import { I_HAT, J_HAT } from "@blitzkit/core";
import { type MeshProps, useThree } from "@react-three/fiber";
import { useThree } from "@react-three/fiber";
import { clamp } from "lodash-es";
import type { QuicklimeEvent } from "quicklime";
import { useEffect, useMemo } from "react";
import { useEffect, useMemo, type ComponentProps } from "react";
import {
Box3,
Color,
@@ -19,8 +19,8 @@ import {
import { unrotateDavaVector } from "../../../core/blitz/unrotateDavaVector";
import { jsxTree } from "../../../core/blitzkit/jsxTree";
import {
type ModelTransformEventData,
modelTransformEvent,
type ModelTransformEventData,
} from "../../../core/blitzkit/modelTransform";
import { discardClippingPlane } from "../../../core/three/discardClippingPlane";
import { Tankopedia } from "../../../stores/tankopedia";
@@ -36,7 +36,7 @@ type StaticArmorSceneComponentProps = {
thickness: number;
thicknessRange: ThicknessRange;
node: Object3D;
onPointerDown?: MeshProps["onPointerDown"];
onPointerDown?: ComponentProps<"mesh">["onPointerDown"];
} & (
| {
type: Exclude<ArmorType, ArmorType.External>;
+30 -30
View File
@@ -1,15 +1,15 @@
---
import { assertSecret, fetchGameDefinitions } from '@blitzkit/core';
import { DEFAULT_LOCALE } from '@blitzkit/i18n';
import { Box, Code, Flex, Heading, Link, Text } from '@radix-ui/themes';
import packageJson from '../../../../package.json';
import { getStrings } from '../core/i18n/getStrings';
import { LinkI18n } from './LinkI18n';
import { LocaleSwitcherThemeWrapper } from './LocaleSwitcher';
import { assertSecret, fetchGameDefinitions } from "@blitzkit/core";
import locales from "@blitzkit/i18n/locales.json";
import { Box, Code, Flex, Heading, Link, Text } from "@radix-ui/themes";
import packageJson from "../../../../package.json";
import { getStrings } from "../core/i18n/getStrings";
import { LinkI18n } from "./LinkI18n";
import { LocaleSwitcherThemeWrapper } from "./LocaleSwitcher";
const gameDefinitions = await fetchGameDefinitions();
const PUBLIC_ASSET_BRANCH = assertSecret(import.meta.env.PUBLIC_BRANCH);
const locale = Astro.params.locale ?? DEFAULT_LOCALE;
const locale = Astro.params.locale ?? locales.default;
const strings = getStrings(locale);
---
@@ -28,13 +28,13 @@ const strings = getStrings(locale);
flexGrow="1"
gap="5"
position="relative"
direction={{ initial: 'column', sm: 'row' }}
direction={{ initial: "column", sm: "row" }}
>
<Flex
direction="column"
align={{
initial: 'center',
sm: 'start',
initial: "center",
sm: "start",
}}
>
<Heading>BlitzKit</Heading>
@@ -51,32 +51,32 @@ const strings = getStrings(locale);
<Flex
gap="6"
width={{
initial: '100%',
sm: 'auto',
initial: "100%",
sm: "auto",
}}
>
<Flex
direction="column"
gap="1"
align={{
initial: 'end',
sm: 'start',
initial: "end",
sm: "start",
}}
flexGrow={{
initial: '1',
sm: '0',
initial: "1",
sm: "0",
}}
flexBasis={{
initial: '0',
sm: 'auto',
initial: "0",
sm: "auto",
}}
>
<Heading size="3">{strings.website.footer.about.title}</Heading>
<Flex
direction="column"
align={{
initial: 'end',
sm: 'start',
initial: "end",
sm: "start",
}}
>
<LinkI18n {locale} href="/docs/about/credits" color="gray">
@@ -106,12 +106,12 @@ const strings = getStrings(locale);
direction="column"
gap="1"
flexGrow={{
initial: '1',
sm: '0',
initial: "1",
sm: "0",
}}
flexBasis={{
initial: '0',
sm: 'auto',
initial: "0",
sm: "auto",
}}
>
<Heading size="3">{strings.website.footer.legal.title}</Heading>
@@ -127,11 +127,11 @@ const strings = getStrings(locale);
</Flex>
</Flex>
<Flex gap="5" display={{ initial: 'flex', sm: 'none' }} width="100%">
<Flex gap="5" display={{ initial: "flex", sm: "none" }} width="100%">
<Flex direction="column" gap="1" flexGrow="1" flexBasis="0" align="end">
<Text size="2" color="gray">BlitzKit</Text>
{
PUBLIC_ASSET_BRANCH !== 'preview' && (
PUBLIC_ASSET_BRANCH !== "preview" && (
<Text size="2" color="gray">
WoTB
</Text>
@@ -145,7 +145,7 @@ const strings = getStrings(locale);
{packageJson.version}
</Code>
{
PUBLIC_ASSET_BRANCH !== 'preview' && (
PUBLIC_ASSET_BRANCH !== "preview" && (
<Code size="2" color="gray">
{gameDefinitions.version}
</Code>
@@ -157,14 +157,14 @@ const strings = getStrings(locale);
</Flex>
</Flex>
<Flex gap="2" align="center" display={{ initial: 'none', sm: 'flex' }}>
<Flex gap="2" align="center" display={{ initial: "none", sm: "flex" }}>
<Text size="2" color="gray">BlitzKit</Text>
<Code size="2" color="gray">
{packageJson.version}
</Code>
{
PUBLIC_ASSET_BRANCH !== 'preview' && (
PUBLIC_ASSET_BRANCH !== "preview" && (
<>
<Text size="2" color="gray">
WoTB
@@ -1,5 +1,5 @@
import { asset, Avatar } from '@blitzkit/core';
import { Cross1Icon, DownloadIcon } from '@radix-ui/react-icons';
import { asset, Avatar } from "@blitzkit/core";
import { Cross1Icon, DownloadIcon } from "@radix-ui/react-icons";
import {
Dialog,
Flex,
@@ -7,11 +7,11 @@ import {
Link,
Skeleton,
Text,
} from '@radix-ui/themes';
import { useRef } from 'react';
import { useIntersection } from '../../hooks/useIntersection';
import { useLocale } from '../../hooks/useLocale';
import type { MaybeSkeletonComponentProps } from '../../types/maybeSkeletonComponentProps';
} from "@radix-ui/themes";
import { useRef } from "react";
import { useIntersection } from "../../hooks/useIntersection";
import { useLocale } from "../../hooks/useLocale";
import type { MaybeSkeletonComponentProps } from "../../types/maybeSkeletonComponentProps";
type GalleryCardProps = MaybeSkeletonComponentProps<{
avatar: Avatar;
@@ -19,9 +19,9 @@ type GalleryCardProps = MaybeSkeletonComponentProps<{
export function GalleryCard(props: GalleryCardProps) {
const src = asset(
`gallery/avatars/${!props.skeleton && `${props.avatar.id}${props.avatar.extension}`}`,
`gallery/avatars/${!props.skeleton && `${props.avatar.id}${props.avatar.extension}`}`
);
const card = useRef<HTMLDivElement>(null);
const card = useRef<HTMLDivElement>(null!);
const { unwrap } = useLocale();
useIntersection(() => props.skeleton && props.onIntersection?.(), card, {
@@ -35,7 +35,7 @@ export function GalleryCard(props: GalleryCardProps) {
width="6rem"
gap="1"
ref={card}
style={{ cursor: 'pointer' }}
style={{ cursor: "pointer" }}
>
{props.skeleton && (
<>
@@ -48,16 +48,16 @@ export function GalleryCard(props: GalleryCardProps) {
<>
<img
style={{
width: '4rem',
height: '4.57rem',
width: "4rem",
height: "4.57rem",
// aspect ratio 7 / 8
objectFit: 'cover',
objectFit: "cover",
}}
src={src}
alt={unwrap(props.avatar.name)}
/>
<Text size="1" align="center" style={{ maxWidth: '100%' }}>
<Text size="1" align="center" style={{ maxWidth: "100%" }}>
{unwrap(props.avatar.name)}
</Text>
</>
@@ -94,7 +94,7 @@ export function GalleryCard(props: GalleryCardProps) {
</Flex>
<Flex justify="center" mt="4">
<Dialog.Title align="center" style={{ maxWidth: '10rem' }}>
<Dialog.Title align="center" style={{ maxWidth: "10rem" }}>
{unwrap(props.avatar.name)}
</Dialog.Title>
</Flex>
@@ -1,7 +1,6 @@
import type { SpotLightProps } from '@react-three/fiber';
import { memo } from 'react';
import { memo, type ComponentProps } from "react";
interface Props extends SpotLightProps {
interface Props extends ComponentProps<"spotLight"> {
debug?: boolean;
}
@@ -1,12 +1,12 @@
import { DEFAULT_LOCALE } from '@blitzkit/i18n';
import { GlobeIcon } from '@radix-ui/react-icons';
import { Flex, Text } from '@radix-ui/themes';
import type { LocaleAcceptorProps } from '../../hooks/useLocale';
import { BlitzKitTheme } from '../BlitzKitTheme';
import { LocaleSwitcher } from '../LocaleSwitcher';
import locales from "@blitzkit/i18n/locales.json";
import { GlobeIcon } from "@radix-ui/react-icons";
import { Flex, Text } from "@radix-ui/themes";
import type { LocaleAcceptorProps } from "../../hooks/useLocale";
import { BlitzKitTheme } from "../BlitzKitTheme";
import { LocaleSwitcher } from "../LocaleSwitcher";
export function HomeLocaleSwitcher({
locale = DEFAULT_LOCALE,
locale = locales.default,
}: LocaleAcceptorProps) {
return (
<BlitzKitTheme>
+5 -5
View File
@@ -1,14 +1,14 @@
import { DEFAULT_LOCALE } from '@blitzkit/i18n';
import { Link, type LinkProps } from '@radix-ui/themes';
import type { LocaleAcceptorProps } from '../hooks/useLocale';
import locales from "@blitzkit/i18n/locales.json";
import { Link, type LinkProps } from "@radix-ui/themes";
import type { LocaleAcceptorProps } from "../hooks/useLocale";
type LinkI18nProps = LinkProps & LocaleAcceptorProps;
export function LinkI18n({ locale, href, ...props }: LinkI18nProps) {
const prefix =
locale === undefined || locale === DEFAULT_LOCALE ? '' : `/${locale}`;
locale === undefined || locale === locales.default ? "" : `/${locale}`;
return (
<Link href={href?.startsWith('/') ? `${prefix}${href}` : href} {...props} />
<Link href={href?.startsWith("/") ? `${prefix}${href}` : href} {...props} />
);
}
@@ -1,12 +1,13 @@
<script>
import { SUPPORTED_LOCALES } from "@blitzkit/i18n";
import locales from "@blitzkit/i18n/locales.json";
import { getBestLocale } from "../core/i18n/getBestLocale";
const isAPI = window.location.pathname.startsWith("/api");
const isI18nPath = SUPPORTED_LOCALES.some((locale) =>
const isI18nPath = locales.supported.some(({ locale }) =>
window.location.pathname.startsWith(`/${locale}`)
);
const bestLocale = getBestLocale();
const currentPathLocale = SUPPORTED_LOCALES.find((locale) =>
const currentPathLocale = locales.supported.find(({ locale }) =>
window.location.pathname.startsWith(`/${locale}`)
);
@@ -1,19 +0,0 @@
import {
ResponsiveBar,
type BarDatum,
type ResponsiveBarSvgProps,
} from '@nivo/bar';
import { nivoTheme } from '../../core/nivo/theme';
export function ThemedBar<RawDatum extends BarDatum>(
props: ResponsiveBarSvgProps<RawDatum>,
) {
return (
<ResponsiveBar
colors={{ scheme: 'yellow_green_blue' }}
theme={nivoTheme}
borderRadius={4}
{...props}
/>
);
}
@@ -1,15 +0,0 @@
import { ResponsiveLine, type LineSvgProps } from '@nivo/line';
import { nivoTheme } from '../../core/nivo/theme';
export function ThemedLine(props: LineSvgProps) {
return (
<ResponsiveLine
colors={{ scheme: 'yellow_green_blue' }}
theme={nivoTheme}
margin={{ top: 50, right: 110, bottom: 50, left: 60 }}
enablePoints={true}
useMesh
{...props}
/>
);
}
@@ -1,15 +1,15 @@
import { Skeleton, Table } from '@radix-ui/themes';
import { times } from 'lodash-es';
import { memo, useRef } from 'react';
import { useIntersection } from '../../hooks/useIntersection';
import { TankPerformanceSortTypeNamesArray } from '../../stores/tankPerformanceSort/constants';
import { Skeleton, Table } from "@radix-ui/themes";
import { times } from "lodash-es";
import { memo, useRef } from "react";
import { useIntersection } from "../../hooks/useIntersection";
import { TankPerformanceSortTypeNamesArray } from "../../stores/tankPerformanceSort/constants";
interface RowLoaderProps {
onIntersection?: () => void;
}
export const RowLoader = memo<RowLoaderProps>(({ onIntersection }) => {
const row = useRef<HTMLTableRowElement>(null);
const row = useRef<HTMLTableRowElement>(null!);
useIntersection(() => onIntersection?.(), row, {
disabled: onIntersection === undefined,
@@ -1,20 +1,20 @@
import { Canvas, type CanvasProps } from '@react-three/fiber';
import { forwardRef, useImperativeHandle, useRef } from 'react';
import { useOnScreen } from '../hooks/useOnScreen';
import { Canvas, type CanvasProps } from "@react-three/fiber";
import { forwardRef, useImperativeHandle, useRef } from "react";
import { useOnScreen } from "../hooks/useOnScreen";
export const SmartCanvas = forwardRef<HTMLCanvasElement, CanvasProps>(
(props, ref) => {
const canvas = useRef<HTMLCanvasElement>(null);
const canvas = useRef<HTMLCanvasElement>(null!);
const onScreen = useOnScreen(canvas);
useImperativeHandle(ref, () => canvas.current!, []);
return (
<Canvas
frameloop={onScreen ? 'demand' : 'never'}
frameloop={onScreen ? "demand" : "never"}
ref={canvas}
{...props}
/>
);
},
}
);
@@ -1,6 +1,6 @@
import { Flex, Skeleton } from '@radix-ui/themes';
import { memo, useRef } from 'react';
import { useIntersection } from '../../../hooks/useIntersection';
import { Flex, Skeleton } from "@radix-ui/themes";
import { memo, useRef } from "react";
import { useIntersection } from "../../../hooks/useIntersection";
interface SkeletonTankCardProps {
onIntersection?: () => void;
@@ -8,7 +8,7 @@ interface SkeletonTankCardProps {
export const SkeletonTankCard = memo(
({ onIntersection }: SkeletonTankCardProps) => {
const card = useRef<HTMLDivElement>(null);
const card = useRef<HTMLDivElement>(null!);
useIntersection(() => onIntersection?.(), card, {
disabled: onIntersection === undefined,
@@ -21,5 +21,5 @@ export const SkeletonTankCard = memo(
</Flex>
);
},
() => true,
() => true
);
@@ -38,7 +38,7 @@ export function Info({
const result = fuzzysort.single(statSearch, name);
if (result) {
label = fuzzysort.highlight(result, (match, index) => (
label = result.highlight((match, index) => (
<Mark key={index}>{match}</Mark>
));
highlighted = true;
@@ -19,8 +19,8 @@ export function TankModel() {
const turret = Duel.use((state) => state.protagonist.turret);
const canvas = useThree((state) => state.gl.domElement);
const hullContainer = useRef<Group>(null);
const turretContainer = useRef<Group>(null);
const gunContainer = useRef<Group>(null);
const turretContainer = useRef<Group>(null!);
const gunContainer = useRef<Group>(null!);
const tankModelDefinition = useTankModelDefinition();
const turretModelDefinition =
tankModelDefinition.turrets[protagonist.turret.id];
@@ -26,8 +26,8 @@ export function TransitionSkeleton() {
const gun = Duel.use((state) => state.protagonist.gun);
const track = Duel.use((state) => state.protagonist.track);
const turret = Duel.use((state) => state.protagonist.turret);
const turretContainer = useRef<Group>(null);
const gunContainer = useRef<Group>(null);
const turretContainer = useRef<Group>(null!);
const gunContainer = useRef<Group>(null!);
const { gltf: armorGltf } = useArmor(tank.id);
const { gltf: modelGltf } = useModel(tank.id);
const modelNodes = Object.values(modelGltf.nodes);
@@ -16,7 +16,7 @@ const tankDefinitions = await awaitableTankDefinitions;
export function HeroSection({ skeleton }: MaybeSkeletonComponentProps) {
const revealed = Tankopedia.use((state) => state.revealed);
const disturbed = Tankopedia.use((state) => state.disturbed);
const canvas = useRef<HTMLCanvasElement>(null);
const canvas = useRef<HTMLCanvasElement>(null!);
const isFullScreen = useFullScreen();
const protagonist = Duel.use((state) => state.protagonist.tank);
const thicknessRange = useMemo(() => {