mirror of
https://github.com/haiwen/seahub.git
synced 2025-09-04 16:31:13 +00:00
Repair eslint wraning (#2453)
This commit is contained in:
@@ -95,11 +95,11 @@ class Account extends Component {
|
||||
renderAvatar = () => {
|
||||
if (this.state.avatarURL) {
|
||||
return (
|
||||
<img src={this.state.avatarURL} width="36" height="36" className="avatar" />
|
||||
<img src={this.state.avatarURL} width="36" height="36" className="avatar" alt={gettext('avatar')} />
|
||||
);
|
||||
}
|
||||
return (
|
||||
<img src="" width="36" height="36" className="avatar" />
|
||||
<img src="" width="36" height="36" className="avatar" alt={gettext('avatar')} />
|
||||
);
|
||||
}
|
||||
|
||||
@@ -107,7 +107,7 @@ class Account extends Component {
|
||||
return (
|
||||
<div id="account">
|
||||
<a id="my-info" onClick={this.onClickAccount} className="account-toggle no-deco d-none d-md-block" aria-label="View profile and more">
|
||||
<span><img src={this.state.avatarURL} width="36" height="36" className="avatar" /></span>
|
||||
<span><img src={this.state.avatarURL} width="36" height="36" className="avatar" alt={gettext('avatar')} /></span>
|
||||
<span className="fas fa-caret-down vam"></span>
|
||||
</a>
|
||||
<span className="account-toggle sf2-icon-more mobile-icon d-md-none" aria-label="View profile and more" onClick={this.onClickAccount}></span>
|
||||
|
@@ -8,20 +8,20 @@ class Notification extends React.Component {
|
||||
this.state = {
|
||||
showNotice: false,
|
||||
notice_html: ''
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
onClick = () => {
|
||||
this.setState({
|
||||
showNotice: !this.state.showNotice
|
||||
})
|
||||
});
|
||||
|
||||
if (!this.state.showNotice) {
|
||||
this.loadNotices()
|
||||
this.loadNotices();
|
||||
}
|
||||
|
||||
if (this.state.showNotice) {
|
||||
seafileAPI.updateNotifications()
|
||||
seafileAPI.updateNotifications();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,8 +29,8 @@ class Notification extends React.Component {
|
||||
seafileAPI.listPopupNotices().then(res => {
|
||||
this.setState({
|
||||
notice_html: res.data.notice_html
|
||||
})
|
||||
})
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
render() {
|
||||
@@ -49,13 +49,12 @@ class Notification extends React.Component {
|
||||
<a href="#" onClick={this.onClick} title={gettext('Close')} aria-label={gettext('Close')} className="sf-popover-close js-close sf2-icon-x1 op-icon float-right"></a>
|
||||
</div>
|
||||
<div className="sf-popover-con">
|
||||
<ul className="notice-list" dangerouslySetInnerHTML={{__html: notice_html}}>
|
||||
</ul>
|
||||
<ul className="notice-list" dangerouslySetInnerHTML={{__html: notice_html}}></ul>
|
||||
<a href="/notification/list/" className="view-all">{gettext('See All Notifications')}</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
|
@@ -1,7 +1,15 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { Button, Modal, ModalHeader, Input, ModalBody, ModalFooter, Form, FormGroup, Label, Col, FormText } from 'reactstrap';
|
||||
import { gettext } from '../../utils/constants';
|
||||
|
||||
const propTypes = {
|
||||
fileType: PropTypes.string,
|
||||
parentPath: PropTypes.string.isRequired,
|
||||
onAddFile: PropTypes.func.isRequired,
|
||||
addFileCancel: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
class CreateFile extends React.Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
@@ -9,17 +17,17 @@ class CreateFile extends React.Component {
|
||||
parentPath: '',
|
||||
childName: props.fileType,
|
||||
};
|
||||
this.newInput = React.createRef()
|
||||
this.newInput = React.createRef();
|
||||
}
|
||||
|
||||
handleChange = (e) => {
|
||||
this.setState({
|
||||
childName: e.target.value,
|
||||
})
|
||||
}) ;
|
||||
}
|
||||
|
||||
handleSubmit = () => {
|
||||
let path = this.state.parentPath + this.state.childName
|
||||
let path = this.state.parentPath + this.state.childName;
|
||||
this.props.onAddFile(path);
|
||||
}
|
||||
|
||||
@@ -34,10 +42,10 @@ class CreateFile extends React.Component {
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
if (this.props.parentPath === "/") {
|
||||
if (this.props.parentPath === '/') {
|
||||
this.setState({parentPath: this.props.parentPath});
|
||||
} else {
|
||||
this.setState({parentPath: this.props.parentPath + "/"});
|
||||
this.setState({parentPath: this.props.parentPath + '/'});
|
||||
}
|
||||
this.newInput.focus();
|
||||
this.newInput.setSelectionRange(0,0);
|
||||
@@ -46,7 +54,7 @@ class CreateFile extends React.Component {
|
||||
render() {
|
||||
return (
|
||||
<Modal isOpen={true} toggle={this.toggle}>
|
||||
<ModalHeader toggle={this.toggle}>{gettext("New File")}</ModalHeader>
|
||||
<ModalHeader toggle={this.toggle}>{gettext('New File')}</ModalHeader>
|
||||
<ModalBody>
|
||||
<Form>
|
||||
<FormGroup row>
|
||||
@@ -54,20 +62,22 @@ class CreateFile extends React.Component {
|
||||
<Col sm={9} className="parent-path"><FormText>{this.state.parentPath}</FormText></Col>
|
||||
</FormGroup>
|
||||
<FormGroup row>
|
||||
<Label for="fileName" sm={3}>{gettext("Name")}: </Label>
|
||||
<Label for="fileName" sm={3}>{gettext('Name')}: </Label>
|
||||
<Col sm={9}>
|
||||
<Input onKeyPress={this.handleKeyPress} innerRef={input => {this.newInput = input}} id="fileName" placeholder={gettext("newName")} value={this.state.childName} onChange={this.handleChange}/>
|
||||
<Input onKeyPress={this.handleKeyPress} innerRef={input => {this.newInput = input;}} id="fileName" placeholder={gettext('newName')} value={this.state.childName} onChange={this.handleChange}/>
|
||||
</Col>
|
||||
</FormGroup>
|
||||
</Form>
|
||||
</ModalBody>
|
||||
<ModalFooter>
|
||||
<Button color="primary" onClick={this.handleSubmit}>{gettext("Submit")}</Button>
|
||||
<Button color="secondary" onClick={this.toggle}>{gettext("Cancel")}</Button>
|
||||
<Button color="primary" onClick={this.handleSubmit}>{gettext('Submit')}</Button>
|
||||
<Button color="secondary" onClick={this.toggle}>{gettext('Cancel')}</Button>
|
||||
</ModalFooter>
|
||||
</Modal>
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
CreateFile.propTypes = propTypes;
|
||||
|
||||
export default CreateFile;
|
||||
|
@@ -1,7 +1,15 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { Button, Modal, ModalHeader, Input, ModalBody, ModalFooter, Form, FormGroup, Label, Col, FormText } from 'reactstrap';
|
||||
import { gettext } from '../../utils/constants';
|
||||
|
||||
const propTypes = {
|
||||
fileType: PropTypes.string,
|
||||
parentPath: PropTypes.string.isRequired,
|
||||
onAddFolder: PropTypes.func.isRequired,
|
||||
addFolderCancel: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
class CreateForder extends React.Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
@@ -9,17 +17,17 @@ class CreateForder extends React.Component {
|
||||
parentPath: '',
|
||||
childName: ''
|
||||
};
|
||||
this.newInput = React.createRef()
|
||||
this.newInput = React.createRef();
|
||||
}
|
||||
|
||||
handleChange = (e) => {
|
||||
this.setState({
|
||||
childName: e.target.value,
|
||||
})
|
||||
});
|
||||
}
|
||||
|
||||
handleSubmit = () => {
|
||||
let path = this.state.parentPath + this.state.childName
|
||||
let path = this.state.parentPath + this.state.childName;
|
||||
this.props.onAddFolder(path);
|
||||
}
|
||||
|
||||
@@ -34,10 +42,10 @@ class CreateForder extends React.Component {
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
if (this.props.parentPath === "/") {
|
||||
if (this.props.parentPath === '/') {
|
||||
this.setState({parentPath: this.props.parentPath});
|
||||
} else {
|
||||
this.setState({parentPath: this.props.parentPath + "/"});
|
||||
this.setState({parentPath: this.props.parentPath + '/'});
|
||||
}
|
||||
this.newInput.focus();
|
||||
this.newInput.setSelectionRange(0,0);
|
||||
@@ -46,7 +54,7 @@ class CreateForder extends React.Component {
|
||||
render() {
|
||||
return (
|
||||
<Modal isOpen={true} toggle={this.toggle}>
|
||||
<ModalHeader toggle={this.toggle}>{gettext("New Folder")}</ModalHeader>
|
||||
<ModalHeader toggle={this.toggle}>{gettext('New Folder')}</ModalHeader>
|
||||
<ModalBody>
|
||||
<Form>
|
||||
<FormGroup row>
|
||||
@@ -54,20 +62,22 @@ class CreateForder extends React.Component {
|
||||
<Col sm={9} className="parent-path"><FormText>{this.state.parentPath}</FormText></Col>
|
||||
</FormGroup>
|
||||
<FormGroup row>
|
||||
<Label for="fileName" sm={3}>{gettext("Name")}: </Label>
|
||||
<Label for="fileName" sm={3}>{gettext('Name')}: </Label>
|
||||
<Col sm={9}>
|
||||
<Input onKeyPress={this.handleKeyPress} innerRef={input => {this.newInput = input}} id="fileName" placeholder={gettext("newName")} value={this.state.childName} onChange={this.handleChange}/>
|
||||
<Input onKeyPress={this.handleKeyPress} innerRef={input => {this.newInput = input;}} id="fileName" placeholder={gettext('newName')} value={this.state.childName} onChange={this.handleChange}/>
|
||||
</Col>
|
||||
</FormGroup>
|
||||
</Form>
|
||||
</ModalBody>
|
||||
<ModalFooter>
|
||||
<Button color="primary" onClick={this.handleSubmit}>{gettext("Submit")}</Button>
|
||||
<Button color="secondary" onClick={this.toggle}>{gettext("Cancel")}</Button>
|
||||
<Button color="primary" onClick={this.handleSubmit}>{gettext('Submit')}</Button>
|
||||
<Button color="secondary" onClick={this.toggle}>{gettext('Cancel')}</Button>
|
||||
</ModalFooter>
|
||||
</Modal>
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
CreateForder.propTypes = propTypes;
|
||||
|
||||
export default CreateForder;
|
||||
|
@@ -1,7 +1,14 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { gettext } from '../../utils/constants';
|
||||
import { Button, Modal, ModalHeader, Input, ModalBody, ModalFooter } from 'reactstrap';
|
||||
|
||||
const propTypes = {
|
||||
currentNode: PropTypes.object,
|
||||
onRename: PropTypes.func.isRequired,
|
||||
toggleCancel: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
class Rename extends React.Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
@@ -75,4 +82,6 @@ class Rename extends React.Component {
|
||||
}
|
||||
}
|
||||
|
||||
Rename.propTypes = propTypes;
|
||||
|
||||
export default Rename;
|
||||
|
@@ -29,7 +29,7 @@ class OperationMenu extends React.Component {
|
||||
repo: repo,
|
||||
is_repo_owner: is_repo_owner
|
||||
});
|
||||
})
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
|
@@ -8,6 +8,7 @@ moment.locale(lang);
|
||||
const propTypes = {
|
||||
isItemFreezed: PropTypes.bool.isRequired,
|
||||
onMenuToggleClick: PropTypes.func.isRequired,
|
||||
draft: PropTypes.object.isRequired,
|
||||
};
|
||||
|
||||
class DraftListItem extends React.Component {
|
||||
@@ -49,14 +50,14 @@ class DraftListItem extends React.Component {
|
||||
let filePath = draft.draft_file_path;
|
||||
let repoID = draft.origin_repo_id;
|
||||
let url = siteRoot + 'lib/' + repoID + '/file' + filePath + '?mode=edit&draft_id=' + draft.id;
|
||||
window.open(url)
|
||||
window.open(url);
|
||||
}
|
||||
|
||||
onLibraryClick = () => {
|
||||
let draft = this.props.draft;
|
||||
let repoID = draft.origin_repo_id;
|
||||
let url = siteRoot + '#common/lib/' + repoID;
|
||||
window.open(url)
|
||||
window.open(url);
|
||||
}
|
||||
|
||||
onReviewClick = () => {
|
||||
@@ -77,7 +78,7 @@ class DraftListItem extends React.Component {
|
||||
localTime = moment(localTime).fromNow();
|
||||
return (
|
||||
<tr className={this.state.highlight} onMouseEnter={this.onMouseEnter} onMouseLeave={this.onMouseLeave}>
|
||||
<td className="icon"><img src={siteRoot + 'media/img/file/192/txt.png'} /></td>
|
||||
<td className="icon"><img src={siteRoot + 'media/img/file/192/txt.png'} alt='icon' /></td>
|
||||
<td className="name a-simulate" onClick={this.onDraftEditClick}>{fileName}</td>
|
||||
<td className="library a-simulate" onClick={this.onLibraryClick}>{draft.repo_name}</td>
|
||||
<td className="review">
|
||||
|
@@ -3,10 +3,12 @@ import PropTypes from 'prop-types';
|
||||
import { gettext } from '../../utils/constants';
|
||||
|
||||
const propTypes = {
|
||||
currentDraft: PropTypes.object.isRequired,
|
||||
isMenuShow: PropTypes.bool.isRequired,
|
||||
menuPosition: PropTypes.object.isRequired,
|
||||
onDeleteHandler: PropTypes.func.isRequired,
|
||||
onPublishHandler: PropTypes.func.isRequired
|
||||
onPublishHandler: PropTypes.func.isRequired,
|
||||
onReviewHandler: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
class DraftListMenu extends React.Component {
|
||||
|
@@ -1,9 +1,9 @@
|
||||
import React from 'react';
|
||||
import PropsType from 'prop-types';
|
||||
import PropTypes from 'prop-types';
|
||||
import { siteRoot, mediaUrl, logoPath, logoWidth, logoHeight, siteTitle } from '../utils/constants';
|
||||
|
||||
const propsType = {
|
||||
onCloseSidePanel: PropsType.func.isRequired,
|
||||
const propTypes = {
|
||||
onCloseSidePanel: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
class Logo extends React.Component {
|
||||
@@ -14,22 +14,22 @@ class Logo extends React.Component {
|
||||
|
||||
render() {
|
||||
return (
|
||||
<div className="top-logo">
|
||||
<a href={siteRoot} id="logo">
|
||||
<img src={mediaUrl + logoPath} height={logoHeight} width={logoWidth} title={siteTitle} alt="logo" />
|
||||
</a>
|
||||
<a
|
||||
className="sf2-icon-x1 sf-popover-close side-panel-close op-icon d-md-none"
|
||||
onClick={this.closeSide}
|
||||
title="Close"
|
||||
aria-label="Close"
|
||||
>
|
||||
</a>
|
||||
</div>
|
||||
<div className="top-logo">
|
||||
<a href={siteRoot} id="logo">
|
||||
<img src={mediaUrl + logoPath} height={logoHeight} width={logoWidth} title={siteTitle} alt="logo" />
|
||||
</a>
|
||||
<a
|
||||
className="sf2-icon-x1 sf-popover-close side-panel-close op-icon d-md-none"
|
||||
onClick={this.closeSide}
|
||||
title="Close"
|
||||
aria-label="Close"
|
||||
>
|
||||
</a>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
Logo.propsType = propsType;
|
||||
Logo.propTypes = propTypes;
|
||||
|
||||
export default Logo;
|
||||
|
@@ -1,6 +1,12 @@
|
||||
import React, { Component } from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import CommonToolbar from './toolbar/common-toolbar';
|
||||
|
||||
const propTypes = {
|
||||
children: PropTypes.object.isRequired,
|
||||
onShowSidePanel: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
class MainPanel extends Component {
|
||||
|
||||
onSearchedClick = () => {
|
||||
@@ -24,4 +30,6 @@ class MainPanel extends Component {
|
||||
}
|
||||
}
|
||||
|
||||
MainPanel.propTypes = propTypes;
|
||||
|
||||
export default MainPanel;
|
||||
|
@@ -1,8 +1,13 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { Link } from '@reach/router';
|
||||
import { gettext, siteRoot } from '../utils/constants';
|
||||
import { seafileAPI } from '../utils/seafile-api';
|
||||
|
||||
const propTypes = {
|
||||
currentTab: PropTypes.string.isRequired,
|
||||
};
|
||||
|
||||
class MainSideNav extends React.Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
@@ -23,14 +28,14 @@ class MainSideNav extends React.Component {
|
||||
grpsExtend = () => {
|
||||
this.setState({
|
||||
groupsExtended: !this.state.groupsExtended,
|
||||
})
|
||||
});
|
||||
this.loadGroups();
|
||||
}
|
||||
|
||||
shExtend = () => {
|
||||
this.setState({
|
||||
sharedExtended: !this.state.sharedExtended,
|
||||
})
|
||||
});
|
||||
}
|
||||
|
||||
loadGroups = () => {
|
||||
@@ -40,14 +45,14 @@ class MainSideNav extends React.Component {
|
||||
this.groupsHeight = (data.length + 1) * _this.listHeight;
|
||||
_this.setState({
|
||||
groupItems: data
|
||||
})
|
||||
})
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
tabItemClick = (param) => {
|
||||
this.setState({
|
||||
currentTab: param
|
||||
})
|
||||
});
|
||||
}
|
||||
|
||||
renderSharedGroups() {
|
||||
@@ -59,8 +64,8 @@ class MainSideNav extends React.Component {
|
||||
<ul className={`grp-list ${this.state.groupsExtended ? 'side-panel-slide' : 'side-panel-slide-up'}`} style={style}>
|
||||
<li className={this.state.currentTab === 'groups' ? 'tab-cur' : ''}>
|
||||
<a href={siteRoot + '#groups/'} onClick={() => this.tabItemClick('groups')}>
|
||||
<span className="sharp" aria-hidden="true">#</span>
|
||||
All Groups
|
||||
<span className="sharp" aria-hidden="true">#</span>
|
||||
{gettext('All Groups')}
|
||||
</a>
|
||||
</li>
|
||||
{this.state.groupItems.map(item => {
|
||||
@@ -71,10 +76,10 @@ class MainSideNav extends React.Component {
|
||||
{item.name}
|
||||
</a>
|
||||
</li>
|
||||
)
|
||||
);
|
||||
})}
|
||||
</ul>
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
renderSharedAdmin() {
|
||||
@@ -107,7 +112,7 @@ class MainSideNav extends React.Component {
|
||||
</a>
|
||||
</li>
|
||||
</ul>
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
render() {
|
||||
@@ -129,13 +134,13 @@ class MainSideNav extends React.Component {
|
||||
</a>
|
||||
</li>
|
||||
<li className={`tab ${this.state.currentTab === 'org' ? 'tab-cur' : ''}`} onClick={() => this.tabItemClick('org')}>
|
||||
<a href={ siteRoot + '#org/' } className="ellipsis" title={gettext('Shared with all')}>
|
||||
<span className="sf2-icon-organization" aria-hidden="true"></span>
|
||||
{gettext('Shared with all')}
|
||||
<a href={ siteRoot + '#org/' } className="ellipsis" title={gettext('Shared with all')}>
|
||||
<span className="sf2-icon-organization" aria-hidden="true"></span>
|
||||
{gettext('Shared with all')}
|
||||
</a>
|
||||
</li>
|
||||
<li className="tab" id="group-nav">
|
||||
<a href="#" className="ellipsis user-select-no" title={gettext('Shared with groups')} onClick={this.grpsExtend}>
|
||||
<a className="ellipsis user-select-no" title={gettext('Shared with groups')} onClick={this.grpsExtend}>
|
||||
<span className={`toggle-icon float-right fas ${this.state.groupsExtended ?'fa-caret-down':'fa-caret-left'}`} aria-hidden="true"></span>
|
||||
<span className="sf2-icon-group" aria-hidden="true"></span>
|
||||
{gettext('Shared with groups')}
|
||||
@@ -171,7 +176,7 @@ class MainSideNav extends React.Component {
|
||||
</Link>
|
||||
</li>
|
||||
<li className="tab" id="share-admin-nav">
|
||||
<a href="#" className="ellipsis user-select-no" title={gettext('Share Admin')} onClick={this.shExtend}>
|
||||
<a className="ellipsis user-select-no" title={gettext('Share Admin')} onClick={this.shExtend}>
|
||||
<span className={`toggle-icon float-right fas ${this.state.sharedExtended ? 'fa-caret-down':'fa-caret-left'}`} aria-hidden="true"></span>
|
||||
<span aria-hidden="true" className="sf2-icon-wrench"></span>
|
||||
{gettext('Share Admin')}
|
||||
@@ -181,8 +186,10 @@ class MainSideNav extends React.Component {
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
MainSideNav.propTypes = propTypes;
|
||||
|
||||
export default MainSideNav;
|
||||
|
@@ -1,4 +1,5 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { processor, processorGetAST } from '@seafile/seafile-editor/dist/utils/seafile-markdown2html';
|
||||
import Prism from 'prismjs';
|
||||
import WikiOutline from './wiki-outline';
|
||||
@@ -9,7 +10,13 @@ const gettext = window.gettext;
|
||||
|
||||
require('@seafile/seafile-editor/dist/editor/code-hight-package');
|
||||
|
||||
const contentClass = "wiki-md-viewer-rendered-content";
|
||||
const contentClass = 'wiki-md-viewer-rendered-content';
|
||||
|
||||
const contentPropTypes = {
|
||||
html: PropTypes.string,
|
||||
renderingContent: PropTypes.bool.isRequired,
|
||||
onLinkClick: PropTypes.func.isRequired
|
||||
};
|
||||
|
||||
class MarkdownViewerContent extends React.Component {
|
||||
|
||||
@@ -20,7 +27,7 @@ class MarkdownViewerContent extends React.Component {
|
||||
componentDidUpdate () {
|
||||
Prism.highlightAll();
|
||||
var links = document.querySelectorAll(`.${contentClass} a`);
|
||||
links.forEach((li) => {li.addEventListener("click", this.onLinkClick); });
|
||||
links.forEach((li) => {li.addEventListener('click', this.onLinkClick); });
|
||||
}
|
||||
|
||||
onLinkClick = (event) => {
|
||||
@@ -32,17 +39,28 @@ class MarkdownViewerContent extends React.Component {
|
||||
return (
|
||||
<div>
|
||||
{ this.props.renderingContent ? (
|
||||
<div className={contentClass + " article"}>Loading...</div>
|
||||
<div className={contentClass + ' article'}>Loading...</div>
|
||||
) : (
|
||||
<div ref={(mdContent) => {this.mdContentRef = mdContent;} }
|
||||
className={contentClass + " article"}
|
||||
className={contentClass + ' article'}
|
||||
dangerouslySetInnerHTML={{ __html: this.props.html }}/>
|
||||
)}
|
||||
</div>
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
MarkdownViewerContent.propTypes = contentPropTypes;
|
||||
|
||||
|
||||
const viewerPropTypes = {
|
||||
isFileLoading: PropTypes.bool.isRequired,
|
||||
lastModified: PropTypes.string,
|
||||
latestContributor: PropTypes.string,
|
||||
markdownContent: PropTypes.string,
|
||||
onLinkClick: PropTypes.func.isRequired
|
||||
};
|
||||
|
||||
class MarkdownViewer extends React.Component {
|
||||
|
||||
constructor(props) {
|
||||
@@ -91,7 +109,7 @@ class MarkdownViewer extends React.Component {
|
||||
if (currentId !== this.state.activeId) {
|
||||
this.setState({
|
||||
activeId: currentId
|
||||
})
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -115,7 +133,7 @@ class MarkdownViewer extends React.Component {
|
||||
window.location.href = window.location.href;
|
||||
}
|
||||
}, 100);
|
||||
})
|
||||
});
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
@@ -139,11 +157,11 @@ class MarkdownViewer extends React.Component {
|
||||
_this.setState({
|
||||
navItems: navItems,
|
||||
activeId: currentId
|
||||
})
|
||||
});
|
||||
}else {
|
||||
_this.setState({
|
||||
navItems: []
|
||||
})
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
@@ -155,12 +173,12 @@ class MarkdownViewer extends React.Component {
|
||||
});
|
||||
for (let i = 0; i < headingList.length; i++) {
|
||||
navItems[i] = {};
|
||||
navItems[i].id = '#user-content-' + headingList[i].data.id
|
||||
navItems[i].id = '#user-content-' + headingList[i].data.id;
|
||||
navItems[i].key = i;
|
||||
navItems[i].clazz = '';
|
||||
navItems[i].depth = headingList[i].depth;
|
||||
for (let child of headingList[i].children) {
|
||||
if (child.type === "text") {
|
||||
if (child.type === 'text') {
|
||||
navItems[i].text = child.value;
|
||||
break;
|
||||
}
|
||||
@@ -173,7 +191,7 @@ class MarkdownViewer extends React.Component {
|
||||
if (this.props.isFileLoading) {
|
||||
return (
|
||||
<span className="loading-icon loading-tip"></span>
|
||||
)
|
||||
);
|
||||
}
|
||||
return (
|
||||
<div className="markdown-container" onScroll={this.scrollHandler}>
|
||||
@@ -182,18 +200,20 @@ class MarkdownViewer extends React.Component {
|
||||
renderingContent={this.state.renderingContent} html={this.state.html}
|
||||
onLinkClick={this.props.onLinkClick}
|
||||
/>
|
||||
<p id="wiki-page-last-modified">{gettext("Last modified by")} {this.props.latestContributor}, <span>{this.props.lastModified}</span></p>
|
||||
<p id="wiki-page-last-modified">{gettext('Last modified by')} {this.props.latestContributor}, <span>{this.props.lastModified}</span></p>
|
||||
</div>
|
||||
<div className="markdown-outline">
|
||||
<WikiOutline
|
||||
navItems={this.state.navItems}
|
||||
handleNavItemClick={this.handleNavItemClick}
|
||||
activeId={this.state.activeId}
|
||||
/>
|
||||
<WikiOutline
|
||||
navItems={this.state.navItems}
|
||||
handleNavItemClick={this.handleNavItemClick}
|
||||
activeId={this.state.activeId}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
MarkdownViewer.propTypes = viewerPropTypes;
|
||||
|
||||
export default MarkdownViewer;
|
||||
|
@@ -3,6 +3,7 @@ import PropTypes from 'prop-types';
|
||||
|
||||
const propTypes = {
|
||||
isShow: PropTypes.bool.isRequired,
|
||||
onClick: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
class MenuControl extends React.Component {
|
||||
|
@@ -6,7 +6,9 @@ import { siteRoot, lang } from '../../utils/constants';
|
||||
moment.locale(lang);
|
||||
const propTypes = {
|
||||
isItemFreezed: PropTypes.bool.isRequired,
|
||||
}
|
||||
item: PropTypes.object.isRequired,
|
||||
};
|
||||
|
||||
class ReviewListItem extends React.Component {
|
||||
|
||||
constructor(props) {
|
||||
@@ -34,13 +36,12 @@ class ReviewListItem extends React.Component {
|
||||
|
||||
onReviewsClick = () => {
|
||||
let item = this.props.item;
|
||||
let filePath = item.draft_file_path;
|
||||
let itemID = item.id;
|
||||
window.open(siteRoot + 'drafts/review/' + itemID);
|
||||
}
|
||||
|
||||
getFileName(filePath) {
|
||||
let lastIndex = filePath.lastIndexOf("/");
|
||||
let lastIndex = filePath.lastIndexOf('/');
|
||||
return filePath.slice(lastIndex+1);
|
||||
}
|
||||
|
||||
@@ -52,11 +53,11 @@ class ReviewListItem extends React.Component {
|
||||
|
||||
return (
|
||||
<tr className={this.state.highlight} onMouseEnter={this.onMouseEnter} onMouseLeave={this.onMouseLeave}>
|
||||
<td className="icon" style={{width: "4%"}}><img src={siteRoot + "media/img/file/192/txt.png"} /></td>
|
||||
<td className="name a-simulate" style={{width: "46%"}} onClick={this.onReviewsClick}>{fileName}</td>
|
||||
<td className="icon" style={{width: '4%'}}><img src={siteRoot + 'media/img/file/192/txt.png'} alt="icon"/></td>
|
||||
<td className="name a-simulate" style={{width: '46%'}} onClick={this.onReviewsClick}>{fileName}</td>
|
||||
<td className='library'>{item.draft_origin_repo_name}</td>
|
||||
<td className="status" style={{width: "20%"}}>{item.status}</td>
|
||||
<td className="update" style={{width: "20%"}}>{localTime}</td>
|
||||
<td className="status" style={{width: '20%'}}>{item.status}</td>
|
||||
<td className="update" style={{width: '20%'}}>{localTime}</td>
|
||||
<td className="menu-toggle"></td>
|
||||
</tr>
|
||||
);
|
||||
|
@@ -37,7 +37,7 @@ class ReviewListView extends React.Component {
|
||||
})}
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@@ -1,9 +1,15 @@
|
||||
import React, { Component } from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { repoID, siteRoot } from '../../utils/constants';
|
||||
import SearchResultItem from './search-result-item';
|
||||
import editorUtilities from '../../utils/editor-utilties';
|
||||
import More from '../more';
|
||||
|
||||
const propTypes = {
|
||||
placeholder: PropTypes.string,
|
||||
onSearchedClick: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
class Search extends Component {
|
||||
|
||||
constructor(props) {
|
||||
@@ -237,4 +243,6 @@ class Search extends Component {
|
||||
}
|
||||
}
|
||||
|
||||
Search.propTypes = propTypes;
|
||||
|
||||
export default Search;
|
||||
|
@@ -1,7 +1,12 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { Modal, ModalBody } from 'reactstrap';
|
||||
import { gettext, siteRoot } from '../utils/constants';
|
||||
|
||||
const propTypes = {
|
||||
className: PropTypes.string,
|
||||
};
|
||||
|
||||
class About extends React.Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
@@ -34,11 +39,13 @@ class About extends React.Component {
|
||||
}
|
||||
}
|
||||
|
||||
About.propTypes = propTypes;
|
||||
|
||||
class SideNavFooter extends React.Component {
|
||||
render() {
|
||||
return (
|
||||
<div className="side-nav-footer">
|
||||
<a href={siteRoot + 'help/'} target="_blank" className="item">{gettext('Help')}</a>
|
||||
<a href={siteRoot + 'help/'} target="_blank" rel="noopener noreferrer" className="item">{gettext('Help')}</a>
|
||||
<About />
|
||||
<a href={siteRoot + 'download_client_program/'} className="item last-item">
|
||||
<span aria-hidden="true" className="sf2-icon-monitor vam"></span>{' '}
|
||||
|
@@ -1,8 +1,14 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import Logo from './logo';
|
||||
import MainSideNav from './main-side-nav';
|
||||
import SideNavFooter from './side-nav-footer';
|
||||
|
||||
const propTypes = {
|
||||
isSidePanelClosed: PropTypes.bool.isRequired,
|
||||
currentTab: PropTypes.string.isRequired,
|
||||
onCloseSidePanel: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
class SidePanel extends React.Component {
|
||||
|
||||
@@ -23,4 +29,6 @@ class SidePanel extends React.Component {
|
||||
}
|
||||
}
|
||||
|
||||
SidePanel.propTypes = propTypes;
|
||||
|
||||
export default SidePanel;
|
||||
|
@@ -1,3 +1,3 @@
|
||||
import Toast from './toast'
|
||||
import Toast from './toast';
|
||||
|
||||
export default Toast;
|
||||
|
@@ -7,7 +7,7 @@ class NoticeContainer extends React.Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
this.transitionTime = 300;
|
||||
this.state = {notices: []}
|
||||
this.state = {notices: []};
|
||||
}
|
||||
|
||||
addNotice = (notice) => {
|
||||
|
@@ -4,37 +4,37 @@ import NoticeContainer from './notice-container';
|
||||
import './toast.css';
|
||||
|
||||
function createNotieContainer() {
|
||||
const div = document.createElement('div')
|
||||
document.body.appendChild(div)
|
||||
const noticeContainer = ReactDOM.render(<NoticeContainer />, div)
|
||||
const div = document.createElement('div');
|
||||
document.body.appendChild(div);
|
||||
const noticeContainer = ReactDOM.render(<NoticeContainer />, div);
|
||||
return {
|
||||
addNotice(notice) {
|
||||
return noticeContainer.addNotice(notice)
|
||||
},
|
||||
destroy() {
|
||||
ReactDOM.unmountComponentAtNode(div)
|
||||
document.body.removeChild(div)
|
||||
}
|
||||
}
|
||||
addNotice(notice) {
|
||||
return noticeContainer.addNotice(notice);
|
||||
},
|
||||
destroy() {
|
||||
ReactDOM.unmountComponentAtNode(div);
|
||||
document.body.removeChild(div);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
let noticeContainer
|
||||
let noticeContainer = null;
|
||||
const notice = (type, content, duration = 2000, onClose) => {
|
||||
if (!noticeContainer) noticeContainer = createNotieContainer()
|
||||
return noticeContainer.addNotice({ type, content, duration, onClose })
|
||||
}
|
||||
if (!noticeContainer) noticeContainer = createNotieContainer();
|
||||
return noticeContainer.addNotice({ type, content, duration, onClose });
|
||||
};
|
||||
|
||||
export default {
|
||||
info(content, duration, onClose) {
|
||||
return notice('info', content, duration, onClose)
|
||||
return notice('info', content, duration, onClose);
|
||||
},
|
||||
success(content, duration, onClose) {
|
||||
return notice('success', content, duration, onClose)
|
||||
return notice('success', content, duration, onClose);
|
||||
},
|
||||
warning(content, duration, onClose) {
|
||||
return notice('warning', content, duration, onClose)
|
||||
return notice('warning', content, duration, onClose);
|
||||
},
|
||||
error(content, duration, onClose) {
|
||||
return notice('danger', content, duration, onClose)
|
||||
return notice('danger', content, duration, onClose);
|
||||
}
|
||||
}
|
||||
};
|
@@ -1,7 +1,19 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { serviceUrl } from '../../utils/constants';
|
||||
import OperationGroup from '../dirent-operation/operation-group';
|
||||
|
||||
const propTypes = {
|
||||
isItemFreezed: PropTypes.bool.isRequired,
|
||||
node: PropTypes.object.isRequired,
|
||||
needOperationGroup: PropTypes.bool.isRequired,
|
||||
onItemMenuHide: PropTypes.func.isRequired,
|
||||
onItemMenuShow: PropTypes.func.isRequired,
|
||||
onMainNodeClick: PropTypes.func.isRequired,
|
||||
onDelete: PropTypes.func.isRequired,
|
||||
onDownload: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
class TreeDirList extends React.Component {
|
||||
|
||||
constructor(props) {
|
||||
@@ -68,7 +80,7 @@ class TreeDirList extends React.Component {
|
||||
return (
|
||||
<tr className={this.state.highlight ? 'tr-highlight' : ''} onMouseEnter={this.onMouseEnter} onMouseLeave={this.onMouseLeave} onMouseOver={this.onMouseOver}>
|
||||
<td className="icon">
|
||||
<img src={node.type === 'dir' ? serviceUrl + '/media/img/folder-192.png' : serviceUrl + '/media/img/file/192/txt.png'}></img>
|
||||
<img src={node.type === 'dir' ? serviceUrl + '/media/img/folder-192.png' : serviceUrl + '/media/img/file/192/txt.png'} alt='icon'></img>
|
||||
</td>
|
||||
<td className="name a-simulate" onClick={this.onMainNodeClick}>{node.name}</td>
|
||||
{
|
||||
@@ -93,4 +105,6 @@ class TreeDirList extends React.Component {
|
||||
}
|
||||
}
|
||||
|
||||
TreeDirList.propTypes = propTypes;
|
||||
|
||||
export default TreeDirList;
|
||||
|
@@ -11,7 +11,7 @@ const propTypes = {
|
||||
node: PropTypes.object.isRequired,
|
||||
onMainNodeClick: PropTypes.func.isRequired,
|
||||
onDeleteItem: PropTypes.func.isRequired,
|
||||
}
|
||||
};
|
||||
|
||||
class TreeDirView extends React.Component {
|
||||
|
||||
|
@@ -1,6 +1,16 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import { gettext } from '../../utils/constants';
|
||||
|
||||
const propTypes = {
|
||||
menuPosition: PropTypes.object.isRequired,
|
||||
currentNode: PropTypes.object.isRequired,
|
||||
toggleRename: PropTypes.func.isRequired,
|
||||
toggleDelete: PropTypes.func.isRequired,
|
||||
toggleAddFile: PropTypes.func.isRequired,
|
||||
toggleAddFolder: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
class NodeMenu extends React.Component {
|
||||
|
||||
toggleAddFile = () => {
|
||||
@@ -64,4 +74,6 @@ class NodeMenu extends React.Component {
|
||||
}
|
||||
}
|
||||
|
||||
NodeMenu.propTypes = propTypes;
|
||||
|
||||
export default NodeMenu;
|
||||
|
@@ -1,7 +1,17 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import MenuControl from '../menu-control';
|
||||
import { permission } from '../../utils/constants';
|
||||
|
||||
const propTypes = {
|
||||
isNodeItemFrezee: PropTypes.bool.isRequired,
|
||||
currentFilePath: PropTypes.string.isRequired,
|
||||
paddingLeft: PropTypes.number.isRequired,
|
||||
node: PropTypes.object.isRequired,
|
||||
treeView: PropTypes.object.isRequired,
|
||||
onDirCollapse: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
function sortByType(a, b) {
|
||||
if (a.type == 'dir' && b.type != 'dir') {
|
||||
return -1;
|
||||
@@ -197,4 +207,6 @@ class TreeNodeView extends React.Component {
|
||||
|
||||
}
|
||||
|
||||
TreeNodeView.propTypes = propTypes;
|
||||
|
||||
export default TreeNodeView;
|
||||
|
@@ -1,7 +1,18 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import TreeNodeView from './tree-node-view';
|
||||
import editorUtilities from '../../utils/editor-utilties';
|
||||
|
||||
const propTypes = {
|
||||
permission: PropTypes.string,
|
||||
isNodeItemFrezee: PropTypes.bool.isRequired,
|
||||
currentFilePath: PropTypes.string.isRequired,
|
||||
treeData: PropTypes.object.isRequired,
|
||||
onShowContextMenu: PropTypes.func.isRequired,
|
||||
onNodeClick: PropTypes.func.isRequired,
|
||||
onDirCollapse: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
class TreeView extends React.PureComponent {
|
||||
|
||||
change = (tree) => {
|
||||
@@ -31,7 +42,7 @@ class TreeView extends React.PureComponent {
|
||||
|
||||
render() {
|
||||
if (!this.props.treeData.root) {
|
||||
return <div>Loading...</div>
|
||||
return <div>Loading...</div>;
|
||||
}
|
||||
|
||||
return (
|
||||
@@ -52,4 +63,6 @@ class TreeView extends React.PureComponent {
|
||||
|
||||
}
|
||||
|
||||
TreeView.propTypes = propTypes;
|
||||
|
||||
export default TreeView;
|
||||
|
@@ -11,15 +11,15 @@ class WikiOutlineItem extends React.Component {
|
||||
|
||||
handleNavItemClick = () => {
|
||||
var activeId = this.props.item.id;
|
||||
this.props.handleNavItemClick(activeId)
|
||||
this.props.handleNavItemClick(activeId);
|
||||
}
|
||||
|
||||
render() {
|
||||
let item = this.props.item;
|
||||
let activeIndex = parseInt(this.props.activeIndex);
|
||||
let levelClass = item.depth === 3 ? " textindent-2" : '';
|
||||
let levelClass = item.depth === 3 ? ' textindent-2' : '';
|
||||
let activeClass = item.key === activeIndex ? ' wiki-outline-item-active' : '';
|
||||
let clazz = "wiki-outline-item"+ levelClass + activeClass;
|
||||
let clazz = 'wiki-outline-item'+ levelClass + activeClass;
|
||||
return (
|
||||
<li className={clazz} data-index={item.key} onClick={this.handleNavItemClick}>
|
||||
<a href={item.id} title={item.text}>{item.text}</a>
|
||||
@@ -33,8 +33,12 @@ WikiOutlineItem.propTypes = itemPropTypes;
|
||||
|
||||
const outlinePropTypes = {
|
||||
navItems: PropTypes.array.isRequired,
|
||||
activeId: PropTypes.oneOfType([
|
||||
PropTypes.string,
|
||||
PropTypes.number
|
||||
]).isRequired,
|
||||
handleNavItemClick: PropTypes.func.isRequired,
|
||||
}
|
||||
};
|
||||
|
||||
class WikiOutline extends React.Component {
|
||||
|
||||
@@ -43,7 +47,7 @@ class WikiOutline extends React.Component {
|
||||
this.state = {
|
||||
activeIndex : 0,
|
||||
scrollTop: 0,
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
componentWillReceiveProps(nextProps) {
|
||||
@@ -57,7 +61,7 @@ class WikiOutline extends React.Component {
|
||||
if (item.id === activeId && item.key !== _this.state.activeIndex) {
|
||||
let scrollTop = 0;
|
||||
if (item.key > 20) {
|
||||
scrollTop = - (item.key - 20)*27 + "px";
|
||||
scrollTop = - (item.key - 20)*27 + 'px';
|
||||
if (parseInt(scrollTop) > 0) { // handle scroll quickly;
|
||||
scrollTop = 0;
|
||||
}
|
||||
@@ -65,7 +69,7 @@ class WikiOutline extends React.Component {
|
||||
_this.setState({
|
||||
activeIndex : item.key,
|
||||
scrollTop: scrollTop
|
||||
})
|
||||
});
|
||||
flag = true;
|
||||
}
|
||||
if (flag) {
|
||||
@@ -86,10 +90,10 @@ class WikiOutline extends React.Component {
|
||||
activeIndex={this.state.activeIndex}
|
||||
handleNavItemClick={this.props.handleNavItemClick}
|
||||
/>
|
||||
)
|
||||
);
|
||||
})}
|
||||
</ul>
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user