17579: added check if search input contains value
[arvados-workbench2.git] / src / components / search-input / search-input.tsx
index edc82d55a419caa55744f39a4e184c66f55fcffc..50338f401c9387b680ef417a715e2130d932b265 100644 (file)
@@ -2,88 +2,10 @@
 //
 // SPDX-License-Identifier: AGPL-3.0
 
-import * as React from 'react';
-import { IconButton, Paper, StyleRulesCallback, withStyles, WithStyles, FormControl, InputLabel, Input, InputAdornment, FormHelperText } from '@material-ui/core';
+import React from 'react';
+import { IconButton, StyleRulesCallback, withStyles, WithStyles, FormControl, InputLabel, Input, InputAdornment, Tooltip } from '@material-ui/core';
 import SearchIcon from '@material-ui/icons/Search';
 
-interface SearchInputDataProps {
-    value: string;
-}
-
-interface SearchInputActionProps {
-    onSearch: (value: string) => any;
-    debounce?: number;
-}
-
-type SearchInputProps = SearchInputDataProps & SearchInputActionProps & WithStyles<CssRules>;
-
-interface SearchInputState {
-    value: string;
-}
-
-export const DEFAULT_SEARCH_DEBOUNCE = 1000;
-
-class SearchInput extends React.Component<SearchInputProps> {
-
-    state: SearchInputState = {
-        value: ""
-    };
-
-    timeout: number;
-
-    render() {
-        const { classes } = this.props;
-        return <form onSubmit={this.handleSubmit}>
-            <FormControl>
-                <InputLabel>Search</InputLabel>
-                <Input
-                    type="text"
-                    value={this.state.value}
-                    onChange={this.handleChange}
-                    endAdornment={
-                        <InputAdornment position="end">
-                            <IconButton
-                                onClick={this.handleSubmit}>
-                                <SearchIcon />
-                            </IconButton>
-                        </InputAdornment>
-                    } />
-            </FormControl>
-        </form>;
-    }
-
-    componentDidMount() {
-        this.setState({ value: this.props.value });
-    }
-
-    componentWillReceiveProps(nextProps: SearchInputProps) {
-        if (nextProps.value !== this.props.value) {
-            this.setState({ value: nextProps.value });
-        }
-    }
-
-    componentWillUnmount() {
-        clearTimeout(this.timeout);
-    }
-
-    handleSubmit = (event: React.FormEvent<HTMLElement>) => {
-        event.preventDefault();
-        clearTimeout(this.timeout);
-        this.props.onSearch(this.state.value);
-    }
-
-    handleChange = (event: React.ChangeEvent<HTMLInputElement>) => {
-        clearTimeout(this.timeout);
-        this.setState({ value: event.target.value });
-        this.timeout = window.setTimeout(
-            () => this.props.onSearch(this.state.value),
-            this.props.debounce || DEFAULT_SEARCH_DEBOUNCE
-        );
-
-    }
-
-}
-
 type CssRules = 'container' | 'input' | 'button';
 
 const styles: StyleRulesCallback<CssRules> = theme => {
@@ -110,4 +32,95 @@ const styles: StyleRulesCallback<CssRules> = theme => {
     };
 };
 
-export default withStyles(styles)(SearchInput);
\ No newline at end of file
+interface SearchInputDataProps {
+    value: string;
+    label?: string;
+    selfClearProp: string;
+}
+
+interface SearchInputActionProps {
+    onSearch: (value: string) => any;
+    debounce?: number;
+}
+
+type SearchInputProps = SearchInputDataProps & SearchInputActionProps & WithStyles<CssRules>;
+
+interface SearchInputState {
+    value: string;
+    label: string;
+    selfClearProp: string;
+}
+
+export const DEFAULT_SEARCH_DEBOUNCE = 1000;
+
+export const SearchInput = withStyles(styles)(
+    class extends React.Component<SearchInputProps> {
+        state: SearchInputState = {
+            value: "",
+            label: "",
+            selfClearProp: ""
+        };
+
+        timeout: number;
+
+        render() {
+            return <form onSubmit={this.handleSubmit}>
+                <FormControl>
+                    <InputLabel>{this.state.label}</InputLabel>
+                    <Input
+                        type="text"
+                        data-cy="search-input"
+                        value={this.state.value}
+                        onChange={this.handleChange}
+                        endAdornment={
+                            <InputAdornment position="end">
+                                <Tooltip title='Search'>
+                                    <IconButton
+                                        onClick={this.handleSubmit}>
+                                        <SearchIcon />
+                                    </IconButton>
+                                </Tooltip>
+                            </InputAdornment>
+                        } />
+                </FormControl>
+            </form>;
+        }
+
+        componentDidMount() {
+            this.setState({
+                value: this.props.value,
+                label: this.props.label || 'Search'
+            });
+        }
+
+        componentWillReceiveProps(nextProps: SearchInputProps) {
+            if (nextProps.value !== this.props.value) {
+                this.setState({ value: nextProps.value });
+            }
+            if (this.state.value !== '' && nextProps.selfClearProp && nextProps.selfClearProp !== this.state.selfClearProp) {
+                this.props.onSearch('');
+                this.setState({ selfClearProp: nextProps.selfClearProp });
+            }
+        }
+
+        componentWillUnmount() {
+            clearTimeout(this.timeout);
+        }
+
+        handleSubmit = (event: React.FormEvent<HTMLElement>) => {
+            event.preventDefault();
+            clearTimeout(this.timeout);
+            this.props.onSearch(this.state.value);
+        }
+
+        handleChange = (event: React.ChangeEvent<HTMLInputElement>) => {
+            clearTimeout(this.timeout);
+            this.setState({ value: event.target.value });
+            this.timeout = window.setTimeout(
+                () => this.props.onSearch(this.state.value),
+                this.props.debounce || DEFAULT_SEARCH_DEBOUNCE
+            );
+
+        }
+    }
+);