IO-2208 added virtualization to conversation list

This commit is contained in:
swtmply
2023-05-18 23:04:10 +08:00
parent 4bc8ff26d2
commit d66fdfb2e0
3 changed files with 167 additions and 91 deletions

View File

@@ -4,9 +4,9 @@ import {
ShrinkOutlined,
SyncOutlined,
} from "@ant-design/icons";
import { useQuery, useSubscription } from "@apollo/client";
import { useLazyQuery, useQuery, useSubscription } from "@apollo/client";
import { Badge, Card, Col, Row, Space, Tag, Tooltip, Typography } from "antd";
import React, { useEffect, useState } from "react";
import React, { useCallback, useEffect, useState } from "react";
import { useTranslation } from "react-i18next";
import { connect } from "react-redux";
import { createStructuredSelector } from "reselect";
@@ -25,7 +25,6 @@ import ChatConversationContainer from "../chat-conversation/chat-conversation.co
import ChatNewConversation from "../chat-new-conversation/chat-new-conversation.component";
import LoadingSpinner from "../loading-spinner/loading-spinner.component";
import "./chat-popup.styles.scss";
import { useInView } from "react-intersection-observer";
const mapStateToProps = createStructuredSelector({
selectedConversation: selectSelectedConversation,
@@ -42,7 +41,6 @@ export function ChatPopupComponent({
}) {
const { t } = useTranslation();
const [pollInterval, setpollInterval] = useState(0);
const { ref, inView } = useInView({});
const { data: unreadData } = useSubscription(
UNREAD_CONVERSATION_COUNT_SUBSCRIPTION
@@ -56,15 +54,14 @@ export function ChatPopupComponent({
// }
// );
const { loading, data, called, refetch, fetchMore, subscribeToMore } =
useQuery(CONVERSATION_LIST_QUERY, {
variables: {
offset: 0,
},
fetchPolicy: "cache-and-network",
nextFetchPolicy: "cache-first",
skip: !chatVisible,
});
const [
getConversations,
{ loading, data, called, fetchMore, subscribeToMore },
] = useLazyQuery(CONVERSATION_LIST_QUERY, {
fetchPolicy: "cache-and-network",
nextFetchPolicy: "cache-first",
skip: !chatVisible,
});
const fcmToken = sessionStorage.getItem("fcmtoken");
@@ -77,18 +74,60 @@ export function ChatPopupComponent({
}, [fcmToken]);
useEffect(() => {
if (called && chatVisible) refetch();
}, [chatVisible, called, refetch]);
if (called && chatVisible)
getConversations({
variables: {
offset: 0,
},
});
}, [chatVisible, called, getConversations]);
useEffect(() => {
if (inView && data && data.conversations) {
const loadMoreConversations = useCallback(() => {
if (data)
fetchMore({
variables: {
offset: data.conversations.length,
},
});
}
}, [inView, data, fetchMore]);
}, [data, fetchMore]);
const subscribeToMoreConversations = useCallback(
() =>
subscribeToMore({
document: CONVERSATION_LIST_SUBSCRIPTION,
variables: { offset: 0 },
updateQuery: (prev, { subscriptionData }) => {
console.log("Hello");
if (
!subscriptionData.data ||
subscriptionData.data.conversations.length === 0
)
return prev;
let conversations = prev.conversations;
const newConversations = subscriptionData.data.conversations;
for (const conversation of newConversations) {
const index = conversations.findIndex(
(prevConversation) => prevConversation.id === conversation.id
);
if (index !== -1) {
conversations.splice(index, 1);
conversations.unshift(conversation);
continue;
}
conversation.unshift(conversation);
}
return Object.assign({}, prev, {
conversations: conversations,
});
},
}),
[subscribeToMore]
);
const unreadCount = unreadData?.messages_aggregate.aggregate.count || 0;
@@ -105,10 +144,10 @@ export function ChatPopupComponent({
<Tooltip title={t("messaging.labels.recentonly")}>
<InfoCircleOutlined />
</Tooltip>
<SyncOutlined
{/* <SyncOutlined
style={{ cursor: "pointer" }}
onClick={() => refetch()}
/>
/> */}
{pollInterval > 0 && (
<Tag color="yellow">{t("messaging.labels.nopush")}</Tag>
)}
@@ -125,7 +164,8 @@ export function ChatPopupComponent({
) : (
<ChatConversationListComponent
conversationList={data ? data.conversations : []}
subscribeToMoreConversations={() => {
loadMoreConversations={loadMoreConversations}
subscribeToMoreConversations={() =>
subscribeToMore({
document: CONVERSATION_LIST_SUBSCRIPTION,
variables: { offset: 0 },
@@ -135,16 +175,33 @@ export function ChatPopupComponent({
subscriptionData.data.conversations.length === 0
)
return prev;
let conversations = [...prev.conversations];
const newConversations =
subscriptionData.data.conversations;
for (const conversation of newConversations) {
const index = conversations.findIndex(
(prevConversation) =>
prevConversation.id === conversation.id
);
if (index !== -1) {
conversations.splice(index, 1);
conversations.unshift(conversation);
continue;
}
conversations.unshift(conversation);
}
return Object.assign({}, prev, {
conversations: [...newConversations],
conversations: conversations,
});
},
});
}}
ref={ref}
})
}
/>
)}
</Col>