fix: Invite by email table overflows in mobile viewport (#7273)

##Description

- This PR solves the issue #7253
- Made the invite table mobile friendly for all media width

## Before


https://github.com/user-attachments/assets/458bd47d-38fb-4ddc-a996-c1bb3908d014

<img width="439" alt="Screenshot 2024-09-27 at 1 30 52 AM"
src="https://github.com/user-attachments/assets/2a0ba6a2-c0f6-42bb-b74d-3a3147f2e7e7">

## After

<img width="440" alt="Screenshot 2024-09-27 at 1 34 11 AM"
src="https://github.com/user-attachments/assets/d31fdeba-574a-4cd0-a61a-bb5fba656109">


https://github.com/user-attachments/assets/7a4f6f9a-7fef-42f1-a226-59a1d73767f4


> [!Note]
> I've added 2 implementations and if either doesn't follow design rules
then it can be changed-
> - Made the trash icon `accent danger`
> - When emails are long, given scroll for ease of convience.

---------

Co-authored-by: Nitin Koche <nitinkoche03@gmail.com>
This commit is contained in:
Harshit Singh
2024-10-08 20:18:15 +05:30
committed by GitHub
parent 10e75174f5
commit 098551b7b8

View File

@ -7,8 +7,8 @@ import {
IconUsers, IconUsers,
IconReload, IconReload,
IconMail, IconMail,
StyledText,
Avatar, Avatar,
MOBILE_VIEWPORT,
} from 'twenty-ui'; } from 'twenty-ui';
import { isNonEmptyArray } from '@sniptt/guards'; import { isNonEmptyArray } from '@sniptt/guards';
import { useTheme } from '@emotion/react'; import { useTheme } from '@emotion/react';
@ -53,6 +53,47 @@ const StyledTable = styled(Table)`
margin-top: ${({ theme }) => theme.spacing(0.5)}; margin-top: ${({ theme }) => theme.spacing(0.5)};
`; `;
const StyledTableRow = styled(TableRow)`
@media (max-width: ${MOBILE_VIEWPORT}px) {
display: grid;
grid-template-columns: 3fr;
}
`;
const StyledTableCell = styled(TableCell)`
padding: ${({ theme }) => theme.spacing(1)};
@media (max-width: ${MOBILE_VIEWPORT}px) {
&:first-child {
max-width: 100%;
padding-top: 2px;
white-space: nowrap;
overflow: scroll;
scroll-behavior: smooth;
}
}
`;
const StyledIconWrapper = styled.div`
left: 2px;
margin-right: ${({ theme }) => theme.spacing(2)};
position: relative;
top: 1px;
`;
const StyledScrollableTextContainer = styled.div`
max-width: 100%;
overflow-x: auto;
white-space: pre-line;
`;
const StyledTextContainer = styled.div`
color: ${({ theme }) => theme.font.color.secondary};
max-width: max-content;
overflow-x: auto;
position: absolute;
@media (min-width: 360px) and (max-width: 420px) {
max-width: 150px;
margin-top: ${({ theme }) => theme.spacing(1)};
}
`;
const StyledTableHeaderRow = styled(Table)` const StyledTableHeaderRow = styled(Table)`
margin-bottom: ${({ theme }) => theme.spacing(1.5)}; margin-bottom: ${({ theme }) => theme.spacing(1.5)};
`; `;
@ -165,28 +206,25 @@ export const SettingsWorkspaceMembers = () => {
<StyledTable key={workspaceMember.id}> <StyledTable key={workspaceMember.id}>
<TableRow> <TableRow>
<TableCell> <TableCell>
<StyledText <StyledIconWrapper>
PrefixComponent={ <Avatar
<Avatar avatarUrl={workspaceMember.avatarUrl}
avatarUrl={workspaceMember.avatarUrl} placeholderColorSeed={workspaceMember.id}
placeholderColorSeed={workspaceMember.id} placeholder={workspaceMember.name.firstName ?? ''}
placeholder={workspaceMember.name.firstName ?? ''} type="rounded"
type="rounded" size="sm"
size="sm" />
/> </StyledIconWrapper>
} <StyledScrollableTextContainer>
text={ {workspaceMember.name.firstName +
workspaceMember.name.firstName +
' ' + ' ' +
workspaceMember.name.lastName workspaceMember.name.lastName}
} </StyledScrollableTextContainer>
/>
</TableCell> </TableCell>
<TableCell> <TableCell>
<StyledText <StyledTextContainer>
text={workspaceMember.userEmail} {workspaceMember.userEmail}
color={theme.font.color.secondary} </StyledTextContainer>
/>
</TableCell> </TableCell>
<TableCell align={'right'}> <TableCell align={'right'}>
{currentWorkspaceMember?.id !== workspaceMember.id && ( {currentWorkspaceMember?.id !== workspaceMember.id && (
@ -225,25 +263,27 @@ export const SettingsWorkspaceMembers = () => {
</StyledTableHeaderRow> </StyledTableHeaderRow>
{workspaceInvitations?.map((workspaceInvitation) => ( {workspaceInvitations?.map((workspaceInvitation) => (
<StyledTable key={workspaceInvitation.id}> <StyledTable key={workspaceInvitation.id}>
<TableRow gridAutoColumns={`1fr 1fr ${theme.spacing(22)}`}> <StyledTableRow
<TableCell> gridAutoColumns={`1fr 1fr ${theme.spacing(22)}`}
<StyledText >
PrefixComponent={ <StyledTableCell>
<IconMail <StyledIconWrapper>
size={theme.icon.size.md} <IconMail
stroke={theme.icon.stroke.sm} size={theme.icon.size.md}
/> stroke={theme.icon.stroke.sm}
} />
text={workspaceInvitation.email} </StyledIconWrapper>
/> <StyledScrollableTextContainer>
</TableCell> {workspaceInvitation.email}
<TableCell align={'right'}> </StyledScrollableTextContainer>
</StyledTableCell>
<StyledTableCell align={'right'}>
<Status <Status
color={'gray'} color={'gray'}
text={getExpiresAtText(workspaceInvitation.expiresAt)} text={getExpiresAtText(workspaceInvitation.expiresAt)}
/> />
</TableCell> </StyledTableCell>
<TableCell align={'right'}> <StyledTableCell align={'right'}>
<StyledButtonContainer> <StyledButtonContainer>
<IconButton <IconButton
onClick={() => { onClick={() => {
@ -266,8 +306,8 @@ export const SettingsWorkspaceMembers = () => {
Icon={IconTrash} Icon={IconTrash}
/> />
</StyledButtonContainer> </StyledButtonContainer>
</TableCell> </StyledTableCell>
</TableRow> </StyledTableRow>
</StyledTable> </StyledTable>
))} ))}
</Table> </Table>