3811 add accounts loader (#3829)

* rename exports

* rename exports

* fix css

* done

* updating image
This commit is contained in:
bosiraphael
2024-02-09 15:29:11 +01:00
committed by GitHub
parent 11d1c4c161
commit 917fc5bd4d
18 changed files with 198 additions and 124 deletions

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

View File

@ -1,17 +1,19 @@
import { Loader } from '@/ui/feedback/loader/components/Loader'; import { Loader } from '@/ui/feedback/loader/components/Loader';
import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder'; import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder';
import { import {
StyledEmptyContainer, AnimatedPlaceholderEmptyContainer,
StyledEmptyTextContainer, AnimatedPlaceholderEmptyTextContainer,
StyledEmptyTitle, AnimatedPlaceholderEmptyTitle,
} from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled'; } from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled';
export const EmailLoader = ({ loadingText }: { loadingText?: string }) => ( export const EmailLoader = ({ loadingText }: { loadingText?: string }) => (
<StyledEmptyContainer> <AnimatedPlaceholderEmptyContainer>
<AnimatedPlaceholder type="loadingMessages" /> <AnimatedPlaceholder type="loadingMessages" />
<StyledEmptyTextContainer> <AnimatedPlaceholderEmptyTextContainer>
<StyledEmptyTitle>{loadingText || 'Loading emails'}</StyledEmptyTitle> <AnimatedPlaceholderEmptyTitle>
{loadingText || 'Loading emails'}
</AnimatedPlaceholderEmptyTitle>
<Loader /> <Loader />
</StyledEmptyTextContainer> </AnimatedPlaceholderEmptyTextContainer>
</StyledEmptyContainer> </AnimatedPlaceholderEmptyContainer>
); );

View File

@ -20,10 +20,10 @@ import {
import { useSnackBar } from '@/ui/feedback/snack-bar-manager/hooks/useSnackBar'; import { useSnackBar } from '@/ui/feedback/snack-bar-manager/hooks/useSnackBar';
import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder'; import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder';
import { import {
StyledEmptyContainer, AnimatedPlaceholderEmptyContainer,
StyledEmptySubTitle, AnimatedPlaceholderEmptySubTitle,
StyledEmptyTextContainer, AnimatedPlaceholderEmptyTextContainer,
StyledEmptyTitle, AnimatedPlaceholderEmptyTitle,
} from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled'; } from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled';
import { Card } from '@/ui/layout/card/components/Card'; import { Card } from '@/ui/layout/card/components/Card';
import { Section } from '@/ui/layout/section/components/Section'; import { Section } from '@/ui/layout/section/components/Section';
@ -155,15 +155,17 @@ export const EmailThreads = ({
if (!firstQueryLoading && !timelineThreads?.length) { if (!firstQueryLoading && !timelineThreads?.length) {
return ( return (
<StyledEmptyContainer> <AnimatedPlaceholderEmptyContainer>
<AnimatedPlaceholder type="emptyInbox" /> <AnimatedPlaceholder type="emptyInbox" />
<StyledEmptyTextContainer> <AnimatedPlaceholderEmptyTextContainer>
<StyledEmptyTitle>Empty Inbox</StyledEmptyTitle> <AnimatedPlaceholderEmptyTitle>
<StyledEmptySubTitle> Empty Inbox
</AnimatedPlaceholderEmptyTitle>
<AnimatedPlaceholderEmptySubTitle>
No email exchange has occurred with this record yet. No email exchange has occurred with this record yet.
</StyledEmptySubTitle> </AnimatedPlaceholderEmptySubTitle>
</StyledEmptyTextContainer> </AnimatedPlaceholderEmptyTextContainer>
</StyledEmptyContainer> </AnimatedPlaceholderEmptyContainer>
); );
} }

View File

@ -11,10 +11,10 @@ import { IconPlus } from '@/ui/display/icon';
import { Button } from '@/ui/input/button/components/Button'; import { Button } from '@/ui/input/button/components/Button';
import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder'; import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder';
import { import {
StyledEmptyContainer, AnimatedPlaceholderEmptyContainer,
StyledEmptySubTitle, AnimatedPlaceholderEmptySubTitle,
StyledEmptyTextContainer, AnimatedPlaceholderEmptyTextContainer,
StyledEmptyTitle, AnimatedPlaceholderEmptyTitle,
} from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled'; } from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled';
const StyledAttachmentsContainer = styled.div` const StyledAttachmentsContainer = styled.div`
@ -66,14 +66,16 @@ export const Attachments = ({
onUploadFile={onUploadFile} onUploadFile={onUploadFile}
/> />
) : ( ) : (
<StyledEmptyContainer> <AnimatedPlaceholderEmptyContainer>
<AnimatedPlaceholder type="noFile" /> <AnimatedPlaceholder type="noFile" />
<StyledEmptyTextContainer> <AnimatedPlaceholderEmptyTextContainer>
<StyledEmptyTitle>No Files</StyledEmptyTitle> <AnimatedPlaceholderEmptyTitle>
<StyledEmptySubTitle> No Files
</AnimatedPlaceholderEmptyTitle>
<AnimatedPlaceholderEmptySubTitle>
There are no associated files with this record. There are no associated files with this record.
</StyledEmptySubTitle> </AnimatedPlaceholderEmptySubTitle>
</StyledEmptyTextContainer> </AnimatedPlaceholderEmptyTextContainer>
<StyledFileInput <StyledFileInput
ref={inputFileRef} ref={inputFileRef}
onChange={handleFileChange} onChange={handleFileChange}
@ -85,7 +87,7 @@ export const Attachments = ({
variant="secondary" variant="secondary"
onClick={handleUploadFileClick} onClick={handleUploadFileClick}
/> />
</StyledEmptyContainer> </AnimatedPlaceholderEmptyContainer>
)} )}
</StyledDropZoneContainer> </StyledDropZoneContainer>
); );

View File

@ -8,10 +8,10 @@ import { IconPlus } from '@/ui/display/icon';
import { Button } from '@/ui/input/button/components/Button'; import { Button } from '@/ui/input/button/components/Button';
import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder'; import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder';
import { import {
StyledEmptyContainer, AnimatedPlaceholderEmptyContainer,
StyledEmptySubTitle, AnimatedPlaceholderEmptySubTitle,
StyledEmptyTextContainer, AnimatedPlaceholderEmptyTextContainer,
StyledEmptyTitle, AnimatedPlaceholderEmptyTitle,
} from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled'; } from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled';
const StyledNotesContainer = styled.div` const StyledNotesContainer = styled.div`
@ -33,14 +33,16 @@ export const Notes = ({
if (notes?.length === 0) { if (notes?.length === 0) {
return ( return (
<StyledEmptyContainer> <AnimatedPlaceholderEmptyContainer>
<AnimatedPlaceholder type="noNote" /> <AnimatedPlaceholder type="noNote" />
<StyledEmptyTextContainer> <AnimatedPlaceholderEmptyTextContainer>
<StyledEmptyTitle>No notes</StyledEmptyTitle> <AnimatedPlaceholderEmptyTitle>
<StyledEmptySubTitle> No notes
</AnimatedPlaceholderEmptyTitle>
<AnimatedPlaceholderEmptySubTitle>
There are no associated notes with this record. There are no associated notes with this record.
</StyledEmptySubTitle> </AnimatedPlaceholderEmptySubTitle>
</StyledEmptyTextContainer> </AnimatedPlaceholderEmptyTextContainer>
<Button <Button
Icon={IconPlus} Icon={IconPlus}
title="New note" title="New note"
@ -52,7 +54,7 @@ export const Notes = ({
}) })
} }
/> />
</StyledEmptyContainer> </AnimatedPlaceholderEmptyContainer>
); );
} }

View File

@ -9,10 +9,10 @@ import { IconPlus } from '@/ui/display/icon';
import { Button } from '@/ui/input/button/components/Button'; import { Button } from '@/ui/input/button/components/Button';
import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder'; import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder';
import { import {
StyledEmptyContainer, AnimatedPlaceholderEmptyContainer,
StyledEmptySubTitle, AnimatedPlaceholderEmptySubTitle,
StyledEmptyTextContainer, AnimatedPlaceholderEmptyTextContainer,
StyledEmptyTitle, AnimatedPlaceholderEmptyTitle,
} from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled'; } from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled';
import { useTabList } from '@/ui/layout/tab/hooks/useTabList'; import { useTabList } from '@/ui/layout/tab/hooks/useTabList';
@ -58,14 +58,14 @@ export const TaskGroups = ({
(activeTabId === 'done' && completedTasks?.length === 0) (activeTabId === 'done' && completedTasks?.length === 0)
) { ) {
return ( return (
<StyledEmptyContainer> <AnimatedPlaceholderEmptyContainer>
<AnimatedPlaceholder type="noTask" /> <AnimatedPlaceholder type="noTask" />
<StyledEmptyTextContainer> <AnimatedPlaceholderEmptyTextContainer>
<StyledEmptyTitle>No Task</StyledEmptyTitle> <AnimatedPlaceholderEmptyTitle>No Task</AnimatedPlaceholderEmptyTitle>
<StyledEmptySubTitle> <AnimatedPlaceholderEmptySubTitle>
There are no tasks for this user filter There are no tasks for this user filter
</StyledEmptySubTitle> </AnimatedPlaceholderEmptySubTitle>
</StyledEmptyTextContainer> </AnimatedPlaceholderEmptyTextContainer>
<Button <Button
Icon={IconPlus} Icon={IconPlus}
title="New task" title="New task"
@ -77,7 +77,7 @@ export const TaskGroups = ({
}) })
} }
/> />
</StyledEmptyContainer> </AnimatedPlaceholderEmptyContainer>
); );
} }

View File

@ -5,10 +5,10 @@ import { useTimelineActivities } from '@/activities/timeline/hooks/useTimelineAc
import { ActivityTargetableObject } from '@/activities/types/ActivityTargetableEntity'; import { ActivityTargetableObject } from '@/activities/types/ActivityTargetableEntity';
import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder'; import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder';
import { import {
StyledEmptyContainer, AnimatedPlaceholderEmptyContainer,
StyledEmptySubTitle, AnimatedPlaceholderEmptySubTitle,
StyledEmptyTextContainer, AnimatedPlaceholderEmptyTextContainer,
StyledEmptyTitle, AnimatedPlaceholderEmptyTitle,
} from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled'; } from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled';
import { useIsMobile } from '@/ui/utilities/responsive/hooks/useIsMobile'; import { useIsMobile } from '@/ui/utilities/responsive/hooks/useIsMobile';
@ -46,16 +46,18 @@ export const Timeline = ({
if (showEmptyState) { if (showEmptyState) {
return ( return (
<StyledEmptyContainer> <AnimatedPlaceholderEmptyContainer>
<AnimatedPlaceholder type="emptyTimeline" /> <AnimatedPlaceholder type="emptyTimeline" />
<StyledEmptyTextContainer> <AnimatedPlaceholderEmptyTextContainer>
<StyledEmptyTitle>Add your first Activity</StyledEmptyTitle> <AnimatedPlaceholderEmptyTitle>
<StyledEmptySubTitle> Add your first Activity
</AnimatedPlaceholderEmptyTitle>
<AnimatedPlaceholderEmptySubTitle>
There are no activities associated with this record.{' '} There are no activities associated with this record.{' '}
</StyledEmptySubTitle> </AnimatedPlaceholderEmptySubTitle>
</StyledEmptyTextContainer> </AnimatedPlaceholderEmptyTextContainer>
<TimelineCreateButtonGroup targetableObject={targetableObject} /> <TimelineCreateButtonGroup targetableObject={targetableObject} />
</StyledEmptyContainer> </AnimatedPlaceholderEmptyContainer>
); );
} }

View File

@ -4,10 +4,10 @@ import { Button } from 'tsup.ui.index';
import { IconRefresh } from '@/ui/display/icon'; import { IconRefresh } from '@/ui/display/icon';
import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder'; import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder';
import { import {
StyledEmptyContainer, AnimatedPlaceholderEmptyContainer,
StyledEmptySubTitle, AnimatedPlaceholderEmptySubTitle,
StyledEmptyTextContainer, AnimatedPlaceholderEmptyTextContainer,
StyledEmptyTitle, AnimatedPlaceholderEmptyTitle,
} from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled'; } from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled';
type GenericErrorFallbackProps = FallbackProps; type GenericErrorFallbackProps = FallbackProps;
@ -17,18 +17,22 @@ export const GenericErrorFallback = ({
resetErrorBoundary, resetErrorBoundary,
}: GenericErrorFallbackProps) => { }: GenericErrorFallbackProps) => {
return ( return (
<StyledEmptyContainer> <AnimatedPlaceholderEmptyContainer>
<AnimatedPlaceholder type="errorIndex" /> <AnimatedPlaceholder type="errorIndex" />
<StyledEmptyTextContainer> <AnimatedPlaceholderEmptyTextContainer>
<StyledEmptyTitle>Servers on a coffee break</StyledEmptyTitle> <AnimatedPlaceholderEmptyTitle>
<StyledEmptySubTitle>{error.message}</StyledEmptySubTitle> Servers on a coffee break
</StyledEmptyTextContainer> </AnimatedPlaceholderEmptyTitle>
<AnimatedPlaceholderEmptySubTitle>
{error.message}
</AnimatedPlaceholderEmptySubTitle>
</AnimatedPlaceholderEmptyTextContainer>
<Button <Button
Icon={IconRefresh} Icon={IconRefresh}
title="Reload" title="Reload"
variant={'secondary'} variant={'secondary'}
onClick={() => resetErrorBoundary()} onClick={() => resetErrorBoundary()}
/> />
</StyledEmptyContainer> </AnimatedPlaceholderEmptyContainer>
); );
}; };

View File

@ -11,10 +11,10 @@ import { IconPlus } from '@/ui/display/icon';
import { Button } from '@/ui/input/button/components/Button'; import { Button } from '@/ui/input/button/components/Button';
import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder'; import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder';
import { import {
StyledEmptyContainer, AnimatedPlaceholderEmptyContainer,
StyledEmptySubTitle, AnimatedPlaceholderEmptySubTitle,
StyledEmptyTextContainer, AnimatedPlaceholderEmptyTextContainer,
StyledEmptyTitle, AnimatedPlaceholderEmptyTitle,
} from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled'; } from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled';
import { DragSelect } from '@/ui/utilities/drag-select/components/DragSelect'; import { DragSelect } from '@/ui/utilities/drag-select/components/DragSelect';
import { ScrollWrapper } from '@/ui/utilities/scroll/components/ScrollWrapper'; import { ScrollWrapper } from '@/ui/utilities/scroll/components/ScrollWrapper';
@ -110,23 +110,23 @@ export const RecordTableWithWrappers = ({
tableBodyRef={tableBodyRef} tableBodyRef={tableBodyRef}
/> />
{!isRecordTableInitialLoading && numberOfTableRows === 0 && ( {!isRecordTableInitialLoading && numberOfTableRows === 0 && (
<StyledEmptyContainer> <AnimatedPlaceholderEmptyContainer>
<AnimatedPlaceholder type="noRecord" /> <AnimatedPlaceholder type="noRecord" />
<StyledEmptyTextContainer> <AnimatedPlaceholderEmptyTextContainer>
<StyledEmptyTitle> <AnimatedPlaceholderEmptyTitle>
Add your first {objectLabel} Add your first {objectLabel}
</StyledEmptyTitle> </AnimatedPlaceholderEmptyTitle>
<StyledEmptySubTitle> <AnimatedPlaceholderEmptySubTitle>
Use our API or add your first {objectLabel} manually Use our API or add your first {objectLabel} manually
</StyledEmptySubTitle> </AnimatedPlaceholderEmptySubTitle>
</StyledEmptyTextContainer> </AnimatedPlaceholderEmptyTextContainer>
<Button <Button
Icon={IconPlus} Icon={IconPlus}
title={`Add a ${objectLabel}`} title={`Add a ${objectLabel}`}
variant={'secondary'} variant={'secondary'}
onClick={createRecord} onClick={createRecord}
/> />
</StyledEmptyContainer> </AnimatedPlaceholderEmptyContainer>
)} )}
</StyledTableContainer> </StyledTableContainer>
</StyledTableWithHeader> </StyledTableWithHeader>

View File

@ -1,27 +1,16 @@
import { useRecoilValue } from 'recoil';
import { ConnectedAccount } from '@/accounts/types/ConnectedAccount'; import { ConnectedAccount } from '@/accounts/types/ConnectedAccount';
import { currentWorkspaceMemberState } from '@/auth/states/currentWorkspaceMemberState';
import { useDeleteOneRecord } from '@/object-record/hooks/useDeleteOneRecord'; import { useDeleteOneRecord } from '@/object-record/hooks/useDeleteOneRecord';
import { useFindManyRecords } from '@/object-record/hooks/useFindManyRecords';
import { H2Title } from '@/ui/display/typography/components/H2Title'; import { H2Title } from '@/ui/display/typography/components/H2Title';
import { Section } from '@/ui/layout/section/components/Section'; import { Section } from '@/ui/layout/section/components/Section';
import { SettingsAccountsCard } from './SettingsAccountsCard'; import { SettingsAccountsCard } from './SettingsAccountsCard';
import { SettingsAccountsEmptyStateCard } from './SettingsAccountsEmptyStateCard'; import { SettingsAccountsEmptyStateCard } from './SettingsAccountsEmptyStateCard';
export const SettingsAccountsConnectedAccountsSection = () => { export const SettingsAccountsConnectedAccountsSection = ({
const currentWorkspaceMember = useRecoilValue(currentWorkspaceMemberState); accounts,
}: {
const accounts = useFindManyRecords<ConnectedAccount>({ accounts: ConnectedAccount[];
objectNameSingular: 'connectedAccount', }) => {
filter: {
accountOwnerId: {
eq: currentWorkspaceMember?.id,
},
},
}).records;
const { deleteOneRecord } = useDeleteOneRecord({ const { deleteOneRecord } = useDeleteOneRecord({
objectNameSingular: 'connectedAccount', objectNameSingular: 'connectedAccount',
}); });

View File

@ -1,6 +1,6 @@
import styled from '@emotion/styled'; import styled from '@emotion/styled';
export const StyledEmptyContainer = styled.div` const StyledEmptyContainer = styled.div`
align-items: center; align-items: center;
width: 100%; width: 100%;
height: 100%; height: 100%;
@ -11,7 +11,9 @@ export const StyledEmptyContainer = styled.div`
text-align: center; text-align: center;
`; `;
export const StyledEmptyTextContainer = styled.div` export { StyledEmptyContainer as AnimatedPlaceholderEmptyContainer };
const StyledEmptyTextContainer = styled.div`
align-items: center; align-items: center;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
@ -21,13 +23,17 @@ export const StyledEmptyTextContainer = styled.div`
width: 100%; width: 100%;
`; `;
export const StyledEmptyTitle = styled.div` export { StyledEmptyTextContainer as AnimatedPlaceholderEmptyTextContainer };
const StyledEmptyTitle = styled.div`
color: ${({ theme }) => theme.font.color.primary}; color: ${({ theme }) => theme.font.color.primary};
font-size: ${({ theme }) => theme.font.size.lg}; font-size: ${({ theme }) => theme.font.size.lg};
font-weight: ${({ theme }) => theme.font.weight.semiBold}; font-weight: ${({ theme }) => theme.font.weight.semiBold};
`; `;
export const StyledEmptySubTitle = styled.div` export { StyledEmptyTitle as AnimatedPlaceholderEmptyTitle };
const StyledEmptySubTitle = styled.div`
color: ${({ theme }) => theme.font.color.tertiary}; color: ${({ theme }) => theme.font.color.tertiary};
font-size: ${({ theme }) => theme.font.size.sm}; font-size: ${({ theme }) => theme.font.size.sm};
font-weight: ${({ theme }) => theme.font.weight.regular}; font-weight: ${({ theme }) => theme.font.weight.regular};
@ -36,3 +42,5 @@ export const StyledEmptySubTitle = styled.div`
overflow: hidden; overflow: hidden;
width: 50%; width: 50%;
`; `;
export { StyledEmptySubTitle as AnimatedPlaceholderEmptySubTitle };

View File

@ -1,6 +1,6 @@
import styled from '@emotion/styled'; import styled from '@emotion/styled';
export const StyledErrorContainer = styled.div` const StyledErrorContainer = styled.div`
align-items: center; align-items: center;
width: 100%; width: 100%;
height: 100%; height: 100%;
@ -11,7 +11,9 @@ export const StyledErrorContainer = styled.div`
text-align: center; text-align: center;
`; `;
export const StyledErrorTextContainer = styled.div` export { StyledErrorContainer as AnimatedPlaceholderErrorContainer };
const StyledErrorTextContainer = styled.div`
align-items: center; align-items: center;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
@ -21,14 +23,18 @@ export const StyledErrorTextContainer = styled.div`
width: 100%; width: 100%;
`; `;
export const StyledErrorTitle = styled.div` export { StyledErrorTextContainer as AnimatedPlaceholderErrorTextContainer };
const StyledErrorTitle = styled.div`
color: ${({ theme }) => theme.font.color.primary}; color: ${({ theme }) => theme.font.color.primary};
font-size: ${({ theme }) => theme.font.size.xl}; font-size: ${({ theme }) => theme.font.size.xl};
font-weight: ${({ theme }) => theme.font.weight.semiBold}; font-weight: ${({ theme }) => theme.font.weight.semiBold};
line-height: ${({ theme }) => theme.text.lineHeight.lg}; line-height: ${({ theme }) => theme.text.lineHeight.lg};
`; `;
export const StyledErrorSubTitle = styled.div` export { StyledErrorTitle as AnimatedPlaceholderErrorTitle };
const StyledErrorSubTitle = styled.div`
color: ${({ theme }) => theme.font.color.tertiary}; color: ${({ theme }) => theme.font.color.tertiary};
font-size: ${({ theme }) => theme.font.size.xs}; font-size: ${({ theme }) => theme.font.size.xs};
font-weight: ${({ theme }) => theme.font.weight.regular}; font-weight: ${({ theme }) => theme.font.weight.regular};
@ -36,3 +42,5 @@ export const StyledErrorSubTitle = styled.div`
max-height: 2.4em; max-height: 2.4em;
overflow: hidden; overflow: hidden;
`; `;
export { StyledErrorSubTitle as AnimatedPlaceholderErrorSubTitle };

View File

@ -6,6 +6,7 @@ export const Background: Record<string, string> = {
errorIndex: '/images/placeholders/background/error_index_bg.png', errorIndex: '/images/placeholders/background/error_index_bg.png',
emptyTimeline: '/images/placeholders/background/empty_timeline_bg.png', emptyTimeline: '/images/placeholders/background/empty_timeline_bg.png',
loadingMessages: '/images/placeholders/background/loading_messages_bg.png', loadingMessages: '/images/placeholders/background/loading_messages_bg.png',
loadingAccounts: '/images/placeholders/background/loading_accounts_bg.png',
emptyInbox: '/images/placeholders/background/empty_inbox_bg.png', emptyInbox: '/images/placeholders/background/empty_inbox_bg.png',
error404: '/images/placeholders/background/404_bg.png', error404: '/images/placeholders/background/404_bg.png',
error500: '/images/placeholders/background/500_bg.png', error500: '/images/placeholders/background/500_bg.png',
@ -19,6 +20,7 @@ export const MovingImage: Record<string, string> = {
errorIndex: '/images/placeholders/moving-image/error_index.png', errorIndex: '/images/placeholders/moving-image/error_index.png',
emptyTimeline: '/images/placeholders/moving-image/empty_timeline.png', emptyTimeline: '/images/placeholders/moving-image/empty_timeline.png',
loadingMessages: '/images/placeholders/moving-image/loading_messages.png', loadingMessages: '/images/placeholders/moving-image/loading_messages.png',
loadingAccounts: '/images/placeholders/moving-image/loading_accounts.png',
emptyInbox: '/images/placeholders/moving-image/empty_inbox.png', emptyInbox: '/images/placeholders/moving-image/empty_inbox.png',
error404: '/images/placeholders/moving-image/404.png', error404: '/images/placeholders/moving-image/404.png',
error500: '/images/placeholders/moving-image/500.png', error500: '/images/placeholders/moving-image/500.png',

View File

@ -11,6 +11,7 @@ type SubMenuTopBarContainerProps = {
children: JSX.Element | JSX.Element[]; children: JSX.Element | JSX.Element[];
title: string; title: string;
Icon: IconComponent; Icon: IconComponent;
className?: string;
}; };
const StyledContainer = styled.div<{ isMobile: boolean }>` const StyledContainer = styled.div<{ isMobile: boolean }>`
@ -24,11 +25,12 @@ export const SubMenuTopBarContainer = ({
children, children,
title, title,
Icon, Icon,
className,
}: SubMenuTopBarContainerProps) => { }: SubMenuTopBarContainerProps) => {
const isMobile = useIsMobile(); const isMobile = useIsMobile();
return ( return (
<StyledContainer isMobile={isMobile}> <StyledContainer isMobile={isMobile} className={className}>
{isMobile && <PageHeader title={title} Icon={Icon} />} {isMobile && <PageHeader title={title} Icon={Icon} />}
<RightDrawerContainer>{children}</RightDrawerContainer> <RightDrawerContainer>{children}</RightDrawerContainer>
</StyledContainer> </StyledContainer>

View File

@ -5,11 +5,11 @@ import { SignInBackgroundMockPage } from '@/sign-in-background-mock/components/S
import { AppPath } from '@/types/AppPath'; import { AppPath } from '@/types/AppPath';
import { MainButton } from '@/ui/input/button/components/MainButton'; import { MainButton } from '@/ui/input/button/components/MainButton';
import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder'; import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder';
import { StyledEmptyTextContainer } from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled'; import { AnimatedPlaceholderEmptyTextContainer } from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled';
import { import {
StyledErrorContainer, AnimatedPlaceholderErrorContainer,
StyledErrorSubTitle, AnimatedPlaceholderErrorSubTitle,
StyledErrorTitle, AnimatedPlaceholderErrorTitle,
} from '@/ui/layout/animated-placeholder/components/ErrorPlaceholderStyled'; } from '@/ui/layout/animated-placeholder/components/ErrorPlaceholderStyled';
const StyledBackDrop = styled.div` const StyledBackDrop = styled.div`
@ -37,15 +37,17 @@ export const NotFound = () => {
return ( return (
<> <>
<StyledBackDrop> <StyledBackDrop>
<StyledErrorContainer> <AnimatedPlaceholderErrorContainer>
<AnimatedPlaceholder type="error404" /> <AnimatedPlaceholder type="error404" />
<StyledEmptyTextContainer> <AnimatedPlaceholderEmptyTextContainer>
<StyledErrorTitle>Off the beaten path</StyledErrorTitle> <AnimatedPlaceholderErrorTitle>
<StyledErrorSubTitle> Off the beaten path
</AnimatedPlaceholderErrorTitle>
<AnimatedPlaceholderErrorSubTitle>
The page you're seeking is either gone or never was. Let's get you The page you're seeking is either gone or never was. Let's get you
back on track back on track
</StyledErrorSubTitle> </AnimatedPlaceholderErrorSubTitle>
</StyledEmptyTextContainer> </AnimatedPlaceholderEmptyTextContainer>
<StyledButtonContainer> <StyledButtonContainer>
<MainButton <MainButton
title="Back to content" title="Back to content"
@ -53,7 +55,7 @@ export const NotFound = () => {
onClick={() => navigate(AppPath.Index)} onClick={() => navigate(AppPath.Index)}
/> />
</StyledButtonContainer> </StyledButtonContainer>
</StyledErrorContainer> </AnimatedPlaceholderErrorContainer>
</StyledBackDrop> </StyledBackDrop>
<SignInBackgroundMockPage /> <SignInBackgroundMockPage />
</> </>

View File

@ -0,0 +1,19 @@
import { Loader } from '@/ui/feedback/loader/components/Loader';
import AnimatedPlaceholder from '@/ui/layout/animated-placeholder/components/AnimatedPlaceholder';
import {
AnimatedPlaceholderEmptyContainer,
AnimatedPlaceholderEmptyTextContainer,
AnimatedPlaceholderEmptyTitle,
} from '@/ui/layout/animated-placeholder/components/EmptyPlaceholderStyled';
export const SettingsAccountLoader = () => (
<AnimatedPlaceholderEmptyContainer>
<AnimatedPlaceholder type="loadingAccounts" />
<AnimatedPlaceholderEmptyTextContainer>
<AnimatedPlaceholderEmptyTitle>
Loading account(s)
</AnimatedPlaceholderEmptyTitle>
<Loader />
</AnimatedPlaceholderEmptyTextContainer>
</AnimatedPlaceholderEmptyContainer>
);

View File

@ -1,17 +1,47 @@
import { useRecoilValue } from 'recoil';
import { ConnectedAccount } from '@/accounts/types/ConnectedAccount';
import { currentWorkspaceMemberState } from '@/auth/states/currentWorkspaceMemberState';
import { useFindManyRecords } from '@/object-record/hooks/useFindManyRecords';
import { SettingsAccountsConnectedAccountsSection } from '@/settings/accounts/components/SettingsAccountsConnectedAccountsSection'; import { SettingsAccountsConnectedAccountsSection } from '@/settings/accounts/components/SettingsAccountsConnectedAccountsSection';
import { SettingsAccountsSettingsSection } from '@/settings/accounts/components/SettingsAccountsSettingsSection'; import { SettingsAccountsSettingsSection } from '@/settings/accounts/components/SettingsAccountsSettingsSection';
import { SettingsPageContainer } from '@/settings/components/SettingsPageContainer'; import { SettingsPageContainer } from '@/settings/components/SettingsPageContainer';
import { IconSettings } from '@/ui/display/icon'; import { IconSettings } from '@/ui/display/icon';
import { SubMenuTopBarContainer } from '@/ui/layout/page/SubMenuTopBarContainer'; import { SubMenuTopBarContainer } from '@/ui/layout/page/SubMenuTopBarContainer';
import { Breadcrumb } from '@/ui/navigation/bread-crumb/components/Breadcrumb'; import { Breadcrumb } from '@/ui/navigation/bread-crumb/components/Breadcrumb';
import { SettingsAccountLoader } from '~/pages/settings/accounts/SettingsAccountLoader';
export const SettingsAccounts = () => { export const SettingsAccounts = () => {
const currentWorkspaceMember = useRecoilValue(currentWorkspaceMemberState);
const { records: accounts, loading } = useFindManyRecords<ConnectedAccount>({
objectNameSingular: 'connectedAccount',
filter: {
accountOwnerId: {
eq: currentWorkspaceMember?.id,
},
},
});
return ( return (
<SubMenuTopBarContainer Icon={IconSettings} title="Settings"> <SubMenuTopBarContainer Icon={IconSettings} title="Settings">
<SettingsPageContainer> <SettingsPageContainer
style={
loading
? { height: '100%', boxSizing: 'border-box', width: '100%' }
: {}
}
>
<Breadcrumb links={[{ children: 'Accounts' }]} /> <Breadcrumb links={[{ children: 'Accounts' }]} />
<SettingsAccountsConnectedAccountsSection />
<SettingsAccountsSettingsSection /> {loading ? (
<SettingsAccountLoader />
) : (
<>
<SettingsAccountsConnectedAccountsSection accounts={accounts} />
<SettingsAccountsSettingsSection />
</>
)}
</SettingsPageContainer> </SettingsPageContainer>
</SubMenuTopBarContainer> </SubMenuTopBarContainer>
); );