Merge pull request #3751 from ethereum/ui_generator

Add section file context menu
pull/3747/head
yann300 2 years ago committed by GitHub
commit da7a4bbc75
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 2
      apps/remix-ide-e2e/src/tests/plugin_api.ts
  2. 2
      apps/remix-ide-e2e/src/tests/remixd.test.ts
  3. 5
      apps/remix-ide-e2e/src/tests/solidityImport.test.ts
  4. 9
      apps/remix-ide/src/app/panels/file-panel.js
  5. 3
      apps/remix-ide/src/app/tabs/compile-tab.js
  6. 12
      apps/remix-ide/src/remixAppManager.js
  7. 27
      libs/remix-ui/workspace/src/lib/components/file-explorer-context-menu.tsx
  8. 6
      libs/remix-ui/workspace/src/lib/remix-ui-workspace.tsx
  9. 5
      libs/remix-ui/workspace/src/lib/types/index.ts
  10. 88
      libs/remix-ui/workspace/src/lib/utils/index.ts

@ -217,7 +217,7 @@ module.exports = {
.rightClickCustom('[data-id="treeViewLitreeViewItemcontracts/1_Storage.sol"]').useXpath().waitForElementVisible('//*[@id="menuitemtestcommand"]').click('//*[@id="menuitemtestcommand"]', async () => { .rightClickCustom('[data-id="treeViewLitreeViewItemcontracts/1_Storage.sol"]').useXpath().waitForElementVisible('//*[@id="menuitemtestcommand"]').click('//*[@id="menuitemtestcommand"]', async () => {
// @ts-ignore // @ts-ignore
browser.click('//*[@data-id="verticalIconsKindlocalPlugin"]').frame(0, async () => { browser.click('//*[@data-id="verticalIconsKindlocalPlugin"]').frame(0, async () => {
await clickAndCheckLog(browser, null, { id: 'localPlugin', name: 'testCommand', label: 'testCommand', type: [], extension: ['.sol'], path: ['contracts/1_Storage.sol'], pattern: [] }, null, null) await clickAndCheckLog(browser, null, { id: 'localPlugin', name: 'testCommand', label: 'testCommand', type: [], extension: ['.sol'], path: ['contracts/1_Storage.sol'], pattern: [], group: 99 }, null, null)
}) })
}) })
}) })

@ -104,7 +104,7 @@ module.exports = {
}) })
.addFile('test_import_node_modules_with_github_import.sol', sources[4]['test_import_node_modules_with_github_import.sol']) .addFile('test_import_node_modules_with_github_import.sol', sources[4]['test_import_node_modules_with_github_import.sol'])
.clickLaunchIcon('solidity') .clickLaunchIcon('solidity')
.setSolidityCompilerVersion('soljson-v0.8.0+commit.c7dfd78e.js') // open-zeppelin moved to pragma ^0.8.0 .setSolidityCompilerVersion('soljson-v0.8.19+commit.7dd6d404.js') // open-zeppelin moved to pragma ^0.8.0
.testContracts('test_import_node_modules_with_github_import.sol', sources[4]['test_import_node_modules_with_github_import.sol'], ['ERC20', 'test11']) .testContracts('test_import_node_modules_with_github_import.sol', sources[4]['test_import_node_modules_with_github_import.sol'], ['ERC20', 'test11'])
}, },
'Static Analysis run with remixd #group3': '' + function (browser) { 'Static Analysis run with remixd #group3': '' + function (browser) {

@ -38,7 +38,7 @@ module.exports = {
'Test GitHub Import - from master branch #group1': function (browser: NightwatchBrowser) { 'Test GitHub Import - from master branch #group1': function (browser: NightwatchBrowser) {
browser browser
.setSolidityCompilerVersion('soljson-v0.8.0+commit.c7dfd78e.js') // open-zeppelin moved to pragma ^0.8.0 (master branch) .setSolidityCompilerVersion('soljson-v0.8.19+commit.7dd6d404.js') // open-zeppelin moved to pragma ^0.8.19 (master branch)
.addFile('Untitled4.sol', sources[3]['Untitled4.sol']) .addFile('Untitled4.sol', sources[3]['Untitled4.sol'])
.clickLaunchIcon('filePanel') .clickLaunchIcon('filePanel')
.verifyContracts(['test7', 'ERC20'], { wait: 10000 }) .verifyContracts(['test7', 'ERC20'], { wait: 10000 })
@ -54,7 +54,7 @@ module.exports = {
'Test GitHub Import - no branch specified #group2': function (browser: NightwatchBrowser) { 'Test GitHub Import - no branch specified #group2': function (browser: NightwatchBrowser) {
browser browser
.setSolidityCompilerVersion('soljson-v0.8.0+commit.c7dfd78e.js') // open-zeppelin moved to pragma ^0.8.0 (master branch) .setSolidityCompilerVersion('soljson-v0.8.19+commit.7dd6d404.js') // open-zeppelin moved to pragma ^0.8.19 (master branch)
.clickLaunchIcon('filePanel') .clickLaunchIcon('filePanel')
.click('li[data-id="treeViewLitreeViewItemREADME.txt"') .click('li[data-id="treeViewLitreeViewItemREADME.txt"')
.addFile('Untitled6.sol', sources[5]['Untitled6.sol']) .addFile('Untitled6.sol', sources[5]['Untitled6.sol'])
@ -64,6 +64,7 @@ module.exports = {
'Test GitHub Import - raw URL #group4': function (browser: NightwatchBrowser) { 'Test GitHub Import - raw URL #group4': function (browser: NightwatchBrowser) {
browser browser
.setSolidityCompilerVersion('soljson-v0.8.19+commit.7dd6d404.js') // open-zeppelin moved to pragma ^0.8.0 (master branch)
.clickLaunchIcon('filePanel') .clickLaunchIcon('filePanel')
.click('li[data-id="treeViewLitreeViewItemREADME.txt"') .click('li[data-id="treeViewLitreeViewItemREADME.txt"')
.addFile('Untitled7.sol', sources[6]['Untitled7.sol']) .addFile('Untitled7.sol', sources[6]['Untitled7.sol'])

@ -66,6 +66,15 @@ module.exports = class Filepanel extends ViewPlugin {
/** /**
* @param item { id: string, name: string, type?: string[], path?: string[], extension?: string[], pattern?: string[] } * @param item { id: string, name: string, type?: string[], path?: string[], extension?: string[], pattern?: string[] }
* typically:
* group 0 for file manipulations
* group 1 for download operations
* group 2 for running operations (script for instance)
* group 3 for publishing operations (gist)
* group 4 for copying operations
* group 5 for solidity file operations (flatten for instance)
* group 6 for compiling operations
* group 7 for generating resource files (UML, documentation, ...)
* @param callback (...args) => void * @param callback (...args) => void
*/ */
registerContextMenuItem (item) { registerContextMenuItem (item) {

@ -123,7 +123,8 @@ class CompileTab extends CompilerApiMixin(ViewPlugin) { // implements ICompilerA
type: [], type: [],
extension: ['.sol'], extension: ['.sol'],
path: [], path: [],
pattern: [] pattern: [],
group: 6
}) })
}) })
try { try {

@ -192,7 +192,8 @@ export class RemixAppManager extends PluginManager {
extension: ['.sol'], extension: ['.sol'],
path: [], path: [],
pattern: [], pattern: [],
sticky: true sticky: true,
group: 5
}) })
await this.call('filePanel', 'registerContextMenuItem', { await this.call('filePanel', 'registerContextMenuItem', {
id: 'nahmii-compiler', id: 'nahmii-compiler',
@ -202,7 +203,8 @@ export class RemixAppManager extends PluginManager {
extension: ['.sol'], extension: ['.sol'],
path: [], path: [],
pattern: [], pattern: [],
sticky: true sticky: true,
group: 6
}) })
await this.call('filePanel', 'registerContextMenuItem', { await this.call('filePanel', 'registerContextMenuItem', {
id: 'solidityumlgen', id: 'solidityumlgen',
@ -212,7 +214,8 @@ export class RemixAppManager extends PluginManager {
extension: ['.sol'], extension: ['.sol'],
path: [], path: [],
pattern: [], pattern: [],
sticky: true sticky: true,
group: 7
}) })
await this.call('filePanel', 'registerContextMenuItem', { await this.call('filePanel', 'registerContextMenuItem', {
id: 'doc-gen', id: 'doc-gen',
@ -222,7 +225,8 @@ export class RemixAppManager extends PluginManager {
extension: ['.sol'], extension: ['.sol'],
path: [], path: [],
pattern: [], pattern: [],
sticky: true sticky: true,
group: 7
}) })
} }
} }

@ -72,12 +72,23 @@ export const FileExplorerContextMenu = (props: FileExplorerContextMenuProps) =>
} }
const menu = () => { const menu = () => {
return actions.filter(item => filterItem(item)).map((item, index) => { let group = 0
const groupedActions = actions.filter(item => filterItem(item)).reduce((acc, item) => {
if (item.group === undefined || item.group === null) item.group = 99
if (!acc[item.group]) acc[item.group] = []
acc[item.group].push(item)
return acc;
}, [])
let key = -1
return groupedActions.map((groupItem, groupIndex) => groupItem.map((item, index) => {
key++
const className = `remixui_liitem ${group !== item.group ? 'border-top': ''}`
group = item.group
if(item.name === "Upload File"){ if(item.name === "Upload File"){
return <li return <li
id={`menuitem${item.name.toLowerCase()}`} id={`menuitem${item.name.toLowerCase()}`}
key={index} key={key}
className='remixui_liitem' className={className}
onClick={()=>{ onClick={()=>{
_paq.push(['trackEvent', 'fileExplorer', 'contextMenu', 'uploadFile']) _paq.push(['trackEvent', 'fileExplorer', 'contextMenu', 'uploadFile'])
setShowFileExplorer(true) setShowFileExplorer(true)
@ -88,8 +99,8 @@ export const FileExplorerContextMenu = (props: FileExplorerContextMenuProps) =>
if(item.name === "Load a Local File"){ if(item.name === "Load a Local File"){
return <li return <li
id={`menuitem${item.name.toLowerCase()}`} id={`menuitem${item.name.toLowerCase()}`}
key={index} key={key}
className='remixui_liitem' className={className}
onClick={()=>{ onClick={()=>{
_paq.push(['trackEvent', 'fileExplorer', 'contextMenu', 'uploadFile']) _paq.push(['trackEvent', 'fileExplorer', 'contextMenu', 'uploadFile'])
setShowFileExplorer(true) setShowFileExplorer(true)
@ -98,8 +109,8 @@ export const FileExplorerContextMenu = (props: FileExplorerContextMenuProps) =>
} }
return <li return <li
id={`menuitem${item.name.toLowerCase()}`} id={`menuitem${item.name.toLowerCase()}`}
key={index} key={key}
className='remixui_liitem' className={className}
onClick={(e) => { onClick={(e) => {
e.stopPropagation() e.stopPropagation()
switch (item.name) { switch (item.name) {
@ -170,7 +181,7 @@ export const FileExplorerContextMenu = (props: FileExplorerContextMenuProps) =>
} }
hideContextMenu() hideContextMenu()
}}>{intl.formatMessage({id: `filePanel.${item.id}`, defaultMessage: item.label || item.name})}</li> }}>{intl.formatMessage({id: `filePanel.${item.id}`, defaultMessage: item.label || item.name})}</li>
}) }))
} }
return ( return (

@ -76,7 +76,8 @@ export function Workspace () {
extension: [], extension: [],
pattern: [], pattern: [],
multiselect: false, multiselect: false,
label: '' label: '',
group: 4
}]) }])
} else { } else {
removeMenuItems([{ removeMenuItems([{
@ -87,7 +88,8 @@ export function Workspace () {
extension: [], extension: [],
pattern: [], pattern: [],
multiselect: false, multiselect: false,
label: '' label: '',
group: 4
}]) }])
} }
}, [canPaste]) }, [canPaste])

@ -5,7 +5,7 @@ import { fileDecoration } from '@remix-ui/file-decorators'
import { RemixAppManager } from 'libs/remix-ui/plugin-manager/src/types' import { RemixAppManager } from 'libs/remix-ui/plugin-manager/src/types'
import { ViewPlugin } from '@remixproject/engine-web' import { ViewPlugin } from '@remixproject/engine-web'
export type action = { name: string, type?: Array<'folder' | 'gist' | 'file' | 'workspace'>, path?: string[], extension?: string[], pattern?: string[], id: string, multiselect: boolean, label: string, sticky?: boolean } export type action = { name: string, type?: Array<'folder' | 'gist' | 'file' | 'workspace'>, path?: string[], extension?: string[], pattern?: string[], id: string, multiselect: boolean, label: string, sticky?: boolean, group: number }
export interface JSONStandardInput { export interface JSONStandardInput {
language: "Solidity"; language: "Solidity";
settings?: any, settings?: any,
@ -176,7 +176,8 @@ export interface WorkSpaceState {
extension?: string[] extension?: string[]
pattern?: string[] pattern?: string[]
multiselect: boolean multiselect: boolean
label: string label: string,
group: number
}[] }[]
focusContext: FileFocusContextType focusContext: FileFocusContextType
focusEdit: { focusEdit: {

@ -5,96 +5,112 @@ export const contextMenuActions: MenuItems = [{
name: 'New File', name: 'New File',
type: ['folder', 'gist', 'workspace'], type: ['folder', 'gist', 'workspace'],
multiselect: false, multiselect: false,
label: '' label: '',
group: 0
}, { }, {
id: 'newFolder', id: 'newFolder',
name: 'New Folder', name: 'New Folder',
type: ['folder', 'gist', 'workspace'], type: ['folder', 'gist', 'workspace'],
multiselect: false, multiselect: false,
label: '' label: '',
group: 0
}, { }, {
id: 'rename', id: 'rename',
name: 'Rename', name: 'Rename',
type: ['file', 'folder'], type: ['file', 'folder'],
multiselect: false, multiselect: false,
label: '' label: '',
group: 0
}, { }, {
id: 'delete', id: 'delete',
name: 'Delete', name: 'Delete',
type: ['file', 'folder', 'gist'], type: ['file', 'folder', 'gist'],
multiselect: false, multiselect: false,
label: '' label: '',
group: 0
},{ },{
id: 'deleteAll',
name: 'Delete All',
type: ['folder', 'file'],
multiselect: true,
label: '',
group: 0
}, {
id: 'copy',
name: 'Copy',
type: ['folder', 'file'],
multiselect: false,
label: '',
group: 1
}, {
id: 'copyFileName',
name: 'Copy name',
type: ['file'],
multiselect: false,
label: '',
group: 1
}, {
id: 'copyFilePath',
name: 'Copy path',
type: ['file'],
multiselect: false,
label: '',
group: 1
}, {
id: 'download', id: 'download',
name: 'Download', name: 'Download',
type: ['file', 'folder', 'workspace'], type: ['file', 'folder', 'workspace'],
multiselect: false, multiselect: false,
label: '' label: '',
group: 2
}, { }, {
id: 'run', id: 'run',
name: 'Run', name: 'Run',
extension: ['.js', '.ts'], extension: ['.js', '.ts'],
multiselect: false, multiselect: false,
label: '' label: '',
group: 3
},{ },{
id: 'pushChangesToGist', id: 'pushChangesToGist',
name: 'Push changes to gist', name: 'Push changes to gist',
type: ['gist'], type: ['gist'],
multiselect: false, multiselect: false,
label: '' label: '',
group: 4
}, { }, {
id: 'publishFolderToGist', id: 'publishFolderToGist',
name: 'Publish folder to gist', name: 'Publish folder to gist',
type: ['folder'], type: ['folder'],
multiselect: false, multiselect: false,
label: '' label: '',
group: 4
}, { }, {
id: 'publishFileToGist', id: 'publishFileToGist',
name: 'Publish file to gist', name: 'Publish file to gist',
type: ['file'], type: ['file'],
multiselect: false, multiselect: false,
label: '' label: '',
group: 4
}, { }, {
id: 'copy',
name: 'Copy',
type: ['folder', 'file'],
multiselect: false,
label: ''
}, {
id: 'copyFileName',
name: 'Copy name',
type: ['file'],
multiselect: false,
label: ''
}, {
id: 'copyFilePath',
name: 'Copy path',
type: ['file'],
multiselect: false,
label: ''
}, {
id: 'deleteAll',
name: 'Delete All',
type: ['folder', 'file'],
multiselect: true,
label: ''
},{
id: 'uploadFile', id: 'uploadFile',
name: 'Load a Local File', name: 'Load a Local File',
type: ['folder', 'gist', 'workspace'], type: ['folder', 'gist', 'workspace'],
multiselect: false, multiselect: false,
label: 'Load a Local File' label: 'Load a Local File',
group: 4
}, { }, {
id: 'publishToGist', id: 'publishToGist',
name: 'Push changes to gist', name: 'Push changes to gist',
type: ['folder', 'gist'], type: ['folder', 'gist'],
multiselect: false, multiselect: false,
label: 'Publish all to Gist' label: 'Publish all to Gist',
group: 4
}, },
{ {
id: 'publishWorkspace', id: 'publishWorkspace',
name: 'Publish Workspace to Gist', name: 'Publish Workspace to Gist',
type: ['workspace'], type: ['workspace'],
multiselect: false, multiselect: false,
label: '' label: '',
group: 4
}] }]
Loading…
Cancel
Save