diff --git a/package.json b/package.json index 3fdea429f4..3c8f52722a 100644 --- a/package.json +++ b/package.json @@ -230,6 +230,7 @@ "react-svg-loader": "^3.0.3", "react-svg-spinner": "^1.0.4", "react-tabs": "^3.2.3", + "react-textarea-autosize": "8.3.0", "redux": "^4.0.5", "redux-devtools-extension": "^2.13.8", "redux-localstorage": "^0.4.1", diff --git a/webapp/javascript/components/TagsBar.tsx b/webapp/javascript/components/TagsBar.tsx index cae8b7b312..a792627a15 100644 --- a/webapp/javascript/components/TagsBar.tsx +++ b/webapp/javascript/components/TagsBar.tsx @@ -1,6 +1,7 @@ import React, { useState, useEffect, useRef } from 'react'; import Button from '@webapp/ui/Button'; import 'react-dom'; +import { useWindowWidth } from '@react-hook/window-size'; import { TagsState } from '@webapp/redux/reducers/continuous'; import Dropdown, { SubMenu, @@ -8,6 +9,7 @@ import Dropdown, { FocusableItem, MenuGroup, } from '@webapp/ui/Dropdown'; +import TextareaAutosize from 'react-textarea-autosize'; import { Prism } from '@webapp/util/prism'; import { Query, brandQuery } from '@webapp/models/query'; import styles from './TagsBar.module.css'; @@ -87,8 +89,11 @@ interface QueryInputProps { } function QueryInput({ initialQuery, onSubmit }: QueryInputProps) { + const windowWidth = useWindowWidth(); const [query, setQuery] = useState(initialQuery); const codeRef = useRef(null); + const textareaRef = useRef(null); + const [textAreaSize, setTextAreaSize] = useState({ width: 0, height: 0 }); // If query updated upstream, most likely the application changed // So we prefer to use it @@ -102,28 +107,49 @@ function QueryInput({ initialQuery, onSubmit }: QueryInputProps) { } }, [query]); + useEffect(() => { + setTextAreaSize({ + width: textareaRef?.current?.['offsetWidth'] || 0, + height: textareaRef?.current?.['offsetHeight'] || 0, + }); + }, [query, windowWidth, onSubmit]); + + const onFormSubmit = ( + e: + | React.FormEvent + | React.KeyboardEvent + ) => { + e.preventDefault(); + onSubmit(query); + }; + + const handleTextareaKeyDown = ( + e: React.KeyboardEvent + ) => { + if ((e.keyCode === 10 || e.keyCode === 13) && e.ctrlKey) { + onFormSubmit(e); + } + }; + return ( -
{ - e.preventDefault(); - onSubmit(query); - }} - > + - setQuery(brandQuery(e.target.value))} + onKeyDown={handleTextareaKeyDown} />