React聊天应用如何实现textarea向上扩展且带动父div同步上移
解决方案
核心思路
你当前代码的核心问题是所有父级容器都设置了固定高度,限制了元素自适应撑开;使用absolute定位脱离文档流自然无法带动父元素同步位移。我们可以通过「自适应高度容器+动态计算textarea高度」的方案实现需求,且因为外层容器本身设置了align-self: flex-end靠底部对齐,高度增加时会自动向上扩展,完全符合你的交互要求。
第一步:修改CSS代码
需要调整的CSS规则如下:
/* 移除固定高度,改用min-height保证最小高度、允许内容撑开 */ .chat-inputbox-container { width: 100%; min-height: 113px; /* 原height改为min-height */ align-self: flex-end; display: flex; justify-content: center; padding: 10px 0; /* 增加上下内边距避免贴边 */ } .chat-inputbox-wrapper { width: 736px; min-height: 92px; /* 原height改为min-height */ display: flex; flex-direction: row; justify-content: space-between; align-items: flex-end; /* 子元素底部对齐,保证高度增加时向上扩展 */ } .chat-microphone-container { width: 32px; min-height: 92px; /* 原height改为min-height */ display: flex; align-items: center; justify-content: center; margin-right: 10px; } .chat-microphone { width: 32px; height: 32px; background: orangered; } .inputbox-container { display: flex; flex-direction: column; gap: 4px; /* 输入框和字数提示的间距 */ } .inputbox-wrapper { width: 694px; min-height: 52px; /* 原height改为min-height */ display: flex; align-items: center; padding: 8px 0; /* 上下内边距适配内容高度变化 */ background: gray; border: 1px solid red; box-sizing: border-box; border-radius: 4px; } .chat-input-box { width: 632px; min-height: 20px; /* 原height改为min-height */ max-height: 100px; /* 限制最大高度,超过后出滚动条 */ font-size: 14px; line-height: 20px; border: hidden; background: #f7f7f7; outline: none; color: #0d1c3d; margin: 0 10px; /* 移除上下固定margin */ resize: none; /* 禁止用户手动调整大小 */ overflow-y: auto; /* 内容超过最大高度时显示滚动条 */ } .input-box-btn { display: flex; flex-direction: row; justify-content: center; align-items: center; padding: 0px; width: 32px; height: 32px; margin-right: 10px; background: #0078b3; border-radius: 4px; flex: none; order: 0; flex-grow: 0; } .input-character { font-size: 12px; line-height: 16px; color: #677083; }
第二步:添加React动态高度逻辑
通过监听textarea的输入事件,动态计算内容高度实现自适应:
import { useRef } from 'react'; const ChatInput = () => { const textareaRef = useRef(null); const handleInput = () => { const textarea = textareaRef.current; if (!textarea) return; // 先重置高度为auto,再赋值为scrollHeight,实现自适应 textarea.style.height = 'auto'; textarea.style.height = `${textarea.scrollHeight}px`; }; return ( <div class='chat-inputbox-container'> <div class='chat-inputbox-wrapper'> <div class='chat-microphone-container'> <div class='chat-microphone'></div> </div> <div class='inputbox-container'> <div class='inputbox-wrapper'> <textarea ref={textareaRef} type='text' class='chat-input-box' onInput={handleInput} ></textarea> <div class='input-box-btn'></div> </div> <div class='input-character-container'> <span class='input-character'> 250 out of 250 characters left </span> </div> </div> </div> </div> ) } export default ChatInput;
该方案不会出现元素脱离文档流的问题,父容器会随textarea高度同步变化,且因为整个输入区域底部对齐,高度增加时只会向上扩展,完全符合聊天输入框的交互需求。
内容的提问来源于stack exchange,提问作者Sumit Ghewade
相关产品推荐
相关产品推荐

