"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const tslib_1 = require("tslib");
const jsx_runtime_1 = require("react/jsx-runtime");
const react_1 = require("react");
const styles_1 = require("@mui/material/styles");
const Card_1 = tslib_1.__importDefault(require("@mui/material/Card"));
const api_services_1 = require("@selfcommunity/api-services");
const utils_1 = require("@selfcommunity/utils");
const material_1 = require("@mui/material");
const react_intl_1 = require("react-intl");
const List_1 = tslib_1.__importDefault(require("@mui/material/List"));
const Choice_1 = tslib_1.__importDefault(require("./Choice"));
const Icon_1 = tslib_1.__importDefault(require("@mui/material/Icon"));
const Errors_1 = require("../../../constants/Errors");
const classnames_1 = tslib_1.__importDefault(require("classnames"));
const constants_1 = require("../constants");
const messages = (0, react_intl_1.defineMessages)({
    showPoll: {
        id: 'ui.feedObject.poll.showPoll',
        defaultMessage: 'ui.feedObject.poll.showPoll'
    },
    hidePoll: {
        id: 'ui.feedObject.poll.hidePoll',
        defaultMessage: 'ui.feedObject.poll.hidePoll'
    },
    expDate: {
        id: 'ui.feedObject.poll.expDate',
        defaultMessage: 'ui.feedObject.poll.expDate'
    },
    voters: {
        id: 'ui.feedObject.poll.voters',
        defaultMessage: 'ui.feedObject.poll.voters'
    },
    votes: {
        id: 'ui.feedObject.poll.votes',
        defaultMessage: 'ui.feedObject.poll.votes'
    }
});
const classes = {
    root: `${constants_1.PREFIX}-poll-object-root`,
    voters: `${constants_1.PREFIX}-poll-object-voters`,
    votes: `${constants_1.PREFIX}-poll-object-votes`,
    toggleButton: `${constants_1.PREFIX}-poll-object-toggle-button`,
    title: `${constants_1.PREFIX}-poll-object-title`,
    expiration: `${constants_1.PREFIX}-poll-object-expiration`,
    closed: `${constants_1.PREFIX}-poll-object-closed`,
    expandIcon: `${constants_1.PREFIX}-poll-object-expand-icon`,
    collapsedIcon: `${constants_1.PREFIX}-poll-object-collapsed-icon`
};
const Root = (0, styles_1.styled)(Card_1.default, {
    name: constants_1.PREFIX,
    slot: 'PollObjectRoot'
})(() => ({}));
function PollObject(props) {
    //  PROPS
    const { className, feedObject, pollObject, disabled, visible = true, onChange, onToggleVisibility } = props, rest = tslib_1.__rest(props, ["className", "feedObject", "pollObject", "disabled", "visible", "onChange", "onToggleVisibility"]);
    // INTL
    const intl = (0, react_intl_1.useIntl)();
    //STATE
    const [obj, setObj] = (0, react_1.useState)(pollObject);
    const [votes, setVotes] = (0, react_1.useState)(getVotes());
    const [choices, setChoices] = (0, react_1.useState)(pollObject.choices);
    const [isVoting, setIsVoting] = (0, react_1.useState)(null);
    const [collapsed, setCollapsed] = (0, react_1.useState)(!visible);
    // CONST
    const multipleChoices = pollObject['multiple_choices'];
    const votable = pollObject['closed'];
    /**
     * Handles choice upvote
     */
    const handleVote = (id) => {
        const prevChoices = [...choices];
        let updatedChoices;
        if (multipleChoices) {
            updatedChoices = prevChoices.map((choice) => Object.assign({}, choice, {
                voted: choice.id === id ? true : choice.voted,
                vote_count: choice.id === id ? choice.vote_count + 1 : choice.vote_count
            }));
            setVotes((prevVotes) => prevVotes + 1);
        }
        else {
            updatedChoices = prevChoices.map((choice) => Object.assign({}, choice, {
                voted: choice.id === id,
                vote_count: choice.id === id ? choice.vote_count + 1 : choice.vote_count > 0 && choice.voted ? choice.vote_count - 1 : choice.vote_count
            }));
            setVotes(updatedChoices.reduce((totalVotes, choice) => totalVotes + choice.vote_count, 0));
        }
        setChoices(updatedChoices);
        onChange(updatedChoices);
    };
    /**
     * Handles choice unvote
     */
    const handleUnVote = (id) => {
        const prevChoices = [...choices];
        const updatedChoices = prevChoices.map((choice) => Object.assign({}, choice, {
            voted: choice.id === id ? false : choice.voted,
            vote_count: choice.id === id && choice.vote_count > 0 ? choice.vote_count - 1 : choice.vote_count
        }));
        setChoices(updatedChoices);
        onChange(updatedChoices);
        setVotes((prevVotes) => prevVotes - 1);
    };
    /**
     * Gets total votes
     */
    function getVotes() {
        const choices = pollObject.choices;
        let totalVotes = 0;
        let defaultVotes = 0;
        for (let i = 0; i < choices.length; i++) {
            totalVotes += choices[i].vote_count;
        }
        return totalVotes ? totalVotes : defaultVotes;
    }
    /**
     * Performs poll vote
     */
    function vote(choiceObj) {
        setIsVoting(choiceObj.id);
        api_services_1.http
            .request({
            url: api_services_1.Endpoints.PollVote.url({ id: feedObject.id, type: feedObject['type'] }),
            method: api_services_1.Endpoints.PollVote.method,
            data: {
                choice: choiceObj.id
            }
        })
            .then((res) => {
            if (choiceObj.voted) {
                handleUnVote(choiceObj.id);
            }
            else {
                handleVote(choiceObj.id);
            }
            setIsVoting(null);
        })
            .catch((error) => {
            utils_1.Logger.error(Errors_1.SCOPE_SC_UI, error);
        });
    }
    /**
     * Handle toggle collapsed/uncollapsed poll
     */
    const handleToggleCollapsedClick = (0, react_1.useMemo)(() => () => {
        onToggleVisibility && onToggleVisibility(collapsed);
        setCollapsed((prev) => !prev);
    }, [setCollapsed, onToggleVisibility]);
    /**
     * Renders the poll object
     */
    let objElement = (0, jsx_runtime_1.jsx)(jsx_runtime_1.Fragment, {});
    if (pollObject) {
        objElement = ((0, jsx_runtime_1.jsxs)(jsx_runtime_1.Fragment, { children: [(0, jsx_runtime_1.jsx)(material_1.CardHeader, { title: (0, jsx_runtime_1.jsx)(jsx_runtime_1.Fragment, { children: (0, jsx_runtime_1.jsx)(material_1.Button, Object.assign({ className: classes.toggleButton, onClick: handleToggleCollapsedClick, "aria-expanded": collapsed, endIcon: (0, jsx_runtime_1.jsx)(Icon_1.default, Object.assign({ className: (0, classnames_1.default)(classes.expandIcon, { [classes.collapsedIcon]: collapsed }) }, { children: "arrow_upward" })) }, { children: collapsed ? intl.formatMessage(messages.showPoll) : intl.formatMessage(messages.hidePoll) })) }) }), (0, jsx_runtime_1.jsx)(material_1.Collapse, Object.assign({ in: !collapsed, timeout: "auto", unmountOnExit: true }, { children: (0, jsx_runtime_1.jsxs)(material_1.CardContent, { children: [(0, jsx_runtime_1.jsx)(material_1.Typography, Object.assign({ variant: "body1", className: classes.title }, { children: obj.title })), obj.expiration_at && Date.parse(obj.expiration_at) >= new Date().getTime() && ((0, jsx_runtime_1.jsxs)(material_1.Typography, Object.assign({ variant: "body2", className: classes.expiration }, { children: [`${intl.formatMessage(messages.expDate)}`, `${intl.formatDate(Date.parse(obj.expiration_at), { year: 'numeric', month: 'numeric', day: 'numeric' })}`] }))), obj.closed && ((0, jsx_runtime_1.jsx)(material_1.Typography, Object.assign({ variant: "body2", className: classes.closed }, { children: (0, jsx_runtime_1.jsx)(react_intl_1.FormattedMessage, { id: "ui.feedObject.poll.closed", defaultMessage: "ui.feedObject.poll.closed" }) }))), (0, jsx_runtime_1.jsx)(List_1.default, { children: choices.map((choice, index) => ((0, jsx_runtime_1.jsx)(material_1.ListItem, { children: (0, jsx_runtime_1.jsx)(Choice_1.default, { elevation: 0, choiceObj: choice, feedObject: disabled ? null : feedObject, votes: votes, vote: vote, isVoting: isVoting, votable: votable }) }, index))) }), multipleChoices ? ((0, jsx_runtime_1.jsxs)("div", Object.assign({ className: classes.votes }, { children: [(0, jsx_runtime_1.jsx)(Icon_1.default, { children: "list" }), (0, jsx_runtime_1.jsx)(material_1.Typography, { children: `${intl.formatMessage(messages.votes, { total: votes })}` })] }))) : ((0, jsx_runtime_1.jsxs)("div", Object.assign({ className: classes.voters }, { children: [(0, jsx_runtime_1.jsx)(Icon_1.default, { children: "people_alt" }), (0, jsx_runtime_1.jsx)(material_1.Typography, { children: `${intl.formatMessage(messages.voters, { total: votes })}` })] })))] }) }))] }));
    }
    (0, react_1.useEffect)(() => {
        setChoices(pollObject.choices);
    }, [pollObject.choices]);
    /**
     * Renders root element
     */
    return ((0, jsx_runtime_1.jsx)(Root, Object.assign({ className: (0, classnames_1.default)(classes.root, className) }, rest, { children: objElement })));
}
exports.default = PollObject;
