mirror of
https://github.com/aljazceru/landscape-template.git
synced 2025-12-29 12:04:23 +01:00
feat: added skeletons to profile tabs, added api mocsk to profile
This commit is contained in:
@@ -1,5 +1,4 @@
|
||||
import Avatar from 'src/features/Profiles/Components/Avatar/Avatar';
|
||||
import dayjs from 'dayjs'
|
||||
|
||||
import Skeleton from 'react-loading-skeleton';
|
||||
|
||||
interface Props {
|
||||
|
||||
@@ -29,6 +29,12 @@ export default function EditProfilePage() {
|
||||
const isMediumScreen = useMediaQuery(MEDIA_QUERIES.isMedium);
|
||||
|
||||
|
||||
const user = useAppSelector(state => state.user.me)
|
||||
|
||||
|
||||
if (!user)
|
||||
return <LoadingPage />
|
||||
|
||||
return (
|
||||
<>
|
||||
<Helmet>
|
||||
|
||||
@@ -17,59 +17,10 @@ interface Props {
|
||||
|
||||
|
||||
|
||||
// function reducer(state: State, action: Action): State {
|
||||
// switch (action.type) {
|
||||
// case 'set':
|
||||
// return {
|
||||
// hasNewChanges: false,
|
||||
// keys: [...action.payload],
|
||||
// oldKeys: [...action.payload],
|
||||
// }
|
||||
// case 'delete':
|
||||
// if (state.keys.length === 1)
|
||||
// return state;
|
||||
// return {
|
||||
// hasNewChanges: true,
|
||||
// oldKeys: state.oldKeys,
|
||||
// keys: [...state.keys.slice(0, action.payload.idx), ...state.keys.slice(action.payload.idx + 1)]
|
||||
// };
|
||||
// case 'update':
|
||||
// return {
|
||||
// hasNewChanges: true,
|
||||
// oldKeys: state.oldKeys,
|
||||
// keys: state.keys.map((item, idx) => {
|
||||
// if (idx === action.payload.idx)
|
||||
// return {
|
||||
// ...item,
|
||||
// name: action.payload.value
|
||||
// }
|
||||
// return item;
|
||||
// }),
|
||||
|
||||
// }
|
||||
// case 'cancel':
|
||||
// return {
|
||||
// hasNewChanges: false,
|
||||
// keys: [...state.oldKeys],
|
||||
// oldKeys: state.oldKeys,
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
|
||||
export default function LinkedAccountsCard({ value, onChange }: Props) {
|
||||
|
||||
const dispatch = useAppDispatch();
|
||||
const inputsRefs = useRef<Nullable<HTMLInputElement>[]>([]);
|
||||
// const [keysState, keysDispatch] = useReducer(reducer, { keys: [], oldKeys: [], hasNewChanges: false, });
|
||||
|
||||
// const [updateKeys, updatingKeysStatus] = useUpdateUserWalletsKeysMutation({
|
||||
// onCompleted: data => {
|
||||
// keysDispatch({
|
||||
// type: "set",
|
||||
// payload: data.updateUserWalletKeys
|
||||
// })
|
||||
// }
|
||||
// })
|
||||
|
||||
const connectNewWallet = () => {
|
||||
dispatch(openModal({ Modal: "LinkingAccountModal" }))
|
||||
|
||||
@@ -0,0 +1,45 @@
|
||||
import React from 'react'
|
||||
import Card from 'src/Components/Card/Card';
|
||||
import Skeleton from 'react-loading-skeleton';
|
||||
|
||||
export default function PreferencesTabSkeleton() {
|
||||
return (
|
||||
<div className="grid grid-cols-1 md:grid-cols-3 gap-24">
|
||||
<div className="col-span-2 flex flex-col gap-24">
|
||||
<Card>
|
||||
<p className="text-body2 font-bold"><Skeleton width="15ch" /></p>
|
||||
<p className="text-body4 text-gray-600 mt-8">
|
||||
<Skeleton width="70%" />
|
||||
<Skeleton width="35%" />
|
||||
</p>
|
||||
|
||||
<div className='mt-24 flex flex-col gap-16'>
|
||||
<ul className="mt-8 relative flex flex-col gap-8">
|
||||
{Array(3).fill(0).map((_, idx) =>
|
||||
<li key={idx} className="flex flex-wrap gap-16 justify-between items-center text-body4 border-b py-12 px-16 border border-gray-200 rounded-16 focus-within:ring-1 ring-primary-200">
|
||||
<div className='p-0 border-0 focus:border-0 focus:outline-none grow
|
||||
focus:ring-0 placeholder:!text-gray-400' >
|
||||
<Skeleton width='20ch'></Skeleton>
|
||||
</div>
|
||||
</li>
|
||||
)}
|
||||
</ul>
|
||||
|
||||
</div>
|
||||
</Card>
|
||||
<Card>
|
||||
<p className="text-body2 font-bold"><Skeleton width="12ch" /></p>
|
||||
<p className="text-body4 text-gray-600 mt-8">
|
||||
<Skeleton width="80%" />
|
||||
<Skeleton width="50%" />
|
||||
<Skeleton width="65%" />
|
||||
</p>
|
||||
<div className="py-42"></div>
|
||||
</Card>
|
||||
</div>
|
||||
<div className="">
|
||||
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
@@ -1,9 +1,8 @@
|
||||
import LinkedAccountsCard from './LinkedAccountsCard/LinkedAccountsCard';
|
||||
import CommentsSettingsCard from './CommentsSettingsCard/CommentsSettingsCard';
|
||||
import { UpdateUserPreferencesMutationVariables, useMyProfilePreferencesQuery, useUpdateUserPreferencesMutation } from 'src/graphql';
|
||||
import LoadingPage from 'src/Components/LoadingPage/LoadingPage';
|
||||
import NotFoundPage from "src/features/Shared/pages/NotFoundPage/NotFoundPage";
|
||||
|
||||
import PreferencesTabSkeleton from './PreferencesTab.Skeleton'
|
||||
import * as yup from "yup";
|
||||
import { yupResolver } from "@hookform/resolvers/yup";
|
||||
import { Controller, SubmitHandler, useForm } from 'react-hook-form';
|
||||
@@ -12,6 +11,7 @@ import { toast } from 'react-toastify';
|
||||
import { NotificationsService } from 'src/services';
|
||||
import { NetworkStatus } from '@apollo/client';
|
||||
import { usePrompt } from 'src/utils/hooks';
|
||||
import { useEffect } from 'react';
|
||||
|
||||
|
||||
interface Props {
|
||||
@@ -45,11 +45,16 @@ export default function PreferencesTab() {
|
||||
});
|
||||
const [mutate, mutationStatus] = useUpdateUserPreferencesMutation();
|
||||
|
||||
usePrompt('You may have some unsaved changes. You still want to leave?', isDirty)
|
||||
useEffect(() => {
|
||||
console.log("MOUNTED");
|
||||
|
||||
}, [])
|
||||
|
||||
// usePrompt('You may have some unsaved changes. You still want to leave?', isDirty)
|
||||
|
||||
|
||||
if (query.networkStatus === NetworkStatus.loading)
|
||||
return <LoadingPage />
|
||||
if (query.loading)
|
||||
return <PreferencesTabSkeleton />
|
||||
|
||||
if (!query.data?.me)
|
||||
return <NotFoundPage />
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
query MyProfilePreferences {
|
||||
me {
|
||||
id
|
||||
walletsKeys {
|
||||
key
|
||||
name
|
||||
@@ -11,6 +12,7 @@ query MyProfilePreferences {
|
||||
|
||||
mutation UpdateUserPreferences($walletsKeys: [UserKeyInputType!]) {
|
||||
updateUserPreferences(userKeys: $walletsKeys) {
|
||||
id
|
||||
walletsKeys {
|
||||
key
|
||||
name
|
||||
|
||||
@@ -3,7 +3,6 @@ import { Link } from 'react-router-dom'
|
||||
import Button from 'src/Components/Button/Button'
|
||||
import Card from 'src/Components/Card/Card'
|
||||
import Avatar from 'src/features/Profiles/Components/Avatar/Avatar'
|
||||
import { useProfileQuery } from 'src/graphql'
|
||||
import { trimText } from 'src/utils/helperFunctions'
|
||||
import { useAppSelector } from 'src/utils/hooks'
|
||||
import { createRoute } from 'src/utils/routing'
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
import Card from 'src/Components/Card/Card';
|
||||
import Skeleton from 'react-loading-skeleton';
|
||||
|
||||
export default function UpdateProfileAboutTabSkeleton() {
|
||||
return (
|
||||
<div className="grid grid-cols-1 md:grid-cols-3 gap-24">
|
||||
<div className="col-span-2 flex flex-col gap-24">
|
||||
<Card className="md:col-span-2" defaultPadding={false}>
|
||||
<div className="bg-gray-100 relative h-[160px] rounded-t-16">
|
||||
<div className="absolute left-24 bottom-0 translate-y-1/2">
|
||||
<div className="w-[120px] aspect-square rounded-full bg-gray-50 border border-gray-200"></div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="p-16 md:p-24 mt-64">
|
||||
|
||||
<p className="text-body2 font-bold"><Skeleton width="12ch" /></p>
|
||||
<p className="text-body4 text-gray-600 mt-8">
|
||||
<Skeleton width="50%" />
|
||||
</p>
|
||||
<div className="py-[250px]"></div>
|
||||
</div>
|
||||
</Card>
|
||||
</div>
|
||||
<div className="">
|
||||
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
@@ -12,6 +12,7 @@ import Card from "src/Components/Card/Card";
|
||||
import LoadingPage from "src/Components/LoadingPage/LoadingPage";
|
||||
import NotFoundPage from "src/features/Shared/pages/NotFoundPage/NotFoundPage";
|
||||
import { setUser } from "src/redux/features/user.slice";
|
||||
import UpdateProfileAboutTabSkeleton from "./UpdateMyProfileTab.Skeleton";
|
||||
|
||||
interface Props {
|
||||
}
|
||||
@@ -75,7 +76,7 @@ export default function UpdateMyProfileTab() {
|
||||
|
||||
|
||||
if (profileQuery.loading)
|
||||
return <LoadingPage />
|
||||
return <UpdateProfileAboutTabSkeleton />
|
||||
|
||||
if (!profileQuery.data?.me)
|
||||
return <NotFoundPage />
|
||||
|
||||
@@ -573,14 +573,14 @@ export type PostDetailsQuery = { __typename?: 'Query', getPostById: { __typename
|
||||
export type MyProfilePreferencesQueryVariables = Exact<{ [key: string]: never; }>;
|
||||
|
||||
|
||||
export type MyProfilePreferencesQuery = { __typename?: 'Query', me: { __typename?: 'MyProfile', nostr_prv_key: string | null, nostr_pub_key: string | null, walletsKeys: Array<{ __typename?: 'WalletKey', key: string, name: string }> } | null };
|
||||
export type MyProfilePreferencesQuery = { __typename?: 'Query', me: { __typename?: 'MyProfile', id: number, nostr_prv_key: string | null, nostr_pub_key: string | null, walletsKeys: Array<{ __typename?: 'WalletKey', key: string, name: string }> } | null };
|
||||
|
||||
export type UpdateUserPreferencesMutationVariables = Exact<{
|
||||
walletsKeys: InputMaybe<Array<UserKeyInputType> | UserKeyInputType>;
|
||||
}>;
|
||||
|
||||
|
||||
export type UpdateUserPreferencesMutation = { __typename?: 'Mutation', updateUserPreferences: { __typename?: 'MyProfile', nostr_pub_key: string | null, nostr_prv_key: string | null, walletsKeys: Array<{ __typename?: 'WalletKey', key: string, name: string }> } };
|
||||
export type UpdateUserPreferencesMutation = { __typename?: 'Mutation', updateUserPreferences: { __typename?: 'MyProfile', id: number, nostr_pub_key: string | null, nostr_prv_key: string | null, walletsKeys: Array<{ __typename?: 'WalletKey', key: string, name: string }> } };
|
||||
|
||||
export type MyProfileAboutQueryVariables = Exact<{ [key: string]: never; }>;
|
||||
|
||||
@@ -1383,6 +1383,7 @@ export type PostDetailsQueryResult = Apollo.QueryResult<PostDetailsQuery, PostDe
|
||||
export const MyProfilePreferencesDocument = gql`
|
||||
query MyProfilePreferences {
|
||||
me {
|
||||
id
|
||||
walletsKeys {
|
||||
key
|
||||
name
|
||||
@@ -1422,6 +1423,7 @@ export type MyProfilePreferencesQueryResult = Apollo.QueryResult<MyProfilePrefer
|
||||
export const UpdateUserPreferencesDocument = gql`
|
||||
mutation UpdateUserPreferences($walletsKeys: [UserKeyInputType!]) {
|
||||
updateUserPreferences(userKeys: $walletsKeys) {
|
||||
id
|
||||
walletsKeys {
|
||||
key
|
||||
name
|
||||
|
||||
@@ -6,7 +6,7 @@ export const user: User & MyProfile = {
|
||||
email: "mtg0987654321@gmail.com",
|
||||
avatar: "https://avatars.dicebear.com/api/bottts/Mtgmtg.svg",
|
||||
bio: "Lorem asiop asklh kluiw wekjhl shkj kljhsva klu khsc klhlkbs mjklwqr kmlk sadlfui mewr qiumnk, asdjomi cskhsdf.",
|
||||
name: "123123124asdfsadfsa8d7fsadfasdf",
|
||||
name: "Mtg",
|
||||
github: "MTG2000",
|
||||
jobTitle: "Front-end Web Developer",
|
||||
join_date: new Date(2021).toISOString(),
|
||||
@@ -14,7 +14,7 @@ export const user: User & MyProfile = {
|
||||
linkedin: "https://www.linkedin.com/in/mtg-softwares-dev/",
|
||||
location: "Germany, Berlin",
|
||||
role: "user",
|
||||
twitter: "john-doe",
|
||||
twitter: "mtg",
|
||||
website: "https://mtg-dev.tech",
|
||||
stories: posts.stories,
|
||||
nostr_prv_key: "123123124asdfsadfsa8d7fsadfasdf",
|
||||
|
||||
@@ -29,6 +29,8 @@ import {
|
||||
MeQuery,
|
||||
ProfileQuery,
|
||||
GetMyDraftsQuery,
|
||||
MyProfileAboutQuery,
|
||||
MyProfilePreferencesQuery,
|
||||
} from 'src/graphql'
|
||||
|
||||
const delay = (ms = 1000) => new Promise((res) => setTimeout(res, ms + Math.random() * 1000))
|
||||
@@ -195,6 +197,7 @@ export const handlers = [
|
||||
|
||||
graphql.query<MeQuery>('Me', async (req, res, ctx) => {
|
||||
await delay()
|
||||
console.log("ME");
|
||||
|
||||
return res(
|
||||
ctx.data({
|
||||
@@ -203,6 +206,27 @@ export const handlers = [
|
||||
)
|
||||
}),
|
||||
|
||||
|
||||
graphql.query<MyProfileAboutQuery>('MyProfileAbout', async (req, res, ctx) => {
|
||||
await delay()
|
||||
return res(
|
||||
ctx.data({
|
||||
me: me(),
|
||||
})
|
||||
)
|
||||
}),
|
||||
|
||||
graphql.query<MyProfilePreferencesQuery>('MyProfilePreferences', async (req, res, ctx) => {
|
||||
await delay()
|
||||
return res(
|
||||
ctx.data({
|
||||
me: me(),
|
||||
})
|
||||
)
|
||||
}),
|
||||
|
||||
|
||||
|
||||
graphql.query<ProfileQuery>('profile', async (req, res, ctx) => {
|
||||
await delay()
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import { MOCK_DATA } from "./data";
|
||||
import { MyProfile, Query, QueryGetFeedArgs, QueryGetPostByIdArgs } from 'src/graphql'
|
||||
import { MyProfile, Query, QueryGetFeedArgs, QueryGetPostByIdArgs, User } from 'src/graphql'
|
||||
import { Chance } from "chance";
|
||||
import { tags } from "./data/tags";
|
||||
import { hackathons } from "./data/hackathon";
|
||||
@@ -72,11 +72,16 @@ export function getAllHackathons() {
|
||||
}
|
||||
|
||||
export function me() {
|
||||
return MOCK_DATA['user'] as MyProfile
|
||||
return {
|
||||
...MOCK_DATA['user'],
|
||||
__typename: "MyProfile",
|
||||
} as MyProfile
|
||||
}
|
||||
|
||||
|
||||
|
||||
export function profile() {
|
||||
return MOCK_DATA['user']
|
||||
return { ...MOCK_DATA['user'], __typename: 'User' } as User
|
||||
}
|
||||
|
||||
export function getMyDrafts(): Query['getMyDrafts'] {
|
||||
|
||||
Reference in New Issue
Block a user