/*!
 * BookiFlex Carbon Fields configuration
 * License: GPL-2.0-or-later
 * © 2026 BookiFlex
 */
(function () {
    'use strict';

    // Configuration constants
    const CONFIG = {
        FIELDS: {
            MAIN_SLEEPING_CAPACITY: 'bflex__at__main_sleeping_capacity',
            MAIN_SLEEPING_ALLOWED_OCCUPANCY: 'bflex__at__main_sleeping_allowed_occupancy',
            ACCOMMODATION_CATEGORY: 'bflex__at__accommodation_category'
        },
        CONTAINER_NAME: 'carbon_fields_container_at_configuration',
        TARGET_VALUES: ['apartment', 'house'],
        THIRD_TAB_SELECTOR: 'ul.cf-container__tabs-list li:nth-child(3)' // Contact info tab
    };

    // State management
    let lastCapacityValue = null;
    let lastCategoryValue = null;

    /**
     * Dynamic Occupancy Manager
     * Handles dynamic updates for occupancy options and tab visibility
     */
    class DynamicOccupancyManager {
        constructor() {
            this.isInitialized = false;
            this.fields = new Map();
        }

        /**
         * Initialize the manager
         */
        init() {
            console.log('Initializing DynamicOccupancyManager...');
            if (!this.validateCarbonFields()) {
                console.warn('Carbon Fields API not available');
                return;
            }

            console.log('Carbon Fields API validated successfully');

            // Checking if Carbon Fields is already initialized
            if (this.isCarbonFieldsReady()) {
                console.log('Carbon Fields already initialized, setting up immediately');
                this.setupSubscription();
            } else {
                console.log('Carbon Fields not ready, registering action');
                const { addAction } = window.cf.hooks;

                addAction('carbon-fields.init', 'carbon-fields/metaboxes', () => {
                    console.log('Carbon Fields initialized via action, setting up subscription...');
                    setTimeout(() => {
                        this.setupSubscription();
                    }, 100);
                });
            }
        }

        /**
         * Check if Carbon Fields is already ready
         */
        isCarbonFieldsReady() {
            try {
                const { select } = window.cf.vendor['@wordpress/data'];
                const fields = select('carbon-fields/metaboxes').getFieldsByContainerId(CONFIG.CONTAINER_NAME);
                return fields && fields.length > 0;
            } catch (error) {
                console.log('Carbon Fields not ready:', error.message);
                return false;
            }
        }

        /**
         * Validate Carbon Fields availability
         */
        validateCarbonFields() {
            return window.cf?.hooks?.addAction &&
                window.cf?.vendor?.['@wordpress/data'];
        }

        /**
         * Setup data subscription
         */
        setupSubscription() {
            if (this.isInitialized) {
                console.log('Already initialized, skipping');
                return;
            }

            console.log('Setting up subscription...');
            this.isInitialized = true;

            const { subscribe, select } = window.cf.vendor['@wordpress/data'];

            // Checking the availability of methods
            if (!subscribe || !select) {
                console.error('WordPress data methods not available');
                return;
            }

            const unsubscribe = subscribe(() => {
                console.log('Subscribe callback triggered');
                try {
                    this.handleFieldUpdates(select);
                } catch (error) {
                    console.error('Error in field updates:', error);
                }
            }, 'carbon-fields/metaboxes');

            console.log('Subscription created:', typeof unsubscribe);

            setTimeout(() => {
                console.log('Initial field update attempt...');
                this.handleFieldUpdates(select);
            }, 100);
        }

        /**
         * Handle field updates
         */
        handleFieldUpdates(select) {
            console.log('Handling field updates...');
            const fields = select('carbon-fields/metaboxes').getFieldsByContainerId(CONFIG.CONTAINER_NAME);

            console.log('Fields found:', fields?.length || 0);

            if (!fields?.length) {
                console.log('No fields found for container:', CONFIG.CONTAINER_NAME);
                return;
            }

            console.log('Available field names:', fields.map(f => f.base_name));

            // this.updateTabVisibility();
            this.updateFieldsMap(fields);
            this.updateOccupancyOptions();
        }

        /**
         * Update internal fields map
         */
        updateFieldsMap(fields) {
            this.fields.clear();
            fields.forEach(field => {
                this.fields.set(field.base_name, field);
            });
        }

        /**
         * Update occupancy options based on capacity
         */
        updateOccupancyOptions() {
            const capacityField = this.fields.get(CONFIG.FIELDS.MAIN_SLEEPING_CAPACITY);
            const occupancyField = this.fields.get(CONFIG.FIELDS.MAIN_SLEEPING_ALLOWED_OCCUPANCY);

            if (!capacityField || !occupancyField) {
                return;
            }

            const currentCapacity = parseInt(capacityField.value, 10);

            // Only update if capacity has changed and is valid
            if (isNaN(currentCapacity) ||
                currentCapacity === lastCapacityValue ||
                currentCapacity === occupancyField.options?.length) {
                return;
            }

            lastCapacityValue = currentCapacity;
            this.generateOccupancyOptions(occupancyField, currentCapacity);
        }

        /**
         * Generate occupancy options
         */
        generateOccupancyOptions(occupancyField, capacity) {
            if (capacity <= 0) {
                console.warn('Invalid capacity value:', capacity);
                return;
            }

            const options = Array.from({ length: capacity }, (_, index) => ({
                value: String(index + 1),
                label: `${index + 1} person${index === 0 ? '' : 's'}`
            }));

            this.updateFieldOptions(occupancyField, options);
        }

        /**
         * Update field options
         */
        async updateFieldOptions(field, options) {
            const { dispatch } = window.cf.vendor['@wordpress/data'];

            try {
                const updatedField = { ...field, options };

                await dispatch('carbon-fields/metaboxes').addFields([updatedField]);
                console.log('Occupancy options updated successfully');
            } catch (error) {
                console.error('Failed to update field options:', error);
            }
        }

        /**
         * Update tab visibility based on accommodation category
         */
        updateTabVisibility() {
            const categoryField = this.fields.get(CONFIG.FIELDS.ACCOMMODATION_CATEGORY);

            if (!categoryField) {
                return;
            }

            // Only update if category has changed
            if (categoryField.value === lastCategoryValue) {
                return;
            }

            lastCategoryValue = categoryField.value;
            this.toggleThirdTab(categoryField.value);
        }

        /**
         * Toggle third tab visibility
         */
        toggleThirdTab(categoryValue) {
            const container = document.getElementById(CONFIG.CONTAINER_NAME);
            const thirdTab = container?.querySelector(CONFIG.THIRD_TAB_SELECTOR);

            if (!thirdTab) {
                console.warn('Third tab not found');
                return false;
            }

            const shouldShow = CONFIG.TARGET_VALUES.includes(categoryValue);
            thirdTab.style.display = shouldShow ? '' : 'none';

            console.log(`Tab visibility updated for category: ${categoryValue} (${shouldShow ? 'visible' : 'hidden'})`);
            return true;
        }
    }

    // Initialize when DOM is ready
    function initializeWhenReady() {
        const manager = new DynamicOccupancyManager();
        manager.init();
    }

    // Start initialization
    initializeWhenReady();
})();