diff --git a/app/components/SidePanel.tsx b/app/components/SidePanel.tsx index 4c36c9c..152f616 100644 --- a/app/components/SidePanel.tsx +++ b/app/components/SidePanel.tsx @@ -16,6 +16,8 @@ type Props = { supabase: ContextProps["supabase"]; addNotification: AddNotificationFunction; userDisplayName: string; + avatarUri: string; + setAvatarUri: SetState; }; export default function SidePanel({ @@ -25,14 +27,14 @@ export default function SidePanel({ supabase, addNotification, userDisplayName, + avatarUri, + setAvatarUri, }: Props) { const [theme, setTheme] = useTheme(); const toggleTheme = () => { setTheme((prevTheme) => (prevTheme === "light" ? "dark" : "light")); }; - const [avatarUri, setAvatarUri] = useState(""); - // generate avatar useEffect(() => { if (!user) { diff --git a/app/root.tsx b/app/root.tsx index 2c88fff..7ba00ee 100644 --- a/app/root.tsx +++ b/app/root.tsx @@ -26,10 +26,7 @@ import { getThemeSession } from "./utils/Navbar/theme.server"; import Navbar from "./components/Navbar"; import SidePanel from "./components/SidePanel"; import insertNewUser from "./utils/insertNewUser"; -import { - PopupNotification, - RawCartItem, -} from "./utils/types/ContextProps.type"; +import { RawCartItem } from "./utils/types/ContextProps.type"; import PopupNotificationsList from "./components/PopupNotificationsList"; import Footer from "./components/Footer"; import { useNotification } from "./components/useNotification"; @@ -66,6 +63,11 @@ function App() { const [supabase] = useState(() => createBrowserClient(env.SUPABASE_URL, env.SUPABASE_ANON_KEY), ); + + const [notifications, addNotification] = useNotification(); + const [avatarUri, setAvatarUri] = useState(""); + const [userDisplayName, setUserDisplayName] = useState(""); + const [user, setUser] = useState(undefined); // force rerender because user is still undefined briefly on first page load const [forceRerenderCounter, setForceRerenderCounter] = useState(0); @@ -84,12 +86,19 @@ function App() { } else if (event === "SIGNED_IN") { setUser(session!.user); // create new profile & avatar - insertNewUser(supabase, { - id: session!.user.id!, - display_name: - session!.user.user_metadata.name || - session!.user.user_metadata.email.split("@")[0], - }); + insertNewUser( + supabase, + { + id: session!.user.id!, + // user name or name from email address + display_name: + session!.user.user_metadata.name || + session!.user.user_metadata.email.split("@")[0], + }, + setAvatarUri, + setUserDisplayName, + addNotification, + ); } else if (event === "SIGNED_OUT") { setUser(undefined); } @@ -114,7 +123,6 @@ function App() { const [theme] = useTheme(); const [sidePanelIsShown, setSidePanelIsShown] = useState(false); - const [userDisplayName, setUserDisplayName] = useState(""); const [wishlist, setWishlist] = useState([]); const [rawCartItems, setRawCartItems] = useState([]); const [cartCount, setCartCount] = useState(0); @@ -180,8 +188,6 @@ function App() { })(); }, [user]); - const [notifications, addNotification] = useNotification(); - return ( @@ -205,6 +211,8 @@ function App() { user={user} addNotification={addNotification} userDisplayName={userDisplayName} + avatarUri={avatarUri} + setAvatarUri={setAvatarUri} /> {/* space for navbar above main page content */} diff --git a/app/utils/insertNewUser.ts b/app/utils/insertNewUser.ts index 7192e50..8bd1e8d 100644 --- a/app/utils/insertNewUser.ts +++ b/app/utils/insertNewUser.ts @@ -1,3 +1,7 @@ +import { createAvatar } from "@dicebear/core"; +import * as bigSmile from "@dicebear/big-smile"; + +import { AddNotificationFunction } from "~/components/useNotification"; import { ContextProps } from "~/utils/types/ContextProps.type"; async function checkProfileExists( @@ -39,6 +43,9 @@ export default async function insertNewUser( id: string; display_name: string; }, + setAvatarUri: SetState, + setUserDisplayName: SetState, + addNotification: AddNotificationFunction, ) { // PROFILE const profileExists = await checkProfileExists(supabase, profileObj.id); @@ -50,17 +57,39 @@ export default async function insertNewUser( console.error("Error inserting new profile", profileInsertError); return; } + setUserDisplayName(profileObj.display_name); } // AVATAR const avatarExists = await checkAvatarExists(supabase, profileObj.id); if (!avatarExists) { - const { error: avatarInsertError } = await supabase + const { data, error: avatarInsertError } = await supabase .from("AVATARS") - .insert({ id: profileObj.id }); + .insert({ id: profileObj.id }) + .select() + .single(); if (avatarInsertError) { console.error("Error inserting new avatar", avatarInsertError); return; } + + setAvatarUri( + createAvatar(bigSmile, { + accessoriesProbability: data.accessoriesProbability!, + backgroundColor: [data.backgroundColor!], + skinColor: [data.skinColor!], + hairColor: [data.hairColor!], + // expect errors of not matching types + // @ts-expect-error + hair: [data.hair!], + // @ts-expect-error + eyes: [data.eyes!], + // @ts-expect-error + mouth: [data.mouth!], + // @ts-expect-error + accessories: [data.accessories!], + }).toDataUri(), + ); + addNotification("Profile created", "SUCCESS"); } }