1
+ import { useState } from "react" ;
1
2
import { useTheme } from "@emotion/react" ;
2
3
import { type Group } from "api/typesGenerated" ;
3
4
4
5
import { Stack } from "components/Stack/Stack" ;
6
+ import { Avatar } from "components/Avatar/Avatar" ;
5
7
import TableCell from "@mui/material/TableCell" ;
6
8
import Button from "@mui/material/Button" ;
7
- import { useState } from "react" ;
9
+ import List from "@mui/material/List" ;
10
+ import ListItem from "@mui/material/ListItem" ;
11
+ import ListItemText from "@mui/material/ListItemText" ;
12
+ import ListItemAvatar from "@mui/material/ListItemAvatar" ;
13
+ import Popover from "@mui/material/Popover" ;
8
14
9
15
type GroupsCellProps = {
10
16
userGroups : readonly Group [ ] | undefined ;
@@ -14,44 +20,85 @@ export function GroupsCell({ userGroups }: GroupsCellProps) {
14
20
const [ isHovering , setIsHovering ] = useState ( false ) ;
15
21
const theme = useTheme ( ) ;
16
22
23
+ // 2023-10-18 - Temporary code - waiting for Bruno to finish the refactoring
24
+ // of PopoverContainer. Popover code should all be torn out and replaced with
25
+ // PopoverContainer once the new API is ready
26
+ const [ anchorEl , setAnchorEl ] = useState < HTMLButtonElement | null > ( null ) ;
27
+ const hideCtaUnderline = isHovering || anchorEl !== null ;
28
+
17
29
return (
18
30
< TableCell >
19
31
{ userGroups === undefined ? (
20
- < em > N/A</ em >
32
+ // Felt right to add emphasis to the undefined state for semantics
33
+ // ("hey, this isn't normal"), but the default italics looked weird in
34
+ // the table UI
35
+ < em css = { { fontStyle : "normal" } } > N/A</ em >
21
36
) : (
22
- < Button
23
- onPointerEnter = { ( ) => setIsHovering ( true ) }
24
- onPointerLeave = { ( ) => setIsHovering ( false ) }
25
- css = { {
26
- width : "100%" ,
27
- border : "none" ,
28
- fontWeight : 400 ,
29
- justifyContent : "flex-start" ,
30
- padding : 0 ,
31
- lineHeight : theme . typography . body2 . lineHeight ,
32
- "&:hover" : {
37
+ < >
38
+ < Button
39
+ onPointerEnter = { ( ) => setIsHovering ( true ) }
40
+ onPointerLeave = { ( ) => setIsHovering ( false ) }
41
+ onClick = { ( event ) => setAnchorEl ( event . currentTarget ) }
42
+ css = { {
43
+ width : "100%" ,
44
+ justifyContent : "flex-start" ,
45
+ fontSize : theme . typography . body1 . fontSize ,
46
+ lineHeight : theme . typography . body2 . lineHeight ,
47
+ fontWeight : 400 ,
33
48
border : "none" ,
34
- backgroundColor : "transparent" ,
35
- } ,
36
- } }
37
- >
38
- < Stack spacing = { 0 } >
39
- < span css = { { fontSize : "1rem" } } >
40
- { userGroups . length } Group{ userGroups . length !== 1 && "s" }
41
- </ span >
42
-
43
- < span
49
+ padding : 0 ,
50
+ "&:hover" : {
51
+ border : "none" ,
52
+ backgroundColor : "transparent" ,
53
+ } ,
54
+ } }
55
+ >
56
+ < Stack spacing = { 0 } >
57
+ < span >
58
+ { userGroups . length } Group{ userGroups . length !== 1 && "s" }
59
+ </ span >
60
+
61
+ < span
62
+ css = { {
63
+ fontSize : "0.75rem" ,
64
+ color : theme . palette . text . secondary ,
65
+ textDecoration : hideCtaUnderline ? "none" : "underline" ,
66
+ textUnderlineOffset : "0.2em" ,
67
+ } }
68
+ >
69
+ See details
70
+ </ span >
71
+ </ Stack >
72
+ </ Button >
73
+
74
+ < Popover
75
+ anchorEl = { anchorEl }
76
+ open = { anchorEl !== null }
77
+ onClose = { ( ) => setAnchorEl ( null ) }
78
+ anchorOrigin = { { vertical : "bottom" , horizontal : "left" } }
79
+ transformOrigin = { { vertical : 16 , horizontal : 0 } }
80
+ >
81
+ < List
82
+ component = "ul"
44
83
css = { {
45
- fontSize : "0.75rem" ,
46
- color : theme . palette . text . secondary ,
47
- textDecoration : isHovering ? "none" : "underline" ,
48
- textUnderlineOffset : "0.2em" ,
84
+ padding : theme . spacing ( 2 ) ,
49
85
} }
50
86
>
51
- See details
52
- </ span >
53
- </ Stack >
54
- </ Button >
87
+ { userGroups . map ( ( group ) => {
88
+ const groupText = group . display_name || group . name ;
89
+ return (
90
+ < ListItem key = { group . id } >
91
+ < ListItemAvatar >
92
+ < Avatar src = { group . avatar_url } alt = { groupText } />
93
+ </ ListItemAvatar >
94
+
95
+ < ListItemText > { groupText } </ ListItemText >
96
+ </ ListItem >
97
+ ) ;
98
+ } ) }
99
+ </ List >
100
+ </ Popover >
101
+ </ >
55
102
) }
56
103
</ TableCell >
57
104
) ;
0 commit comments