2022-10-04 16:00:00 -07:00
|
|
|
import React from 'react';
|
|
|
|
import { defineMessages, useIntl } from 'react-intl';
|
|
|
|
|
2022-10-25 08:40:14 -07:00
|
|
|
import { unblockAccount } from 'soapbox/actions/accounts';
|
|
|
|
import { openModal } from 'soapbox/actions/modals';
|
|
|
|
import { Button, HStack, IconButton, Stack, Text, Textarea } from 'soapbox/components/ui';
|
|
|
|
import { useChatContext } from 'soapbox/contexts/chat-context';
|
|
|
|
import { useAppDispatch, useAppSelector } from 'soapbox/hooks';
|
2022-10-04 16:00:00 -07:00
|
|
|
|
|
|
|
const messages = defineMessages({
|
|
|
|
placeholder: { id: 'chat.input.placeholder', defaultMessage: 'Type a message' },
|
|
|
|
send: { id: 'chat.actions.send', defaultMessage: 'Send' },
|
|
|
|
failedToSend: { id: 'chat.failed_to_send', defaultMessage: 'Message failed to send.' },
|
|
|
|
retry: { id: 'chat.retry', defaultMessage: 'Retry?' },
|
2022-10-25 08:40:14 -07:00
|
|
|
blocked: { id: 'chat_message_list.blocked', defaultMessage: 'You blocked this user' },
|
|
|
|
unblock: { id: 'chat_composer.unblock', defaultMessage: 'Unblock' },
|
2022-10-31 12:51:51 -07:00
|
|
|
unblockMessage: { id: 'chat_settings.unblock.message', defaultMessage: 'Unblocking will allow this profile to direct message you and view your content.' },
|
2022-10-25 08:40:14 -07:00
|
|
|
unblockHeading: { id: 'chat_settings.unblock.heading', defaultMessage: 'Unblock @{acct}' },
|
|
|
|
unblockConfirm: { id: 'chat_settings.unblock.confirm', defaultMessage: 'Unblock' },
|
2022-10-04 16:00:00 -07:00
|
|
|
});
|
|
|
|
|
2022-10-04 16:10:58 -07:00
|
|
|
interface IChatComposer extends Pick<React.TextareaHTMLAttributes<HTMLTextAreaElement>, 'onKeyDown' | 'onChange' | 'disabled'> {
|
2022-10-04 16:00:00 -07:00
|
|
|
value: string,
|
|
|
|
onSubmit: () => void,
|
|
|
|
hasErrorSubmittingMessage?: boolean,
|
|
|
|
}
|
|
|
|
|
|
|
|
/** Textarea input for chats. */
|
2022-10-17 08:50:33 -07:00
|
|
|
const ChatComposer = React.forwardRef<HTMLTextAreaElement | null, IChatComposer>(({
|
2022-10-04 16:00:00 -07:00
|
|
|
onKeyDown,
|
|
|
|
onChange,
|
|
|
|
value,
|
|
|
|
onSubmit,
|
|
|
|
hasErrorSubmittingMessage = false,
|
2022-10-04 16:10:58 -07:00
|
|
|
disabled = false,
|
2022-10-04 16:00:00 -07:00
|
|
|
}, ref) => {
|
2022-10-25 08:40:14 -07:00
|
|
|
const dispatch = useAppDispatch();
|
2022-10-04 16:00:00 -07:00
|
|
|
const intl = useIntl();
|
|
|
|
|
2022-10-25 08:40:14 -07:00
|
|
|
const { chat } = useChatContext();
|
2022-11-02 12:28:16 -07:00
|
|
|
|
2022-10-25 08:40:14 -07:00
|
|
|
const isBlocked = useAppSelector((state) => state.getIn(['relationships', chat?.account?.id, 'blocked_by']));
|
|
|
|
const isBlocking = useAppSelector((state) => state.getIn(['relationships', chat?.account?.id, 'blocking']));
|
|
|
|
|
2022-10-04 16:10:58 -07:00
|
|
|
const isSubmitDisabled = disabled || value.length === 0;
|
2022-10-04 16:00:00 -07:00
|
|
|
|
2022-10-25 08:40:14 -07:00
|
|
|
const handleUnblockUser = () => {
|
|
|
|
dispatch(openModal('CONFIRM', {
|
|
|
|
heading: intl.formatMessage(messages.unblockHeading, { acct: chat?.account.acct }),
|
|
|
|
message: intl.formatMessage(messages.unblockMessage),
|
|
|
|
confirm: intl.formatMessage(messages.unblockConfirm),
|
|
|
|
confirmationTheme: 'primary',
|
|
|
|
onConfirm: () => dispatch(unblockAccount(chat?.account.id as string)),
|
|
|
|
}));
|
|
|
|
};
|
|
|
|
|
|
|
|
if (isBlocking) {
|
|
|
|
return (
|
|
|
|
<div className='mt-auto p-6 shadow-3xl dark:border-t-2 dark:border-solid dark:border-gray-800'>
|
|
|
|
<Stack space={3} alignItems='center'>
|
|
|
|
<Text align='center' theme='muted'>
|
|
|
|
{intl.formatMessage(messages.blocked)}
|
|
|
|
</Text>
|
|
|
|
|
|
|
|
<Button theme='secondary' onClick={handleUnblockUser}>
|
|
|
|
{intl.formatMessage(messages.unblock)}
|
|
|
|
</Button>
|
|
|
|
</Stack>
|
|
|
|
</div>
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
if (isBlocked) {
|
2022-10-25 10:07:25 -07:00
|
|
|
return null;
|
2022-10-25 08:40:14 -07:00
|
|
|
}
|
|
|
|
|
2022-10-04 16:00:00 -07:00
|
|
|
return (
|
|
|
|
<div className='mt-auto pt-4 px-4 shadow-3xl'>
|
|
|
|
<HStack alignItems='center' justifyContent='between' space={4}>
|
|
|
|
<Stack grow>
|
|
|
|
<Textarea
|
|
|
|
autoFocus
|
|
|
|
ref={ref}
|
|
|
|
placeholder={intl.formatMessage(messages.placeholder)}
|
|
|
|
onKeyDown={onKeyDown}
|
|
|
|
value={value}
|
|
|
|
onChange={onChange}
|
|
|
|
isResizeable={false}
|
|
|
|
autoGrow
|
|
|
|
maxRows={5}
|
2022-10-04 16:10:58 -07:00
|
|
|
disabled={disabled}
|
2022-10-04 16:00:00 -07:00
|
|
|
/>
|
|
|
|
</Stack>
|
|
|
|
|
|
|
|
<IconButton
|
|
|
|
src={require('icons/airplane.svg')}
|
|
|
|
iconClassName='w-5 h-5'
|
|
|
|
className='text-primary-500'
|
|
|
|
disabled={isSubmitDisabled}
|
|
|
|
onClick={onSubmit}
|
|
|
|
/>
|
|
|
|
</HStack>
|
|
|
|
|
|
|
|
<HStack alignItems='center' className='h-5' space={1}>
|
|
|
|
{hasErrorSubmittingMessage && (
|
|
|
|
<>
|
|
|
|
<Text theme='danger' size='xs'>
|
|
|
|
{intl.formatMessage(messages.failedToSend)}
|
|
|
|
</Text>
|
|
|
|
|
|
|
|
<button onClick={onSubmit} className='flex hover:underline'>
|
|
|
|
<Text theme='primary' size='xs' tag='span'>
|
|
|
|
{intl.formatMessage(messages.retry)}
|
|
|
|
</Text>
|
|
|
|
</button>
|
|
|
|
</>
|
|
|
|
)}
|
|
|
|
</HStack>
|
|
|
|
</div>
|
|
|
|
);
|
|
|
|
});
|
|
|
|
|
|
|
|
export default ChatComposer;
|