import BaseComponent from "../BaseComponent";
import AppData from "../../Common/AppData";
import { fetchData } from "../../Utils/Fetch";
import UserUtil from "../../Utils/UserUtil";
import EventBus from "../../Events/EventBus";

class Settings {
    init() {
        if (!jQuery('.settings-ui')[0]) {
            return;
        }
        if (jQuery('.settings-ui').data('initializied') !== 'true') {
            new SettingsHandler(jQuery('.settings-ui'));
        }
    }
}

class SettingsHandler extends BaseComponent {

    constructor(component_base_ui) {
        super(component_base_ui);
        this.handleRouteChange();
        this._handleEvents();
        this._handleTimeAndDateOnLoad();
        this._handleDailySleepTimeOnLoad();
    }

    _handleEvents() {
        const _this = this;

        this._component_base_ui.find('.close-btn').on('click', function(event) {
            event.preventDefault();
            window.location.hash = '';
        });

        this._component_base_ui.find('.delete-account-btn').on('click', function(event) {
            event.preventDefault();
            _this._handleDeleteAccount();
        });

        this._component_base_ui.find('.show-time-date-toggle').on('change', function(event) {
            _this._handleShowTimeAndDate(jQuery(this));
        });

        this._component_base_ui.find('.daily-sleep-time-toggle').on('change', function(event) {
            _this._handleDailySleepTime(jQuery(this));
        });

        this._component_base_ui.find('.daily-sleep-time-hour, .daily-sleep-time-minute, .daily-sleep-time-period').on('change', function(event) {
            _this._handleDailySleepTimeChange();
        });

        this.handlePopupClickOutside({
            newHash: '',
        });

        this._component_base_ui.find('.tab-btn').on('click', function(event) {
            event.preventDefault();
            const target = jQuery(this).data('tab');
            _this._handleTabbedPane(target);
        });
    }

    onRouteChange(payload) {
        if (payload?.key === 'settings') {
            this._showPopup(payload);
        } else {
            this._closePopup();
        }
    }

    async _showPopup(payload) {

        this.show();
        this.fadeIn();

        this._handleTabbedPane('1');
    }

    _handleTabbedPane(target) {
        this._component_base_ui.find(`.tab-btn`).removeClass('selected');
        this._component_base_ui.find(`.tab-btn[data-tab="${target}"]`).addClass('selected');
        this._component_base_ui.find('.tab-content').addClass('hidden');
        this._component_base_ui.find(`.tab-content[data-tab="${target}"]`).removeClass('hidden');
    }

    _closePopup() {
        this.hide();
        this.fadeOut();
    }

    async _handleDeleteAccount() {
        const _this = this;

        // Check if user is logged in
        const isLoggedIn = await UserUtil.isLoggedIn();
        if (!isLoggedIn) {
            alert('You must be logged in to delete your account.');
            return;
        }

        // Show confirmation dialog
        const confirmTitle = AppData.getInstance().getLabel('delete_account_confirmation_title');
        const confirmMessage = AppData.getInstance().getLabel('delete_account_confirmation_message');
        const confirmButtonText = AppData.getInstance().getLabel('delete_account_confirm_btn');

        const confirmed = confirm(confirmTitle + '\n\n' + confirmMessage);

        if (!confirmed) {
            return;
        }

        // Proceed with account deletion
        try {
            const result = await fetchData('user/delete-account', 'POST');

            if (result && result.status === 200) {
                alert(AppData.getInstance().getLabel('delete_account_success_message'));

                // Log out user and redirect
                window.location.hash = '';
                window.location.reload();
            } else {
                const errorMessage = result?.message || AppData.getInstance().getLabel('delete_account_error_message');
                alert(errorMessage);
            }
        } catch (error) {
            console.error('Error deleting account:', error);
            alert(AppData.getInstance().getLabel('delete_account_error_message'));
        }
    }

    _handleTimeAndDateOnLoad() {
        if (UserUtil.isLoggedIn()) {
            const user_show_user_time_date = UserUtil.getUserMetaByKey('show_user_time_date', null);

            if (user_show_user_time_date === 'on') {
                this._component_base_ui.find('.show-time-date-toggle').prop('checked', true);
            }
        }
    }

    async _handleShowTimeAndDate($toggle) {
        const metaKey = $toggle.data('meta-key');
        const isChecked = $toggle.is(':checked');
        const value = isChecked ? 'on' : 'off';

        try {
            // Check if user is logged in
            const isLoggedIn = await UserUtil.isLoggedIn();

            if (!isLoggedIn) {
                // Revert toggle state
                $toggle.prop('checked', !isChecked);
                alert(AppData.getInstance().getLabel('login_required_message') || 'You must be logged in to change this setting.');
                return;
            }

            // Update user meta via API
            const result = await fetchData('user/update-meta', 'POST', {
                meta_key: metaKey,
                meta_value: value
            });

            if (result && result.status === 200) {
                // Update local user data
                const userData = AppData.getInstance().get('user_data');
                if (userData && userData.meta) {
                    userData.meta[metaKey] = value;
                    AppData.getInstance().set('user_data', userData);
                }

                // Trigger EventBus to show/hide time and date
                EventBus.getInstance().triggerDynamicEvent(
                    isChecked ? 'SHOW_TIME_AND_DATE' : 'HIDE_TIME_AND_DATE',
                    { value }
                );
            } else {
                // Revert toggle state on error
                $toggle.prop('checked', !isChecked);
                const errorMessage = result?.message || AppData.getInstance().getLabel('settings_update_error') || 'Failed to update setting. Please try again.';
                alert(errorMessage);
            }
        } catch (error) {
            console.error('Error updating show time and date setting:', error);
            // Revert toggle state on error
            $toggle.prop('checked', !isChecked);
            alert(AppData.getInstance().getLabel('settings_update_error') || 'An error occurred while updating the setting.');
        }
    }

    _handleDailySleepTimeOnLoad() {
        if (UserUtil.isLoggedIn()) {
            const user_daily_sleep_time = UserUtil.getUserMetaByKey('daily_sleep_time_enabled', null);

            if (user_daily_sleep_time === 'on') {
                this._component_base_ui.find('.daily-sleep-time-toggle').prop('checked', true);
                this._component_base_ui.find('.daily-sleep-time-picker').removeClass('hidden');
            }
        }
    }

    async _handleDailySleepTime($toggle) {
        const metaKey = $toggle.data('meta-key');
        const isChecked = $toggle.is(':checked');
        const value = isChecked ? 'on' : 'off';

        try {
            const isLoggedIn = await UserUtil.isLoggedIn();

            if (!isLoggedIn) {
                $toggle.prop('checked', !isChecked);
                alert(AppData.getInstance().getLabel('login_required_message') || 'You must be logged in to change this setting.');
                return;
            }

            const result = await fetchData('user/update-meta', 'POST', {
                meta_key: metaKey,
                meta_value: value
            });

            if (result && result.status === 200) {
                const userData = AppData.getInstance().get('user_data');
                if (userData && userData.meta) {
                    userData.meta[metaKey] = value;
                    AppData.getInstance().set('user_data', userData);
                }

                // Show/hide and enable/disable time picker based on toggle state
                if (isChecked) {
                    this._component_base_ui.find('.daily-sleep-time-picker').removeClass('hidden');
                    this._component_base_ui.find('.daily-sleep-time-hour, .daily-sleep-time-minute, .daily-sleep-time-period')
                        .prop('disabled', false)
                        .removeClass('opacity-50 cursor-not-allowed');
                } else {
                    this._component_base_ui.find('.daily-sleep-time-picker').addClass('hidden');
                    this._component_base_ui.find('.daily-sleep-time-hour, .daily-sleep-time-minute, .daily-sleep-time-period')
                        .prop('disabled', true)
                        .addClass('opacity-50 cursor-not-allowed');
                }

                EventBus.getInstance().triggerDynamicEvent(
                    isChecked ? 'DAILY_SLEEP_TIME_ENABLED' : 'DAILY_SLEEP_TIME_DISABLED',
                    { value }
                );

                // Fire time changed event if enabled
                if (isChecked) {
                    this._fireDailySleepTimeChangedEvent();
                }
            } else {
                $toggle.prop('checked', !isChecked);
                const errorMessage = result?.message || AppData.getInstance().getLabel('settings_update_error') || 'Failed to update setting. Please try again.';
                alert(errorMessage);
            }
        } catch (error) {
            console.error('Error updating daily sleep time setting:', error);
            $toggle.prop('checked', !isChecked);
            alert(AppData.getInstance().getLabel('settings_update_error') || 'An error occurred while updating the setting.');
        }
    }

    async _handleDailySleepTimeChange() {
        try {
            const isLoggedIn = await UserUtil.isLoggedIn();

            if (!isLoggedIn) {
                alert(AppData.getInstance().getLabel('login_required_message') || 'You must be logged in to change this setting.');
                return;
            }

            const hour = parseInt(this._component_base_ui.find('.daily-sleep-time-hour').val());
            const minute = parseInt(this._component_base_ui.find('.daily-sleep-time-minute').val());
            const period = this._component_base_ui.find('.daily-sleep-time-period').val();

            // Convert to 24-hour format
            let hour24 = hour;
            if (period === 'PM' && hour !== 12) {
                hour24 = hour + 12;
            } else if (period === 'AM' && hour === 12) {
                hour24 = 0;
            }

            const timeValue = `${String(hour24).padStart(2, '0')}:${String(minute).padStart(2, '0')}`;

            const result = await fetchData('user/update-meta', 'POST', {
                meta_key: 'daily_sleep_time',
                meta_value: timeValue
            });

            if (result && result.status === 200) {
                const userData = AppData.getInstance().get('user_data');
                if (userData && userData.meta) {
                    userData.meta['daily_sleep_time'] = timeValue;
                    AppData.getInstance().set('user_data', userData);
                }

                // Fire the time changed event
                this._fireDailySleepTimeChangedEvent();
            } else {
                const errorMessage = result?.message || AppData.getInstance().getLabel('settings_update_error') || 'Failed to update setting. Please try again.';
                alert(errorMessage);
            }
        } catch (error) {
            console.error('Error updating daily sleep time:', error);
            alert(AppData.getInstance().getLabel('settings_update_error') || 'An error occurred while updating the setting.');
        }
    }

    _fireDailySleepTimeChangedEvent() {
        const hour = parseInt(this._component_base_ui.find('.daily-sleep-time-hour').val());
        const minute = parseInt(this._component_base_ui.find('.daily-sleep-time-minute').val());
        const period = this._component_base_ui.find('.daily-sleep-time-period').val();

        // Convert to 24-hour format
        let hour24 = hour;
        if (period === 'PM' && hour !== 12) {
            hour24 = hour + 12;
        } else if (period === 'AM' && hour === 12) {
            hour24 = 0;
        }

        const timeValue = `${String(hour24).padStart(2, '0')}:${String(minute).padStart(2, '0')}`;

        EventBus.getInstance().triggerDynamicEvent('DAILY_SLEEP_TIME_CHANGED', {
            time: timeValue,
            hour: hour24,
            minute: minute
        });
    }
}

export default Settings;
