import { Button } from 'antd'; import { Virtuoso } from 'react-virtuoso'; import { useState, useMemo, useRef, CSSProperties } from 'react'; import { EditFilled, VerticalAlignBottomOutlined } from '@ant-design/icons'; import { ConnectedClientInfoEvent, MessageType, NameChangeEvent, } from '../../../interfaces/socket-events'; import s from './ChatContainer.module.scss'; import { ChatMessage } from '../../../interfaces/chat-message.model'; import { ChatTextField, ChatUserMessage } from '..'; import ChatModeratorNotification from '../ChatModeratorNotification/ChatModeratorNotification'; import ChatActionMessage from '../ChatAction/ChatActionMessage'; interface Props { messages: ChatMessage[]; // loading: boolean; usernameToHighlight: string; chatUserId: string; isModerator: boolean; isMobile: boolean | undefined; } export default function ChatContainer(props: Props) { const { messages, usernameToHighlight, chatUserId, isModerator, isMobile } = props; const [atBottom, setAtBottom] = useState(false); // const [showButton, setShowButton] = useState(false); const chatContainerRef = useRef(null); // const spinIcon = ; const getNameChangeViewForMessage = (message: NameChangeEvent) => { const { oldName, user } = message; const { displayName, displayColor } = user; const color = `var(--theme-user-colors-${displayColor})`; return (
{oldName} is now known as {displayName}
); }; const getUserJoinedMessage = (message: ChatMessage) => { const { user } = message; const { displayName, displayColor } = user; const color = `var(--theme-user-colors-${displayColor})`; return ( ${displayName} joined the chat.`} /> ); }; const getConnectedInfoMessage = (message: ConnectedClientInfoEvent) => { const modStatusUpdate = checkIsModerator(message); if (!modStatusUpdate) { // Important note: We can't return null or an element with zero width // or zero height. So to work around this we return a very small 1x1 div. const st: CSSProperties = { width: '1px', height: '1px' }; return
; } // Alert the user that they are a moderator. return ; }; const getViewForMessage = ( index: number, message: ChatMessage | NameChangeEvent | ConnectedClientInfoEvent, ) => { switch (message.type) { case MessageType.CHAT: return ( ); case MessageType.NAME_CHANGE: return getNameChangeViewForMessage(message as NameChangeEvent); case MessageType.CONNECTED_USER_INFO: return getConnectedInfoMessage(message); case MessageType.USER_JOINED: return getUserJoinedMessage(message as ChatMessage); default: return null; } }; const MessagesTable = useMemo( () => ( <> getViewForMessage(index, message)} followOutput="auto" alignToBottom atBottomStateChange={bottom => setAtBottom(bottom)} /> {!atBottom && (
)} ), [messages, usernameToHighlight, chatUserId, isModerator, atBottom, isMobile], ); return (
{ //
// stream chat //
// } {MessagesTable}
); } function isSameUserAsLast(messages: ChatMessage[], index: number): boolean { const message = messages[index]; const { user: { id }, } = message; const lastMessage = messages[index - 1]; if (lastMessage.type !== MessageType.CHAT) { return false; } return id === lastMessage?.user.id; } function checkIsModerator(message) { const { user } = message; const { scopes } = user; if (!scopes || scopes.length === 0) { return false; } return scopes.includes('MODERATOR'); }