Add support for disabled chat state in the chat input field. Closes #2761
This commit is contained in:
parent
de71984d46
commit
4a0476b237
@ -593,6 +593,18 @@ Example.args = {
|
|||||||
chatUserId: 'testuser',
|
chatUserId: 'testuser',
|
||||||
isModerator: true,
|
isModerator: true,
|
||||||
showInput: true,
|
showInput: true,
|
||||||
|
chatAvailable: true,
|
||||||
|
};
|
||||||
|
|
||||||
|
export const ChatDisabled = Template.bind({});
|
||||||
|
ChatDisabled.args = {
|
||||||
|
loading: false,
|
||||||
|
messages,
|
||||||
|
usernameToHighlight: 'testuser',
|
||||||
|
chatUserId: 'testuser',
|
||||||
|
isModerator: true,
|
||||||
|
showInput: true,
|
||||||
|
chatAvailable: false,
|
||||||
};
|
};
|
||||||
|
|
||||||
export const SingleMessage = Template.bind({});
|
export const SingleMessage = Template.bind({});
|
||||||
@ -603,4 +615,5 @@ SingleMessage.args = {
|
|||||||
chatUserId: 'testuser',
|
chatUserId: 'testuser',
|
||||||
isModerator: true,
|
isModerator: true,
|
||||||
showInput: true,
|
showInput: true,
|
||||||
|
chatAvailable: true,
|
||||||
};
|
};
|
||||||
|
@ -25,6 +25,7 @@ export type ChatContainerProps = {
|
|||||||
isModerator: boolean;
|
isModerator: boolean;
|
||||||
showInput?: boolean;
|
showInput?: boolean;
|
||||||
height?: string;
|
height?: string;
|
||||||
|
chatAvailable: boolean;
|
||||||
};
|
};
|
||||||
|
|
||||||
function shouldCollapseMessages(
|
function shouldCollapseMessages(
|
||||||
@ -92,6 +93,7 @@ export const ChatContainer: FC<ChatContainerProps> = ({
|
|||||||
isModerator,
|
isModerator,
|
||||||
showInput,
|
showInput,
|
||||||
height,
|
height,
|
||||||
|
chatAvailable: chatEnabled,
|
||||||
}) => {
|
}) => {
|
||||||
const [showScrollToBottomButton, setShowScrollToBottomButton] = useState(false);
|
const [showScrollToBottomButton, setShowScrollToBottomButton] = useState(false);
|
||||||
const [isAtBottom, setIsAtBottom] = useState(false);
|
const [isAtBottom, setIsAtBottom] = useState(false);
|
||||||
@ -284,7 +286,7 @@ export const ChatContainer: FC<ChatContainerProps> = ({
|
|||||||
{MessagesTable}
|
{MessagesTable}
|
||||||
{showInput && (
|
{showInput && (
|
||||||
<div className={styles.chatTextField}>
|
<div className={styles.chatTextField}>
|
||||||
<ChatTextField />
|
<ChatTextField enabled={chatEnabled} />
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
|
@ -58,9 +58,13 @@ const Template: ComponentStory<typeof ChatTextField> = args => (
|
|||||||
);
|
);
|
||||||
|
|
||||||
export const Example = Template.bind({});
|
export const Example = Template.bind({});
|
||||||
|
Example.args = {
|
||||||
|
enabled: true,
|
||||||
|
};
|
||||||
|
|
||||||
export const LongerMessage = Template.bind({});
|
export const LongerMessage = Template.bind({});
|
||||||
LongerMessage.args = {
|
LongerMessage.args = {
|
||||||
|
enabled: true,
|
||||||
defaultText:
|
defaultText:
|
||||||
'Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.',
|
'Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.',
|
||||||
};
|
};
|
||||||
@ -72,3 +76,16 @@ LongerMessage.parameters = {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
export const DisabledChat = Template.bind({});
|
||||||
|
DisabledChat.args = {
|
||||||
|
enabled: false,
|
||||||
|
};
|
||||||
|
|
||||||
|
DisabledChat.parameters = {
|
||||||
|
docs: {
|
||||||
|
description: {
|
||||||
|
story: 'Should not allow you to type anything and should state that chat is disabled.',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
@ -122,11 +122,12 @@ const getCharacterCount = node => {
|
|||||||
|
|
||||||
export type ChatTextFieldProps = {
|
export type ChatTextFieldProps = {
|
||||||
defaultText?: string;
|
defaultText?: string;
|
||||||
|
enabled: boolean;
|
||||||
};
|
};
|
||||||
|
|
||||||
const characterLimit = 300;
|
const characterLimit = 300;
|
||||||
|
|
||||||
export const ChatTextField: FC<ChatTextFieldProps> = ({ defaultText }) => {
|
export const ChatTextField: FC<ChatTextFieldProps> = ({ defaultText, enabled }) => {
|
||||||
const [showEmojis, setShowEmojis] = useState(false);
|
const [showEmojis, setShowEmojis] = useState(false);
|
||||||
const [characterCount, setCharacterCount] = useState(defaultText?.length);
|
const [characterCount, setCharacterCount] = useState(defaultText?.length);
|
||||||
const websocketService = useRecoilValue<WebsocketService>(websocketServiceAtom);
|
const websocketService = useRecoilValue<WebsocketService>(websocketServiceAtom);
|
||||||
@ -241,8 +242,10 @@ export const ChatTextField: FC<ChatTextFieldProps> = ({ defaultText }) => {
|
|||||||
className="chat-text-input"
|
className="chat-text-input"
|
||||||
onKeyDown={onKeyDown}
|
onKeyDown={onKeyDown}
|
||||||
onPaste={onPaste}
|
onPaste={onPaste}
|
||||||
|
disabled={!enabled}
|
||||||
|
readOnly={!enabled}
|
||||||
renderElement={renderElement}
|
renderElement={renderElement}
|
||||||
placeholder="Send a message to chat"
|
placeholder={enabled ? 'Send a message to chat' : 'Chat is currently unavailable.'}
|
||||||
style={{ width: '100%' }}
|
style={{ width: '100%' }}
|
||||||
role="textbox"
|
role="textbox"
|
||||||
aria-label="Chat text input"
|
aria-label="Chat text input"
|
||||||
@ -262,6 +265,7 @@ export const ChatTextField: FC<ChatTextFieldProps> = ({ defaultText }) => {
|
|||||||
/>
|
/>
|
||||||
</Slate>
|
</Slate>
|
||||||
|
|
||||||
|
{enabled && (
|
||||||
<div style={{ display: 'flex', paddingLeft: '5px' }}>
|
<div style={{ display: 'flex', paddingLeft: '5px' }}>
|
||||||
<button
|
<button
|
||||||
type="button"
|
type="button"
|
||||||
@ -280,6 +284,7 @@ export const ChatTextField: FC<ChatTextFieldProps> = ({ defaultText }) => {
|
|||||||
<SendOutlined />
|
<SendOutlined />
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
)}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
|
@ -293,6 +293,7 @@ export const Content: FC = () => {
|
|||||||
notifyItemSelected={() => setShowNotifyModal(true)}
|
notifyItemSelected={() => setShowNotifyModal(true)}
|
||||||
followItemSelected={() => setShowFollowModal(true)}
|
followItemSelected={() => setShowFollowModal(true)}
|
||||||
externalActionSelected={externalActionSelected}
|
externalActionSelected={externalActionSelected}
|
||||||
|
chatEnabled={isChatAvailable}
|
||||||
/>
|
/>
|
||||||
) : (
|
) : (
|
||||||
<DesktopContent
|
<DesktopContent
|
||||||
|
@ -25,6 +25,7 @@ export type MobileContentProps = {
|
|||||||
messages: ChatMessage[];
|
messages: ChatMessage[];
|
||||||
currentUser: CurrentUser;
|
currentUser: CurrentUser;
|
||||||
showChat: boolean;
|
showChat: boolean;
|
||||||
|
chatEnabled: boolean;
|
||||||
actions: ExternalAction[];
|
actions: ExternalAction[];
|
||||||
externalActionSelected: (action: ExternalAction) => void;
|
externalActionSelected: (action: ExternalAction) => void;
|
||||||
supportsBrowserNotifications: boolean;
|
supportsBrowserNotifications: boolean;
|
||||||
@ -62,6 +63,7 @@ export const MobileContent: FC<MobileContentProps> = ({
|
|||||||
messages,
|
messages,
|
||||||
currentUser,
|
currentUser,
|
||||||
showChat,
|
showChat,
|
||||||
|
chatEnabled,
|
||||||
actions,
|
actions,
|
||||||
setExternalActionToDisplay,
|
setExternalActionToDisplay,
|
||||||
setShowNotifyPopup,
|
setShowNotifyPopup,
|
||||||
@ -80,6 +82,7 @@ export const MobileContent: FC<MobileContentProps> = ({
|
|||||||
usernameToHighlight={displayName}
|
usernameToHighlight={displayName}
|
||||||
chatUserId={id}
|
chatUserId={id}
|
||||||
isModerator={false}
|
isModerator={false}
|
||||||
|
chatAvailable={chatEnabled}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -5,7 +5,11 @@ import dynamic from 'next/dynamic';
|
|||||||
import { ChatMessage } from '../../../interfaces/chat-message.model';
|
import { ChatMessage } from '../../../interfaces/chat-message.model';
|
||||||
import styles from './Sidebar.module.scss';
|
import styles from './Sidebar.module.scss';
|
||||||
|
|
||||||
import { currentUserAtom, visibleChatMessagesSelector } from '../../stores/ClientConfigStore';
|
import {
|
||||||
|
currentUserAtom,
|
||||||
|
visibleChatMessagesSelector,
|
||||||
|
isChatAvailableSelector,
|
||||||
|
} from '../../stores/ClientConfigStore';
|
||||||
|
|
||||||
// Lazy loaded components
|
// Lazy loaded components
|
||||||
const ChatContainer = dynamic(
|
const ChatContainer = dynamic(
|
||||||
@ -18,6 +22,8 @@ const ChatContainer = dynamic(
|
|||||||
export const Sidebar: FC = () => {
|
export const Sidebar: FC = () => {
|
||||||
const currentUser = useRecoilValue(currentUserAtom);
|
const currentUser = useRecoilValue(currentUserAtom);
|
||||||
const messages = useRecoilValue<ChatMessage[]>(visibleChatMessagesSelector);
|
const messages = useRecoilValue<ChatMessage[]>(visibleChatMessagesSelector);
|
||||||
|
const isChatAvailable = useRecoilValue(isChatAvailableSelector);
|
||||||
|
|
||||||
if (!currentUser) {
|
if (!currentUser) {
|
||||||
return <Sider className={styles.root} collapsedWidth={0} width={320} />;
|
return <Sider className={styles.root} collapsedWidth={0} width={320} />;
|
||||||
}
|
}
|
||||||
@ -30,6 +36,7 @@ export const Sidebar: FC = () => {
|
|||||||
usernameToHighlight={displayName}
|
usernameToHighlight={displayName}
|
||||||
chatUserId={id}
|
chatUserId={id}
|
||||||
isModerator={isModerator}
|
isModerator={isModerator}
|
||||||
|
chatAvailable={isChatAvailable}
|
||||||
/>
|
/>
|
||||||
</Sider>
|
</Sider>
|
||||||
);
|
);
|
||||||
|
@ -5,11 +5,13 @@ import {
|
|||||||
ClientConfigStore,
|
ClientConfigStore,
|
||||||
currentUserAtom,
|
currentUserAtom,
|
||||||
visibleChatMessagesSelector,
|
visibleChatMessagesSelector,
|
||||||
|
isChatAvailableSelector,
|
||||||
} from '../../../../components/stores/ClientConfigStore';
|
} from '../../../../components/stores/ClientConfigStore';
|
||||||
|
|
||||||
export default function ReadOnlyChatEmbed() {
|
export default function ReadOnlyChatEmbed() {
|
||||||
const currentUser = useRecoilValue(currentUserAtom);
|
const currentUser = useRecoilValue(currentUserAtom);
|
||||||
const messages = useRecoilValue<ChatMessage[]>(visibleChatMessagesSelector);
|
const messages = useRecoilValue<ChatMessage[]>(visibleChatMessagesSelector);
|
||||||
|
const isChatAvailable = useRecoilValue(isChatAvailableSelector);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
@ -22,6 +24,7 @@ export default function ReadOnlyChatEmbed() {
|
|||||||
isModerator={false}
|
isModerator={false}
|
||||||
showInput={false}
|
showInput={false}
|
||||||
height="100vh"
|
height="100vh"
|
||||||
|
chatAvailable={isChatAvailable}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
|
@ -8,6 +8,7 @@ import {
|
|||||||
clientConfigStateAtom,
|
clientConfigStateAtom,
|
||||||
appStateAtom,
|
appStateAtom,
|
||||||
serverStatusState,
|
serverStatusState,
|
||||||
|
isChatAvailableSelector,
|
||||||
} from '../../../../components/stores/ClientConfigStore';
|
} from '../../../../components/stores/ClientConfigStore';
|
||||||
import Header from '../../../../components/ui/Header/Header';
|
import Header from '../../../../components/ui/Header/Header';
|
||||||
import { ClientConfig } from '../../../../interfaces/client-config.model';
|
import { ClientConfig } from '../../../../interfaces/client-config.model';
|
||||||
@ -21,6 +22,7 @@ export default function ReadWriteChatEmbed() {
|
|||||||
const clientStatus = useRecoilValue<ServerStatus>(serverStatusState);
|
const clientStatus = useRecoilValue<ServerStatus>(serverStatusState);
|
||||||
|
|
||||||
const appState = useRecoilValue<AppStateOptions>(appStateAtom);
|
const appState = useRecoilValue<AppStateOptions>(appStateAtom);
|
||||||
|
const isChatAvailable = useRecoilValue(isChatAvailableSelector);
|
||||||
|
|
||||||
const { name, chatDisabled } = clientConfig;
|
const { name, chatDisabled } = clientConfig;
|
||||||
const { videoAvailable } = appState;
|
const { videoAvailable } = appState;
|
||||||
@ -41,6 +43,7 @@ export default function ReadWriteChatEmbed() {
|
|||||||
isModerator={currentUser.isModerator}
|
isModerator={currentUser.isModerator}
|
||||||
showInput
|
showInput
|
||||||
height="80vh"
|
height="80vh"
|
||||||
|
chatAvailable={isChatAvailable}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user