stop button

pull/2257/head^2
filip mertens 3 years ago committed by yann300
parent b20db41b45
commit f98383b1cf
  1. 13
      libs/remix-ui/search/src/lib/components/Exclude.tsx
  2. 31
      libs/remix-ui/search/src/lib/components/Find.tsx
  3. 19
      libs/remix-ui/search/src/lib/components/Include.tsx
  4. 1
      libs/remix-ui/search/src/lib/components/Search.tsx
  5. 6
      libs/remix-ui/search/src/lib/components/StopSearch.tsx
  6. 13
      libs/remix-ui/search/src/lib/components/results/ResultItem.tsx
  7. 8
      libs/remix-ui/search/src/lib/components/results/Results.tsx
  8. 18
      libs/remix-ui/search/src/lib/context/context.tsx
  9. 9
      libs/remix-ui/search/src/lib/reducers/Reducer.ts
  10. 3
      libs/remix-ui/search/src/lib/search.css
  11. 4
      libs/remix-ui/search/src/lib/types/index.ts

@ -4,12 +4,16 @@ import { SearchContext } from '../context/context'
export const Exclude = props => { export const Exclude = props => {
const { setExclude, cancelSearch } = useContext(SearchContext) const { setExclude, cancelSearch } = useContext(SearchContext)
const [excludeInput, setExcludeInput] = useState<string>('.*/**/*') const [excludeInput, setExcludeInput] = useState<string>('.*/**/*')
const timeOutId = useRef(null)
const change = async e => { const change = async e => {
setExcludeInput(e.target.value) setExcludeInput(e.target.value)
clearTimeout(timeOutId.current)
await cancelSearch() await cancelSearch()
timeOutId.current = setTimeout(() => setExclude(e.target.value), 500) }
const handleKeypress = async e => {
if (e.charCode === 13 || e.keyCode === 13) {
await setExclude(excludeInput)
}
} }
useEffect(() => { useEffect(() => {
@ -21,9 +25,10 @@ export const Exclude = props => {
<div className="search_plugin_find-part pl-3"> <div className="search_plugin_find-part pl-3">
<label className='mt-2'>Files to exclude</label> <label className='mt-2'>Files to exclude</label>
<input <input
id='search_exclude' id='search_exclude ( Enter to exclude )'
placeholder="Exclude ie .git/**/*" placeholder="Exclude ie .git/**/*"
className="form-control" className="form-control"
onKeyPress={handleKeypress}
onChange={async(e) => change(e)} onChange={async(e) => change(e)}
value={excludeInput} value={excludeInput}
></input> ></input>

@ -10,33 +10,38 @@ export const Find = () => {
toggleMatchWholeWord, toggleMatchWholeWord,
toggleUseRegex toggleUseRegex
} = useContext(SearchContext) } = useContext(SearchContext)
const timeOutId = useRef(null)
const [inputValue, setInputValue] = useState(""); const [inputValue, setInputValue] = useState('')
const change = async(e) => { const change = async e => {
setInputValue(e.target.value) setInputValue(e.target.value)
clearTimeout(timeOutId.current)
await cancelSearch() await cancelSearch()
timeOutId.current = setTimeout(async () => await setFind(e.target.value), 500)
} }
useEffect(() =>{ const handleKeypress = async e => {
if (e.charCode === 13 || e.keyCode === 13) {
await setFind(inputValue)
}
}
useEffect(() => {
setInputValue('') setInputValue('')
},[state.workspace]) }, [state.workspace])
return ( return (
<> <>
<div className="search_plugin_find-part"> <div className="search_plugin_find-part">
<div className="search_plugin_search-input"> <div className="search_plugin_search-input">
<input <input
id='search_input' id="search_input"
placeholder="Search" placeholder="Search ( Enter to search )"
className="form-control" className="form-control"
value={inputValue} value={inputValue}
onChange={async(e) => await change(e)} onChange={async e => await change(e)}
onKeyPress={handleKeypress}
></input> ></input>
<div className="search_plugin_controls"> <div className="search_plugin_controls">
<div <div
data-id='search_case_sensitive' data-id="search_case_sensitive"
title="Match Case" title="Match Case"
className={`monaco-custom-checkbox codicon codicon-case-sensitive ${ className={`monaco-custom-checkbox codicon codicon-case-sensitive ${
state.casesensitive ? 'checked' : '' state.casesensitive ? 'checked' : ''
@ -50,7 +55,7 @@ export const Find = () => {
}} }}
></div> ></div>
<div <div
data-id='search_whole_word' data-id="search_whole_word"
title="Match Whole Word" title="Match Whole Word"
className={`monaco-custom-checkbox codicon codicon-whole-word ${ className={`monaco-custom-checkbox codicon codicon-whole-word ${
state.matchWord ? 'checked' : '' state.matchWord ? 'checked' : ''
@ -64,7 +69,7 @@ export const Find = () => {
}} }}
></div> ></div>
<div <div
data-id='search_use_regex' data-id="search_use_regex"
title="Use Regular Expression" title="Use Regular Expression"
className={`monaco-custom-checkbox codicon codicon-regex ${ className={`monaco-custom-checkbox codicon codicon-regex ${
state.useRegExp ? 'checked' : '' state.useRegExp ? 'checked' : ''

@ -1,16 +1,22 @@
import React, { useContext, useRef, useState } from 'react' import React, { useContext, useEffect, useRef, useState } from 'react'
import { SearchContext } from '../context/context' import { SearchContext } from '../context/context'
export const Include = props => { export const Include = props => {
const { setInclude, cancelSearch } = useContext(SearchContext) const { setInclude, cancelSearch } = useContext(SearchContext)
const [includeInput, setIncludeInput] = useState<string>('') const [includeInput, setIncludeInput] = useState<string>('*.sol, *.js')
const timeOutId = useRef(null)
const change = async e => { const change = async e => {
setIncludeInput(e.target.value) setIncludeInput(e.target.value)
clearTimeout(timeOutId.current)
await cancelSearch() await cancelSearch()
timeOutId.current = setTimeout(() => setInclude(e.target.value), 500)
} }
const handleKeypress = async e => {
if (e.charCode === 13 || e.keyCode === 13) {
await setInclude(includeInput)
}
}
useEffect(() => {
setInclude(includeInput)
}, [])
return ( return (
<> <>
@ -18,9 +24,10 @@ export const Include = props => {
<label className='mt-2'>Files to include</label> <label className='mt-2'>Files to include</label>
<input <input
id='search_include' id='search_include'
placeholder="Include ie contracts/**/*.sol" placeholder="Include ie *.sol ( Enter to include )"
className="form-control" className="form-control"
onChange={async(e) => change(e)} onChange={async(e) => change(e)}
onKeyPress={handleKeypress}
value={includeInput} value={includeInput}
></input> ></input>
</div> </div>

@ -6,7 +6,6 @@ import { Include } from './Include'
import { Exclude } from './Exclude' import { Exclude } from './Exclude'
import { FindContainer } from './FindContainer' import { FindContainer } from './FindContainer'
import { Undo } from './Undo' import { Undo } from './Undo'
import { CacncelSearch } from './CancelSearch'
export const SearchTab = props => { export const SearchTab = props => {

@ -2,12 +2,12 @@ import React from "react"
import { useContext } from "react" import { useContext } from "react"
import { SearchContext } from "../context/context" import { SearchContext } from "../context/context"
export const CacncelSearch = () => { export const StopSearch = () => {
const { cancelSearch } = useContext(SearchContext) const { cancelSearch } = useContext(SearchContext)
const cancel = async () => { const cancel = async () => {
await cancelSearch() await cancelSearch(false)
} }
return ( return (
<a onClick={async () => await cancel()}>stop</a> <a className="badge badge-danger search_plugin_stop" onClick={async () => await cancel()}>stop</a>
) )
} }

@ -28,8 +28,10 @@ export const ResultItem = (props: ResultItemProps) => {
useEffect(() => { useEffect(() => {
if (props.file.forceReload) { if (props.file.forceReload) {
console.log('force reload')
clearTimeout(reloadTimeOut.current) clearTimeout(reloadTimeOut.current)
clearTimeout(loadTimeout.current) clearTimeout(loadTimeout.current)
subscribed.current = true
reloadTimeOut.current = setTimeout(() => reload(), 1000) reloadTimeOut.current = setTimeout(() => reload(), 1000)
} }
}, [props.file.forceReload]) }, [props.file.forceReload])
@ -47,6 +49,16 @@ export const ResultItem = (props: ResultItemProps) => {
} }
}, []) }, [])
useEffect((): any => {
if(!state.run){
clearTimeout(reloadTimeOut.current)
clearTimeout(loadTimeout.current)
subscribed.current = false
} else {
subscribed.current = true
}
},[state.run])
const confirmReplace = async () => { const confirmReplace = async () => {
setLoading(true) setLoading(true)
try { try {
@ -65,6 +77,7 @@ export const ResultItem = (props: ResultItemProps) => {
} }
const doLoad = () => { const doLoad = () => {
if(!subscribed.current) return
findText(props.file.filename).then(res => { findText(props.file.filename).then(res => {
if (subscribed.current) { if (subscribed.current) {
setLines(res) setLines(res)

@ -1,5 +1,6 @@
import React, { useContext, useEffect } from 'react' import React, { useContext, useEffect } from 'react'
import { SearchContext } from '../../context/context' import { SearchContext } from '../../context/context'
import { StopSearch } from '../StopSearch'
import { ResultItem } from './ResultItem' import { ResultItem } from './ResultItem'
export const Results = () => { export const Results = () => {
@ -7,11 +8,12 @@ export const Results = () => {
return ( return (
<div data-id="search_results" className="mt-2"> <div data-id="search_results" className="mt-2">
<div className="search_plugin_search_indicator py-1"> <div className="search_plugin_search_indicator py-1">
{' '} {state.searching && !state.clipped ? <StopSearch></StopSearch> : null} {state.searching && !state.clipped
{state.searching && !state.clipped
? `searching in ${state.searching}` ? `searching in ${state.searching}`
: null} : null}<br></br>
</div> </div>
{state.find && !state.clipped ? ( {state.find && !state.clipped ? (
<div className="search_plugin_result_count_number badge badge-pill badge-secondary"> <div className="search_plugin_result_count_number badge badge-pill badge-secondary">
showing {state.count} results {state.fileCount} in files showing {state.count} results {state.fileCount} in files

@ -45,7 +45,7 @@ export interface SearchingStateInterface {
replaceAllInFile: (result: SearchResult) => Promise<void> replaceAllInFile: (result: SearchResult) => Promise<void>
undoReplace: (buffer: undoBufferRecord) => Promise<void> undoReplace: (buffer: undoBufferRecord) => Promise<void>
clearUndo: () => void clearUndo: () => void
cancelSearch: () => Promise<void> cancelSearch: (clearResults?:boolean) => Promise<void>
} }
export const SearchContext = createContext<SearchingStateInterface>(null) export const SearchContext = createContext<SearchingStateInterface>(null)
@ -177,6 +177,13 @@ export const SearchProvider = ({
}) })
}, },
setRun(value: boolean) {
dispatch({
type: 'SET_RUN',
payload: value
})
},
findText: async (path: string) => { findText: async (path: string) => {
if (!plugin) return if (!plugin) return
try { try {
@ -191,6 +198,7 @@ export const SearchProvider = ({
clearSearchingTimeout.current = setTimeout(() => value.setSearching(null), 500) clearSearchingTimeout.current = setTimeout(() => value.setSearching(null), 500)
return result return result
} catch (e) { } catch (e) {
console.log(e)
value.setSearching(null) value.setSearching(null)
// do nothing // do nothing
} }
@ -275,9 +283,10 @@ export const SearchProvider = ({
}) })
}, },
cancelSearch: async () => { cancelSearch: async (clearResults: boolean = true) => {
plugin.cancel('fileManager') plugin.cancel('fileManager')
value.clearStats() if(clearResults) value.clearStats()
value.setRun(false)
}, },
setClipped: (value: boolean) => { setClipped: (value: boolean) => {
@ -305,6 +314,7 @@ export const SearchProvider = ({
}) })
plugin.on('fileManager', 'fileAdded', async file => { plugin.on('fileManager', 'fileAdded', async file => {
setFiles(await getDirectory('/', plugin)) setFiles(await getDirectory('/', plugin))
await reloadStateForFile(file)
}) })
plugin.on('fileManager', 'currentFileChanged', async file => { plugin.on('fileManager', 'currentFileChanged', async file => {
value.setCurrentFile(file) value.setCurrentFile(file)
@ -372,7 +382,7 @@ export const SearchProvider = ({
useEffect(() => { useEffect(() => {
if(state.count>500) { if(state.count>500) {
value.setClipped(true) value.setClipped(true)
value.cancelSearch() value.cancelSearch(false)
} }
}, [state.count]) }, [state.count])

@ -40,7 +40,8 @@ export const SearchReducer = (state: SearchState = SearchingInitialState, action
return { return {
...state, ...state,
searchResults: action.payload, searchResults: action.payload,
count: 0 count: 0,
run: true
} }
case 'SET_UNDO_ENABLED': case 'SET_UNDO_ENABLED':
if(state.undoBuffer[`${action.payload.workspace}/${action.payload.path}`]){ if(state.undoBuffer[`${action.payload.workspace}/${action.payload.path}`]){
@ -116,7 +117,11 @@ export const SearchReducer = (state: SearchState = SearchingInitialState, action
...state, ...state,
clipped: action.payload clipped: action.payload
} }
case 'SET_RUN':
return {
...state,
run: action.payload
}
case 'TOGGLE_CASE_SENSITIVE': case 'TOGGLE_CASE_SENSITIVE':
return { return {
...state, ...state,

@ -138,4 +138,7 @@
white-space: pre; white-space: pre;
text-overflow: ellipsis; text-overflow: ellipsis;
overflow: hidden; overflow: hidden;
}
.search_plugin_stop{
cursor: pointer;
} }

@ -65,6 +65,7 @@ export interface SearchState {
currentFile: string, currentFile: string,
workspace: string, workspace: string,
searching: string | null, searching: string | null,
run: boolean,
} }
export const SearchingInitialState: SearchState = { export const SearchingInitialState: SearchState = {
@ -87,5 +88,6 @@ export const SearchingInitialState: SearchState = {
undoBuffer: null, undoBuffer: null,
currentFile: '', currentFile: '',
workspace: '', workspace: '',
searching: null searching: null,
run: false,
} }
Loading…
Cancel
Save