import React, { ChangeEvent, forwardRef } from "react"; import styled, { useTheme } from "styled-components"; import Box, { BoxSpan } from "../../Styled/Box"; import { RawButton } from "../../Styled/Button"; import Icon, { StyledIcon } from "../../Styled/Icon"; import Text from "../../Styled/Text"; const SearchInput = styled.input<{ rounded?: boolean }>` box-sizing: border-box; margin-top: 0; margin-bottom: 0; border: none; border-radius: 4px; height: 40px; width: 100%; display: block; padding: 0.5rem 40px; vertical-align: middle; -webkit-appearance: none; `; interface SearchBoxProps { onSearchTextChanged: (text: string) => void; onDoSearch: () => void; searchText: string; onFocus?: () => void; placeholder?: string; onClear?: () => void; alwaysShowClear?: boolean; autoFocus?: boolean; inputBoxRef?: React.Ref; } /** * Simple dumb search box component that leaves the actual execution of searches to the component that renders it. Note * that just like an input, this calls onSearchTextChanged when the value is changed, and expects that its parent * component will listen for this and update searchText with the new value. */ export const SearchBox: React.FC = ({ onSearchTextChanged, onDoSearch, searchText, onFocus, placeholder = "Search", onClear, alwaysShowClear = false, autoFocus = false, inputBoxRef }) => { const theme = useTheme(); const handleChange = (event: ChangeEvent) => { const value = event.target.value; onSearchTextChanged(value); }; const clearSearch = () => { onSearchTextChanged(""); if (onClear) { onClear(); } }; const hasValue = searchText.length > 0; return (
{ event.preventDefault(); event.stopPropagation(); onDoSearch(); }} css={` position: relative; width: 100%; `} > {(alwaysShowClear || hasValue) && ( {/* The type="button" here stops the browser from assuming the close button is the submit button */} )}
); }; type WrappedSearchBoxProps = Omit; const SearchBoxWithRef = ( props: WrappedSearchBoxProps, ref: React.Ref ) => ; export default forwardRef(SearchBoxWithRef);