1
0
mirror of https://github.com/haiwen/seahub.git synced 2025-09-25 14:50:29 +00:00

Icon bg more (#7902)

* [op icon] changed the default color for all the operation icons; added background for the operation icons in 'views/people' items when hover on them

* ['system admin'] library view: added background for the items & the operation icons when hover on them

* [system admin] user/org/institution: added background for the 'edit' icons in the 'info' page when hover on them

* [system admin] user - Shared Libraries: added background for the items when hover on them

* [system admin] group - libraries: added background for the items & the operation icons when hover on them

* [system admin] group - members: added background for the operation icons when hover on them

* [system admin] org - groups: added background for the items & the operation icons when hover on them

* [system admin] org - libraries: added background for the items & the operation icons when hover on them

* [org admin] Devices - Desktop/Mobile: added background for the items & the operation icons when hover on them

* [org admin] Libraries - All/Trash: added background for the items & the operation icons when hover on them

* [org admin] Users - All/Admin: fixup for the operation icons when hover on them

* [org admin] Users - user - profile: added background for the operation icons when hover on them

* [org admin] Users - user - owned libraries: added background for the items & the operation icons when hover on them

* [org admin] Groups: fixup for the operation icons when hover on them

* [org admin] Groups - Group - Libraries: added background for the items & the operation icons when hover on them

* [org admin] Search Groups: fixup for the operation icons when hover on them

* [org admin] Departments - Department - Members: fixup for the operation icons when hover on them

* [org admin] Links - All Public Links: fixup for the operation icons when hover on them

* [org admin] Logs - File Access: added background for the operation icons when hover on them

* [org admin] Logs - Permission: added background for the operation icons when hover on them

* [org admin] Logs - File Update: added background for the operation icons when hover on them

* fixup
This commit is contained in:
llj
2025-06-09 10:11:02 +08:00
committed by GitHub
parent 9031109f23
commit f0f255a03a
23 changed files with 287 additions and 127 deletions

View File

@@ -2,20 +2,20 @@ import React from 'react';
import PropTypes from 'prop-types'; import PropTypes from 'prop-types';
import { gettext } from '../utils/constants'; import { gettext } from '../utils/constants';
const EditIcon = (props) => { function EditIcon({ onClick }) {
return ( return (
<span <i
role="button" role="button"
title={gettext('Edit')} title={gettext('Edit')}
aria-label={gettext('Edit')} aria-label={gettext('Edit')}
className="sf3-font sf3-font-rename attr-action-icon" className="sf3-font sf3-font-rename op-icon op-icon-bg-light ml-1"
onClick={props.onClick}> onClick={onClick}>
</span> </i>
); );
}; }
EditIcon.propTypes = { EditIcon.propTypes = {
onClick: PropTypes.func.isRequired, onClick: PropTypes.func.isRequired
}; };
export default EditIcon; export default EditIcon;

View File

@@ -35,7 +35,7 @@ const OpMenu = ({ onRename, onFreezed, onUnFreezed }) => {
tag="i" tag="i"
role="button" role="button"
tabIndex="0" tabIndex="0"
className="sf-dropdown-toggle sf3-font-more sf3-font face-recognition-more-operations-toggle" className="sf-dropdown-toggle op-icon sf3-font-more sf3-font face-recognition-more-operations-toggle"
title={gettext('More operations')} title={gettext('More operations')}
aria-label={gettext('More operations')} aria-label={gettext('More operations')}
data-toggle="dropdown" data-toggle="dropdown"

View File

@@ -111,7 +111,7 @@ class DepartmentsV2MembersItem extends React.Component {
direction="down" direction="down"
> >
<DropdownToggle <DropdownToggle
tag='a' tag='i'
role="button" role="button"
className='op-icon sf3-font-more sf3-font' className='op-icon sf3-font-more sf3-font'
title={gettext('More operations')} title={gettext('More operations')}

View File

@@ -1,6 +1,7 @@
import React, { Component, Fragment } from 'react'; import React, { Component, Fragment } from 'react';
import PropTypes from 'prop-types'; import PropTypes from 'prop-types';
import dayjs from 'dayjs'; import dayjs from 'dayjs';
import classnames from 'classnames';
import relativeTime from 'dayjs/plugin/relativeTime'; import relativeTime from 'dayjs/plugin/relativeTime';
import { orgAdminAPI } from '../../../utils/org-admin-api'; import { orgAdminAPI } from '../../../utils/org-admin-api';
import { orgID, gettext } from '../../../utils/constants'; import { orgID, gettext } from '../../../utils/constants';
@@ -88,6 +89,7 @@ class Item extends Component {
constructor(props) { constructor(props) {
super(props); super(props);
this.state = { this.state = {
isHighlighted: false,
unlinked: false, unlinked: false,
isOpIconShown: false, isOpIconShown: false,
isUnlinkDeviceDialogOpen: false isUnlinkDeviceDialogOpen: false
@@ -95,15 +97,20 @@ class Item extends Component {
} }
handleMouseOver = () => { handleMouseOver = () => {
this.setState({ isOpIconShown: true }); this.setState({
isHighlighted: true,
isOpIconShown: true
});
}; };
handleMouseOut = () => { handleMouseOut = () => {
this.setState({ isOpIconShown: false }); this.setState({
isHighlighted: false,
isOpIconShown: false
});
}; };
handleUnlink = (e) => { handleUnlink = () => {
e.preventDefault();
if (this.props.item.is_desktop_client) { if (this.props.item.is_desktop_client) {
this.toggleUnlinkDeviceDialog(); this.toggleUnlinkDeviceDialog();
} else { } else {
@@ -129,7 +136,7 @@ class Item extends Component {
render() { render() {
const item = this.props.item; const item = this.props.item;
const { unlinked, isUnlinkDeviceDialogOpen, isOpIconShown } = this.state; const { unlinked, isUnlinkDeviceDialogOpen, isOpIconShown, isHighlighted } = this.state;
if (unlinked) { if (unlinked) {
return null; return null;
@@ -137,7 +144,13 @@ class Item extends Component {
return ( return (
<Fragment> <Fragment>
<tr onMouseEnter={this.handleMouseOver} onMouseLeave={this.handleMouseOut}> <tr
className={classnames({
'tr-highlight': isHighlighted
})}
onMouseEnter={this.handleMouseOver}
onMouseLeave={this.handleMouseOut}
>
<td>{item.user_name}</td> <td>{item.user_name}</td>
<td>{item.platform}{' / '}{item.client_version}</td> <td>{item.platform}{' / '}{item.client_version}</td>
<td>{item.device_name}</td> <td>{item.device_name}</td>
@@ -146,7 +159,12 @@ class Item extends Component {
<span title={dayjs(item.last_accessed).format('dddd, MMMM D, YYYY h:mm:ss A')}>{dayjs(item.last_accessed).fromNow()}</span> <span title={dayjs(item.last_accessed).format('dddd, MMMM D, YYYY h:mm:ss A')}>{dayjs(item.last_accessed).fromNow()}</span>
</td> </td>
<td> <td>
<a href="#" className={`sf3-font-delete1 sf3-font action-icon ${isOpIconShown ? '' : 'invisible'}`} title={gettext('Unlink')} onClick={this.handleUnlink}></a> <i
className={`sf3-font-delete1 sf3-font op-icon ${isOpIconShown ? '' : 'invisible'}`}
title={gettext('Unlink')}
onClick={this.handleUnlink}
>
</i>
</td> </td>
</tr> </tr>
{isUnlinkDeviceDialogOpen && {isUnlinkDeviceDialogOpen &&

View File

@@ -173,7 +173,6 @@ class RepoItem extends React.Component {
}; };
onDropdownToggleClick = (e) => { onDropdownToggleClick = (e) => {
e.preventDefault();
this.toggleOperationMenu(e); this.toggleOperationMenu(e);
}; };
@@ -243,7 +242,8 @@ class RepoItem extends React.Component {
{isOperationMenuShow && {isOperationMenuShow &&
<Dropdown isOpen={this.state.isItemMenuShow} toggle={this.toggleOperationMenu}> <Dropdown isOpen={this.state.isItemMenuShow} toggle={this.toggleOperationMenu}>
<DropdownToggle <DropdownToggle
tag="a" tag="i"
role="button"
className="op-icon sf3-font-more sf3-font" className="op-icon sf3-font-more sf3-font"
title={gettext('More operations')} title={gettext('More operations')}
aria-label={gettext('More operations')} aria-label={gettext('More operations')}

View File

@@ -3,6 +3,7 @@ import PropTypes from 'prop-types';
import { Button } from 'reactstrap'; import { Button } from 'reactstrap';
import dayjs from 'dayjs'; import dayjs from 'dayjs';
import relativeTime from 'dayjs/plugin/relativeTime'; import relativeTime from 'dayjs/plugin/relativeTime';
import classnames from 'classnames';
import { Utils } from '../../../utils/utils'; import { Utils } from '../../../utils/utils';
import { orgAdminAPI } from '../../../utils/org-admin-api'; import { orgAdminAPI } from '../../../utils/org-admin-api';
import { gettext, orgID } from '../../../utils/constants'; import { gettext, orgID } from '../../../utils/constants';
@@ -69,15 +70,17 @@ class Content extends Component {
</thead> </thead>
<tbody> <tbody>
{items.map((item, index) => { {items.map((item, index) => {
return (<Item return (
key={index} <Item
repo={item} key={index}
isItemFreezed={this.state.isItemFreezed} repo={item}
onFreezedItem={this.onFreezedItem} isItemFreezed={this.state.isItemFreezed}
onUnfreezedItem={this.onUnfreezedItem} onFreezedItem={this.onFreezedItem}
onDeleteRepo={this.props.onDeleteRepo} onUnfreezedItem={this.onUnfreezedItem}
onRestoreRepo={this.props.onRestoreRepo} onDeleteRepo={this.props.onDeleteRepo}
/>); onRestoreRepo={this.props.onRestoreRepo}
/>
);
})} })}
</tbody> </tbody>
</table> </table>
@@ -117,7 +120,7 @@ class Item extends Component {
constructor(props) { constructor(props) {
super(props); super(props);
this.state = { this.state = {
highlight: false, isHighlighted: false,
isOpIconShown: false, isOpIconShown: false,
isDeleteRepoDialogOpen: false, isDeleteRepoDialogOpen: false,
isRestoreRepoDialogOpen: false isRestoreRepoDialogOpen: false
@@ -128,7 +131,7 @@ class Item extends Component {
if (!this.props.isItemFreezed) { if (!this.props.isItemFreezed) {
this.setState({ this.setState({
isOpIconShown: true, isOpIconShown: true,
highlight: true isHighlighted: true
}); });
} }
}; };
@@ -137,14 +140,14 @@ class Item extends Component {
if (!this.props.isItemFreezed) { if (!this.props.isItemFreezed) {
this.setState({ this.setState({
isOpIconShown: false, isOpIconShown: false,
highlight: false isHighlighted: false
}); });
} }
}; };
onUnfreezedItem = () => { onUnfreezedItem = () => {
this.setState({ this.setState({
highlight: false, isHighlighted: false,
isOpIconShow: false isOpIconShow: false
}); });
this.props.onUnfreezedItem(); this.props.onUnfreezedItem();
@@ -219,14 +222,20 @@ class Item extends Component {
render() { render() {
const { repo } = this.props; const { repo } = this.props;
const { isOpIconShown, isDeleteRepoDialogOpen, isRestoreRepoDialogOpen } = this.state; const { isHighlighted, isOpIconShown, isDeleteRepoDialogOpen, isRestoreRepoDialogOpen } = this.state;
const iconUrl = Utils.getLibIconUrl(repo); const iconUrl = Utils.getLibIconUrl(repo);
const iconTitle = Utils.getLibIconTitle(repo); const iconTitle = Utils.getLibIconTitle(repo);
const repoName = '<span class="op-target">' + Utils.HTMLescape(repo.name) + '</span>'; const repoName = '<span class="op-target">' + Utils.HTMLescape(repo.name) + '</span>';
return ( return (
<Fragment> <Fragment>
<tr onMouseEnter={this.handleMouseOver} onMouseLeave={this.handleMouseOut}> <tr
className={classnames({
'tr-highlight': isHighlighted
})}
onMouseEnter={this.handleMouseOver}
onMouseLeave={this.handleMouseOut}
>
<td><img src={iconUrl} title={iconTitle} alt={iconTitle} width="24" /></td> <td><img src={iconUrl} title={iconTitle} alt={iconTitle} width="24" /></td>
<td>{repo.name}</td> <td>{repo.name}</td>
<td> <td>

View File

@@ -1,5 +1,6 @@
import React, { Component, Fragment } from 'react'; import React, { Component, Fragment } from 'react';
import PropTypes from 'prop-types'; import PropTypes from 'prop-types';
import classnames from 'classnames';
import { Link } from '@gatsbyjs/reach-router'; import { Link } from '@gatsbyjs/reach-router';
import { orgAdminAPI } from '../../utils/org-admin-api'; import { orgAdminAPI } from '../../utils/org-admin-api';
import { gettext, siteRoot } from '../../utils/constants'; import { gettext, siteRoot } from '../../utils/constants';
@@ -76,7 +77,7 @@ class Content extends Component {
return ( return (
<Fragment> <Fragment>
<table className="table-hover"> <table>
<thead> <thead>
<tr> <tr>
<th width="4%">{/* icon*/}</th> <th width="4%">{/* icon*/}</th>
@@ -106,6 +107,7 @@ class Item extends Component {
constructor(props) { constructor(props) {
super(props); super(props);
this.state = { this.state = {
isHighlighted: false,
isOpIconShown: false, isOpIconShown: false,
deleted: false, deleted: false,
isDeleteRepoDialogOpen: false, isDeleteRepoDialogOpen: false,
@@ -115,18 +117,19 @@ class Item extends Component {
handleMouseOver = () => { handleMouseOver = () => {
this.setState({ this.setState({
isHighlighted: true,
isOpIconShown: true isOpIconShown: true
}); });
}; };
handleMouseOut = () => { handleMouseOut = () => {
this.setState({ this.setState({
isHighlighted: false,
isOpIconShown: false isOpIconShown: false
}); });
}; };
handleDeleteIconClick = (e) => { handleDeleteIconClick = () => {
e.preventDefault();
this.toggleDeleteRepoDialog(); this.toggleDeleteRepoDialog();
}; };
@@ -154,7 +157,7 @@ class Item extends Component {
}; };
render() { render() {
const { deleted, isOpIconShown, isDeleteRepoDialogOpen } = this.state; const { deleted, isOpIconShown, isDeleteRepoDialogOpen, isHighlighted } = this.state;
const repo = this.props.data; const repo = this.props.data;
if (deleted) { if (deleted) {
@@ -163,7 +166,13 @@ class Item extends Component {
return ( return (
<Fragment> <Fragment>
<tr onMouseOver={this.handleMouseOver} onMouseOut={this.handleMouseOut}> <tr
className={classnames({
'tr-highlight': isHighlighted
})}
onMouseOver={this.handleMouseOver}
onMouseOut={this.handleMouseOut}
>
<td> <td>
<img src={Utils.getLibIconUrl(repo)} alt={Utils.getLibIconTitle(repo)} title={Utils.getLibIconTitle(repo)} width="24" /> <img src={Utils.getLibIconUrl(repo)} alt={Utils.getLibIconTitle(repo)} title={Utils.getLibIconTitle(repo)} width="24" />
</td> </td>
@@ -171,7 +180,12 @@ class Item extends Component {
<td>{Utils.bytesToSize(repo.size)}</td> <td>{Utils.bytesToSize(repo.size)}</td>
<td><Link to={`${siteRoot}org/useradmin/info/${encodeURIComponent(repo.shared_by)}/`}>{repo.shared_by_name}</Link></td> <td><Link to={`${siteRoot}org/useradmin/info/${encodeURIComponent(repo.shared_by)}/`}>{repo.shared_by_name}</Link></td>
<td> <td>
<a href="#" className={`action-icon sf3-font-delete1 sf3-font${isOpIconShown ? '' : ' invisible'}`} title={gettext('Delete')} onClick={this.handleDeleteIconClick}></a> <i
className={`op-icon sf3-font-delete1 sf3-font${isOpIconShown ? '' : ' invisible'}`}
title={gettext('Delete')}
onClick={this.handleDeleteIconClick}
>
</i>
</td> </td>
</tr> </tr>
{isDeleteRepoDialogOpen && ( {isDeleteRepoDialogOpen && (

View File

@@ -37,7 +37,6 @@ class GroupItem extends React.Component {
}; };
onDropdownToggleClick = (e) => { onDropdownToggleClick = (e) => {
e.preventDefault();
this.toggleOperationMenu(e); this.toggleOperationMenu(e);
}; };
@@ -102,7 +101,7 @@ class GroupItem extends React.Component {
{isOperationMenuShow && {isOperationMenuShow &&
<Dropdown isOpen={this.state.isItemMenuShow} toggle={this.toggleOperationMenu}> <Dropdown isOpen={this.state.isItemMenuShow} toggle={this.toggleOperationMenu}>
<DropdownToggle <DropdownToggle
tag="a" tag="i"
className="op-icon sf3-font-more sf3-font" className="op-icon sf3-font-more sf3-font"
title={gettext('More operations')} title={gettext('More operations')}
aria-label={gettext('More operations')} aria-label={gettext('More operations')}
@@ -156,7 +155,7 @@ class OrgGroupsSearchGroupsResult extends React.Component {
<th width="30%">{gettext('Name')}</th> <th width="30%">{gettext('Name')}</th>
<th width="35%">{gettext('Creator')}</th> <th width="35%">{gettext('Creator')}</th>
<th width="23%">{gettext('Created At')}</th> <th width="23%">{gettext('Created At')}</th>
<th width="12%" className="text-center">{gettext('Operations')}</th> <th width="12%"></th>
</tr> </tr>
</thead> </thead>
<tbody> <tbody>

View File

@@ -179,7 +179,7 @@ class OrgGroups extends Component {
<th width="30%">{gettext('Name')}</th> <th width="30%">{gettext('Name')}</th>
<th width="35%">{gettext('Creator')}</th> <th width="35%">{gettext('Creator')}</th>
<th width="23%">{gettext('Created At')}</th> <th width="23%">{gettext('Created At')}</th>
<th width="12%" className="text-center">{gettext('Operations')}</th> <th width="12%"></th>
</tr> </tr>
</thead> </thead>
<tbody> <tbody>
@@ -251,7 +251,6 @@ class GroupItem extends React.Component {
}; };
onDropdownToggleClick = (e) => { onDropdownToggleClick = (e) => {
e.preventDefault();
this.toggleOperationMenu(e); this.toggleOperationMenu(e);
}; };
@@ -319,7 +318,7 @@ class GroupItem extends React.Component {
{isOperationMenuShow && {isOperationMenuShow &&
<Dropdown isOpen={this.state.isItemMenuShow} toggle={this.toggleOperationMenu}> <Dropdown isOpen={this.state.isItemMenuShow} toggle={this.toggleOperationMenu}>
<DropdownToggle <DropdownToggle
tag="a" tag="i"
className="op-icon sf3-font-more sf3-font" className="op-icon sf3-font-more sf3-font"
title={gettext('More operations')} title={gettext('More operations')}
aria-label={gettext('More operations')} aria-label={gettext('More operations')}

View File

@@ -173,7 +173,6 @@ class RepoItem extends React.Component {
}; };
onDropdownToggleClick = (e) => { onDropdownToggleClick = (e) => {
e.preventDefault();
this.toggleOperationMenu(e); this.toggleOperationMenu(e);
}; };
@@ -207,7 +206,7 @@ class RepoItem extends React.Component {
{this.state.showMenu && {this.state.showMenu &&
<Dropdown isOpen={this.state.isItemMenuShow} toggle={this.toggleOperationMenu}> <Dropdown isOpen={this.state.isItemMenuShow} toggle={this.toggleOperationMenu}>
<DropdownToggle <DropdownToggle
tag="a" tag="i"
className="op-icon sf3-font-more sf3-font" className="op-icon sf3-font-more sf3-font"
title={gettext('More operations')} title={gettext('More operations')}
aria-label={gettext('More operations')} aria-label={gettext('More operations')}

View File

@@ -184,7 +184,7 @@ class FileAuditItem extends React.Component {
<a href={siteRoot + 'org/useradmin/info/' + fileEvent.user_email + '/'}>{fileEvent.user_name}</a>{' '} <a href={siteRoot + 'org/useradmin/info/' + fileEvent.user_email + '/'}>{fileEvent.user_name}</a>{' '}
<Dropdown size='sm' isOpen={this.state.userDropdownOpen} toggle={this.toggleUserDropdown} <Dropdown size='sm' isOpen={this.state.userDropdownOpen} toggle={this.toggleUserDropdown}
className={this.state.highlight ? '' : 'vh'} tag="span"> className={this.state.highlight ? '' : 'vh'} tag="span">
<DropdownToggle tag="i" className="sf-dropdown-toggle sf3-font-more sf3-font"></DropdownToggle> <DropdownToggle tag="i" className="op-icon sf-dropdown-toggle sf3-font-more sf3-font"></DropdownToggle>
<DropdownMenu> <DropdownMenu>
<DropdownItem onClick={this.props.filterUser.bind(this, fileEvent.user_email)}> <DropdownItem onClick={this.props.filterUser.bind(this, fileEvent.user_email)}>
{gettext('Only Show')}{' '} {gettext('Only Show')}{' '}
@@ -225,7 +225,7 @@ class FileAuditItem extends React.Component {
{ fileEvent.repo_name && { fileEvent.repo_name &&
<Dropdown size='sm' isOpen={this.state.repoDropdownOpen} toggle={this.toggleRepoDropdown} <Dropdown size='sm' isOpen={this.state.repoDropdownOpen} toggle={this.toggleRepoDropdown}
className={this.state.highlight ? '' : 'vh'} > className={this.state.highlight ? '' : 'vh'} >
<DropdownToggle tag="i" className="sf-dropdown-toggle sf3-font-more sf3-font"></DropdownToggle> <DropdownToggle tag="i" className="op-icon sf-dropdown-toggle sf3-font-more sf3-font"></DropdownToggle>
<DropdownMenu> <DropdownMenu>
<DropdownItem size='sm' onClick={this.props.filterRepo.bind(this, fileEvent.repo_name)}> <DropdownItem size='sm' onClick={this.props.filterRepo.bind(this, fileEvent.repo_name)}>
{gettext('Only Show')}{' '}<span className="font-weight-bold">{fileEvent.repo_name}</span> {gettext('Only Show')}{' '}<span className="font-weight-bold">{fileEvent.repo_name}</span>

View File

@@ -210,7 +210,7 @@ class FileUpdateItem extends React.Component {
<a href={siteRoot + 'org/useradmin/info/' + fileEvent.user_email + '/'}>{fileEvent.user_name}</a>{' '} <a href={siteRoot + 'org/useradmin/info/' + fileEvent.user_email + '/'}>{fileEvent.user_name}</a>{' '}
<Dropdown size='sm' isOpen={this.state.userDropdownOpen} toggle={this.toggleUserDropdown} <Dropdown size='sm' isOpen={this.state.userDropdownOpen} toggle={this.toggleUserDropdown}
className={this.state.highlight ? '' : 'vh'} tag="span"> className={this.state.highlight ? '' : 'vh'} tag="span">
<DropdownToggle tag="i" className="sf-dropdown-toggle sf3-font-more sf3-font"></DropdownToggle> <DropdownToggle tag="i" className="op-icon sf-dropdown-toggle sf3-font-more sf3-font"></DropdownToggle>
<DropdownMenu> <DropdownMenu>
<DropdownItem onClick={this.props.filterUser.bind(this, fileEvent.user_email)}> <DropdownItem onClick={this.props.filterUser.bind(this, fileEvent.user_email)}>
{gettext('Only Show')}{' '}<span className="font-weight-bold">{fileEvent.user_name}</span> {gettext('Only Show')}{' '}<span className="font-weight-bold">{fileEvent.user_name}</span>
@@ -236,7 +236,7 @@ class FileUpdateItem extends React.Component {
{ fileEvent.repo_name && { fileEvent.repo_name &&
<Dropdown size='sm' isOpen={this.state.repoDropdownOpen} toggle={this.toggleRepoDropdown} <Dropdown size='sm' isOpen={this.state.repoDropdownOpen} toggle={this.toggleRepoDropdown}
className={this.state.highlight ? '' : 'vh'} > className={this.state.highlight ? '' : 'vh'} >
<DropdownToggle tag="i" className="sf-dropdown-toggle sf3-font-more sf3-font"></DropdownToggle> <DropdownToggle tag="i" className="op-icon sf-dropdown-toggle sf3-font-more sf3-font"></DropdownToggle>
<DropdownMenu> <DropdownMenu>
<DropdownItem size='sm' onClick={this.props.filterRepo.bind(this, fileEvent.repo_name)}> <DropdownItem size='sm' onClick={this.props.filterRepo.bind(this, fileEvent.repo_name)}>
{gettext('Only Show')}{' '} {gettext('Only Show')}{' '}

View File

@@ -157,7 +157,7 @@ class PermAuditItem extends React.Component {
<a href={siteRoot + 'org/useradmin/info/' + permEvent.from_user_email + '/'}>{permEvent.from_user_name}</a>{' '} <a href={siteRoot + 'org/useradmin/info/' + permEvent.from_user_email + '/'}>{permEvent.from_user_name}</a>{' '}
<Dropdown size='sm' isOpen={this.state.userDropdownOpen} toggle={this.toggleUserDropdown} <Dropdown size='sm' isOpen={this.state.userDropdownOpen} toggle={this.toggleUserDropdown}
className={this.state.highlight ? '' : 'vh'} tag="span"> className={this.state.highlight ? '' : 'vh'} tag="span">
<DropdownToggle tag="i" className="sf-dropdown-toggle sf3-font-more sf3-font"></DropdownToggle> <DropdownToggle tag="i" className="op-icon sf-dropdown-toggle sf3-font-more sf3-font"></DropdownToggle>
<DropdownMenu> <DropdownMenu>
<DropdownItem onClick={this.props.filterUser.bind(this, permEvent.from_user_email)}> <DropdownItem onClick={this.props.filterUser.bind(this, permEvent.from_user_email)}>
{gettext('Only Show')}{' '} {gettext('Only Show')}{' '}

View File

@@ -85,7 +85,6 @@ class UserItem extends React.Component {
}; };
onDropdownToggleClick = (e) => { onDropdownToggleClick = (e) => {
e.preventDefault();
this.toggleOperationMenu(e); this.toggleOperationMenu(e);
}; };
@@ -176,7 +175,7 @@ class UserItem extends React.Component {
{isOperationMenuShow && ( {isOperationMenuShow && (
<Dropdown isOpen={this.state.isItemMenuShow} toggle={this.toggleOperationMenu}> <Dropdown isOpen={this.state.isItemMenuShow} toggle={this.toggleOperationMenu}>
<DropdownToggle <DropdownToggle
tag="a" tag="i"
className="op-icon sf3-font-more sf3-font" className="op-icon sf3-font-more sf3-font"
title={gettext('More operations')} title={gettext('More operations')}
aria-label={gettext('More operations')} aria-label={gettext('More operations')}

View File

@@ -8,6 +8,7 @@ import OrgAdminUserNav from '../../components/org-admin-user-nav';
import SetOrgUserName from '../../components/dialog/set-org-user-name'; import SetOrgUserName from '../../components/dialog/set-org-user-name';
import SetOrgUserContactEmail from '../../components/dialog/set-org-user-contact-email'; import SetOrgUserContactEmail from '../../components/dialog/set-org-user-contact-email';
import SetOrgUserQuota from '../../components/dialog/set-org-user-quota'; import SetOrgUserQuota from '../../components/dialog/set-org-user-quota';
import EditIcon from '../../components/edit-icon';
import MainPanelTopbar from './main-panel-topbar'; import MainPanelTopbar from './main-panel-topbar';
import '../../css/org-admin-user.css'; import '../../css/org-admin-user.css';
@@ -136,13 +137,13 @@ class Content extends Component {
<dt>{gettext('Name')}</dt> <dt>{gettext('Name')}</dt>
<dd> <dd>
{name || '--'} {name || '--'}
<span title={gettext('Edit')} className="attr-action-icon sf3-font sf3-font-rename" onClick={this.toggleSetNameDialog}></span> <EditIcon onClick={this.toggleSetNameDialog} />
</dd> </dd>
<dt>{gettext('Contact Email')}</dt> <dt>{gettext('Contact Email')}</dt>
<dd> <dd>
{contact_email || '--'} {contact_email || '--'}
<span title={gettext('Edit')} className="attr-action-icon sf3-font sf3-font-rename" onClick={this.toggleSetContactEmailDialog}></span> <EditIcon onClick={this.toggleSetContactEmailDialog} />
</dd> </dd>
<dt>{gettext('Organization')}</dt> <dt>{gettext('Organization')}</dt>
@@ -151,7 +152,7 @@ class Content extends Component {
<dt>{gettext('Space Used / Quota')}</dt> <dt>{gettext('Space Used / Quota')}</dt>
<dd> <dd>
{`${Utils.bytesToSize(quota_usage)}${quota_total > 0 ? ' / ' + Utils.bytesToSize(quota_total) : ''}`} {`${Utils.bytesToSize(quota_usage)}${quota_total > 0 ? ' / ' + Utils.bytesToSize(quota_total) : ''}`}
<span title={gettext('Edit')} className="attr-action-icon sf3-font sf3-font-rename" onClick={this.toggleSetQuotaDialog}></span> <EditIcon onClick={this.toggleSetQuotaDialog} />
</dd> </dd>
</dl> </dl>
{isSetNameDialogOpen && {isSetNameDialogOpen &&

View File

@@ -1,6 +1,7 @@
import React, { Component, Fragment } from 'react'; import React, { Component, Fragment } from 'react';
import PropTypes from 'prop-types'; import PropTypes from 'prop-types';
import dayjs from 'dayjs'; import dayjs from 'dayjs';
import classnames from 'classnames';
import { orgAdminAPI } from '../../utils/org-admin-api'; import { orgAdminAPI } from '../../utils/org-admin-api';
import { gettext } from '../../utils/constants'; import { gettext } from '../../utils/constants';
import { Utils } from '../../utils/utils'; import { Utils } from '../../utils/utils';
@@ -102,6 +103,7 @@ class Item extends Component {
constructor(props) { constructor(props) {
super(props); super(props);
this.state = { this.state = {
isHighlighted: false,
isOpIconShown: false, isOpIconShown: false,
deleted: false, deleted: false,
isDeleteRepoDialogOpen: false, isDeleteRepoDialogOpen: false,
@@ -111,18 +113,19 @@ class Item extends Component {
handleMouseOver = () => { handleMouseOver = () => {
this.setState({ this.setState({
isHighlighted: true,
isOpIconShown: true isOpIconShown: true
}); });
}; };
handleMouseOut = () => { handleMouseOut = () => {
this.setState({ this.setState({
isHighlighted: false,
isOpIconShown: false isOpIconShown: false
}); });
}; };
handleDeleteIconClick = (e) => { handleDeleteIconClick = () => {
e.preventDefault();
this.toggleDeleteRepoDialog(); this.toggleDeleteRepoDialog();
}; };
@@ -150,7 +153,7 @@ class Item extends Component {
}; };
render() { render() {
const { deleted, isOpIconShown, isDeleteRepoDialogOpen } = this.state; const { deleted, isOpIconShown, isDeleteRepoDialogOpen, isHighlighted } = this.state;
const repo = this.props.data; const repo = this.props.data;
if (deleted) { if (deleted) {
@@ -159,7 +162,13 @@ class Item extends Component {
return ( return (
<Fragment> <Fragment>
<tr onMouseOver={this.handleMouseOver} onMouseOut={this.handleMouseOut}> <tr
className={classnames({
'tr-highlight': isHighlighted
})}
onMouseOver={this.handleMouseOver}
onMouseOut={this.handleMouseOut}
>
<td> <td>
<img src={Utils.getLibIconUrl(repo)} alt={Utils.getLibIconTitle(repo)} title={Utils.getLibIconTitle(repo)} width="24" /> <img src={Utils.getLibIconUrl(repo)} alt={Utils.getLibIconTitle(repo)} title={Utils.getLibIconTitle(repo)} width="24" />
</td> </td>
@@ -167,7 +176,13 @@ class Item extends Component {
<td>{Utils.bytesToSize(repo.size)}</td> <td>{Utils.bytesToSize(repo.size)}</td>
<td title={dayjs(repo.last_modified).format('dddd, MMMM D, YYYY h:mm:ss A')}>{dayjs(repo.last_modified).format('YYYY-MM-DD')}</td> <td title={dayjs(repo.last_modified).format('dddd, MMMM D, YYYY h:mm:ss A')}>{dayjs(repo.last_modified).format('YYYY-MM-DD')}</td>
<td> <td>
<a href="#" className={`action-icon sf3-font-delete1 sf3-font${isOpIconShown ? '' : ' invisible'}`} title={gettext('Delete')} onClick={this.handleDeleteIconClick}></a> <i
role="button"
className={`op-icon sf3-font-delete1 sf3-font${isOpIconShown ? '' : ' invisible'}`}
title={gettext('Delete')}
onClick={this.handleDeleteIconClick}
>
</i>
</td> </td>
</tr> </tr>
{isDeleteRepoDialogOpen && ( {isDeleteRepoDialogOpen && (

View File

@@ -60,14 +60,16 @@ class Content extends Component {
</thead> </thead>
<tbody> <tbody>
{items.map((item, index) => { {items.map((item, index) => {
return (<Item return (
key={index} <Item
item={item} key={index}
isItemFreezed={this.state.isItemFreezed} item={item}
toggleItemFreezed={this.toggleItemFreezed} isItemFreezed={this.state.isItemFreezed}
removeMember={this.props.removeMember} toggleItemFreezed={this.toggleItemFreezed}
updateMemberRole={this.props.updateMemberRole} removeMember={this.props.removeMember}
/>); updateMemberRole={this.props.updateMemberRole}
/>
);
})} })}
</tbody> </tbody>
</table> </table>
@@ -174,7 +176,13 @@ class Item extends Component {
</td> </td>
<td> <td>
{item.role != 'Owner' && {item.role != 'Owner' &&
<a href="#" className={`action-icon sf2-icon-x3 ${highlighted ? '' : 'invisible'}`} title={gettext('Remove')} onClick={this.toggleDeleteDialog}></a> <i
role="button"
className={`op-icon sf2-icon-x3 ${highlighted ? '' : 'invisible'}`}
title={gettext('Remove')}
onClick={this.toggleDeleteDialog}
>
</i>
} }
</td> </td>
</tr> </tr>

View File

@@ -1,5 +1,6 @@
import React, { Component, Fragment } from 'react'; import React, { Component, Fragment } from 'react';
import PropTypes from 'prop-types'; import PropTypes from 'prop-types';
import classnames from 'classnames';
import { Utils } from '../../../utils/utils'; import { Utils } from '../../../utils/utils';
import { systemAdminAPI } from '../../../utils/system-admin-api'; import { systemAdminAPI } from '../../../utils/system-admin-api';
import { siteRoot, gettext, isPro } from '../../../utils/constants'; import { siteRoot, gettext, isPro } from '../../../utils/constants';
@@ -32,7 +33,7 @@ class Content extends Component {
); );
const table = ( const table = (
<Fragment> <Fragment>
<table className="table-hover"> <table>
<thead> <thead>
<tr> <tr>
<th width="5%">{/* icon */}</th> <th width="5%">{/* icon */}</th>
@@ -44,11 +45,13 @@ class Content extends Component {
</thead> </thead>
<tbody> <tbody>
{items.map((item, index) => { {items.map((item, index) => {
return (<Item return (
key={index} <Item
item={item} key={index}
unshareRepo={this.props.unshareRepo} item={item}
/>); unshareRepo={this.props.unshareRepo}
/>
);
})} })}
</tbody> </tbody>
</table> </table>
@@ -75,23 +78,27 @@ class Item extends Component {
constructor(props) { constructor(props) {
super(props); super(props);
this.state = { this.state = {
isHighlighted: false,
isOpIconShown: false, isOpIconShown: false,
isUnshareRepoDialogOpen: false isUnshareRepoDialogOpen: false
}; };
} }
handleMouseEnter = () => { handleMouseEnter = () => {
this.setState({ isOpIconShown: true }); this.setState({
isHighlighted: true,
isOpIconShown: true
});
}; };
handleMouseLeave = () => { handleMouseLeave = () => {
this.setState({ isOpIconShown: false }); this.setState({
isHighlighted: false,
isOpIconShown: false
});
}; };
toggleUnshareRepoDialog = (e) => { toggleUnshareRepoDialog = () => {
if (e) {
e.preventDefault();
}
this.setState({ isUnshareRepoDialogOpen: !this.state.isUnshareRepoDialogOpen }); this.setState({ isUnshareRepoDialogOpen: !this.state.isUnshareRepoDialogOpen });
}; };
@@ -117,7 +124,7 @@ class Item extends Component {
}; };
render() { render() {
let { isOpIconShown, isUnshareRepoDialogOpen } = this.state; let { isOpIconShown, isUnshareRepoDialogOpen, isHighlighted } = this.state;
let { item } = this.props; let { item } = this.props;
let iconUrl = Utils.getLibIconUrl(item); let iconUrl = Utils.getLibIconUrl(item);
@@ -128,7 +135,13 @@ class Item extends Component {
return ( return (
<Fragment> <Fragment>
<tr onMouseEnter={this.handleMouseEnter} onMouseLeave={this.handleMouseLeave}> <tr
className={classnames({
'tr-highlight': isHighlighted
})}
onMouseEnter={this.handleMouseEnter}
onMouseLeave={this.handleMouseLeave}
>
<td><img src={iconUrl} title={iconTitle} alt={iconTitle} width="24" /></td> <td><img src={iconUrl} title={iconTitle} alt={iconTitle} width="24" /></td>
<td>{this.renderRepoName()}</td> <td>{this.renderRepoName()}</td>
<td>{Utils.bytesToSize(item.size)}</td> <td>{Utils.bytesToSize(item.size)}</td>
@@ -136,7 +149,13 @@ class Item extends Component {
<UserLink email={item.shared_by} name={item.shared_by_name} /> <UserLink email={item.shared_by} name={item.shared_by_name} />
</td> </td>
<td> <td>
<a href="#" className={`action-icon sf2-icon-x3 ${isOpIconShown ? '' : 'invisible'}`} title={gettext('Unshare')} onClick={this.toggleUnshareRepoDialog}></a> <i
role="button"
className={`op-icon sf2-icon-x3 ${isOpIconShown ? '' : 'invisible'}`}
title={gettext('Unshare')}
onClick={this.toggleUnshareRepoDialog}
>
</i>
</td> </td>
</tr> </tr>
{isUnshareRepoDialogOpen && {isUnshareRepoDialogOpen &&

View File

@@ -1,6 +1,7 @@
import React, { Component, Fragment } from 'react'; import React, { Component, Fragment } from 'react';
import PropTypes from 'prop-types'; import PropTypes from 'prop-types';
import dayjs from 'dayjs'; import dayjs from 'dayjs';
import classnames from 'classnames';
import { Utils } from '../../../utils/utils'; import { Utils } from '../../../utils/utils';
import { systemAdminAPI } from '../../../utils/system-admin-api'; import { systemAdminAPI } from '../../../utils/system-admin-api';
import { siteRoot, gettext } from '../../../utils/constants'; import { siteRoot, gettext } from '../../../utils/constants';
@@ -42,11 +43,13 @@ class Content extends Component {
</thead> </thead>
<tbody> <tbody>
{items.map((item, index) => { {items.map((item, index) => {
return (<Item return (
key={index} <Item
item={item} key={index}
deleteGroup={this.props.deleteGroup} item={item}
/>); deleteGroup={this.props.deleteGroup}
/>
);
})} })}
</tbody> </tbody>
</table> </table>
@@ -73,23 +76,27 @@ class Item extends Component {
constructor(props) { constructor(props) {
super(props); super(props);
this.state = { this.state = {
isHighlighted: false,
isOpIconShown: false, isOpIconShown: false,
isDeleteDialogOpen: false isDeleteDialogOpen: false
}; };
} }
handleMouseEnter = () => { handleMouseEnter = () => {
this.setState({ isOpIconShown: true }); this.setState({
isHighlighted: true,
isOpIconShown: true
});
}; };
handleMouseLeave = () => { handleMouseLeave = () => {
this.setState({ isOpIconShown: false }); this.setState({
isHighlighted: false,
isOpIconShown: false
});
}; };
toggleDeleteDialog = (e) => { toggleDeleteDialog = () => {
if (e) {
e.preventDefault();
}
this.setState({ isDeleteDialogOpen: !this.state.isDeleteDialogOpen }); this.setState({ isDeleteDialogOpen: !this.state.isDeleteDialogOpen });
}; };
@@ -100,7 +107,7 @@ class Item extends Component {
render() { render() {
const { item } = this.props; const { item } = this.props;
const { isOpIconShown, isDeleteDialogOpen } = this.state; const { isOpIconShown, isDeleteDialogOpen, isHighlighted } = this.state;
const itemName = '<span class="op-target">' + Utils.HTMLescape(item.group_name) + '</span>'; const itemName = '<span class="op-target">' + Utils.HTMLescape(item.group_name) + '</span>';
const deleteDialogMsg = gettext('Are you sure you want to delete {placeholder} ?').replace('{placeholder}', itemName); const deleteDialogMsg = gettext('Are you sure you want to delete {placeholder} ?').replace('{placeholder}', itemName);
@@ -109,12 +116,23 @@ class Item extends Component {
return ( return (
<Fragment> <Fragment>
<tr onMouseEnter={this.handleMouseEnter} onMouseLeave={this.handleMouseLeave}> <tr
className={classnames({
'tr-highlight': isHighlighted
})}
onMouseEnter={this.handleMouseEnter}
onMouseLeave={this.handleMouseLeave}
>
<td><a href={groupUrl}>{item.group_name}</a></td> <td><a href={groupUrl}>{item.group_name}</a></td>
<td><UserLink email={item.creator_email} name={item.creator_name} /></td> <td><UserLink email={item.creator_email} name={item.creator_name} /></td>
<td>{dayjs(item.created_at).format('YYYY-MM-DD HH:mm:ss')}</td> <td>{dayjs(item.created_at).format('YYYY-MM-DD HH:mm:ss')}</td>
<td> <td>
<a href="#" className={`action-icon sf3-font-delete1 sf3-font ${isOpIconShown ? '' : 'invisible'}`} title={gettext('Delete')} onClick={this.toggleDeleteDialog}></a> <i
className={`op-icon sf3-font-delete1 sf3-font ${isOpIconShown ? '' : 'invisible'}`}
title={gettext('Delete')}
onClick={this.toggleDeleteDialog}
>
</i>
</td> </td>
</tr> </tr>
{isDeleteDialogOpen && {isDeleteDialogOpen &&

View File

@@ -1,5 +1,6 @@
import React, { Component, Fragment } from 'react'; import React, { Component, Fragment } from 'react';
import PropTypes from 'prop-types'; import PropTypes from 'prop-types';
import classnames from 'classnames';
import { Utils } from '../../../utils/utils'; import { Utils } from '../../../utils/utils';
import { systemAdminAPI } from '../../../utils/system-admin-api'; import { systemAdminAPI } from '../../../utils/system-admin-api';
import { gettext } from '../../../utils/constants'; import { gettext } from '../../../utils/constants';
@@ -25,7 +26,7 @@ class Content extends Component {
); );
const table = ( const table = (
<Fragment> <Fragment>
<table className="table-hover"> <table>
<thead> <thead>
<tr> <tr>
<th width="5%"></th> <th width="5%"></th>
@@ -37,11 +38,13 @@ class Content extends Component {
</thead> </thead>
<tbody> <tbody>
{items.map((item, index) => { {items.map((item, index) => {
return (<Item return (
key={index} <Item
item={item} key={index}
deleteRepo={this.props.deleteRepo} item={item}
/>); deleteRepo={this.props.deleteRepo}
/>
);
})} })}
</tbody> </tbody>
</table> </table>
@@ -64,17 +67,24 @@ class Item extends Component {
constructor(props) { constructor(props) {
super(props); super(props);
this.state = { this.state = {
isHighlighted: false,
isOpIconShown: false, isOpIconShown: false,
isDeleteDialogOpen: false isDeleteDialogOpen: false
}; };
} }
handleMouseEnter = () => { handleMouseEnter = () => {
this.setState({ isOpIconShown: true }); this.setState({
isHighlighted: true,
isOpIconShown: true
});
}; };
handleMouseLeave = () => { handleMouseLeave = () => {
this.setState({ isOpIconShown: false }); this.setState({
isHighlighted: false,
isOpIconShown: false
});
}; };
toggleDeleteDialog = (e) => { toggleDeleteDialog = (e) => {
@@ -90,7 +100,7 @@ class Item extends Component {
render() { render() {
const { item } = this.props; const { item } = this.props;
const { isOpIconShown, isDeleteDialogOpen } = this.state; const { isOpIconShown, isDeleteDialogOpen, isHighlighted } = this.state;
const iconUrl = Utils.getLibIconUrl(item); const iconUrl = Utils.getLibIconUrl(item);
const iconTitle = Utils.getLibIconTitle(item); const iconTitle = Utils.getLibIconTitle(item);
@@ -100,7 +110,13 @@ class Item extends Component {
return ( return (
<Fragment> <Fragment>
<tr onMouseEnter={this.handleMouseEnter} onMouseLeave={this.handleMouseLeave}> <tr
className={classnames({
'tr-highlight': isHighlighted
})}
onMouseEnter={this.handleMouseEnter}
onMouseLeave={this.handleMouseLeave}
>
<td><img src={iconUrl} title={iconTitle} alt={iconTitle} width="24" /></td> <td><img src={iconUrl} title={iconTitle} alt={iconTitle} width="24" /></td>
<td>{item.repo_name}</td> <td>{item.repo_name}</td>
<td>{item.repo_id}</td> <td>{item.repo_id}</td>
@@ -113,7 +129,12 @@ class Item extends Component {
} }
</td> </td>
<td> <td>
<a href="#" className={`action-icon sf3-font-delete1 sf3-font ${isOpIconShown ? '' : 'invisible'}`} title={gettext('Delete')} onClick={this.toggleDeleteDialog}></a> <i
className={`op-icon sf3-font-delete1 sf3-font ${isOpIconShown ? '' : 'invisible'}`}
title={gettext('Delete')}
onClick={this.toggleDeleteDialog}
>
</i>
</td> </td>
</tr> </tr>
{isDeleteDialogOpen && {isDeleteDialogOpen &&

View File

@@ -3,6 +3,7 @@ import PropTypes from 'prop-types';
import { Link } from '@gatsbyjs/reach-router'; import { Link } from '@gatsbyjs/reach-router';
import dayjs from 'dayjs'; import dayjs from 'dayjs';
import relativeTime from 'dayjs/plugin/relativeTime'; import relativeTime from 'dayjs/plugin/relativeTime';
import classnames from 'classnames';
import { gettext } from '../../../utils/constants'; import { gettext } from '../../../utils/constants';
import { Utils } from '../../../utils/utils'; import { Utils } from '../../../utils/utils';
import Loading from '../../../components/loading'; import Loading from '../../../components/loading';
@@ -14,18 +15,21 @@ class DirentItem extends React.Component {
constructor(props) { constructor(props) {
super(props); super(props);
this.state = { this.state = {
isHighlighted: false,
isOpIconShown: false isOpIconShown: false
}; };
} }
handleMouseOver = () => { handleMouseOver = () => {
this.setState({ this.setState({
isHighlighted: true,
isOpIconShown: true isOpIconShown: true
}); });
}; };
handleMouseOut = () => { handleMouseOut = () => {
this.setState({ this.setState({
isHighlighted: false,
isOpIconShown: false isOpIconShown: false
}); });
}; };
@@ -34,24 +38,28 @@ class DirentItem extends React.Component {
this.props.openFolder(this.props.dirent); this.props.openFolder(this.props.dirent);
}; };
deleteDirent = (e) => { deleteDirent = () => {
e.preventDefault();
this.props.deleteDirent(this.props.dirent); this.props.deleteDirent(this.props.dirent);
}; };
downloadDirent = (e) => { downloadDirent = () => {
e.preventDefault();
this.props.downloadDirent(this.props.dirent); this.props.downloadDirent(this.props.dirent);
}; };
render() { render() {
let { isOpIconShown } = this.state; let { isOpIconShown, isHighlighted } = this.state;
let { dirent, fromSystemRepo } = this.props; let { dirent, fromSystemRepo } = this.props;
let iconUrl = Utils.getDirentIcon(dirent); let iconUrl = Utils.getDirentIcon(dirent);
return ( return (
<Fragment> <Fragment>
<tr onMouseEnter={this.handleMouseOver} onMouseLeave={this.handleMouseOut}> <tr
className={classnames({
'tr-highlight': isHighlighted
})}
onMouseEnter={this.handleMouseOver}
onMouseLeave={this.handleMouseOut}
>
<td className="text-center"><img src={iconUrl} width="24" alt='' /></td> <td className="text-center"><img src={iconUrl} width="24" alt='' /></td>
<td> <td>
{dirent.is_file ? {dirent.is_file ?
@@ -61,10 +69,20 @@ class DirentItem extends React.Component {
</td> </td>
<td> <td>
{isOpIconShown && fromSystemRepo && {isOpIconShown && fromSystemRepo &&
<a href="#" className="op-icon sf3-font-delete1 sf3-font" title={gettext('Delete')} onClick={this.deleteDirent}></a> <i
className="op-icon sf3-font-delete1 sf3-font"
title={gettext('Delete')}
onClick={this.deleteDirent}
>
</i>
} }
{isOpIconShown && dirent.is_file && {isOpIconShown && dirent.is_file &&
<a href="#" className="op-icon sf3-font sf3-font-download1" title={gettext('Download')} onClick={this.downloadDirent}></a> <i
className="op-icon sf3-font sf3-font-download1"
title={gettext('Download')}
onClick={this.downloadDirent}
>
</i>
} }
</td> </td>
<td>{dirent.size}</td> <td>{dirent.size}</td>

View File

@@ -3,6 +3,7 @@ import PropTypes from 'prop-types';
import { Link } from '@gatsbyjs/reach-router'; import { Link } from '@gatsbyjs/reach-router';
import dayjs from 'dayjs'; import dayjs from 'dayjs';
import relativeTime from 'dayjs/plugin/relativeTime'; import relativeTime from 'dayjs/plugin/relativeTime';
import classnames from 'classnames';
import { Utils } from '../../../utils/utils'; import { Utils } from '../../../utils/utils';
import { systemAdminAPI } from '../../../utils/system-admin-api'; import { systemAdminAPI } from '../../../utils/system-admin-api';
import { isPro, siteRoot, gettext } from '../../../utils/constants'; import { isPro, siteRoot, gettext } from '../../../utils/constants';
@@ -24,7 +25,7 @@ class Content extends Component {
return <p className="error text-center mt-4">{errorMsg}</p>; return <p className="error text-center mt-4">{errorMsg}</p>;
} else { } else {
const table = ( const table = (
<table className="table-hover"> <table>
<thead> <thead>
<tr> <tr>
<th width="5%"></th> <th width="5%"></th>
@@ -57,6 +58,25 @@ Content.propTypes = {
class Item extends Component { class Item extends Component {
constructor(props) {
super(props);
this.state = {
isHighlighted: false
};
}
handleMouseOver = () => {
this.setState({
isHighlighted: true
});
};
handleMouseOut = () => {
this.setState({
isHighlighted: false
});
};
renderRepoName = () => { renderRepoName = () => {
const { item } = this.props; const { item } = this.props;
const repo = item; const repo = item;
@@ -89,8 +109,15 @@ class Item extends Component {
const { item } = this.props; const { item } = this.props;
const iconUrl = Utils.getLibIconUrl(item); const iconUrl = Utils.getLibIconUrl(item);
const iconTitle = Utils.getLibIconTitle(item); const iconTitle = Utils.getLibIconTitle(item);
const { isHighlighted } = this.state;
return ( return (
<tr> <tr
className={classnames({
'tr-highlight': isHighlighted
})}
onMouseOver={this.handleMouseOver}
onMouseOut={this.handleMouseOut}
>
<td><img src={iconUrl} title={iconTitle} alt={iconTitle} width="24" /></td> <td><img src={iconUrl} title={iconTitle} alt={iconTitle} width="24" /></td>
<td>{this.renderRepoName()}</td> <td>{this.renderRepoName()}</td>
<td>{this.getOwnerLink()}</td> <td>{this.getOwnerLink()}</td>

View File

@@ -567,7 +567,7 @@ a, a:hover {
.op-icon { .op-icon {
font-size: 1rem; font-size: 1rem;
line-height: 1; line-height: 1;
color: #999; color: #666;
cursor: pointer; cursor: pointer;
display: inline-flex; display: inline-flex;
width: 24px; width: 24px;
@@ -580,7 +580,7 @@ a, a:hover {
.op-icon:focus, .op-icon:focus,
.op-icon:hover { .op-icon:hover {
color: #666; color: #666; /* to overwrite the styles for `a:hover` */
text-decoration: none; text-decoration: none;
background: #e5e5e5; background: #e5e5e5;
} }
@@ -590,10 +590,6 @@ a, a:hover {
background: #efefef; /* for .op-icon shown in white containers */ background: #efefef; /* for .op-icon shown in white containers */
} }
.tr-highlight .op-icon {
color: #666;
}
.action-icon, .action-icon,
.attr-action-icon { .attr-action-icon {
margin-left: 0.5rem; margin-left: 0.5rem;