Complete input fields functionality

pull/1140/head
ioedeveloper 4 years ago
parent 99395f7ead
commit be2341a0c4
  1. 62
      libs/remix-ui/file-explorer/src/lib/actions/fileSystem.ts
  2. 127
      libs/remix-ui/file-explorer/src/lib/file-explorer.tsx
  3. 42
      libs/remix-ui/file-explorer/src/lib/reducers/fileSystem.ts

@ -1,6 +1,6 @@
import React from 'react' import React from 'react'
import { File } from '../types' import { File } from '../types'
import { extractNameFromKey } from '../utils' import { extractNameFromKey, extractParentFromKey } from '../utils'
export const fetchDirectoryError = (error: any) => { export const fetchDirectoryError = (error: any) => {
return { return {
@ -29,7 +29,7 @@ export const fileSystemReset = () => {
} }
} }
const normalize = (filesList): any => { const normalize = (parent, filesList, newInputType?: string): any => {
const folders = {} const folders = {}
const files = {} const files = {}
@ -53,14 +53,32 @@ const normalize = (filesList): any => {
} }
}) })
if (newInputType === 'folder') {
const path = parent + '/blank'
folders[path] = {
path: path,
name: '',
isDirectory: true
}
} else if (newInputType === 'file') {
const path = parent + '/blank'
files[path] = {
path: path,
name: '',
isDirectory: false
}
}
return Object.assign({}, folders, files) return Object.assign({}, folders, files)
} }
const fetchDirectoryContent = async (provider, folderPath: string): Promise<any> => { const fetchDirectoryContent = async (provider, folderPath: string, newInputType?: string): Promise<any> => {
return new Promise((resolve) => { return new Promise((resolve) => {
provider.resolveDirectory(folderPath, (error, fileTree) => { provider.resolveDirectory(folderPath, (error, fileTree) => {
if (error) console.error(error) if (error) console.error(error)
const files = normalize(fileTree) const files = normalize(folderPath, fileTree, newInputType)
resolve({ [extractNameFromKey(folderPath)]: files }) resolve({ [extractNameFromKey(folderPath)]: files })
}) })
@ -153,3 +171,39 @@ export const setWorkspace = (name: string) => (dispatch: React.Dispatch<any>) =>
dispatch(setCurrentWorkspace(name)) dispatch(setCurrentWorkspace(name))
} }
} }
export const addInputFieldSuccess = (path: string, files: File[]) => {
return {
type: 'ADD_INPUT_FIELD',
payload: { path, files }
}
}
export const addInputField = (provider, type: string, path: string) => (dispatch: React.Dispatch<any>) => {
const promise = fetchDirectoryContent(provider, path, type)
promise.then((files) => {
dispatch(addInputFieldSuccess(path, files))
}).catch((error) => {
console.error(error)
})
return promise
}
export const removeInputFieldSuccess = (path: string, files: File[]) => {
return {
type: 'REMOVE_INPUT_FIELD',
payload: { path, files }
}
}
export const removeInputField = (provider, path: string) => (dispatch: React.Dispatch<any>) => {
const promise = fetchDirectoryContent(provider, path)
promise.then((files) => {
dispatch(removeInputFieldSuccess(path, files))
}).catch((error) => {
console.error(error)
})
return promise
}

@ -8,7 +8,7 @@ import { FileExplorerMenu } from './file-explorer-menu' // eslint-disable-line
import { FileExplorerContextMenu } from './file-explorer-context-menu' // eslint-disable-line import { FileExplorerContextMenu } from './file-explorer-context-menu' // eslint-disable-line
import { FileExplorerProps, File } from './types' import { FileExplorerProps, File } from './types'
import { fileSystemReducer, fileSystemInitialState } from './reducers/fileSystem' import { fileSystemReducer, fileSystemInitialState } from './reducers/fileSystem'
import { fetchDirectory, setProvider, resolveDirectory, setWorkspace } from './actions/fileSystem' import { fetchDirectory, setProvider, resolveDirectory, setWorkspace, addInputField, removeInputField } from './actions/fileSystem'
import * as helper from '../../../../../apps/remix-ide/src/lib/helper' import * as helper from '../../../../../apps/remix-ide/src/lib/helper'
import QueryParams from '../../../../../apps/remix-ide/src/lib/query-params' import QueryParams from '../../../../../apps/remix-ide/src/lib/query-params'
@ -713,70 +713,64 @@ export const FileExplorer = (props: FileExplorerProps) => {
} }
const editModeOn = (path: string, type: string, isNew: boolean = false) => { const editModeOn = (path: string, type: string, isNew: boolean = false) => {
if (filesProvider.isReadOnly(path)) return if (fileSystem.provider.provider.isReadOnly(path)) return
setState(prevState => { setState(prevState => {
return { ...prevState, focusEdit: { ...prevState.focusEdit, element: path, isNew, type } } return { ...prevState, focusEdit: { ...prevState.focusEdit, element: path, isNew, type } }
}) })
} }
// const editModeOff = async (content: string) => { const editModeOff = async (content: string) => {
// if (typeof content === 'string') content = content.trim() if (typeof content === 'string') content = content.trim()
// const parentFolder = extractParentFromKey(state.focusEdit.element) const parentFolder = extractParentFromKey(state.focusEdit.element)
// if (!content || (content.trim() === '')) { if (!content || (content.trim() === '')) {
// if (state.focusEdit.isNew) { if (state.focusEdit.isNew) {
// const files = removePath(state.focusEdit.element, state.files) removeInputField(fileSystem.provider.provider, parentFolder)(dispatch)
// const updatedFiles = files.filter(file => file) setState(prevState => {
return { ...prevState, focusEdit: { element: null, isNew: false, type: '', lastEdit: '' } }
// setState(prevState => { })
// return { ...prevState, files: updatedFiles, focusEdit: { element: null, isNew: false, type: '', lastEdit: '' } } } else {
// }) editRef.current.textContent = state.focusEdit.lastEdit
// } else { setState(prevState => {
// editRef.current.textContent = state.focusEdit.lastEdit return { ...prevState, focusEdit: { element: null, isNew: false, type: '', lastEdit: '' } }
// setState(prevState => { })
// return { ...prevState, focusEdit: { element: null, isNew: false, type: '', lastEdit: '' } } }
// }) } else {
// } if (state.focusEdit.lastEdit === content) {
// } else { editRef.current.textContent = content
// if (state.focusEdit.lastEdit === content) { return setState(prevState => {
// editRef.current.textContent = content return { ...prevState, focusEdit: { element: null, isNew: false, type: '', lastEdit: '' } }
// return setState(prevState => { })
// return { ...prevState, focusEdit: { element: null, isNew: false, type: '', lastEdit: '' } } }
// }) if (helper.checkSpecialChars(content)) {
// } modal('Validation Error', 'Special characters are not allowed', {
// if (helper.checkSpecialChars(content)) { label: 'OK',
// modal('Validation Error', 'Special characters are not allowed', { fn: () => {}
// label: 'OK', }, null)
// fn: () => {} } else {
// }, null) if (state.focusEdit.isNew) {
// } else { // state.focusEdit.type === 'file' ? createNewFile(joinPath(parentFolder, content)) : createNewFolder(joinPath(parentFolder, content))
// if (state.focusEdit.isNew) { removeInputField(fileSystem.provider.provider, parentFolder)(dispatch)
// state.focusEdit.type === 'file' ? createNewFile(joinPath(parentFolder, content)) : createNewFolder(joinPath(parentFolder, content)) } else {
// const files = removePath(state.focusEdit.element, state.files) const oldPath: string = state.focusEdit.element
// const updatedFiles = files.filter(file => file) // const oldName = extractNameFromKey(oldPath)
// const newPath = oldPath.replace(oldName, content)
// setState(prevState => {
// return { ...prevState, files: updatedFiles }
// })
// } else {
// const oldPath: string = state.focusEdit.element
// const oldName = extractNameFromKey(oldPath)
// const newPath = oldPath.replace(oldName, content)
// editRef.current.textContent = extractNameFromKey(oldPath) editRef.current.textContent = extractNameFromKey(oldPath)
// renamePath(oldPath, newPath) // renamePath(oldPath, newPath)
// } }
// setState(prevState => { setState(prevState => {
// return { ...prevState, focusEdit: { element: null, isNew: false, type: '', lastEdit: '' } } return { ...prevState, focusEdit: { element: null, isNew: false, type: '', lastEdit: '' } }
// }) })
// } }
// } }
// } }
const handleNewFileInput = async (parentFolder?: string) => { const handleNewFileInput = async (parentFolder?: string) => {
if (!parentFolder) parentFolder = state.focusElement[0] ? state.focusElement[0].type === 'folder' ? state.focusElement[0].key : extractParentFromKey(state.focusElement[0].key) : name if (!parentFolder) parentFolder = state.focusElement[0] ? state.focusElement[0].type === 'folder' ? state.focusElement[0].key ? state.focusElement[0].key : name : extractParentFromKey(state.focusElement[0].key) : name
const expandPath = [...new Set([...state.expandPath, parentFolder])] const expandPath = [...new Set([...state.expandPath, parentFolder])]
await addInputField(fileSystem.provider.provider, 'file', parentFolder)(dispatch)
setState(prevState => { setState(prevState => {
return { ...prevState, expandPath } return { ...prevState, expandPath }
}) })
@ -784,22 +778,23 @@ export const FileExplorer = (props: FileExplorerProps) => {
} }
const handleNewFolderInput = async (parentFolder?: string) => { const handleNewFolderInput = async (parentFolder?: string) => {
if (!parentFolder) parentFolder = state.focusElement[0] ? state.focusElement[0].type === 'folder' ? state.focusElement[0].key : extractParentFromKey(state.focusElement[0].key) : name if (!parentFolder) parentFolder = state.focusElement[0] ? state.focusElement[0].type === 'folder' ? state.focusElement[0].key ? state.focusElement[0].key : name : extractParentFromKey(state.focusElement[0].key) : name
else if ((parentFolder.indexOf('.sol') !== -1) || (parentFolder.indexOf('.js') !== -1)) parentFolder = extractParentFromKey(parentFolder) else if ((parentFolder.indexOf('.sol') !== -1) || (parentFolder.indexOf('.js') !== -1)) parentFolder = extractParentFromKey(parentFolder)
const expandPath = [...new Set([...state.expandPath, parentFolder])] const expandPath = [...new Set([...state.expandPath, parentFolder])]
await addInputField(fileSystem.provider.provider, 'folder', parentFolder)(dispatch)
setState(prevState => { setState(prevState => {
return { ...prevState, expandPath } return { ...prevState, expandPath }
}) })
editModeOn(parentFolder + '/blank', 'folder', true) editModeOn(parentFolder + '/blank', 'folder', true)
} }
// const handleEditInput = (event) => { const handleEditInput = (event) => {
// if (event.which === 13) { if (event.which === 13) {
// event.preventDefault() event.preventDefault()
// editModeOff(editRef.current.innerText) editModeOff(editRef.current.innerText)
// } }
// } }
const handleMouseOver = (path: string) => { const handleMouseOver = (path: string) => {
setState(prevState => { setState(prevState => {
@ -820,11 +815,11 @@ export const FileExplorer = (props: FileExplorerProps) => {
ref={state.focusEdit.element === file.path ? editRef : null} ref={state.focusEdit.element === file.path ? editRef : null}
suppressContentEditableWarning={true} suppressContentEditableWarning={true}
contentEditable={state.focusEdit.element === file.path} contentEditable={state.focusEdit.element === file.path}
// onKeyDown={handleEditInput} onKeyDown={handleEditInput}
// onBlur={(e) => { onBlur={(e) => {
// e.stopPropagation() e.stopPropagation()
// editModeOff(editRef.current.innerText) editModeOff(editRef.current.innerText)
// }} }}
> >
<span <span
title={file.path} title={file.path}

@ -9,6 +9,7 @@ export const fileSystemInitialState = {
files: { files: {
files: [], files: [],
workspaceName: null, workspaceName: null,
blankPath: null,
isRequesting: false, isRequesting: false,
isSuccessful: false, isSuccessful: false,
error: null error: null
@ -134,6 +135,32 @@ export const fileSystemReducer = (state = fileSystemInitialState, action: Action
} }
} }
} }
case 'ADD_INPUT_FIELD': {
return {
...state,
files: {
...state.files,
files: addInputField(state.files.workspaceName, action.payload.path, state.files.files, action.payload.files),
blankPath: action.payload.path,
isRequesting: false,
isSuccessful: true,
error: null
}
}
}
case 'REMOVE_INPUT_FIELD': {
return {
...state,
files: {
...state.files,
files: removeInputField(state.files.workspaceName, state.files.blankPath, state.files.files, action.payload.files),
blankPath: null,
isRequesting: false,
isSuccessful: true,
error: null
}
}
}
default: default:
throw new Error() throw new Error()
} }
@ -141,8 +168,8 @@ export const fileSystemReducer = (state = fileSystemInitialState, action: Action
const resolveDirectory = (root, path: string, files, content) => { const resolveDirectory = (root, path: string, files, content) => {
const pathArr = path.split('/') const pathArr = path.split('/')
if (pathArr[0] !== root) pathArr.unshift(root)
if (pathArr[0] !== root) pathArr.unshift(root)
files = _.set(files, pathArr, { files = _.set(files, pathArr, {
isDirectory: true, isDirectory: true,
path, path,
@ -152,3 +179,16 @@ const resolveDirectory = (root, path: string, files, content) => {
return files return files
} }
const addInputField = (root, path: string, files, content) => {
if (Object.keys(content)[0] === root) return { [Object.keys(content)[0]]: { ...content[Object.keys(content)[0]], ...files[Object.keys(content)[0]] } }
return resolveDirectory(root, path, files, content)
}
const removeInputField = (root, path: string, files, content) => {
if (Object.keys(content)[0] === root) {
delete files[root][path + '/' + 'blank']
return files
}
return resolveDirectory(root, path, files, content)
}

Loading…
Cancel
Save