import { Link } from "react-router-dom";
import { Message, User, Channel, Users, Emojis } from "../types";
import { useState, createRef, useEffect } from "react";
import axios from "axios";

import "../styles/MessageComponent.css";

export default function MessageComponent({ message, user, channel }: {
        message: Message;
        user: User | undefined;
        channel: Channel | undefined;
    }) {
    const [reply, setReply] = useState(false);
    const token = localStorage.getItem("token");
    const [replyContent, setReplyContent] = useState("");
    const [searchedUsers, setSearchedUsers] = useState<Users>([]);
    const [searchedEmojis, setSearchedEmojis] = useState<Emojis>([]);
    const ref = createRef<HTMLInputElement>();

    function getMessageArray(message: Message) {
        const array = []
        var string = ''
        message.content.split(" ").forEach((word) => {
            if (word.startsWith("@")) {
                const mention = message.mentions.find((mention) => `@${mention.username}` === word);
                if (mention) {
                    array.push(string)
                    string = ''
                    array.push(word)
                } else {
                    string += word + " "
                }
            } else if (word.startsWith("https://") || word.startsWith("http://")) {
                array.push(string)
                string = ''
                array.push(word)
            } else if (word.startsWith(":") && word.endsWith(":") && word.length > 2) {
                array.push(string)
                string = ''
                array.push(word)
            } else {
                string += word + " "
            }
        });
        array.push(string)
        return array.filter((word) => word !== '');
    }

    function handleReply(e: React.FormEvent<HTMLFormElement>, messageId: number) {
        e.preventDefault();
        axios
            .post(`/api/messages/${messageId}/reply`, {
                token: token,
                message: replyContent,
            })
            .then(() => {
                setReplyContent("");
                setReply(false);
                setSearchedUsers([]);
                setSearchedEmojis([]);
            })
            .catch((err) => {
                console.error(err.response.data);
            });
    }

    function handleDelete() {
        if (!window.confirm("Are you sure you want to delete this message?")) {
            return;
        }
        axios
            .post(`/api/messages/${message.id}/delete`, {
                token: token,
            })
            .catch((err) => {
                console.error(err.response.data);
            });
    }

    useEffect(() => {
        const words = replyContent.toString().split(" ");
        const lastWord = words[words.length - 1];
    
        if (lastWord && lastWord.startsWith("@")) {
            const username = lastWord.slice(1);
            axios
                .get(`/api/searchuser?search=${username}`)
                .then((res) => {
                    setSearchedUsers(res.data);
                })
                .catch((err) => {
                    console.error(err.response.data);
                });
        } else {
            setSearchedUsers([]);
        }

        if (lastWord && lastWord.startsWith(":")) {
            const emojiName = lastWord.slice(1);
            axios
                .get(`/api/searchemojis?search=${emojiName}`)
                .then((res) => {
                    setSearchedEmojis(res.data);
                })
                .catch((err) => {
                    console.error(err.response.data);
                });
        } else {
            setSearchedEmojis([]);
        }
    }, [replyContent]);
    
    return (
        <div key={message.id} className="message">
            <div className="message-content">
                <img src={`/api/users/${message.username}/pfp`} alt="" className="message-user-pfp" />
                <div className="message-content-right">
                    <span><Link to={`/u/${message.username}`}>{message.username}</Link> {new Date(message.date * 1000).toLocaleString()}</span>
                    <div className="message-text">
                        {getMessageArray(message).map((word, index) => {
                            if (word.startsWith("@")) {
                                return <span key={index} ><Link to={`/u/${word.substring(1)}`}>{word}</Link> </span>
                            } else if (word.startsWith("https://") || word.startsWith("http://")) {
                                return <span key={index} ><Link to={word}>{word}</Link> </span>
                            } else if (word.startsWith(":") && word.endsWith(":") && word.length > 2) {
                                const emojiName = word.substring(1, word.length - 1);
                                return <span key={index} ><img src={`/api/emojis/${emojiName}`} alt={emojiName} className="message-emoji" /> </span>
                            }
                            return <span key={index}>{word} </span>;
                        })}
                    </div>
                </div>
            </div>
            <div>
                {message.content.toLocaleLowerCase().includes("gros cochon") && (
                    <img src="/pig.png" alt="Gros cochon" className="pig" />
                )}
            </div>
            <div>
                {message.content.toLocaleLowerCase().includes("le poisson steve") && (
                    <img src="/le_poisson_steve.png" alt="Le poisson steve" className="fish" />
                )}
            </div>
            {channel?.owner_id == user?.id || user?.admin == 1 || user?.username == message.username ? (
                user?.id === message.user_id || user?.id === channel?.owner_id || user?.admin === 1) && (
                    <button onClick={handleDelete}>Delete</button>
            ) : (
                <p>In <Link to={`/c/${message.channel_name}`}>{message.channel_name}</Link></p>
            )}
            {channel && user && !reply && (
                <button onClick={() => setReply(true)}>Reply</button>
            )}
            {reply && (
                <form onSubmit={(e) => handleReply(e, message.id)} className="message-form">
                    <input 
                        type="text"
                        placeholder="Message"
                        value={replyContent}
                        onChange={(e) => setReplyContent(e.target.value)}
                        ref={ref}
                    />
                    <button type="submit">Send</button>
                    {searchedUsers.length > 0 && (
                        <div className="mentions">
                            {searchedUsers.map((user) => (
                                <div key={user.id} className="mention">
                                    <Link to={`/u/${user.username}`}>{user.username}</Link>
                                    <button
                                        type="button"
                                        onClick={() => {
                                            setReplyContent(
                                                replyContent.split(" ").slice(0, -1).join(" ") + " @" + user.username + " "
                                            );
                                            setSearchedUsers([]);
                                            ref.current?.focus();
                                        }}
                                    >
                                        Mention
                                    </button>
                                </div>
                            ))}
                        </div>
                    )}
                    {searchedEmojis.length > 0 && (
                        <div className="emojis">
                            {searchedEmojis.map((emoji) => (
                                <div key={emoji.id} className="search-emoji">
                                    <img src={`/api/emojis/${emoji.name}`} alt={emoji.name} className="emojis-emoji" />
                                    <span>:{emoji.name}:</span>
                                    <button
                                        type="button"
                                        onClick={() => {
                                            setReplyContent(
                                                replyContent.split(" ").slice(0, -1).join(" ") + " :" + emoji.name + ": "
                                            );
                                            setSearchedEmojis([]);
                                            ref.current?.focus();
                                        }}
                                    >
                                        Add Emoji
                                    </button>
                                </div>
                            ))}
                        </div>
                    )}
                    <button onClick={() => setReply(false)}>Cancel</button>
                </form>
            )}
            {message.has_replies == true && (
                <div className="message-replies">
                    {message.replies.map((reply) => (
                        <MessageComponent message={reply} user={user} channel={channel} key={reply.id} />
                    ))}
                </div>
            )}
            {!channel && (
                <p>in: <Link to={`/c/${message.channel_name}`}>{message.channel_name}</Link></p>
            )}
        </div>
    );
}