mirror of
https://github.com/coder/coder.git
synced 2025-07-15 22:20:27 +00:00
feat: Make workspaces, timeline, templates rows obviously clickable (#2047)
* add right arrow to build table rows * Add clickable rows to template and workspace list * Specify 1% width for chevron right
This commit is contained in:
@ -1,10 +1,11 @@
|
||||
import Box from "@material-ui/core/Box"
|
||||
import { makeStyles, Theme } from "@material-ui/core/styles"
|
||||
import { fade, makeStyles, Theme } from "@material-ui/core/styles"
|
||||
import Table from "@material-ui/core/Table"
|
||||
import TableBody from "@material-ui/core/TableBody"
|
||||
import TableCell from "@material-ui/core/TableCell"
|
||||
import TableHead from "@material-ui/core/TableHead"
|
||||
import TableRow from "@material-ui/core/TableRow"
|
||||
import KeyboardArrowRight from "@material-ui/icons/KeyboardArrowRight"
|
||||
import useTheme from "@material-ui/styles/useTheme"
|
||||
import { FC } from "react"
|
||||
import { useNavigate } from "react-router-dom"
|
||||
@ -41,6 +42,7 @@ export const BuildsTable: FC<BuildsTableProps> = ({ builds, className }) => {
|
||||
<TableCell width="20%">{Language.durationLabel}</TableCell>
|
||||
<TableCell width="40%">{Language.startedAtLabel}</TableCell>
|
||||
<TableCell width="20%">{Language.statusLabel}</TableCell>
|
||||
<TableCell></TableCell>
|
||||
</TableRow>
|
||||
</TableHead>
|
||||
<TableBody>
|
||||
@ -79,6 +81,11 @@ export const BuildsTable: FC<BuildsTableProps> = ({ builds, className }) => {
|
||||
<TableCell>
|
||||
<span style={{ color: status.color }}>{status.status}</span>
|
||||
</TableCell>
|
||||
<TableCell>
|
||||
<div className={styles.arrowCell}>
|
||||
<KeyboardArrowRight className={styles.arrowRight} />
|
||||
</div>
|
||||
</TableCell>
|
||||
</TableRow>
|
||||
)
|
||||
})}
|
||||
@ -102,11 +109,23 @@ const useStyles = makeStyles((theme) => ({
|
||||
cursor: "pointer",
|
||||
|
||||
"&:hover td": {
|
||||
backgroundColor: theme.palette.background.default,
|
||||
backgroundColor: fade(theme.palette.primary.light, 0.1),
|
||||
},
|
||||
|
||||
"&:focus": {
|
||||
outline: `1px solid ${theme.palette.secondary.dark}`,
|
||||
},
|
||||
|
||||
"& .MuiTableCell-root:last-child": {
|
||||
paddingRight: theme.spacing(2),
|
||||
},
|
||||
},
|
||||
arrowRight: {
|
||||
color: fade(theme.palette.primary.contrastText, 0.7),
|
||||
width: 20,
|
||||
height: 20,
|
||||
},
|
||||
arrowCell: {
|
||||
display: "flex",
|
||||
},
|
||||
}))
|
||||
|
@ -1,13 +1,15 @@
|
||||
import Link from "@material-ui/core/Link"
|
||||
import { makeStyles } from "@material-ui/core/styles"
|
||||
import { fade, makeStyles } from "@material-ui/core/styles"
|
||||
import Table from "@material-ui/core/Table"
|
||||
import TableBody from "@material-ui/core/TableBody"
|
||||
import TableCell from "@material-ui/core/TableCell"
|
||||
import TableHead from "@material-ui/core/TableHead"
|
||||
import TableRow from "@material-ui/core/TableRow"
|
||||
import KeyboardArrowRight from "@material-ui/icons/KeyboardArrowRight"
|
||||
import dayjs from "dayjs"
|
||||
import relativeTime from "dayjs/plugin/relativeTime"
|
||||
import { FC } from "react"
|
||||
import { useNavigate } from "react-router-dom"
|
||||
import * as TypesGen from "../../api/typesGenerated"
|
||||
import { AvatarData } from "../../components/AvatarData/AvatarData"
|
||||
import { CodeExample } from "../../components/CodeExample/CodeExample"
|
||||
@ -71,6 +73,8 @@ export interface TemplatesPageViewProps {
|
||||
|
||||
export const TemplatesPageView: FC<TemplatesPageViewProps> = (props) => {
|
||||
const styles = useStyles()
|
||||
const navigate = useNavigate()
|
||||
|
||||
return (
|
||||
<Margins>
|
||||
<PageHeader>
|
||||
@ -88,6 +92,7 @@ export const TemplatesPageView: FC<TemplatesPageViewProps> = (props) => {
|
||||
<TableCell>{Language.nameLabel}</TableCell>
|
||||
<TableCell>{Language.usedByLabel}</TableCell>
|
||||
<TableCell>{Language.lastUpdatedLabel}</TableCell>
|
||||
<TableCell width="1%"></TableCell>
|
||||
</TableRow>
|
||||
</TableHead>
|
||||
<TableBody>
|
||||
@ -104,21 +109,39 @@ export const TemplatesPageView: FC<TemplatesPageViewProps> = (props) => {
|
||||
</TableCell>
|
||||
</TableRow>
|
||||
)}
|
||||
{props.templates?.map((template) => (
|
||||
<TableRow key={template.id}>
|
||||
<TableCell>
|
||||
<AvatarData
|
||||
title={template.name}
|
||||
subtitle={template.description}
|
||||
link={`/templates/${template.name}`}
|
||||
/>
|
||||
</TableCell>
|
||||
{props.templates?.map((template) => {
|
||||
const navigateToTemplatePage = () => {
|
||||
navigate(`/templates/${template.name}`)
|
||||
}
|
||||
return (
|
||||
<TableRow
|
||||
key={template.id}
|
||||
hover
|
||||
data-testid={`template-${template.id}`}
|
||||
tabIndex={0}
|
||||
onClick={navigateToTemplatePage}
|
||||
onKeyDown={(event) => {
|
||||
if (event.key === "Enter") {
|
||||
navigateToTemplatePage()
|
||||
}
|
||||
}}
|
||||
className={styles.clickableTableRow}
|
||||
>
|
||||
<TableCell>
|
||||
<AvatarData title={template.name} subtitle={template.description} />
|
||||
</TableCell>
|
||||
|
||||
<TableCell>{Language.developerCount(template.workspace_owner_count)}</TableCell>
|
||||
<TableCell>{Language.developerCount(template.workspace_owner_count)}</TableCell>
|
||||
|
||||
<TableCell data-chromatic="ignore">{dayjs().to(dayjs(template.updated_at))}</TableCell>
|
||||
</TableRow>
|
||||
))}
|
||||
<TableCell data-chromatic="ignore">{dayjs().to(dayjs(template.updated_at))}</TableCell>
|
||||
<TableCell>
|
||||
<div className={styles.arrowCell}>
|
||||
<KeyboardArrowRight className={styles.arrowRight} />
|
||||
</div>
|
||||
</TableCell>
|
||||
</TableRow>
|
||||
)
|
||||
})}
|
||||
</TableBody>
|
||||
</Table>
|
||||
</Margins>
|
||||
@ -129,4 +152,27 @@ const useStyles = makeStyles((theme) => ({
|
||||
emptyDescription: {
|
||||
maxWidth: theme.spacing(62),
|
||||
},
|
||||
clickableTableRow: {
|
||||
cursor: "pointer",
|
||||
|
||||
"&:hover td": {
|
||||
backgroundColor: fade(theme.palette.primary.light, 0.1),
|
||||
},
|
||||
|
||||
"&:focus": {
|
||||
outline: `1px solid ${theme.palette.secondary.dark}`,
|
||||
},
|
||||
|
||||
"& .MuiTableCell-root:last-child": {
|
||||
paddingRight: theme.spacing(2),
|
||||
},
|
||||
},
|
||||
arrowRight: {
|
||||
color: fade(theme.palette.primary.contrastText, 0.7),
|
||||
width: 20,
|
||||
height: 20,
|
||||
},
|
||||
arrowCell: {
|
||||
display: "flex",
|
||||
},
|
||||
}))
|
||||
|
@ -4,7 +4,7 @@ import InputAdornment from "@material-ui/core/InputAdornment"
|
||||
import Link from "@material-ui/core/Link"
|
||||
import Menu from "@material-ui/core/Menu"
|
||||
import MenuItem from "@material-ui/core/MenuItem"
|
||||
import { makeStyles, Theme } from "@material-ui/core/styles"
|
||||
import { fade, makeStyles, Theme } from "@material-ui/core/styles"
|
||||
import Table from "@material-ui/core/Table"
|
||||
import TableBody from "@material-ui/core/TableBody"
|
||||
import TableCell from "@material-ui/core/TableCell"
|
||||
@ -12,13 +12,14 @@ import TableHead from "@material-ui/core/TableHead"
|
||||
import TableRow from "@material-ui/core/TableRow"
|
||||
import TextField from "@material-ui/core/TextField"
|
||||
import AddCircleOutline from "@material-ui/icons/AddCircleOutline"
|
||||
import KeyboardArrowRight from "@material-ui/icons/KeyboardArrowRight"
|
||||
import SearchIcon from "@material-ui/icons/Search"
|
||||
import useTheme from "@material-ui/styles/useTheme"
|
||||
import dayjs from "dayjs"
|
||||
import relativeTime from "dayjs/plugin/relativeTime"
|
||||
import { FormikErrors, useFormik } from "formik"
|
||||
import { FC, useState } from "react"
|
||||
import { Link as RouterLink } from "react-router-dom"
|
||||
import { Link as RouterLink, useNavigate } from "react-router-dom"
|
||||
import * as TypesGen from "../../api/typesGenerated"
|
||||
import { AvatarData } from "../../components/AvatarData/AvatarData"
|
||||
import { CloseDropdown, OpenDropdown } from "../../components/DropdownArrows/DropdownArrows"
|
||||
@ -90,6 +91,7 @@ export interface WorkspacesPageViewProps {
|
||||
|
||||
export const WorkspacesPageView: FC<WorkspacesPageViewProps> = ({ loading, workspaces, filter, onFilter }) => {
|
||||
const styles = useStyles()
|
||||
const navigate = useNavigate()
|
||||
const theme: Theme = useTheme()
|
||||
|
||||
const form = useFormik<FilterFormValues>({
|
||||
@ -196,6 +198,7 @@ export const WorkspacesPageView: FC<WorkspacesPageViewProps> = ({ loading, works
|
||||
<TableCell>Version</TableCell>
|
||||
<TableCell>Last Built</TableCell>
|
||||
<TableCell>Status</TableCell>
|
||||
<TableCell width="1%"></TableCell>
|
||||
</TableRow>
|
||||
</TableHead>
|
||||
<TableBody>
|
||||
@ -228,14 +231,25 @@ export const WorkspacesPageView: FC<WorkspacesPageViewProps> = ({ loading, works
|
||||
{workspaces &&
|
||||
workspaces.map((workspace) => {
|
||||
const status = getDisplayStatus(theme, workspace.latest_build)
|
||||
const navigateToWorkspacePage = () => {
|
||||
navigate(`/@${workspace.owner_name}/${workspace.name}`)
|
||||
}
|
||||
return (
|
||||
<TableRow key={workspace.id}>
|
||||
<TableRow
|
||||
key={workspace.id}
|
||||
hover
|
||||
data-testid={`workspace-${workspace.id}`}
|
||||
tabIndex={0}
|
||||
onClick={navigateToWorkspacePage}
|
||||
onKeyDown={(event) => {
|
||||
if (event.key === "Enter") {
|
||||
navigateToWorkspacePage()
|
||||
}
|
||||
}}
|
||||
className={styles.clickableTableRow}
|
||||
>
|
||||
<TableCell>
|
||||
<AvatarData
|
||||
title={workspace.name}
|
||||
subtitle={workspace.owner_name}
|
||||
link={`/@${workspace.owner_name}/${workspace.name}`}
|
||||
/>
|
||||
<AvatarData title={workspace.name} subtitle={workspace.owner_name} />
|
||||
</TableCell>
|
||||
<TableCell>{workspace.template_name}</TableCell>
|
||||
<TableCell>
|
||||
@ -253,6 +267,11 @@ export const WorkspacesPageView: FC<WorkspacesPageViewProps> = ({ loading, works
|
||||
<TableCell>
|
||||
<span style={{ color: status.color }}>{status.status}</span>
|
||||
</TableCell>
|
||||
<TableCell>
|
||||
<div className={styles.arrowCell}>
|
||||
<KeyboardArrowRight className={styles.arrowRight} />
|
||||
</div>
|
||||
</TableCell>
|
||||
</TableRow>
|
||||
)
|
||||
})}
|
||||
@ -297,4 +316,27 @@ const useStyles = makeStyles((theme) => ({
|
||||
border: "none",
|
||||
},
|
||||
},
|
||||
clickableTableRow: {
|
||||
cursor: "pointer",
|
||||
|
||||
"&:hover td": {
|
||||
backgroundColor: fade(theme.palette.primary.light, 0.1),
|
||||
},
|
||||
|
||||
"&:focus": {
|
||||
outline: `1px solid ${theme.palette.secondary.dark}`,
|
||||
},
|
||||
|
||||
"& .MuiTableCell-root:last-child": {
|
||||
paddingRight: theme.spacing(2),
|
||||
},
|
||||
},
|
||||
arrowRight: {
|
||||
color: fade(theme.palette.primary.contrastText, 0.7),
|
||||
width: 20,
|
||||
height: 20,
|
||||
},
|
||||
arrowCell: {
|
||||
display: "flex",
|
||||
},
|
||||
}))
|
||||
|
Reference in New Issue
Block a user