0

我希望聊天窗口在我发送文本时向下滚动。

实际上发送的消息不会触发滚动,所以它们是隐藏的。

这是一个示例(我正在使用 MS Fluent UI for React 库的聊天组件)

我找到了这篇文章,但我无法整合它(不知道在哪里声明了 endMessage )在我的情况下它的价值是undefined.

import React from "react";
import { Avatar, Chat, Divider, Input } from "@fluentui/react-northstar";
import { AcceptIcon } from "@fluentui/react-icons-northstar";

const janeAvatar = {
  image: "public/images/avatar/small/ade.jpg",
  status: {
    color: "green",
    icon: <AcceptIcon />
  }
};

const ChatExample = () => {
  const items = [
    {
      message: (
        <Chat.Message
          content="Hello"
          author="John Doe"
          timestamp="Yesterday, 10:15 PM"
          mine
        />
      ),
      contentPosition: "end",
      attached: "top",
      key: "message-id-1"
    },
    {
      message: (
        <Chat.Message
          content="I'm back!"
          author="John Doe"
          timestamp="Yesterday, 10:15 PM"
          mine
        />
      ),
      contentPosition: "end",
      attached: true,
      key: "message-id-2"
    },
    {
      message: (
        <Chat.Message
          content={{
            content: (
              <div>
                What do you think about <a href="#">www.goodFood.com</a>?
              </div>
            )
          }}
          author="John Doe"
          timestamp="Yesterday, 10:15 PM"
          mine
        />
      ),
      contentPosition: "end",
      attached: "bottom",
      key: "message-id-3"
    },
    {
      gutter: <Avatar {...janeAvatar} />,
      message: (
        <Chat.Message
          content="Hi"
          author="Jane Doe"
          timestamp="Yesterday, 10:15 PM"
        />
      ),
      attached: "top",
      key: "message-id-4"
    },
    {
      gutter: <Avatar {...janeAvatar} />,
      message: (
        <Chat.Message
          content="Looks good!"
          author="Jane Doe"
          timestamp="Yesterday, 10:15 PM"
        />
      ),
      attached: true,
      key: "message-id-5"
    },
    {
      gutter: <Avatar {...janeAvatar} />,
      message: (
        <Chat.Message
          content={
            <div>
              I also like <a href="#">www.goodFood2.com</a>.
            </div>
          }
          author="Jane Doe"
          timestamp="Yesterday, 10:15 PM"
        />
      ),
      attached: "bottom",
      key: "message-id-6"
    },
    {
      message: (
        <Chat.Message
          content="Would you like to grab lunch there?"
          author="John Doe"
          timestamp="Yesterday, 10:16 PM"
          mine
        />
      ),
      contentPosition: "end",
      key: "message-id-7"
    },
    {
      gutter: <Avatar {...janeAvatar} />,
      message: (
        <Chat.Message
          content="Sure! Let's try it."
          author="Jane Doe"
          timestamp="Yesterday, 10:15 PM"
        />
      ),
      key: "message-id-8"
    },
    {
      children: <Divider content="Today" color="brand" important />,
      key: "message-id-9"
    },
    {
      message: (
        <Chat.Message
          content="Ok, let's go."
          author="John Doe"
          timestamp="Today, 11:15 PM"
          mine
        />
      ),
      contentPosition: "end",
      key: "message-id-10"
    }
  ];
  const [inputValue, setInputValue] = React.useState("");
  const [itemsChat, setItemsChat] = React.useState(items);
  const chatStyle = {
    height: 500,
    overflow: "scroll"
  };
  const handleKeyDown = event => {
    if (event.key == "Enter") {
      console.log(event);
      let elm = {
        message: (
          <Chat.Message
            content={inputValue}
            author="John Doe"
            timestamp="Yesterday, 10:15 PM"
            mine
          />
        ),
        contentPosition: "end",
        attached: "top",
        key: "message-id-1"
      };
      setItemsChat(itemsChat => [...itemsChat, elm]);
      setInputValue("");
    }
  };
  return (
    <div>
      <Chat style={chatStyle} items={itemsChat} />

      <Input
        fluid
        placeholder="Inverted color input..."
        value={inputValue}
        onKeyDown={event => handleKeyDown(event)}
        onChange={event => setInputValue(event.target.value)}
      />
    </div>
  );
};

export default ChatExample;
4

2 回答 2

5

您可以简单地使用具有itemsChatas 依赖关系的效果。只需抓住聊天ul元素并滚动到底部。

useEffect(() => {
    document.querySelector('.ui-chat').scrollTop = document.querySelector('.ui-chat').scrollHeight
  }, [itemsChat])

您的代码的工作副本在这里

于 2020-05-17T12:58:43.100 回答
1

endMessage 变量是对他们在聊天结束时包含的空 div 的引用。

你可以在 React 文档中了解更多关于 React 中的引用:https ://reactjs.org/docs/refs-and-the-dom.html

另一个问题的示例代码的不同之处在于它们不使用内置的 createRef 方法,而是传递一个自定义函数,该函数将更新 .endMessage 变量以指向当前元素。

React 文档中显示的方法是在组件顶部添加一个变量并用 useRef 钩子填充它(将其命名为 endMessage 以与另一篇文章中的方案保持一致)然后在 div 中作为最后一条聊天消息,您可以将该变量用于 ref 道具:

<div ref={endMessage} />

在成功发布新帖子的回调函数中,您将调用endMessage.current.scrollIntoView(注意:使用内置 react ref 钩子或函数时需要使用 current 。如果将自定义函数传递给 ref 道具,您始终可以分配当前部分直接引用,如其他 SO 帖子中所示。

我不熟悉您使用的 Chat 组件,因此我无法真正提供有关如何将该 div 放在最底部的任何提示。另一个问题是关于一个通用/自编程的聊天工具,只是假设您可以控制聊天框,并且可以在最后放置一个静态元素来呈现动态聊天消息列表。

于 2020-05-17T12:44:37.500 回答