Bug.tsx

  1import React from 'react';
  2
  3import Button from '@material-ui/core/Button';
  4import { makeStyles } from '@material-ui/core/styles';
  5import ArrowBackIcon from '@material-ui/icons/ArrowBack';
  6
  7import BugTitleForm from 'src/components/BugTitleForm/BugTitleForm';
  8import IfLoggedIn from 'src/components/IfLoggedIn/IfLoggedIn';
  9import Label from 'src/components/Label';
 10
 11import { BugFragment } from './Bug.generated';
 12import CommentForm from './CommentForm';
 13import TimelineQuery from './TimelineQuery';
 14
 15/**
 16 * Css in JS Styles
 17 */
 18const useStyles = makeStyles((theme) => ({
 19  main: {
 20    maxWidth: 1200,
 21    margin: 'auto',
 22    marginTop: theme.spacing(4),
 23  },
 24  header: {
 25    marginRight: theme.spacing(2),
 26    marginLeft: theme.spacing(3) + 205,
 27  },
 28  title: {
 29    ...theme.typography.h5,
 30  },
 31  id: {
 32    ...theme.typography.subtitle1,
 33    marginLeft: theme.spacing(1),
 34  },
 35  container: {
 36    display: 'flex',
 37    marginBottom: theme.spacing(1),
 38    marginRight: theme.spacing(2),
 39    marginLeft: theme.spacing(2),
 40  },
 41  timeline: {
 42    flex: 1,
 43    marginTop: theme.spacing(2),
 44    marginRight: theme.spacing(2),
 45    minWidth: 400,
 46  },
 47  leftSidebar: {
 48    marginTop: theme.spacing(2),
 49    marginRight: theme.spacing(2),
 50  },
 51  rightSidebar: {
 52    marginTop: theme.spacing(2),
 53    flex: '0 0 200px',
 54  },
 55  rightSidebarTitle: {
 56    fontWeight: 'bold',
 57  },
 58  labelList: {
 59    listStyle: 'none',
 60    padding: 0,
 61    margin: 0,
 62  },
 63  label: {
 64    marginTop: theme.spacing(1),
 65    marginBottom: theme.spacing(1),
 66    '& > *': {
 67      display: 'block',
 68    },
 69  },
 70  noLabel: {
 71    ...theme.typography.body2,
 72  },
 73  commentForm: {
 74    marginLeft: 48,
 75  },
 76  backButton: {
 77    position: 'sticky',
 78    top: '80px',
 79    backgroundColor: theme.palette.primary.dark,
 80    color: theme.palette.primary.contrastText,
 81    '&:hover': {
 82      backgroundColor: theme.palette.primary.main,
 83      color: theme.palette.primary.contrastText,
 84    },
 85  },
 86}));
 87
 88type Props = {
 89  bug: BugFragment;
 90};
 91
 92function Bug({ bug }: Props) {
 93  const classes = useStyles();
 94
 95  return (
 96    <main className={classes.main}>
 97      <div className={classes.header}>
 98        <BugTitleForm bug={bug} />
 99      </div>
100      <div className={classes.container}>
101        <div className={classes.leftSidebar}>
102          <Button
103            variant="contained"
104            className={classes.backButton}
105            aria-label="back to issue list"
106            href="/"
107          >
108            <ArrowBackIcon />
109            Back to List
110          </Button>
111        </div>
112        <div className={classes.timeline}>
113          <TimelineQuery id={bug.id} />
114          <IfLoggedIn>
115            {() => (
116              <div className={classes.commentForm}>
117                <CommentForm bug={bug} />
118              </div>
119            )}
120          </IfLoggedIn>
121        </div>
122        <div className={classes.rightSidebar}>
123          <span className={classes.rightSidebarTitle}>Labels</span>
124          <ul className={classes.labelList}>
125            {bug.labels.length === 0 && (
126              <span className={classes.noLabel}>None yet</span>
127            )}
128            {bug.labels.map((l) => (
129              <li className={classes.label} key={l.name}>
130                <Label label={l} key={l.name} />
131              </li>
132            ))}
133          </ul>
134        </div>
135      </div>
136    </main>
137  );
138}
139
140export default Bug;