import React from 'react';
import { FlatList, StyleSheet, Text, View } from 'react-native';
import Modal from 'react-native-modal';
import Touchable from 'react-native-platform-touchable';

import Emoji from './message/Emoji';
import I18n from '../i18n';
import { CustomIcon } from '../lib/Icons';
import sharedStyles from '../views/Styles';
import { themes } from '../lib/constants';
import { TSupportedThemes, useTheme, withTheme } from '../theme';
import { TGetCustomEmoji } from '../definitions/IEmoji';
import { TMessageModel, ILoggedUser } from '../definitions';
import SafeAreaView from './SafeAreaView';

const styles = StyleSheet.create({
	safeArea: {
		backgroundColor: 'transparent'
	},
	titleContainer: {
		alignItems: 'center',
		paddingVertical: 10
	},
	title: {
		fontSize: 16,
		...sharedStyles.textSemibold,
		...sharedStyles.textAlignCenter
	},
	reactCount: {
		fontSize: 13,
		...sharedStyles.textRegular
	},
	peopleReacted: {
		fontSize: 14,
		...sharedStyles.textMedium
	},
	peopleItemContainer: {
		flex: 1,
		flexDirection: 'column',
		justifyContent: 'center'
	},
	emojiContainer: {
		width: 50,
		height: 50,
		alignItems: 'center',
		justifyContent: 'center'
	},
	itemContainer: {
		height: 50,
		flexDirection: 'row'
	},
	listContainer: {
		flex: 1
	},
	closeButton: {
		position: 'absolute',
		left: 0,
		top: 10
	}
});
const standardEmojiStyle = { fontSize: 20 };
const customEmojiStyle = { width: 20, height: 20 };

interface ISharedFields {
	user?: Pick<ILoggedUser, 'username'>;
	baseUrl: string;
	getCustomEmoji: TGetCustomEmoji;
}

interface IItem extends ISharedFields {
	item: {
		usernames: string[];
		emoji: string;
	};
}

interface IModalContent extends ISharedFields {
	message?: TMessageModel;
	onClose: () => void;
	theme: TSupportedThemes;
}

interface IReactionsModal extends ISharedFields {
	message?: TMessageModel;
	isVisible: boolean;
	onClose(): void;
}

const Item = React.memo(({ item, user, baseUrl, getCustomEmoji }: IItem) => {
	const { theme } = useTheme();
	const count = item.usernames.length;
	let usernames = item.usernames
		.slice(0, 3)
		.map((username: string) => (username === user?.username ? I18n.t('you') : username))
		.join(', ');
	if (count > 3) {
		usernames = `${usernames} ${I18n.t('and_more')} ${count - 3}`;
	} else {
		usernames = usernames.replace(/,(?=[^,]*$)/, ` ${I18n.t('and')}`);
	}
	return (
		<View style={styles.itemContainer}>
			<View style={styles.emojiContainer}>
				<Emoji
					content={item.emoji}
					standardEmojiStyle={standardEmojiStyle}
					customEmojiStyle={customEmojiStyle}
					baseUrl={baseUrl}
					getCustomEmoji={getCustomEmoji}
				/>
			</View>
			<View style={styles.peopleItemContainer}>
				<Text style={[styles.reactCount, { color: themes[theme].buttonText }]}>
					{count === 1 ? I18n.t('1_person_reacted') : I18n.t('N_people_reacted', { n: count })}
				</Text>
				<Text style={[styles.peopleReacted, { color: themes[theme].buttonText }]}>{usernames}</Text>
			</View>
		</View>
	);
});

const ModalContent = React.memo(({ message, onClose, ...props }: IModalContent) => {
	if (message && message.reactions) {
		return (
			<SafeAreaView style={styles.safeArea}>
				<Touchable onPress={onClose}>
					<View style={styles.titleContainer}>
						<CustomIcon style={[styles.closeButton, { color: themes[props.theme].buttonText }]} name='close' size={20} />
						<Text style={[styles.title, { color: themes[props.theme].buttonText }]}>{I18n.t('Reactions')}</Text>
					</View>
				</Touchable>
				<FlatList
					style={styles.listContainer}
					data={message.reactions}
					renderItem={({ item }) => <Item item={item} {...props} />}
					keyExtractor={item => item.emoji}
				/>
			</SafeAreaView>
		);
	}
	return null;
});

const ReactionsModal = React.memo(
	({ isVisible, onClose, ...props }: IReactionsModal) => {
		const { theme } = useTheme();
		return (
			<Modal
				isVisible={isVisible}
				onBackdropPress={onClose}
				onBackButtonPress={onClose}
				backdropOpacity={0.8}
				onSwipeComplete={onClose}
				swipeDirection={['up', 'left', 'right', 'down']}>
				<ModalContent onClose={onClose} theme={theme} {...props} />
			</Modal>
		);
	},
	(prevProps, nextProps) => prevProps.isVisible === nextProps.isVisible
);

ReactionsModal.displayName = 'ReactionsModal';
ModalContent.displayName = 'ReactionsModalContent';
Item.displayName = 'ReactionsModalItem';

export default withTheme(ReactionsModal);