Include pattern for context menu

pull/668/head
ioedeveloper 4 years ago
parent adcdb3d440
commit 154b95d3ae
  1. 16
      libs/remix-ui/file-explorer/src/lib/file-explorer-context-menu.tsx
  2. 121
      libs/remix-ui/file-explorer/src/lib/file-explorer.tsx
  3. 3
      libs/remix-ui/file-explorer/src/lib/types/index.ts

@ -4,7 +4,7 @@ import { FileExplorerContextMenuProps } from './types'
import './css/file-explorer-context-menu.css'
export const FileExplorerContextMenu = (props: FileExplorerContextMenuProps) => {
const { actions, createNewFile, createNewFolder, deletePath, renamePath, hideContextMenu, extractParentFromKey, publishToGist, pageX, pageY, path, type, ...otherProps } = props
const { actions, createNewFile, createNewFolder, deletePath, renamePath, hideContextMenu, extractParentFromKey, publishToGist, runScript, pageX, pageY, path, type, ...otherProps } = props
const contextMenuRef = useRef(null)
useEffect(() => {
@ -23,10 +23,13 @@ export const FileExplorerContextMenu = (props: FileExplorerContextMenuProps) =>
}, [pageX, pageY])
const menu = () => {
return actions.filter(item => item.type.findIndex(name => {
if ((name === 'browser/gists') && (type === 'folder') && (extractParentFromKey(path) === name)) return true // add publish to gist for gist folders
return name === type
}) !== -1).map((item, index) => {
return actions.filter(item => {
if (item.type.findIndex(name => name === type) !== -1) return true
else if (item.path.findIndex(key => key === path) !== -1) return true
else if (item.extension.findIndex(ext => path.endsWith(ext)) !== -1) return true
else if (item.pattern.filter(value => path.match(new RegExp(value))).length > 0) return true
else return false
}).map((item, index) => {
return <li
id={`menuitem${item.name.toLowerCase()}`}
key={index}
@ -49,6 +52,9 @@ export const FileExplorerContextMenu = (props: FileExplorerContextMenuProps) =>
case 'Push changes to gist':
publishToGist()
break
case 'Run':
runScript(path)
break
default:
break
}

@ -77,19 +77,40 @@ export const FileExplorer = (props: FileExplorerProps) => {
const files = await fetchDirectoryContent(name)
const actions = [{
name: 'New File',
type: ['folder']
type: ['folder'],
path: [],
extension: [],
pattern: []
}, {
name: 'New Folder',
type: ['folder']
type: ['folder'],
path: [],
extension: [],
pattern: []
}, {
name: 'Rename',
type: ['file', 'folder']
type: ['file', 'folder'],
path: [],
extension: [],
pattern: []
}, {
name: 'Delete',
type: ['file', 'folder']
type: ['file', 'folder'],
path: [],
extension: [],
pattern: []
}, {
name: 'Push changes to gist',
type: ['browser/gists']
type: [],
path: [],
extension: [],
pattern: ['^browser/gists/([0-9]|[a-z])*$']
}, {
name: 'Run',
type: [],
path: [],
extension: ['.js'],
pattern: []
}]
setState(prevState => {
@ -100,8 +121,8 @@ export const FileExplorer = (props: FileExplorerProps) => {
useEffect(() => {
if (state.fileManager) {
props.filesProvider.event.register('fileExternallyChanged', fileExternallyChanged)
props.filesProvider.event.register('fileRenamedError', fileRenamedError)
filesProvider.event.register('fileExternallyChanged', fileExternallyChanged)
filesProvider.event.register('fileRenamedError', fileRenamedError)
}
}, [state.fileManager])
@ -125,14 +146,14 @@ export const FileExplorer = (props: FileExplorerProps) => {
useEffect(() => {
// unregister event to update state in callback
if (props.filesProvider.event.registered.fileAdded) props.filesProvider.event.unregister('fileAdded', fileAdded)
if (props.filesProvider.event.registered.folderAdded) props.filesProvider.event.unregister('folderAdded', folderAdded)
if (props.filesProvider.event.registered.fileRemoved) props.filesProvider.event.unregister('fileRemoved', fileRemoved)
if (props.filesProvider.event.registered.fileRenamed) props.filesProvider.event.unregister('fileRenamed', fileRenamed)
props.filesProvider.event.register('fileAdded', fileAdded)
props.filesProvider.event.register('folderAdded', folderAdded)
props.filesProvider.event.register('fileRemoved', fileRemoved)
props.filesProvider.event.register('fileRenamed', fileRenamed)
if (filesProvider.event.registered.fileAdded) filesProvider.event.unregister('fileAdded', fileAdded)
if (filesProvider.event.registered.folderAdded) filesProvider.event.unregister('folderAdded', folderAdded)
if (filesProvider.event.registered.fileRemoved) filesProvider.event.unregister('fileRemoved', fileRemoved)
if (filesProvider.event.registered.fileRenamed) filesProvider.event.unregister('fileRenamed', fileRenamed)
filesProvider.event.register('fileAdded', fileAdded)
filesProvider.event.register('folderAdded', folderAdded)
filesProvider.event.register('fileRemoved', fileRemoved)
filesProvider.event.register('fileRenamed', fileRenamed)
}, [state.files])
const resolveDirectory = async (folderPath, dir: File[]): Promise<File[]> => {
@ -302,64 +323,6 @@ export const FileExplorer = (props: FileExplorerProps) => {
}
}
const addEmptyFile = (parentFolder: string, files: File[]): File[] => {
if (parentFolder === name) {
files.push({
path: 'browser/blank',
name: '',
isDirectory: false
})
return files
}
return files.map(file => {
if (file.child) {
if (file.path === parentFolder) {
file.child = [...file.child, {
path: file.path + '/blank',
name: '',
isDirectory: false
}]
return file
} else {
file.child = addEmptyFile(parentFolder, file.child)
return file
}
} else {
return file
}
})
}
const addEmptyFolder = (parentFolder: string, files: File[]): File[] => {
if (parentFolder === name) {
files.unshift({
path: 'browser/blank',
name: '',
isDirectory: true
})
return files
}
return files.map(file => {
if (file.child) {
if (file.path === parentFolder) {
file.child = [{
path: file.path + '/blank',
name: '',
isDirectory: true
}, ...file.child]
return file
} else {
file.child = addEmptyFolder(parentFolder, file.child)
return file
}
} else {
return file
}
})
}
const removePath = (path: string, files: File[]): File[] => {
return files.map(file => {
if (file.path === path) {
@ -474,7 +437,7 @@ export const FileExplorer = (props: FileExplorerProps) => {
// pick that up via the 'fileAdded' event from the files module.
[...target.files].forEach((file) => {
const files = props.filesProvider
const files = filesProvider
const loadFile = (name: string): void => {
const fileReader = new FileReader()
@ -574,7 +537,7 @@ export const FileExplorer = (props: FileExplorerProps) => {
// If 'id' is not defined, it is not a gist update but a creation so we have to take the files from the browser explorer.
const folder = id ? 'browser/gists/' + id : 'browser/'
packageFiles(props.filesProvider, folder, async (error, packaged) => {
packageFiles(filesProvider, folder, async (error, packaged) => {
if (error) {
console.log(error)
modal('Publish to gist Failed', 'Failed to create gist: ' + error.message, {
@ -640,6 +603,13 @@ export const FileExplorer = (props: FileExplorerProps) => {
})
}
const runScript = async (path: string) => {
filesProvider.get(path, (error, content: string) => {
if (error) return console.log(error)
plugin.call('scriptRunner', 'execute', content)
})
}
const handleHideModal = () => {
setState(prevState => {
return { ...prevState, modalOptions: { ...state.modalOptions, hide: true } }
@ -910,6 +880,7 @@ export const FileExplorer = (props: FileExplorerProps) => {
createNewFolder={handleNewFolderInput}
deletePath={deletePath}
renamePath={editModeOn}
runScript={runScript}
pageX={state.focusContext.x}
pageY={state.focusContext.y}
path={file.path}

@ -25,7 +25,7 @@ export interface FileExplorerMenuProps {
}
export interface FileExplorerContextMenuProps {
actions: { name: string, type: string[] }[],
actions: { name: string, type: string[], path: string[], extension: string[], pattern: string[] }[],
createNewFile: (folder?: string) => void,
createNewFolder: (parentFolder?: string) => void,
deletePath: (path: string) => void,
@ -33,6 +33,7 @@ export interface FileExplorerContextMenuProps {
hideContextMenu: () => void,
extractParentFromKey?: (key: string) => string,
publishToGist?: () => void,
runScript?: (path: string) => void,
pageX: number,
pageY: number,
path: string,

Loading…
Cancel
Save