Introduction
Creating a seamless user experience often hinges on the small details, such as a well-designed text area for user input. In this blog post, we’ll dive into the implementation of a dynamic text area using React, which adjusts its height based on the input content and provides a smooth user experience.
Component Breakdown
CommonTextArea Component
The CommonTextArea component is a reusable component that encapsulates the logic for a dynamic text area. Here’s a detailed look at its structure and functionality:
import clsx from "clsx";
import { useLayoutEffect, useState } from "react";
export default function CommonTextArea({
inputRef,
isFocuse,
isInputError,
onChangeInput,
handleKeyDown,
setIsFocuse,
textBoxValue,
parentClassName,
textAreaClassName,
placeHolder,
}: {
inputRef: React.RefObject<HTMLTextAreaElement>;
isFocuse?: boolean;
isInputError?: boolean;
onChangeInput: (event: React.ChangeEvent<HTMLTextAreaElement>) => void;
handleKeyDown: (event: React.KeyboardEvent<HTMLTextAreaElement>) => void;
setIsFocuse: React.Dispatch<React.SetStateAction<boolean>>;
textBoxValue?: string;
parentClassName?: string;
textAreaClassName?: string;
placeHolder?: string;
}) {
const [scrollBar, setScrollBar] = useState<boolean>(false);
useLayoutEffect(() => {
const textArea: any =
inputRef.current ?? document.getElementById("text_area_input");
if (textArea) {
textArea.style.height = "0px";
const scrollHeight = textArea.scrollHeight;
textArea.style.height = scrollHeight + "px";
if (scrollHeight >= 200) {
setScrollBar(true);
} else {
setScrollBar(false);
}
}
}, [inputRef, textBoxValue]);
return (
<div
className={clsx(
{
"form-input-error": isInputError,
"ask-question-input-focus": isFocuse,
},
parentClassName
)}
onClick={() => {
setIsFocuse(true);
}}
>
<textarea
id="text_area_input"
ref={inputRef}
className={clsx(textAreaClassName, "textarea_design", {
"overflow-y-auto": scrollBar,
})}
placeholder={placeHolder}
value={textBoxValue}
onClick={() => {
setIsFocuse(true);
}}
onKeyDown={handleKeyDown}
style={{ height: "57px" }}
onChange={onChangeInput}
/>
</div>
);
}
Key Features
Dynamic Height Adjustment: The text area dynamically adjusts its height based on the input content, ensuring that users have a comfortable and responsive typing experience.
Conditional Styling: The component uses the clsx library to conditionally apply styles based on the component's state, such as focus or error states.
Scrollable Content: When the content exceeds a certain height, a scrollbar appears, ensuring that the text area remains user-friendly and does not overflow.
App Component Integration
The CommonTextArea component can be easily integrated into any React application. Here’s how you can use it:
const inputRef = useRef<HTMLTextAreaElement | null>(null);
const [isFocuse, setIsFocuse] = useState<boolean>(false);
const [isInputError, setIsInputError] = useState<boolean>(false);
const onChangeInput = (e: React.ChangeEvent<HTMLTextAreaElement>) => {
setChatPrompt(e.target.value);
setIsInputError(false);
};
const handleKeyDown = (e: React.KeyboardEvent<HTMLTextAreaElement>) => {
setIsFocuse(true);
if (e.key === "Enter" && !e.shiftKey) {
e.preventDefault();
onSubmitdata(); // submit event
}
};
useEffect(() => {
inputRef?.current?.focus();
}, [inputRef]);
return (
<CommonTextArea
inputRef={inputRef}
isFocuse={isFocuse}
isInputError={isInputError}
onChangeInput={onChangeInput}
handleKeyDown={handleKeyDown}
setIsFocuse={setIsFocuse}
textBoxValue={"default text box value"}
parentClassName={"text_area_parent "}
textAreaClassName={"ask-question-input caret-raisinblack"}
/>
);
CSS Styling
Proper styling is crucial for a great user experience. Here are the styles used in this implementation:
.form-input-error {
border-color: red;
background-color: #f5f5f5;
}
.ask-question-input-focus {
outline: none;
border-color: #0f9d58;
color: #2d2d2d;
background-color: #e6f4ea;
}
.text_area_parent {
width: 100%;
background-color: #f5f5f5;
display: flex;
justify-content: start;
align-items: center;
padding: 5px;
border-radius: 10px;
font-size: 16px;
border: 1px solid transparent;
transition: border-color 0.3s, background-color 0.3s;
}
.ask-question-input {
width: 100%;
background-color: transparent;
font-size: 16px;
border: none;
outline: none;
resize: none;
overflow: hidden;
max-height: 230px;
padding: 14px;
}
.ask-question-input::-webkit-scrollbar-thumb {
background-color: #d9d9d9;
}
Conclusion
By implementing a dynamic text area in your React application, you can significantly enhance user experience, making text inputs more user-friendly and visually appealing. The CommonTextArea component is highly customizable and can be adapted to various use cases, ensuring a consistent and responsive design throughout your application.
[(https://andarist.github.io/react-textarea-autosize/)]
[https://www.npmjs.com/package/react-textarea-autosize]
also you dont want to custom then you can use this package
Top comments (0)