From f5d5aa39dc192e4138c98a75077558d4e117cde5 Mon Sep 17 00:00:00 2001
From: Zamitto <167933696+zamitto@users.noreply.github.com>
Date: Wed, 25 Dec 2024 20:28:56 -0300
Subject: [PATCH] feat: game card animation
---
.../services/download/download-manager.ts | 4 +-
.../profile-content/profile-content.tsx | 168 +--------------
.../user-library-game-card.tsx | 204 ++++++++++++++++++
3 files changed, 210 insertions(+), 166 deletions(-)
create mode 100644 src/renderer/src/pages/profile/profile-content/user-library-game-card.tsx
diff --git a/src/main/services/download/download-manager.ts b/src/main/services/download/download-manager.ts
index 80a3f6fb..0d9f5cbb 100644
--- a/src/main/services/download/download-manager.ts
+++ b/src/main/services/download/download-manager.ts
@@ -244,7 +244,7 @@ export class DownloadManager {
private static async getDownloadPayload(game: Game) {
switch (game.downloader) {
case Downloader.Gofile: {
- const id = game!.uri!.split("/").pop();
+ const id = game.uri!.split("/").pop();
const token = await GofileApi.authorize();
const downloadLink = await GofileApi.getDownloadLink(id!);
@@ -258,7 +258,7 @@ export class DownloadManager {
};
}
case Downloader.PixelDrain: {
- const id = game!.uri!.split("/").pop();
+ const id = game.uri!.split("/").pop();
return {
action: "start",
diff --git a/src/renderer/src/pages/profile/profile-content/profile-content.tsx b/src/renderer/src/pages/profile/profile-content/profile-content.tsx
index 2217d569..ed63029b 100644
--- a/src/renderer/src/pages/profile/profile-content/profile-content.tsx
+++ b/src/renderer/src/pages/profile/profile-content/profile-content.tsx
@@ -3,26 +3,18 @@ import { useCallback, useContext, useEffect, useMemo } from "react";
import { ProfileHero } from "../profile-hero/profile-hero";
import { useAppDispatch, useFormat } from "@renderer/hooks";
import { setHeaderTitle } from "@renderer/features";
-import { steamUrlBuilder } from "@shared";
-import { SPACING_UNIT, vars } from "@renderer/theme.css";
-
+import { SPACING_UNIT } from "@renderer/theme.css";
import * as styles from "./profile-content.css";
-import { ClockIcon, TelescopeIcon, TrophyIcon } from "@primer/octicons-react";
+import { TelescopeIcon } from "@primer/octicons-react";
import { useTranslation } from "react-i18next";
import { useNavigate } from "react-router-dom";
import { LockedProfile } from "./locked-profile";
import { ReportProfile } from "../report-profile/report-profile";
import { FriendsBox } from "./friends-box";
import { RecentGamesBox } from "./recent-games-box";
-import type { UserGame } from "@types";
-import {
- buildGameAchievementPath,
- buildGameDetailsPath,
- formatDownloadProgress,
-} from "@renderer/helpers";
import { MAX_MINUTES_TO_SHOW_IN_PLAYTIME } from "@renderer/constants";
import { UserStatsBox } from "./user-stats-box";
-import HydraIcon from "@renderer/assets/icons/hydra.svg?react";
+import { UserLibraryGameCard } from "./user-library-game-card";
export function ProfileContent() {
const { userProfile, isMe, userStats } = useContext(userProfileContext);
@@ -47,26 +39,6 @@ export function ProfileContent() {
return userProfile?.relation?.status === "ACCEPTED";
}, [userProfile]);
- const buildUserGameDetailsPath = useCallback(
- (game: UserGame) => {
- if (!userProfile?.hasActiveSubscription || game.achievementCount === 0) {
- return buildGameDetailsPath({
- ...game,
- objectId: game.objectId,
- });
- }
-
- const userParams = userProfile
- ? {
- userId: userProfile.id,
- }
- : undefined;
-
- return buildGameAchievementPath({ ...game }, userParams);
- },
- [userProfile]
- );
-
const formatPlayTime = useCallback(
(playTimeInSeconds = 0) => {
const minutes = playTimeInSeconds / 60;
@@ -129,137 +101,7 @@ export function ProfileContent() {
{userProfile?.libraryGames?.map((game) => (
- -
-
-
+
))}
>
@@ -271,7 +113,6 @@ export function ProfileContent() {
-
)}
@@ -284,7 +125,6 @@ export function ProfileContent() {
userStats,
numberFormatter,
t,
- buildUserGameDetailsPath,
formatPlayTime,
navigate,
]);
diff --git a/src/renderer/src/pages/profile/profile-content/user-library-game-card.tsx b/src/renderer/src/pages/profile/profile-content/user-library-game-card.tsx
new file mode 100644
index 00000000..8f437a1d
--- /dev/null
+++ b/src/renderer/src/pages/profile/profile-content/user-library-game-card.tsx
@@ -0,0 +1,204 @@
+import { UserGame } from "@types";
+import * as styles from "./profile-content.css";
+import HydraIcon from "@renderer/assets/icons/hydra.svg?react";
+import { useFormat } from "@renderer/hooks";
+import { useNavigate } from "react-router-dom";
+import { useCallback, useContext } from "react";
+import {
+ buildGameAchievementPath,
+ buildGameDetailsPath,
+ formatDownloadProgress,
+} from "@renderer/helpers";
+import { userProfileContext } from "@renderer/context";
+import { vars } from "@renderer/theme.css";
+import { ClockIcon, TrophyIcon } from "@primer/octicons-react";
+import { MAX_MINUTES_TO_SHOW_IN_PLAYTIME } from "@renderer/constants";
+import { useTranslation } from "react-i18next";
+import { steamUrlBuilder } from "@shared";
+
+interface UserLibraryGameCardProps {
+ game: UserGame;
+}
+
+export function UserLibraryGameCard({ game }: UserLibraryGameCardProps) {
+ const { userProfile } = useContext(userProfileContext);
+ const { t } = useTranslation("user_profile");
+ const { numberFormatter } = useFormat();
+ const navigate = useNavigate();
+
+ // const handleCloseClick = useCallback(() => {
+ // setIsClosing(true);
+ // const zero = performance.now();
+
+ // requestAnimationFrame(function animateClosing(time) {
+ // if (time - zero <= 400) {
+ // requestAnimationFrame(animateClosing);
+ // } else {
+ // onClose();
+ // setIsClosing(false);
+ // }
+ // });
+ // }, [onClose]);
+
+ const buildUserGameDetailsPath = useCallback(
+ (game: UserGame) => {
+ if (!userProfile?.hasActiveSubscription || game.achievementCount === 0) {
+ return buildGameDetailsPath({
+ ...game,
+ objectId: game.objectId,
+ });
+ }
+
+ const userParams = userProfile
+ ? {
+ userId: userProfile.id,
+ }
+ : undefined;
+
+ return buildGameAchievementPath({ ...game }, userParams);
+ },
+ [userProfile]
+ );
+
+ const formatPlayTime = useCallback(
+ (playTimeInSeconds = 0) => {
+ const minutes = playTimeInSeconds / 60;
+
+ if (minutes < MAX_MINUTES_TO_SHOW_IN_PLAYTIME) {
+ return t("amount_minutes", {
+ amount: minutes.toFixed(0),
+ });
+ }
+
+ const hours = minutes / 60;
+ return t("amount_hours", { amount: numberFormatter.format(hours) });
+ },
+ [numberFormatter, t]
+ );
+
+ return (
+
+
+
+ );
+}