1import React, { useState } from 'react';
2
3import IconButton from '@material-ui/core/IconButton';
4import Paper from '@material-ui/core/Paper';
5import Tooltip from '@material-ui/core/Tooltip/Tooltip';
6import { makeStyles } from '@material-ui/core/styles';
7import EditIcon from '@material-ui/icons/Edit';
8
9import Author, { Avatar } from 'src/components/Author';
10import Content from 'src/components/Content';
11import Date from 'src/components/Date';
12import IfLoggedIn from 'src/components/IfLoggedIn/IfLoggedIn';
13
14import { BugFragment } from './Bug.generated';
15import EditCommentForm from './EditCommentForm';
16import { AddCommentFragment } from './MessageCommentFragment.generated';
17import { CreateFragment } from './MessageCreateFragment.generated';
18
19const useStyles = makeStyles((theme) => ({
20 author: {
21 fontWeight: 'bold',
22 },
23 container: {
24 display: 'flex',
25 },
26 avatar: {
27 marginTop: 2,
28 },
29 bubble: {
30 flex: 1,
31 marginLeft: theme.spacing(1),
32 minWidth: 0,
33 },
34 header: {
35 ...theme.typography.body1,
36 padding: '0.5rem 1rem',
37 borderBottom: `1px solid ${theme.palette.divider}`,
38 display: 'flex',
39 borderTopRightRadius: theme.shape.borderRadius,
40 borderTopLeftRadius: theme.shape.borderRadius,
41 backgroundColor: theme.palette.info.main,
42 color: theme.palette.info.contrastText,
43 },
44 title: {
45 flex: 1,
46 },
47 tag: {
48 ...theme.typography.button,
49 color: '#888',
50 border: '#ddd solid 1px',
51 padding: '0 0.5rem',
52 fontSize: '0.75rem',
53 borderRadius: 2,
54 marginLeft: '0.5rem',
55 },
56 body: {
57 ...theme.typography.body2,
58 padding: '0.5rem',
59 },
60 editButton: {
61 color: theme.palette.info.contrastText,
62 padding: '0rem',
63 marginLeft: theme.spacing(1),
64 fontSize: '0.75rem',
65 '&:hover': {
66 backgroundColor: 'inherit',
67 },
68 },
69}));
70
71type Props = {
72 bug: BugFragment;
73 op: AddCommentFragment | CreateFragment;
74};
75
76function Message({ bug, op }: Props) {
77 const classes = useStyles();
78 const [editMode, switchToEditMode] = useState(false);
79 const [comment, setComment] = useState(op);
80
81 const editComment = (id: String) => {
82 switchToEditMode(true);
83 };
84
85 function readMessageView() {
86 return (
87 <Paper elevation={1} className={classes.bubble}>
88 <header className={classes.header}>
89 <div className={classes.title}>
90 <Author className={classes.author} author={comment.author} />
91 <span> commented </span>
92 <Date date={comment.createdAt} />
93 </div>
94 {comment.edited && <div className={classes.tag}>Edited</div>}
95 <IfLoggedIn>
96 {() => (
97 <Tooltip title="Edit Message" placement="top" arrow={true}>
98 <IconButton
99 disableRipple
100 className={classes.editButton}
101 aria-label="edit message"
102 onClick={() => editComment(comment.id)}
103 >
104 <EditIcon />
105 </IconButton>
106 </Tooltip>
107 )}
108 </IfLoggedIn>
109 </header>
110 <section className={classes.body}>
111 <Content markdown={comment.message} />
112 </section>
113 </Paper>
114 );
115 }
116
117 function editMessageView() {
118 const cancelEdition = () => {
119 switchToEditMode(false);
120 };
121
122 const onPostSubmit = (comment: AddCommentFragment | CreateFragment) => {
123 setComment(comment);
124 switchToEditMode(false);
125 };
126
127 return (
128 <div className={classes.bubble}>
129 <EditCommentForm
130 bug={bug}
131 onCancelClick={cancelEdition}
132 // Close edit view after submitted changes
133 onPostSubmit={onPostSubmit}
134 comment={comment}
135 />
136 </div>
137 );
138 }
139
140 return (
141 <article className={classes.container}>
142 <Avatar author={comment.author} className={classes.avatar} />
143 {editMode ? editMessageView() : readMessageView()}
144 </article>
145 );
146}
147
148export default Message;