From ee9dbdaf74b9cf6168b6ab3af82513dc8d629a9c Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Tr=C3=A8sAbhi?= <43380238+tresabhi@users.noreply.github.com>
Date: Sun, 1 Sep 2024 17:41:50 -0500
Subject: [PATCH] feat: better loading
---
.../MetaSection/components/Votes/index.tsx | 44 ++++++++++-----
.../MetaSection/components/VotesSkeleton.tsx | 55 -------------------
.../components/Model/MetaSection/index.tsx | 11 ++--
.../Model/TechTreeSection/index.tsx | 20 +++----
src/hooks/useTankVotes.ts | 45 +++++++--------
5 files changed, 65 insertions(+), 110 deletions(-)
delete mode 100644 src/app/tools/tankopedia/[id]/components/Model/MetaSection/components/VotesSkeleton.tsx
diff --git a/src/app/tools/tankopedia/[id]/components/Model/MetaSection/components/Votes/index.tsx b/src/app/tools/tankopedia/[id]/components/Model/MetaSection/components/Votes/index.tsx
index f0f25b76b..4f1fc68c4 100644
--- a/src/app/tools/tankopedia/[id]/components/Model/MetaSection/components/Votes/index.tsx
+++ b/src/app/tools/tankopedia/[id]/components/Model/MetaSection/components/Votes/index.tsx
@@ -1,4 +1,4 @@
-import { Flex, Heading, Text } from '@radix-ui/themes';
+import { Flex, Heading, Skeleton, Text } from '@radix-ui/themes';
import { memo } from 'react';
import { WargamingLoginButton } from '../../../../../../../../../components/Navbar/components/WargamingLoginButton';
import { formatCompact } from '../../../../../../../../../core/math/formatCompact';
@@ -19,9 +19,11 @@ export const Votes = memo(
return (
-
+
- {formatCompact(votes.votes)} {votes.votes === 1 ? 'vote' : 'votes'}
+ {!votes && }
+ {votes && formatCompact(votes.votes)}{' '}
+ {votes && (votes.votes > 1 ? 'votes' : 'vote')}
{!wargaming && (
@@ -37,8 +39,14 @@ export const Votes = memo(
gap={{ initial: '0', sm: '6' }}
direction={{ initial: 'column', sm: 'row' }}
>
-
-
+
+
- {wargaming && (
-
+
+
<>
- {votes.last_updated
- ? `You voted on ${new Date(votes.last_updated).toLocaleDateString()}`
- : `You haven't voted yet`}
+ {votes ? (
+ wargaming ? (
+ votes.last_updated ? (
+ `You voted on ${new Date(votes.last_updated).toLocaleDateString()}`
+ ) : (
+ `You haven't voted yet`
+ )
+ ) : (
+ 'Login to vote'
+ )
+ ) : (
+
+ )}
>
- )}
+
);
diff --git a/src/app/tools/tankopedia/[id]/components/Model/MetaSection/components/VotesSkeleton.tsx b/src/app/tools/tankopedia/[id]/components/Model/MetaSection/components/VotesSkeleton.tsx
deleted file mode 100644
index 3c567f776..000000000
--- a/src/app/tools/tankopedia/[id]/components/Model/MetaSection/components/VotesSkeleton.tsx
+++ /dev/null
@@ -1,55 +0,0 @@
-import { PaperPlaneIcon } from '@radix-ui/react-icons';
-import { Button, Flex, Heading, Skeleton, Text } from '@radix-ui/themes';
-import { WargamingLoginButton } from '../../../../../../../../components/Navbar/components/WargamingLoginButton';
-import * as App from '../../../../../../../../stores/app';
-
-export function VotesSkeleton() {
- const wargaming = App.useDeferred(
- undefined,
- (state) => state.logins.wargaming,
- );
-
- return (
-
-
-
-
-
-
- {!wargaming && (
-
- Login to vote
-
- )}
- {wargaming && (
-
- )}
-
-
-
-
-
- Easiness
-
-
-
- Firepower
-
-
-
-
-
- Maneuverability
-
-
-
- Survivability
-
-
-
-
-
- );
-}
diff --git a/src/app/tools/tankopedia/[id]/components/Model/MetaSection/index.tsx b/src/app/tools/tankopedia/[id]/components/Model/MetaSection/index.tsx
index de21f6ff3..9911023cf 100644
--- a/src/app/tools/tankopedia/[id]/components/Model/MetaSection/index.tsx
+++ b/src/app/tools/tankopedia/[id]/components/Model/MetaSection/index.tsx
@@ -1,6 +1,5 @@
import { ChevronLeftIcon, MixIcon } from '@radix-ui/react-icons';
import { Button, Code, Flex } from '@radix-ui/themes';
-import { Suspense } from 'react';
import { classIcons } from '../../../../../../../components/ClassIcon';
import { Link } from '../../../../../../../components/Link';
import { asset } from '../../../../../../../core/blitzkit/asset';
@@ -9,7 +8,6 @@ import * as App from '../../../../../../../stores/app';
import * as Duel from '../../../../../../../stores/duel';
import { Listing } from './components/Listing';
import { Votes } from './components/Votes';
-import { VotesSkeleton } from './components/VotesSkeleton';
export function MetaSection() {
const developerMode = App.useDeferred(false, (state) => state.developerMode);
@@ -40,7 +38,10 @@ export function MetaSection() {
-
+
{protagonist.nameFull && (
{protagonist.nameFull}
@@ -139,9 +140,7 @@ export function MetaSection() {
- }>
-
-
+
);
diff --git a/src/app/tools/tankopedia/[id]/components/Model/TechTreeSection/index.tsx b/src/app/tools/tankopedia/[id]/components/Model/TechTreeSection/index.tsx
index 0ac640b39..bb305add6 100644
--- a/src/app/tools/tankopedia/[id]/components/Model/TechTreeSection/index.tsx
+++ b/src/app/tools/tankopedia/[id]/components/Model/TechTreeSection/index.tsx
@@ -1,6 +1,6 @@
import { CaretLeftIcon, CaretRightIcon, PlusIcon } from '@radix-ui/react-icons';
import { Flex, Heading, IconButton, ScrollArea, Text } from '@radix-ui/themes';
-import { use, useEffect, useMemo, useRef, useState } from 'react';
+import { Fragment, use, useEffect, useMemo, useRef, useState } from 'react';
import { asset } from '../../../../../../../core/blitzkit/asset';
import { imgur } from '../../../../../../../core/blitzkit/imgur';
import { tankDefinitions } from '../../../../../../../core/blitzkit/tankDefinitions';
@@ -128,6 +128,7 @@ export function TechTreeSection() {
return (
- {index > 0 && }
+
+ {index > 0 && }
- >
+
);
})}
@@ -180,14 +180,14 @@ export function TechTreeSection() {
<>
{master.successors!.map((id, index) => (
- <>
+
{index > 0 && (
-
+
)}
-
- >
+
+
))}
>
)}
diff --git a/src/hooks/useTankVotes.ts b/src/hooks/useTankVotes.ts
index b7d004749..dec1694e1 100644
--- a/src/hooks/useTankVotes.ts
+++ b/src/hooks/useTankVotes.ts
@@ -1,4 +1,4 @@
-import { use, useMemo } from 'react';
+import { useEffect, useState } from 'react';
import { TankVotes } from '../app/api/tank-voting/[id]/average/route';
import { unwrapBlitzkitResponse } from '../core/blitzkit/unwrapBlitzkitResponse';
import * as App from '../stores/app';
@@ -20,32 +20,25 @@ const cache: Record | TankVotes> = {};
export function useTankVotes(id: number) {
const wargaming = App.use((state) => state.logins.wargaming);
- const promise = useMemo(
- () =>
- new Promise((resolve) => {
- if (id in cache) {
- resolve(cache[id]);
- } else {
- const cacheable = fetch(
- `http://localhost:3000/api/tank-voting/${id}/average${
- wargaming
- ? `?player=${wargaming.id}&token=${wargaming.token}`
- : ''
- }`,
- )
- .then(
- (response) =>
- response.json() as Promise>,
- )
- .then(unwrapBlitzkitResponse);
- cacheable.then(resolve);
+ const [votes, setVotes] = useState(null);
- cache[id] = cacheable;
- }
- }),
- [id, wargaming],
- );
- const votes = use(promise);
+ useEffect(() => {
+ if (id in cache) {
+ Promise.all([cache[id]]).then(([votes]) => setVotes(votes));
+ } else {
+ const cacheable = fetch(
+ `/api/tank-voting/${id}/average${
+ wargaming ? `?player=${wargaming.id}&token=${wargaming.token}` : ''
+ }`,
+ )
+ .then(
+ (response) => response.json() as Promise>,
+ )
+ .then(unwrapBlitzkitResponse);
+ cacheable.then(setVotes);
+ cache[id] = cacheable;
+ }
+ }, [id, wargaming]);
return votes;
}