首页 > 解决方案 > react native flat list 重新渲染所有项目并添加每个新项目

问题描述

我有一个简单的聊天系统,它与 express/socket io 一起运行,并与 FlatList 进行原生反应以呈现消息。

我的问题是,每次我接收或发送消息时,IE:向显示的消息添加消息,整个 FlatList 都会重新呈现,这会使它闪烁,正如您在下面的视频中看到的那样,看看这里发生了什么!

我将消息添加到平面列表的方式如下:

  const [messages, setMessages] = useState<any[]>([WELCOME_MESSAGE]);
// the following line i use when i get a new message from the server ... and the definition in the beginning of the component (so the problem isn't here...) 
    setMessages([newMessage, ...messages]);

平面列表代码本身如下:

    <FlatList
      inverted
      style={{}}
      contentContainerStyle={{
        flexGrow: 1,

        // justifyContent: "flex-end",
        paddingHorizontal: 12,
        paddingBottom: 30,
      }}
      data={data}
      renderItem={({ item }) => (
        <ChatMessage data={item} key={item._id + ""} />
      )}
      keyExtractor={(item) => item._id}
      // keyExtractor={(item) => item._id}
      refreshControl={
        <RefreshControl refreshing={loading} onRefresh={onUpdate} />
      }
    />

页面中唯一的useEffect语句如下:

  useEffect(() => {
    const unsubscribe = navigation.addListener("focus", loadMessage);

    // Return the function to unsubscribe from the event so it gets removed on unmount
    return unsubscribe;
  },[navigation]);

当我收到消息时,这就是我所做的::

  socket.on('update-chat' ,async(data : any)=>{
    console.log('<<<<<<< recieve message <<<<<<<');
    console.log(data);
    console.log('<<<<<<< recieve message <<<<<<<');
    let roomID = '' ;
    await getRoomID().then((data)=>{
            console.log('getting the room id and setting the hook...', data);
            roomID = (data?.headers.room != null)? data.headers.room  : ''; 
    });

    console.log('setting room to use in update chat...');
    // TODO check if we have the room id locally...
      if(roomID != null && roomID === data.roomId && roomID !== ''){
        // TODO ==>  just get the data and start working on the display... 
        // updating display...
        console.log('udpate chat , rooomID : ' + roomID);
        addMessage(data.message);
      }else{
        // TODO ==> store the roomID and then update display...
        // saving the roomID for later use and then update displays...
        console.log('roomID');
        await useRoom.save(data.roomId||'') ;
        addMessage(data.message); 
      }
  });

当我使用这个应用程序发短信时,它会像你们在视频中看到的那样,然后重新渲染组件变得非常疯狂,直到聊天一段时间后我得到以下错误:

PayloadTooLargeError: request entity too large

如果我继续这样做,我会得到(我只在 android 设备上得到以下内容,我不确定它是否与手头的问题有关-我将其包括在内以防万一-):

Warning: Please report: Excessive number of pending callbacks: 501. Some pending callbacks that might have leaked by never being called from native code:

之后,该应用程序只是冻结了一段时间......

标签: react-nativesocket.ioexpochatreact-native-flatlist

解决方案


推荐阅读