From d6963d1978683ebbb96abb9e2a1ccba61270e2b7 Mon Sep 17 00:00:00 2001 From: Roland Osborne Date: Tue, 26 Apr 2022 12:19:18 -0700 Subject: [PATCH] support switching conversation without close --- .../User/Conversation/useConversation.hook.js | 26 ++++++++++++++++--- net/web/src/VirtualList/VirtualList.jsx | 18 +++++++++++-- net/web/src/context/useCardContext.hook.js | 20 +++++++++++--- 3 files changed, 55 insertions(+), 9 deletions(-) diff --git a/net/web/src/User/Conversation/useConversation.hook.js b/net/web/src/User/Conversation/useConversation.hook.js index d5336c65..0569903e 100644 --- a/net/web/src/User/Conversation/useConversation.hook.js +++ b/net/web/src/User/Conversation/useConversation.hook.js @@ -7,6 +7,8 @@ import { ChannelContext } from 'context/ChannelContext'; export function useConversation() { const [state, setState] = useState({ + cardId: null, + channelId: null, topics: [], }); @@ -17,6 +19,7 @@ export function useConversation() { const conversation = useContext(ConversationContext); const topics = useRef(new Map()); const revision = useRef(null); + const id = useRef({}); const updateState = (value) => { setState((s) => ({ ...s, ...value })); @@ -101,10 +104,27 @@ export function useConversation() { } useEffect(() => { - if (card.state.init && channel.state.init) { - updateConversation(); + if (id.current.channelId != channelId || id.current.cardId) { + id.current = { cardId, channelId }; + topics.current = new Map(); + revision.current = null; + updateState({ cardId, channelId, topics: [] }); } - }, [card, channel]); + if (card.state.init && channel.state.init) { + if (cardId) { + if(card.state.cards.get(cardId)?.data.cardDetail.status != 'connected') { + window.alert("You are no longer connected to the host"); + navigate('/user') + } + } + try { + updateConversation(); + } + catch (err) { + console.log(err); + } + } + }, [card, channel, cardId, channelId]); return { state, actions }; } diff --git a/net/web/src/VirtualList/VirtualList.jsx b/net/web/src/VirtualList/VirtualList.jsx index bb4b3a8b..3c6a1d35 100644 --- a/net/web/src/VirtualList/VirtualList.jsx +++ b/net/web/src/VirtualList/VirtualList.jsx @@ -2,7 +2,7 @@ import React, { useRef, useState, useEffect } from 'react'; import { VirtualListWrapper, VirtualItem } from './VirtualList.styled'; import ReactResizeDetector from 'react-resize-detector'; -export function VirtualList({ items, itemRenderer }) { +export function VirtualList({ id, items, itemRenderer }) { const REDZONE = 256; // recenter on canvas if in canvas edge redzone const HOLDZONE = 512; // drop slots outside of holdzone of view @@ -21,6 +21,7 @@ export function VirtualList({ items, itemRenderer }) { let containers = useRef([]); let anchorBottom = useRef(true); let listRef = useRef(); + let view = useRef(null); const addSlot = (id, slot) => { setSlots((m) => { m.set(id, slot); return new Map(m); }) @@ -34,6 +35,10 @@ export function VirtualList({ items, itemRenderer }) { setSlots((m) => { m.delete(id); return new Map(m); }) } + const clearSlots = () => { + setSlots((m) => { new Map() }) + } + const growCanvasHeight = (val) => { setCanvasHeight((h) => { if (val > h) { @@ -51,8 +56,17 @@ export function VirtualList({ items, itemRenderer }) { }, [viewHeight]); useEffect(() => { + if (view.current != id) { + view.current = id; + latch.current = true; + containers.current = []; + anchorBottom.current = true; + scrollTop.current = 0; + listRef.current.scrollTo({ top: scrollTop.current, left: 0 }); + clearSlots(); + } setItems(); - }, [items]); + }, [items, id]); useEffect(() => { if (latch.current) { diff --git a/net/web/src/context/useCardContext.hook.js b/net/web/src/context/useCardContext.hook.js index 4f93edc9..22241a31 100644 --- a/net/web/src/context/useCardContext.hook.js +++ b/net/web/src/context/useCardContext.hook.js @@ -91,6 +91,10 @@ export function useCardContext() { cur.data.notifiedChannel = card.data.notifiedChannel; } } + else { + cur.channels = new Map(); + cur.articles = new Map(); + } cur.revision = card.revision; cards.current.set(card.id, cur); } @@ -137,7 +141,12 @@ export function useCardContext() { if (next.current == null) { next.current = rev; if (revision.current != rev) { - await updateCards(); + try { + await updateCards(); + } + catch(err) { + console.log(err); + } updateState({ init: true, cards: cards.current }); revision.current = rev; } @@ -171,8 +180,11 @@ export function useCardContext() { }, getCardByGuid: getCardByGuid, getImageUrl: (cardId) => { - let { data } = cards.current.get(cardId); - return getCardImageUrl(access.current, cardId, data.profileRevision) + let card = cards.current.get(cardId); + if (!card) { + return null; + } + return getCardImageUrl(access.current, cardId, card.data.profileRevision) }, addChannelTopic: async (cardId, channelId, message, assets) => { let { cardProfile, cardDetail } = cards.current.get(cardId).data; @@ -183,7 +195,7 @@ export function useCardContext() { getChannelRevision: (cardId, channelId) => { let card = cards.current.get(cardId); let channel = card.channels.get(channelId); - return channel.revision; + return channel?.revision; }, getChannelTopics: async (cardId, channelId, revision) => { let card = cards.current.get(cardId);