mirror of
https://github.com/haiwen/seahub.git
synced 2025-09-08 02:10:24 +00:00
Wiki mode improve (#2539)
This commit is contained in:
@@ -77,7 +77,7 @@ class CreateFile extends React.Component {
|
||||
});
|
||||
} else if (pos === 0 ) {
|
||||
this.setState({
|
||||
childName: '(draft)' + this.state.childname,
|
||||
childName: '(draft)' + this.state.childName,
|
||||
isDraft: !this.state.isdraft
|
||||
});
|
||||
} else {
|
||||
@@ -93,10 +93,11 @@ class CreateFile extends React.Component {
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
if (this.props.parentPath === '/') {
|
||||
this.setState({parentPath: this.props.parentPath});
|
||||
let parentPath = this.props.parentPath;
|
||||
if (parentPath[parentPath.length - 1] === '/') { // mainPanel
|
||||
this.setState({parentPath: parentPath});
|
||||
} else {
|
||||
this.setState({parentPath: this.props.parentPath + '/'});
|
||||
this.setState({parentPath: parentPath + '/'}); // sidePanel
|
||||
}
|
||||
this.newInput.focus();
|
||||
this.newInput.setSelectionRange(0,0);
|
||||
|
@@ -42,10 +42,11 @@ class CreateForder extends React.Component {
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
if (this.props.parentPath === '/') {
|
||||
this.setState({parentPath: this.props.parentPath});
|
||||
let parentPath = this.props.parentPath;
|
||||
if (parentPath[parentPath.length - 1] === '/') { // mainPanel
|
||||
this.setState({parentPath: parentPath});
|
||||
} else {
|
||||
this.setState({parentPath: this.props.parentPath + '/'});
|
||||
this.setState({parentPath: parentPath + '/'}); // sidePanel
|
||||
}
|
||||
this.newInput.focus();
|
||||
this.newInput.setSelectionRange(0,0);
|
||||
|
@@ -25,7 +25,7 @@ class DetailListView extends React.Component {
|
||||
|
||||
getDirentPostion = () => {
|
||||
let { repo, direntPath } = this.props;
|
||||
let position = repo.repo_name + '/';
|
||||
let position = repo.repo_name;
|
||||
if (direntPath !== '/') {
|
||||
let index = direntPath.lastIndexOf('/');
|
||||
let path = direntPath.slice(0, index);
|
||||
@@ -40,6 +40,10 @@ class DetailListView extends React.Component {
|
||||
});
|
||||
}
|
||||
|
||||
onFileTagChanged = () => {
|
||||
this.props.onFileTagChanged(this.props.dirent, this.props.direntPath);
|
||||
}
|
||||
|
||||
render() {
|
||||
let { direntType, direntDetail, fileTagList } = this.props;
|
||||
let position = this.getDirentPostion();
|
||||
@@ -64,7 +68,7 @@ class DetailListView extends React.Component {
|
||||
<tr><th width="35%"></th><td width="65%"></td></tr>
|
||||
<tr><th>{gettext('Size')}</th><td>{direntDetail.size}</td></tr>
|
||||
<tr><th>{gettext('Position')}</th><td>{position}</td></tr>
|
||||
<tr><th>{gettext('Last Update')}</th><td>{moment(direntDetail.mtime).format('YYYY-MM-DD')}</td></tr>
|
||||
<tr><th>{gettext('Last Update')}</th><td>{moment(direntDetail.last_modified).fromNow()}</td></tr>
|
||||
<tr className="file-tag-container"><th>{gettext('Tags')}</th>
|
||||
<td>
|
||||
<ul className="file-tag-list">
|
||||
@@ -88,7 +92,7 @@ class DetailListView extends React.Component {
|
||||
fileTagList={fileTagList}
|
||||
filePath={this.props.direntPath}
|
||||
toggleCancel={this.onEditFileTagToggle}
|
||||
onFileTagChanged={this.props.onFileTagChanged}
|
||||
onFileTagChanged={this.onFileTagChanged}
|
||||
/>
|
||||
}
|
||||
</Fragment>
|
||||
|
@@ -6,10 +6,9 @@ import URLDecorator from '../../utils/url-decorator';
|
||||
import Toast from '../toast';
|
||||
import DirentMenu from './dirent-menu';
|
||||
import DirentRename from './dirent-rename';
|
||||
import FileTag from '../../models/file-tag';
|
||||
|
||||
const propTypes = {
|
||||
filePath: PropTypes.string.isRequired,
|
||||
path: PropTypes.string.isRequired,
|
||||
isItemFreezed: PropTypes.bool.isRequired,
|
||||
dirent: PropTypes.object.isRequired,
|
||||
onItemClick: PropTypes.func.isRequired,
|
||||
@@ -22,7 +21,7 @@ const propTypes = {
|
||||
onDirentItemMove: PropTypes.func.isRequired,
|
||||
onDirentItemCopy: PropTypes.func.isRequired,
|
||||
onItemDetails: PropTypes.func.isRequired,
|
||||
updateViewList: PropTypes.func.isRequired,
|
||||
updateDirent: PropTypes.func.isRequired,
|
||||
currentRepo: PropTypes.object,
|
||||
isRepoOwner: PropTypes.bool,
|
||||
};
|
||||
@@ -36,15 +35,13 @@ class DirentListItem extends React.Component {
|
||||
highlight: false,
|
||||
isItemMenuShow: false,
|
||||
menuPosition: {top: 0, left: 0 },
|
||||
fileTagList: [],
|
||||
};
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
document.addEventListener('click', this.onItemMenuHide);
|
||||
this.getFileTag();
|
||||
}
|
||||
|
||||
|
||||
componentWillUnmount() {
|
||||
document.removeEventListener('click', this.onItemMenuHide);
|
||||
}
|
||||
@@ -113,21 +110,21 @@ class DirentListItem extends React.Component {
|
||||
onItemSelected = () => {
|
||||
//todos;
|
||||
}
|
||||
|
||||
|
||||
onItemStarred = () => {
|
||||
let dirent = this.props.dirent;
|
||||
let filePath = this.getDirentPath(dirent);
|
||||
if (dirent.starred) {
|
||||
seafileAPI.unStarFile(repoID, filePath).then(() => {
|
||||
this.props.updateViewList(this.props.filePath);
|
||||
this.props.updateDirent(this.props.dirent, "starred", false);
|
||||
});
|
||||
} else {
|
||||
seafileAPI.starFile(repoID, filePath).then(() => {
|
||||
this.props.updateViewList(this.props.filePath);
|
||||
this.props.updateDirent(this.props.dirent, "starred", true);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
onItemClick = () => {
|
||||
let direntPath = this.getDirentPath(this.props.dirent);
|
||||
this.props.onItemClick(direntPath);
|
||||
@@ -141,13 +138,12 @@ class DirentListItem extends React.Component {
|
||||
|
||||
onItemDelete = (e) => {
|
||||
e.nativeEvent.stopImmediatePropagation(); //for document event
|
||||
let direntPath = this.getDirentPath(this.props.dirent);
|
||||
this.props.onItemDelete(direntPath);
|
||||
this.props.onItemDelete(this.props.dirent);
|
||||
}
|
||||
|
||||
onItemMenuItemClick = (operation) => {
|
||||
switch(operation) {
|
||||
case 'Rename':
|
||||
case 'Rename':
|
||||
this.onRenameMenuItemClick();
|
||||
break;
|
||||
case 'Move':
|
||||
@@ -202,21 +198,20 @@ class DirentListItem extends React.Component {
|
||||
this.onRenameCancel();
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
if (!newName) {
|
||||
let errMessage = 'It is required.';
|
||||
Toast.error(gettext(errMessage));
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
if (newName.indexOf('/') > -1) {
|
||||
let errMessage = 'Name should not include "/".';
|
||||
Toast.error(gettext(errMessage));
|
||||
return false;
|
||||
}
|
||||
|
||||
let direntPath = this.getDirentPath(this.props.dirent);
|
||||
this.props.onItemRename(direntPath, newName);
|
||||
this.props.onItemRename(this.props.dirent, newName);
|
||||
this.onRenameCancel();
|
||||
}
|
||||
|
||||
@@ -226,7 +221,7 @@ class DirentListItem extends React.Component {
|
||||
});
|
||||
this.props.onUnfreezedItem();
|
||||
}
|
||||
|
||||
|
||||
onDirentItemMove = () => {
|
||||
let direntPath = this.getDirentPath(this.props.dirent);
|
||||
this.props.onDirentItemMove(this.props.dirent, direntPath);
|
||||
@@ -252,7 +247,8 @@ class DirentListItem extends React.Component {
|
||||
onLockItem = () => {
|
||||
let filePath = this.getDirentPath(this.props.dirent);
|
||||
seafileAPI.lockfile(repoID, filePath).then(() => {
|
||||
this.props.updateViewList(this.props.filePath);
|
||||
this.props.updateDirent(this.props.dirent, "is_locked", true);
|
||||
this.props.updateDirent(this.props.dirent, "locked_by_me", true);
|
||||
});
|
||||
this.onItemMenuHide();
|
||||
}
|
||||
@@ -260,14 +256,15 @@ class DirentListItem extends React.Component {
|
||||
onUnlockItem = () => {
|
||||
let filePath = this.getDirentPath(this.props.dirent);
|
||||
seafileAPI.unlockfile(repoID, filePath).then(() => {
|
||||
this.props.updateViewList(this.props.filePath);
|
||||
this.props.updateDirent(this.props.dirent, "is_locked", false);
|
||||
this.props.updateDirent(this.props.dirent, "locked_by_me", false);
|
||||
});
|
||||
this.onItemMenuHide();
|
||||
}
|
||||
|
||||
onNewDraft = () => {
|
||||
let filePath = this.getDirentPath(this.props.dirent);
|
||||
seafileAPI.createDraft(repoID,filePath).then(res => {
|
||||
seafileAPI.createDraft(repoID, filePath).then(res => {
|
||||
let draft_file_Path = res.data.draft_file_path;
|
||||
let draftId = res.data.id;
|
||||
let url = URLDecorator.getUrl({type: 'draft_view', repoID: repoID, filePath: draft_file_Path, draftId: draftId});
|
||||
@@ -303,26 +300,10 @@ class DirentListItem extends React.Component {
|
||||
}
|
||||
|
||||
getDirentPath = (dirent) => {
|
||||
let path = this.props.filePath;
|
||||
let path = this.props.path;
|
||||
return path === '/' ? path + dirent.name : path + '/' + dirent.name;
|
||||
}
|
||||
|
||||
getFileTag = () => {
|
||||
if (this.props.dirent.type === 'file' && this.props.dirent.file_tags!== undefined) {
|
||||
let FileTgas = this.props.dirent.file_tags;
|
||||
let fileTagList = [];
|
||||
FileTgas.forEach(item => {
|
||||
let fileTag = new FileTag(item)
|
||||
fileTagList.push(fileTag)
|
||||
});
|
||||
this.setState({fileTagList: fileTagList});
|
||||
}
|
||||
}
|
||||
|
||||
componentWillReceiveProps() {
|
||||
this.getFileTag();
|
||||
}
|
||||
|
||||
render() {
|
||||
let { dirent } = this.props;
|
||||
return (
|
||||
@@ -348,7 +329,7 @@ class DirentListItem extends React.Component {
|
||||
</td>
|
||||
<td>
|
||||
<div className="dirent-item tag-list tag-list-stacked ">
|
||||
{ dirent.type !== 'dir' && this.state.fileTagList.map((fileTag) => {
|
||||
{ dirent.type !== 'dir' && dirent.file_tags.map((fileTag) => {
|
||||
return (
|
||||
<span className={`file-tag bg-${fileTag.color}`} key={fileTag.id} title={fileTag.name}></span>
|
||||
);
|
||||
@@ -357,7 +338,7 @@ class DirentListItem extends React.Component {
|
||||
</td>
|
||||
<td className="operation">
|
||||
{
|
||||
this.state.isOperationShow &&
|
||||
this.state.isOperationShow &&
|
||||
<div className="operations">
|
||||
<ul className="operation-group">
|
||||
<li className="operation-group-item">
|
||||
@@ -374,8 +355,8 @@ class DirentListItem extends React.Component {
|
||||
</li>
|
||||
</ul>
|
||||
{
|
||||
this.state.isItemMenuShow &&
|
||||
<DirentMenu
|
||||
this.state.isItemMenuShow &&
|
||||
<DirentMenu
|
||||
dirent={this.props.dirent}
|
||||
menuPosition={this.state.menuPosition}
|
||||
onMenuItemClick={this.onItemMenuItemClick}
|
||||
|
@@ -10,7 +10,7 @@ import MoveDirentDialog from '../dialog/move-dirent-dialog';
|
||||
import CopyDirentDialog from '../dialog/copy-dirent-dialog';
|
||||
|
||||
const propTypes = {
|
||||
filePath: PropTypes.string.isRequired,
|
||||
path: PropTypes.string.isRequired,
|
||||
direntList: PropTypes.array.isRequired,
|
||||
onItemDelete: PropTypes.func.isRequired,
|
||||
onItemRename: PropTypes.func.isRequired,
|
||||
@@ -18,7 +18,7 @@ const propTypes = {
|
||||
onItemMove: PropTypes.func.isRequired,
|
||||
onItemCopy: PropTypes.func.isRequired,
|
||||
onItemDetails: PropTypes.func.isRequired,
|
||||
updateViewList: PropTypes.func.isRequired,
|
||||
updateDirent: PropTypes.func.isRequired,
|
||||
isDirentListLoading: PropTypes.bool.isRequired,
|
||||
isRepoOwner: PropTypes.bool,
|
||||
currentRepo: PropTypes.object,
|
||||
@@ -42,7 +42,7 @@ class DirentListView extends React.Component {
|
||||
onFreezedItem = () => {
|
||||
this.setState({isItemFreezed: true});
|
||||
}
|
||||
|
||||
|
||||
onUnfreezedItem = () => {
|
||||
this.setState({isItemFreezed: false});
|
||||
}
|
||||
@@ -70,15 +70,15 @@ class DirentListView extends React.Component {
|
||||
onItemMove = (repo, direntPath, moveToDirentPath) => {
|
||||
this.props.onItemMove(repo, direntPath, moveToDirentPath);
|
||||
}
|
||||
|
||||
|
||||
onCancelMove = () => {
|
||||
this.setState({isMoveDialogShow: false});
|
||||
}
|
||||
|
||||
|
||||
onItemCopy = (repo, direntPath, copyToDirentPath) => {
|
||||
this.props.onItemCopy(repo, direntPath, copyToDirentPath);
|
||||
}
|
||||
|
||||
|
||||
onCancelCopy = () => {
|
||||
this.setState({isCopyDialogShow: false});
|
||||
}
|
||||
@@ -90,7 +90,7 @@ class DirentListView extends React.Component {
|
||||
onItemDownload = (dirent, direntPath) => {
|
||||
if (dirent.type === 'dir') {
|
||||
this.setState({isProgressDialogShow: true, progress: 0});
|
||||
editorUtilities.zipDownload(this.props.filePath, dirent.name).then(res => {
|
||||
editorUtilities.zipDownload(this.props.path, dirent.name).then(res => {
|
||||
this.zip_token = res.data['zip_token'];
|
||||
this.addDownloadAnimation();
|
||||
this.interval = setInterval(this.addDownloadAnimation, 1000);
|
||||
@@ -161,14 +161,13 @@ class DirentListView extends React.Component {
|
||||
<DirentListItem
|
||||
key={index}
|
||||
dirent={dirent}
|
||||
filePath={this.props.filePath}
|
||||
path={this.props.path}
|
||||
currentRepo={this.props.currentRepo}
|
||||
isRepoOwner={this.props.isRepoOwner}
|
||||
onItemClick={this.props.onItemClick}
|
||||
onRenameMenuItemClick={this.onRenameMenuItemClick}
|
||||
onItemDelete={this.props.onItemDelete}
|
||||
onItemRename={this.props.onItemRename}
|
||||
updateViewList={this.props.updateViewList}
|
||||
isItemFreezed={this.state.isItemFreezed}
|
||||
onFreezedItem={this.onFreezedItem}
|
||||
onUnfreezedItem={this.onUnfreezedItem}
|
||||
@@ -176,30 +175,31 @@ class DirentListView extends React.Component {
|
||||
onDirentItemMove={this.onDirentItemMove}
|
||||
onDirentItemCopy={this.onDirentItemCopy}
|
||||
onItemDetails={this.onItemDetails}
|
||||
updateDirent={this.props.updateDirent}
|
||||
/>
|
||||
);
|
||||
})
|
||||
}
|
||||
</tbody>
|
||||
</table>
|
||||
{this.state.isProgressDialogShow &&
|
||||
{this.state.isProgressDialogShow &&
|
||||
<ZipDownloadDialog progress={this.state.progress} onCancelDownload={this.onCancelDownload}
|
||||
/>
|
||||
}
|
||||
{this.state.isMoveDialogShow &&
|
||||
<MoveDirentDialog
|
||||
dirent={this.state.currentDirent}
|
||||
direntPath={this.state.direntPath}
|
||||
<MoveDirentDialog
|
||||
dirent={this.state.currentDirent}
|
||||
direntPath={this.state.direntPath}
|
||||
onItemMove={this.props.onItemMove}
|
||||
onCancelMove={this.onCancelMove}
|
||||
/>
|
||||
}
|
||||
{this.state.isCopyDialogShow &&
|
||||
<CopyDirentDialog
|
||||
dirent={this.state.currentDirent}
|
||||
direntPath={this.state.direntPath}
|
||||
<CopyDirentDialog
|
||||
dirent={this.state.currentDirent}
|
||||
direntPath={this.state.direntPath}
|
||||
onItemCopy={this.props.onItemCopy}
|
||||
onCancelCopy={this.onCancelCopy}
|
||||
onCancelCopy={this.onCancelCopy}
|
||||
/>
|
||||
}
|
||||
</Fragment>
|
||||
|
@@ -23,7 +23,7 @@ const propTypes = {
|
||||
minFileSizeErrorCallback: PropTypes.func,
|
||||
fileTypeErrorCallback: PropTypes.func,
|
||||
dragAndDrop: PropTypes.bool.isRequired,
|
||||
filePath: PropTypes.string.isRequired,
|
||||
path: PropTypes.string.isRequired,
|
||||
onFileSuccess: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
@@ -71,7 +71,7 @@ class FileUploader extends React.Component {
|
||||
|
||||
bindCallbackHandler = () => {
|
||||
let {maxFilesErrorCallback, minFileSizeErrorCallback, maxFileSizeErrorCallback, fileTypeErrorCallback } = this.props;
|
||||
|
||||
|
||||
if (maxFilesErrorCallback) {
|
||||
this.resumable.opts.maxFilesErrorCallback = this.props.maxFilesErrorCallback;
|
||||
}
|
||||
@@ -112,7 +112,7 @@ class FileUploader extends React.Component {
|
||||
return; // is upload a folder;
|
||||
}
|
||||
if (enableResumableFileUpload) {
|
||||
seafileAPI.getFileUploadedBytes(repoID, this.props.filePath, file.fileName).then(res => {
|
||||
seafileAPI.getFileUploadedBytes(repoID, this.props.path, file.fileName).then(res => {
|
||||
let uploadedBytes = res.data.uploadedBytes;
|
||||
let offset = Math.floor(uploadedBytes / (1024 * 1024));
|
||||
file.markChunksCompleted(offset);
|
||||
@@ -122,7 +122,7 @@ class FileUploader extends React.Component {
|
||||
|
||||
onFileAdded = (resumableFile, files) => {
|
||||
//get parent_dir、relative_path;
|
||||
let filePath = this.props.filePath === '/' ? '/' : this.props.filePath + '/';
|
||||
let path = this.props.path === '/' ? '/' : this.props.path + '/';
|
||||
let fileName = resumableFile.fileName;
|
||||
let relativePath = resumableFile.relativePath;
|
||||
let isFile = fileName === relativePath;
|
||||
@@ -131,12 +131,12 @@ class FileUploader extends React.Component {
|
||||
resumableFile.formData = {};
|
||||
if (isFile) {
|
||||
resumableFile.formData = {
|
||||
parent_dir: filePath,
|
||||
parent_dir: path,
|
||||
};
|
||||
} else {
|
||||
let relative_path = relativePath.slice(0, relativePath.lastIndexOf('/') + 1);
|
||||
resumableFile.formData = {
|
||||
parent_dir: filePath,
|
||||
parent_dir: path,
|
||||
relative_path: relative_path
|
||||
};
|
||||
}
|
||||
@@ -168,7 +168,7 @@ class FileUploader extends React.Component {
|
||||
}
|
||||
|
||||
filesAddedComplete = (resumable, files) => {
|
||||
// single file uploading can check repetition, because custom dialog conn't prevent program execution;
|
||||
// single file uploading can check repetition, because custom dialog conn't prevent program execution;
|
||||
}
|
||||
|
||||
setUploadFileList = (files) => {
|
||||
@@ -198,7 +198,7 @@ class FileUploader extends React.Component {
|
||||
}
|
||||
return item;
|
||||
});
|
||||
|
||||
|
||||
this.setState({uploadFileList: uploadFileList});
|
||||
}
|
||||
|
||||
@@ -216,7 +216,7 @@ class FileUploader extends React.Component {
|
||||
}
|
||||
|
||||
onComplete = () => {
|
||||
|
||||
|
||||
}
|
||||
|
||||
onPause = () => [
|
||||
@@ -238,7 +238,7 @@ class FileUploader extends React.Component {
|
||||
onCancel = () => {
|
||||
|
||||
}
|
||||
|
||||
|
||||
setHeaders = (resumableFile, resumable) => {
|
||||
let offset = resumable.offset;
|
||||
let chunkSize = resumable.getOpt('chunkSize');
|
||||
@@ -249,13 +249,13 @@ class FileUploader extends React.Component {
|
||||
if (fileSize - resumable.endByte < chunkSize && !resumable.getOpt('forceChunkSize')) {
|
||||
endByte = fileSize;
|
||||
}
|
||||
|
||||
|
||||
let headers = {
|
||||
'Accept': 'application/json; text/javascript, */*; q=0.01',
|
||||
'Content-Disposition': 'attachment; filename="' + encodeURI(resumableFile.fileName) + '"',
|
||||
'Content-Range': 'bytes ' + startByte + '-' + endByte + '/' + fileSize,
|
||||
};
|
||||
|
||||
|
||||
return headers;
|
||||
}
|
||||
|
||||
@@ -277,7 +277,7 @@ class FileUploader extends React.Component {
|
||||
onFileUpload = () => {
|
||||
this.uploadInput.removeAttribute('webkitdirectory');
|
||||
this.uploadInput.click();
|
||||
seafileAPI.getUploadLink(repoID, this.props.filePath).then(res => {
|
||||
seafileAPI.getUploadLink(repoID, this.props.path).then(res => {
|
||||
this.resumable.opts.target = res.data;
|
||||
});
|
||||
}
|
||||
@@ -285,14 +285,14 @@ class FileUploader extends React.Component {
|
||||
onFolderUpload = () => {
|
||||
this.uploadInput.setAttribute('webkitdirectory', 'webkitdirectory');
|
||||
this.uploadInput.click();
|
||||
seafileAPI.getUploadLink(repoID, this.props.filePath).then(res => {
|
||||
seafileAPI.getUploadLink(repoID, this.props.path).then(res => {
|
||||
this.resumable.opts.target = res.data;
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
onDragStart = () => {
|
||||
this.uploadInput.setAttribute('webkitdirectory', 'webkitdirectory');
|
||||
seafileAPI.getUploadLink(repoID, this.props.filePath).then(res => {
|
||||
seafileAPI.getUploadLink(repoID, this.props.path).then(res => {
|
||||
this.resumable.opts.target = res.data;
|
||||
});
|
||||
}
|
||||
@@ -328,13 +328,13 @@ class FileUploader extends React.Component {
|
||||
// this.setState({isUploadRemindDialogShow: false});
|
||||
|
||||
this.setUploadFileList(this.resumable.files);
|
||||
|
||||
|
||||
this.resumable.upload();
|
||||
}
|
||||
|
||||
uploadFile = () => {
|
||||
// this.setState({isUploadRemindDialogShow: false});
|
||||
|
||||
|
||||
this.setUploadFileList(this.resumable.files);
|
||||
this.resumable.upload();
|
||||
}
|
||||
@@ -352,7 +352,7 @@ class FileUploader extends React.Component {
|
||||
</div>
|
||||
{
|
||||
this.state.isUploadProgressDialogShow &&
|
||||
<UploadProgressDialog
|
||||
<UploadProgressDialog
|
||||
uploadFileList={this.state.uploadFileList}
|
||||
totalProgress={this.state.totalProgress}
|
||||
onMinimizeUploadDialog={this.onMinimizeUploadDialog}
|
||||
@@ -362,7 +362,7 @@ class FileUploader extends React.Component {
|
||||
}
|
||||
{
|
||||
this.state.isUploadRemindDialogShow &&
|
||||
<UploadRemindDialog
|
||||
<UploadRemindDialog
|
||||
currentResumableFile={this.state.currentResumableFile}
|
||||
replaceRepetitionFile={this.replaceRepetitionFile}
|
||||
uploadFile={this.uploadFile}
|
||||
|
@@ -7,7 +7,7 @@ import CreateTagDialog from '../dialog/create-tag-dialog';
|
||||
import UpdateTagDialog from '../dialog/update-tag-dialog';
|
||||
|
||||
const propTypes = {
|
||||
filePath: PropTypes.string.isRequired
|
||||
path: PropTypes.string.isRequired
|
||||
};
|
||||
|
||||
class PathToolbar extends React.Component {
|
||||
@@ -42,15 +42,13 @@ class PathToolbar extends React.Component {
|
||||
}
|
||||
|
||||
isMarkdownFile(filePath) {
|
||||
let lastIndex = filePath.lastIndexOf('/');
|
||||
let name = filePath.slice(lastIndex + 1);
|
||||
let name = Utils.getFileName(filePath);
|
||||
return name.indexOf('.md') > -1 ? true : false;
|
||||
}
|
||||
|
||||
|
||||
render() {
|
||||
let isFile = this.isMarkdownFile(this.props.filePath);
|
||||
let index = this.props.filePath.lastIndexOf('/');
|
||||
let name = this.props.filePath.slice(index + 1);
|
||||
let isFile = this.isMarkdownFile(this.props.path);
|
||||
let name = Utils.getFileName(this.props.path);
|
||||
let trashUrl = siteRoot + 'repo/recycle/' + repoID + '/?referer=' + encodeURIComponent(location.href);
|
||||
let historyUrl = siteRoot + 'repo/history/' + repoID + '/?referer=' + encodeURIComponent(location.href);
|
||||
if ( (name === slug || name === '') && !isFile && permission) {
|
||||
@@ -62,8 +60,8 @@ class PathToolbar extends React.Component {
|
||||
<li className="toolbar-item"><a className="op-link sf2-icon-history" href={historyUrl} title={gettext('History')} aria-label={gettext('History')}></a></li>
|
||||
</ul>
|
||||
{
|
||||
this.state.isListRepoTagShow &&
|
||||
<ListTagDialog
|
||||
this.state.isListRepoTagShow &&
|
||||
<ListTagDialog
|
||||
onListTagCancel={this.onListRepoTagToggle}
|
||||
onCreateRepoTag={this.onCreateRepoTagToggle}
|
||||
onUpdateRepoTag={this.onUpdateRepoTagToggle}
|
||||
@@ -71,27 +69,27 @@ class PathToolbar extends React.Component {
|
||||
}
|
||||
{
|
||||
this.state.isCreateRepoTagShow &&
|
||||
<CreateTagDialog
|
||||
<CreateTagDialog
|
||||
toggleCancel={this.onCreateRepoTagToggle}
|
||||
/>
|
||||
}
|
||||
{
|
||||
this.state.isUpdateRepoTagShow &&
|
||||
<UpdateTagDialog
|
||||
currentTag={this.state.currentTag}
|
||||
<UpdateTagDialog
|
||||
currentTag={this.state.currentTag}
|
||||
toggleCancel={this.onUpdateRepoTagToggle}
|
||||
/>
|
||||
}
|
||||
</Fragment>
|
||||
);
|
||||
} else if ( !isFile && permission) {
|
||||
} else if (!isFile && permission) {
|
||||
return (
|
||||
<ul className="path-toolbar">
|
||||
<li className="toolbar-item"><a className="op-link sf2-icon-trash" href={trashUrl} title={gettext('Trash')} aria-label={gettext('Trash')}></a></li>
|
||||
</ul>
|
||||
);
|
||||
} else if (permission) {
|
||||
historyUrl = siteRoot + 'repo/file_revisions/' + repoID + '/?p=' + Utils.encodePath(this.props.filePath) + '&referer=' + encodeURIComponent(location.href);
|
||||
historyUrl = siteRoot + 'repo/file_revisions/' + repoID + '/?p=' + Utils.encodePath(this.props.path) + '&referer=' + encodeURIComponent(location.href);
|
||||
return (
|
||||
<ul className="path-toolbar">
|
||||
<li className="toolbar-item"><a className="op-link sf2-icon-history" href={historyUrl} title={gettext('History')} aria-label={gettext('History')}></a></li>
|
||||
|
@@ -16,7 +16,7 @@ class Node {
|
||||
|
||||
return node;
|
||||
}
|
||||
|
||||
|
||||
constructor({name, type, size, last_update_time, permission, parent_path, isExpanded, children}) {
|
||||
this.name = name;
|
||||
this.type = type;
|
||||
@@ -28,7 +28,7 @@ class Node {
|
||||
this.children = children ? children : [];
|
||||
this.parent = null;
|
||||
}
|
||||
|
||||
|
||||
clone() {
|
||||
var n = new Node({
|
||||
name: this.name,
|
||||
@@ -39,10 +39,10 @@ class Node {
|
||||
parent_path: this.parent_path,
|
||||
isExpanded: this.isExpanded
|
||||
});
|
||||
n.children = this.children.map(child => {
|
||||
var newChild = child.clone();
|
||||
newChild.parent = n;
|
||||
return newChild;
|
||||
n.children = this.children.map(child => {
|
||||
var newChild = child.clone();
|
||||
newChild.parent = n;
|
||||
return newChild;
|
||||
});
|
||||
return n;
|
||||
}
|
||||
@@ -122,4 +122,4 @@ class Node {
|
||||
|
||||
}
|
||||
|
||||
export default Node;
|
||||
export default Node;
|
||||
|
@@ -5,7 +5,7 @@ import { permission } from '../../utils/constants';
|
||||
|
||||
const propTypes = {
|
||||
isNodeItemFrezee: PropTypes.bool.isRequired,
|
||||
currentFilePath: PropTypes.string.isRequired,
|
||||
currentPath: PropTypes.string.isRequired,
|
||||
paddingLeft: PropTypes.number.isRequired,
|
||||
node: PropTypes.object.isRequired,
|
||||
treeView: PropTypes.object.isRequired,
|
||||
@@ -31,10 +31,10 @@ class TreeNodeView extends React.Component {
|
||||
};
|
||||
}
|
||||
|
||||
onClick = (e) => {
|
||||
onClick = () => {
|
||||
// e.nativeEvent.stopImmediatePropagation();
|
||||
let { node } = this.props;
|
||||
this.props.treeView.onNodeClick(e, node);
|
||||
this.props.treeView.onNodeClick(node);
|
||||
}
|
||||
|
||||
onMouseEnter = () => {
|
||||
@@ -55,7 +55,7 @@ class TreeNodeView extends React.Component {
|
||||
|
||||
handleCollapse = (e) => {
|
||||
e.stopPropagation();
|
||||
this.props.onDirCollapse(e, this.props.node);
|
||||
this.props.onDirCollapse(this.props.node);
|
||||
}
|
||||
|
||||
onDragStart = (e) => {
|
||||
@@ -121,7 +121,7 @@ class TreeNodeView extends React.Component {
|
||||
paddingLeft={this.props.paddingLeft}
|
||||
treeView={this.props.treeView}
|
||||
isNodeItemFrezee={this.props.isNodeItemFrezee}
|
||||
currentFilePath={this.props.currentFilePath}
|
||||
currentPath={this.props.currentPath}
|
||||
onDirCollapse={this.props.onDirCollapse}
|
||||
/>
|
||||
);
|
||||
@@ -138,7 +138,7 @@ class TreeNodeView extends React.Component {
|
||||
let isShow = (this.props.node.path === this.props.currentFilePath);
|
||||
return (
|
||||
<div className="right-icon">
|
||||
<MenuControl
|
||||
<MenuControl
|
||||
isShow={this.state.isMenuIconShow || isShow}
|
||||
onClick={this.onMenuControlClick}
|
||||
/>
|
||||
@@ -186,11 +186,11 @@ class TreeNodeView extends React.Component {
|
||||
|
||||
return (
|
||||
<div type={type} className="tree-node" style={styles}>
|
||||
<div
|
||||
onMouseLeave={this.onMouseLeave}
|
||||
<div
|
||||
onMouseLeave={this.onMouseLeave}
|
||||
onMouseEnter={this.onMouseEnter}
|
||||
onClick={this.onClick}
|
||||
type={type}
|
||||
type={type}
|
||||
className={`tree-node-inner text-nowrap ${hlClass} ${node.name === '/'? 'hide': ''}`}
|
||||
>
|
||||
<div className="tree-node-text" type={type} draggable="true" onDragStart={this.onDragStart}>{node.name}</div>
|
||||
|
@@ -6,7 +6,7 @@ import editorUtilities from '../../utils/editor-utilties';
|
||||
const propTypes = {
|
||||
permission: PropTypes.string,
|
||||
isNodeItemFrezee: PropTypes.bool.isRequired,
|
||||
currentFilePath: PropTypes.string.isRequired,
|
||||
currentPath: PropTypes.string.isRequired,
|
||||
treeData: PropTypes.object.isRequired,
|
||||
onShowContextMenu: PropTypes.func.isRequired,
|
||||
onNodeClick: PropTypes.func.isRequired,
|
||||
@@ -22,18 +22,14 @@ class TreeView extends React.PureComponent {
|
||||
*/
|
||||
}
|
||||
|
||||
toggleCollapse = (e, node) => {
|
||||
this.props.onDirCollapse(e, node);
|
||||
}
|
||||
|
||||
onDragStart = (e, node) => {
|
||||
const url = editorUtilities.getFileURL(node);
|
||||
e.dataTransfer.setData('text/uri-list', url);
|
||||
e.dataTransfer.setData('text/plain', url);
|
||||
}
|
||||
|
||||
onNodeClick = (e, node) => {
|
||||
this.props.onNodeClick(e, node);
|
||||
onNodeClick = (node) => {
|
||||
this.props.onNodeClick(node);
|
||||
}
|
||||
|
||||
onShowContextMenu = (e, node) => {
|
||||
@@ -53,7 +49,7 @@ class TreeView extends React.PureComponent {
|
||||
node={this.props.treeData.root}
|
||||
isNodeItemFrezee={this.props.isNodeItemFrezee}
|
||||
permission={this.props.permission}
|
||||
currentFilePath={this.props.currentFilePath}
|
||||
currentPath={this.props.currentPath}
|
||||
onShowContextMenu={this.props.onShowContextMenu}
|
||||
onDirCollapse={this.props.onDirCollapse}
|
||||
/>
|
||||
|
@@ -62,6 +62,25 @@ class Tree {
|
||||
return false;
|
||||
}
|
||||
|
||||
deleteNodeByPath(path) {
|
||||
let node = this.getNodeByPath(path);
|
||||
this.deleteNode(node);
|
||||
}
|
||||
|
||||
moveNode(node, moveToNode, isDestroy) {
|
||||
let moveNode = node.clone();
|
||||
this.addNodeToParent(moveNode, moveToNode);
|
||||
if (isDestroy) {
|
||||
this.deleteNode(node);
|
||||
}
|
||||
}
|
||||
|
||||
moveNodeByPath(path, moveToPath, isDestroy) {
|
||||
let node = this.getNodeByPath(path);
|
||||
let moveToNode = this.getNodeByPath(moveToPath);
|
||||
this.moveNode(node, moveToNode, isDestroy);
|
||||
}
|
||||
|
||||
updateNodeParam(node, param, newValue) {
|
||||
let treeNode = this.findNodeFromTree(node);
|
||||
if (treeNode && treeNode[param]) {
|
||||
@@ -71,6 +90,11 @@ class Tree {
|
||||
return false;
|
||||
}
|
||||
|
||||
updateNodeParamByPath(path, param, newValue) {
|
||||
let node = this.getNodeByPath(path);
|
||||
this.updateNodeParam(node, param, newValue);
|
||||
}
|
||||
|
||||
findNode(node) {
|
||||
return this.findNodeFromTree(node);
|
||||
}
|
||||
|
Reference in New Issue
Block a user