Skip to content

Commit 19c8f9e

Browse files
committed
feat: glossary empty view + close menu on click
1 parent 8427804 commit 19c8f9e

File tree

4 files changed

+118
-5
lines changed

4 files changed

+118
-5
lines changed

webapp/src/ee/glossary/components/AddFirstGlossaryMessage.tsx

+8-1
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,14 @@ export const AddFirstGlossaryMessage: React.VFC<
4545
<T keyName="glossaries_list_empty_title" />
4646
</Typography>
4747
<Typography mt={2}>
48-
<T keyName="glossaries_list_empty_message" />
48+
<T
49+
keyName="glossaries_list_empty_message"
50+
params={{
51+
bestPractice: (
52+
<a href="https://docs.tolgee.io/platform/projects_and_organizations/glossary" />
53+
),
54+
}}
55+
/>
4956
</Typography>
5057
</StyledText>
5158
<StyledImage draggable="false" height={props.height || '170px'}>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,99 @@
1+
import React, { ComponentProps } from 'react';
2+
import { Box, Button, Card, Link, styled, Typography } from '@mui/material';
3+
import { PlusCircle, UploadCloud02 } from '@untitled-ui/icons-react';
4+
import { EmptyState } from 'tg.component/common/EmptyState';
5+
import { T } from '@tolgee/react';
6+
7+
const StyledBox = styled(Box)`
8+
display: flex;
9+
gap: ${({ theme }) => theme.spacing(2)};
10+
align-items: center;
11+
justify-content: center;
12+
text-align: center;
13+
margin: ${({ theme }) => theme.spacing(2)};
14+
flex-wrap: wrap;
15+
`;
16+
17+
const StyledCard = styled(Card)`
18+
display: flex;
19+
flex-direction: column;
20+
align-items: center;
21+
justify-content: center;
22+
text-align: center;
23+
gap: ${({ theme }) => theme.spacing(2)};
24+
border-radius: 20px;
25+
width: 490px;
26+
padding: ${({ theme }) => theme.spacing(4)};
27+
`;
28+
29+
const StyledPlusCircle = styled(PlusCircle)`
30+
color: ${({ theme }) => theme.palette.primary.light};
31+
width: 32px;
32+
height: 32px;
33+
`;
34+
35+
const StyledUploadCloud02 = styled(UploadCloud02)`
36+
color: ${({ theme }) => theme.palette.primary.light};
37+
width: 32px;
38+
height: 32px;
39+
`;
40+
41+
const StyledDescription = styled(Typography)`
42+
color: ${({ theme }) => theme.palette.text.secondary};
43+
margin-bottom: ${({ theme }) => theme.spacing(5)};
44+
`;
45+
46+
type Props = {
47+
loading?: boolean;
48+
wrapperProps?: ComponentProps<typeof Box>;
49+
onCreate?: () => void;
50+
onImport?: () => void;
51+
};
52+
53+
export const GlossaryEmptyListMessage: React.VFC<Props> = ({
54+
loading,
55+
wrapperProps,
56+
onCreate,
57+
onImport,
58+
}) => {
59+
return (
60+
<EmptyState loading={loading} wrapperProps={wrapperProps}>
61+
<StyledBox>
62+
<StyledCard>
63+
<StyledPlusCircle />
64+
<Typography variant="h4">
65+
<T keyName="glossary_empty_placeholder_add_term_title" />
66+
</Typography>
67+
<StyledDescription variant="body1">
68+
<T keyName="glossary_empty_placeholder_add_term_description" />
69+
</StyledDescription>
70+
<Button onClick={onCreate} variant="contained" color="primary">
71+
<T keyName="glossary_empty_placeholder_add_term_button" />
72+
</Button>
73+
<Link href="https://docs.tolgee.io/platform/projects_and_organizations/glossary">
74+
<Typography variant="body2">
75+
<T keyName="glossary_empty_placeholder_add_term_best_practices" />
76+
</Typography>
77+
</Link>
78+
</StyledCard>
79+
<StyledCard>
80+
<StyledUploadCloud02 />
81+
<Typography variant="h4">
82+
<T keyName="glossary_empty_placeholder_import_terms_title" />
83+
</Typography>
84+
<StyledDescription variant="body1">
85+
<T keyName="glossary_empty_placeholder_import_terms_description" />
86+
</StyledDescription>
87+
<Button onClick={onImport} variant="contained" color="primary">
88+
<T keyName="glossary_empty_placeholder_import_terms_button" />
89+
</Button>
90+
<Link href="https://docs.tolgee.io/platform/projects_and_organizations/glossary/import/csv-format">
91+
<Typography variant="body2">
92+
<T keyName="glossary_empty_placeholder_import_terms_csv_format" />
93+
</Typography>
94+
</Link>
95+
</StyledCard>
96+
</StyledBox>
97+
</EmptyState>
98+
);
99+
};

webapp/src/ee/glossary/components/GlossaryListItemMenu.tsx

+5-3
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,7 @@ export const GlossaryListItemMenu: FC<Props> = ({ glossary, organization }) => {
3636
};
3737

3838
const onDelete = () => {
39+
setAnchorEl(null);
3940
confirmation({
4041
title: <T keyName="delete_glossary_confirmation_title" />,
4142
message: <T keyName="delete_glossary_confirmation_message" />,
@@ -51,8 +52,6 @@ export const GlossaryListItemMenu: FC<Props> = ({ glossary, organization }) => {
5152
});
5253
};
5354

54-
// TODO: close menu when clicking on item
55-
5655
return (
5756
<>
5857
<Tooltip title={t('glossaries_list_more_button')}>
@@ -97,7 +96,10 @@ export const GlossaryListItemMenu: FC<Props> = ({ glossary, organization }) => {
9796
{canManage && (
9897
<MenuItem
9998
data-cy="glossary-edit-button"
100-
onClick={() => setIsEditing(true)}
99+
onClick={() => {
100+
setAnchorEl(null);
101+
setIsEditing(true);
102+
}}
101103
>
102104
<T keyName="glossary_edit_button" />
103105
</MenuItem>

webapp/src/ee/glossary/views/GlossaryView.tsx

+6-1
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ import { useRouteMatch } from 'react-router-dom';
77
import React, { useMemo, useState } from 'react';
88
import { GlossaryTermCreateUpdateDialog } from 'tg.ee.module/glossary/views/GlossaryTermCreateUpdateDialog';
99
import { GlossaryViewBody } from 'tg.ee.module/glossary/components/GlossaryViewBody';
10+
import { GlossaryEmptyListMessage } from 'tg.ee.module/glossary/components/GlossaryEmptyListMessage';
1011

1112
export const GlossaryView = () => {
1213
const [search, setSearch] = useState('');
@@ -148,7 +149,11 @@ export const GlossaryView = () => {
148149
onSearch={setSearch}
149150
/>
150151
) : (
151-
<>Empty TODO</>
152+
<GlossaryEmptyListMessage
153+
loading={termsLoadable.isLoading}
154+
onCreate={onCreate}
155+
onImport={undefined /* TODO */}
156+
/>
152157
)}
153158
</BaseOrganizationSettingsView>
154159
);

0 commit comments

Comments
 (0)