Merge branch '16719-collection-version-basic-ui'
[arvados-workbench2.git] / src / components / file-tree / file-tree-item.tsx
1 // Copyright (C) The Arvados Authors. All rights reserved.
2 //
3 // SPDX-License-Identifier: AGPL-3.0
4
5 import * as React from "react";
6 import { TreeItem } from "../tree/tree";
7 import { DirectoryIcon, MoreOptionsIcon, DefaultIcon, FileIcon } from "../icon/icon";
8 import { Typography, IconButton, StyleRulesCallback, withStyles, WithStyles, Tooltip } from '@material-ui/core';
9 import { formatFileSize } from "~/common/formatters";
10 import { ListItemTextIcon } from "../list-item-text-icon/list-item-text-icon";
11 import { FileTreeData } from "./file-tree-data";
12
13 type CssRules = "root" | "spacer" | "sizeInfo" | "button" | "moreOptions";
14
15 const fileTreeItemStyle: StyleRulesCallback<CssRules> = theme => ({
16     root: {
17         display: "flex",
18         alignItems: "center",
19         paddingRight: `${theme.spacing.unit * 1.5}px`
20     },
21     spacer: {
22         flex: "1"
23     },
24     sizeInfo: {
25         width: `${theme.spacing.unit * 8}px`
26     },
27     button: {
28         width: theme.spacing.unit * 3,
29         height: theme.spacing.unit * 3,
30         marginRight: theme.spacing.unit,
31     },
32     moreOptions: {
33         position: 'absolute'
34     }
35 });
36
37 export interface FileTreeItemProps {
38     item: TreeItem<FileTreeData>;
39     onMoreClick: (event: React.MouseEvent<any>, item: TreeItem<FileTreeData>) => void;
40 }
41 export const FileTreeItem = withStyles(fileTreeItemStyle)(
42     class extends React.Component<FileTreeItemProps & WithStyles<CssRules>> {
43         render() {
44             const { classes, item } = this.props;
45             return <>
46                 <div className={classes.root}>
47                     <ListItemTextIcon
48                         icon={getIcon(item.data.type)}
49                         name={item.data.name} />
50                     <div className={classes.spacer} />
51                     <Typography
52                         className={classes.sizeInfo}
53                         variant="caption">{formatFileSize(item.data.size)}</Typography>
54                     <Tooltip title="More options" disableFocusListener>
55                         <IconButton
56                             data-cy='file-item-options-btn'
57                             className={classes.button}
58                             onClick={this.handleClick}>
59                             <MoreOptionsIcon className={classes.moreOptions} />
60                         </IconButton>
61                     </Tooltip>
62                 </div >
63             </>;
64         }
65
66         handleClick = (event: React.MouseEvent<any>) => {
67             this.props.onMoreClick(event, this.props.item);
68         }
69     });
70
71 export const getIcon = (type: string) => {
72     switch (type) {
73         case 'directory':
74             return DirectoryIcon;
75         case 'file':
76             return FileIcon;
77         default:
78             return DefaultIcon;
79     }
80 };
81