You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React.js中如何向动态渲染的列表窗口添加组件

React.js中如何向动态渲染的列表窗口添加组件

嘿,我看了你的代码,问题主要出在数据结构不统一和对react-window渲染逻辑的误解上,咱们一步步理顺解决:

首先你最开始的items是字符串数组,但handleAdd里往list中添加的是{name, id: uuidv4()}这样的对象,这就导致Row组件里artistName={items[index]}(也就是现在的list[index]),新增项时取到的是对象而非字符串,自然渲染不出正确内容。而且你之前尝试直接把RowComponent实例塞进列表的思路也不对——react-window是数据驱动渲染的,我们只需要维护好数据源,组件会自动根据数据生成对应的行,不需要把组件实例存在state里。

下面是修改后的完整代码,我标注了关键改动点:

import React from 'react'
import { FixedSizeList } from 'react-window';
import RowComponent from './RowComponent';
import { v4 as uuidv4 } from 'uuid';

// 1. 统一数据结构:初始列表也用对象数组,和后续添加的项结构保持一致
const initialItems = [
  { name: "National Anthem", id: uuidv4() }
];

function SongList() {
  // 2. 用统一结构的initialItems初始化state
  const [list, setList] = React.useState(initialItems);
  const [name, setName] = React.useState('');

  function handleChange(event){
    setName(event.target.value);
  }

  function handleAdd(){
    if(!name.trim()) return; // 加个空值判断,避免添加空项
    // 3. 添加结构一致的对象,用扩展运算符比concat更直观
    const newList = [...list, {name, id: uuidv4()}];
    setList(newList);
    setName('');
  }

  return (
    <div>
      <FixedSizeList
        height={600}
        width={450}
        itemSize={75}
        itemCount={list.length} // 这里会随list长度自动变化,触发列表重新渲染
        className="list-container"
      >
        {/* 4. 直接在render prop里使用最新的list,避免闭包导致的旧数据问题 */}
        {({ index, style }) => (
          <RowComponent 
            artistName={list[index].name} 
            num={index} 
            style={style} 
          />
        )}
      </FixedSizeList>
      <div className='adder'>
        <input type="text" value={name} onChange={handleChange} />
      </div>
      <div className="d-grid gap-2 col-6 mx-auto">
        <button className="btn btn-primary m-3" type="button" onClick={handleAdd}>Add Song</button>
      </div>
    </div>
  );
}

export default SongList;

再强调几个关键要点:

  • 始终保持列表数据源的结构统一,不要混合字符串和对象,否则渲染时会出现类型不匹配的问题
  • react-window不需要你把组件实例存在state里,只需要维护好数据,它会根据itemCount和index自动渲染对应的组件
  • 避免把Row组件单独定义在外部(除非你把list作为props传给它),不然会因为闭包捕获旧数据,导致新增项无法正常渲染

这样修改后,你输入歌曲名点击添加按钮,列表就会自动新增对应的RowComponent啦!

备注:内容来源于stack exchange,提问作者AllinTheSauce

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.22 15:13:14