feat: showing first content on profile page

This commit is contained in:
Zamitto 2024-06-12 22:23:12 -03:00
parent b8895afc0a
commit 4e73009997
7 changed files with 116 additions and 25 deletions

View file

@ -2,20 +2,41 @@ import { registerEvent } from "../register-event";
import { userProfileSchema } from "../helpers/validators";
import { logger } from "@main/services";
import { HydraApi } from "@main/services/hydra-api";
import { steamGamesWorker } from "@main/workers";
import { LibraryGame, SteamGame, UserProfile } from "@types";
const getUserProfile = async (
_event: Electron.IpcMainInvokeEvent,
username: string
) => {
return HydraApi.get(`/profile/${username}`)
.then((response) => {
const profile = userProfileSchema.parse(response.data);
return profile;
})
.catch((err) => {
logger.error(`getUserProfile: ${username}`, err);
return null;
});
): Promise<UserProfile | null> => {
try {
const response = await HydraApi.get(`/profile/${username}`);
const profile = userProfileSchema.parse(response.data);
const recentGames = await Promise.all(
profile.recentGames.map(async (game) => {
const steamGame = await steamGamesWorker.run(Number(game.objectId), {
name: "getById",
});
return { ...game, title: steamGame.name, objectId: game.objectId };
})
);
const libraryGames = await Promise.all(
profile.game.map(async (game) => {
const steamGame = await steamGamesWorker.run(Number(game.objectId), {
name: "getById",
});
return { ...game, title: steamGame.name, objectID: game.objectId };
})
);
return { ...profile, game: libraryGames, recentGames };
} catch (err) {
logger.error(`getUserProfile: ${username}`, err);
return null;
}
};
registerEvent("getUserProfile", getUserProfile);

View file

@ -144,7 +144,7 @@ export function Sidebar() {
};
const handleClickProfile = () => {
navigate("/profile/brownie");
navigate("/profile/zamitto");
};
return (

View file

@ -1,5 +1,6 @@
import { UserProfile } from "@types";
import { useTranslation } from "react-i18next";
import * as styles from "./profile.css";
export interface ProfileContentProps {
userProfile: UserProfile;
@ -8,9 +9,29 @@ export interface ProfileContentProps {
export const ProfileContent = ({ userProfile }: ProfileContentProps) => {
const { t } = useTranslation("profile");
console.log(userProfile.recentGames);
return (
<>
<p>{userProfile.username}</p>
<section className={styles.profileHeader}>
<img
className={styles.profileAvatar}
src="https://avatars.githubusercontent.com/u/167933696?v=4"
/>
<div className={styles.profileInformation}>
<h3 style={{ fontWeight: "bold" }}>{userProfile.username}</h3>
<p style={{ fontSize: 12 }}>Jogando ABC</p>
</div>
</section>
<h2>Feed</h2>
{userProfile.recentGames.map((game) => {
return <p key={game.objectID}>{game.title}</p>;
})}
<h2>Games</h2>
{userProfile.game.map((game) => {
return <p key={game.objectID}>{game.title}</p>;
})}
</>
);
};

View file

@ -1,7 +1,11 @@
import Skeleton from "react-loading-skeleton";
import * as styles from "./profile.css";
export const ProfileSkeleton = () => {
return (
<>
<p>Loading....</p>
<Skeleton className={styles.profileHeaderSkeleton} />
<Skeleton width={135} />
</>
);
};

View file

@ -1,7 +1,41 @@
export const UserProfile = () => {
return (
<>
<p>Tela do usuarioooooooo</p>
</>
);
};
import { SPACING_UNIT, vars } from "../../theme.css";
import { style } from "@vanilla-extract/css";
export const wrapper = style({
padding: "24px",
width: "100%",
display: "flex",
flexDirection: "column",
});
export const profileHeader = style({
display: "flex",
gap: `${SPACING_UNIT + SPACING_UNIT / 2}px`,
alignItems: "center",
padding: `${SPACING_UNIT * 2}px ${SPACING_UNIT * 2}px`,
color: vars.color.muted,
borderRadius: "4px",
border: `solid 1px ${vars.color.border}`,
width: "100%",
});
export const profileAvatar = style({
width: "96px",
height: "96px",
borderRadius: "50%",
display: "flex",
justifyContent: "center",
alignItems: "center",
backgroundColor: vars.color.background,
position: "relative",
});
export const profileInformation = style({
display: "flex",
flexDirection: "column",
alignItems: "flex-start",
});
export const profileHeaderSkeleton = style({
height: "200px",
});

View file

@ -5,6 +5,9 @@ import { setHeaderTitle } from "@renderer/features";
import { useAppDispatch } from "@renderer/hooks";
import { ProfileSkeleton } from "./profile-skeleton";
import { ProfileContent } from "./profile-content";
import { SkeletonTheme } from "react-loading-skeleton";
import { vars } from "@renderer/theme.css";
import * as styles from "./profile.css";
export const Profile = () => {
const { username } = useParams();
@ -21,7 +24,15 @@ export const Profile = () => {
});
}, [dispatch]);
if (!userProfile) return <ProfileSkeleton />;
return <ProfileContent userProfile={userProfile} />;
return (
<SkeletonTheme baseColor={vars.color.background} highlightColor="#444">
<div className={styles.wrapper}>
{userProfile ? (
<ProfileContent userProfile={userProfile} />
) : (
<ProfileSkeleton />
)}
</div>
</SkeletonTheme>
);
};

View file

@ -236,8 +236,8 @@ export interface RealDebridUser {
export interface UserProfile {
username: string;
game: any[];
recentGames: any[];
game: Partial<CatalogueEntry>[];
recentGames: Partial<CatalogueEntry>[];
}
export interface DownloadSource {