/* Yatoon: scoped i18n wrapper -- keeps __() out of the global namespace. */
(function () {
/**
 * Yatoon i18n bridge.
 *
 * Every user-facing literal in this file is wrapped in __(). This resolves it
 * against the WordPress JS translation catalog registered for this handle via
 * wp_set_script_translations(), so a locale's .json file translates the
 * interactive booking flow -- not just the PHP-rendered chrome around it.
 *
 * The fallback matters: if wp-i18n is unavailable for any reason (an
 * aggressive JS optimizer, a very old core, a hand-rolled enqueue) __() must
 * still return the original English rather than throwing and taking the whole
 * booking form down with it. A missing translation is a cosmetic problem; a
 * dead booking form is a lost sale.
 */
var __ = (function () {
    var d = 'yatoon-booking-system';
    if (typeof window !== 'undefined' && window.wp && window.wp.i18n && typeof window.wp.i18n.__ === 'function') {
        return function (s) { return window.wp.i18n.__(s, d); };
    }
    return function (s) { return s; };
})();

/**
 * Yatoon Manage Booking - Customer self-service JS
 * Handles cancel and reschedule interactions on the [yatoon_manage_booking] page.
 */
(function ($) {
    'use strict';

    var cfg     = window.yatoonManage || {};
    var ajaxurl = cfg.ajaxurl || '';
    var nonce   = cfg.nonce   || '';
    var token   = cfg.token   || '';
    var i18n    = cfg.i18n    || {};

    var $actions         = $('#yatoon-manage-actions');
    var $reschedulePanel = $('#yatoon-reschedule-panel');
    var $changePanel     = $('#yatoon-change-services-panel');
    var $changeList      = $('#yatoon-change-services-list');
    var $manageMSG       = $('#yatoon-manage-msg');
    var $slotsMSG        = $('#yatoon-slots-msg');
    var $slotsWrap       = $('#yatoon-slots-wrap');
    var $slotsList       = $('#yatoon-slots-list');
    var $confirmRow      = $('#yatoon-reschedule-confirm-row');

    var selectedSlot = null;
    var overlayInjected = false;
    var manageServices = [];
    var currentManageItems = [];
    var manageStaffRequestId = 0;
    var lastFocusedElement = null;

    function ensureOverlay() {
        if (overlayInjected) return;

        $('body').append(
            '<div id="yatoon-manage-overlay" role="dialog" aria-modal="true" aria-labelledby="yatoon-manage-overlay-title" style="display:none;position:fixed;inset:0;background:rgba(17,24,39,.55);z-index:99999;padding:20px;box-sizing:border-box;align-items:center;justify-content:center;">' +
                '<div tabindex="-1" class="yatoon-manage-dialog" style="width:100%;max-width:420px;background:#fff;border-radius:18px;box-shadow:0 25px 80px rgba(0,0,0,.25);overflow:hidden;">' +
                    '<div style="padding:22px 22px 18px;">' +
                        '<h3 id="yatoon-manage-overlay-title" style="margin:0 0 10px;font-size:20px;line-height:1.2;color:#111827;"></h3>' +
                        '<div id="yatoon-manage-overlay-body" style="font-size:15px;line-height:1.6;color:#4b5563;"></div>' +
                    '</div>' +
                    '<div id="yatoon-manage-overlay-actions" style="display:flex;gap:10px;justify-content:flex-end;padding:0 22px 22px;"></div>' +
                '</div>' +
            '</div>'
        );

        $(document).on('click', '#yatoon-manage-overlay', function (e) {
            if (e.target === this) {
                hideOverlay();
            }
        });

        $(document).on('keydown', '#yatoon-manage-overlay', function (e) {
            if (e.key === 'Escape') {
                e.preventDefault();
                hideOverlay();
                return;
            }
            if (e.key !== 'Tab') return;
            var $focusable = $(this).find('button:not(:disabled),a[href],input:not(:disabled),select:not(:disabled),textarea:not(:disabled),[tabindex]:not([tabindex="-1"])').filter(':visible');
            if (!$focusable.length) return;
            var first = $focusable[0];
            var last = $focusable[$focusable.length - 1];
            if (e.shiftKey && document.activeElement === first) { e.preventDefault(); last.focus(); }
            else if (!e.shiftKey && document.activeElement === last) { e.preventDefault(); first.focus(); }
        });

        overlayInjected = true;
    }

    function hideOverlay() {
        $('#yatoon-manage-overlay').hide();
        $('#yatoon-manage-overlay-actions').empty();
        if (lastFocusedElement && document.contains(lastFocusedElement)) lastFocusedElement.focus();
    }

    function showDialog(opts) {
        ensureOverlay();

        var options = opts || {};
        var $overlay = $('#yatoon-manage-overlay');
        var $title = $('#yatoon-manage-overlay-title');
        var $body = $('#yatoon-manage-overlay-body');
        var $actions = $('#yatoon-manage-overlay-actions');
        var buttons = options.buttons || [];

        $title.text(options.title || '');
        lastFocusedElement = document.activeElement;
        $body.text(options.body || '');
        $actions.empty();

        $.each(buttons, function (_, button) {
            var $btn = $('<button type="button">')
                .text(button.label || 'OK')
                .attr('style', button.style || 'padding:11px 16px;border-radius:10px;border:none;background:#ec4899;color:#fff;font-weight:600;cursor:pointer;')
                .on('click', function () {
                    hideOverlay();
                    if (typeof button.onClick === 'function') {
                        button.onClick();
                    }
                });
            $actions.append($btn);
        });

        $overlay.css('display', 'flex');
        window.setTimeout(function () { $actions.find('button').first().trigger('focus'); }, 0);
    }

    function showInfo(title, body) {
        showDialog({
            title: title,
            body: body,
            buttons: [
                {
                    label: i18n.ok || 'OK'
                }
            ]
        });
    }

    function showAfterCancelActions() {
        $('#yatoon-after-cancel-actions').remove();
        var bookUrl = cfg.bookUrl || '/';
        var $wrap = $('<div id="yatoon-after-cancel-actions" class="yatoon-after-cancel-actions">');
        $('<a class="yatoon-btn yatoon-btn-primary">')
            .attr('href', bookUrl)
            .text(__('Book another appointment'))
            .appendTo($wrap);
        $('<button type="button" class="yatoon-btn yatoon-btn-ghost">')
            .text(__('View updated status'))
            .on('click', function () {
                reloadFresh();
            })
            .appendTo($wrap);
        $manageMSG.after($wrap);
    }

    function confirmAction(title, body, onConfirm) {
        showDialog({
            title: title,
            body: body,
            buttons: [
                {
                    label: i18n.cancel || __('Keep Appointment'),
                    style: 'padding:11px 16px;border-radius:10px;border:1px solid #d1d5db;background:#fff;color:#374151;font-weight:600;cursor:pointer;'
                },
                {
                    label: i18n.confirm || __('Confirm'),
                    style: 'padding:11px 16px;border-radius:10px;border:none;background:#ec4899;color:#fff;font-weight:600;cursor:pointer;',
                    onClick: onConfirm
                }
            ]
        });
    }

    // ── Cancel ────────────────────────────────────────────────────────────────
    $('#yatoon-cancel-btn').on('click', function () {
        var $btn = $(this);
        var originalText = $btn.text();
        var $choices = $('.yatoon-cancel-item');
        var selectedIds = [];

        $choices.filter(':checked').each(function () {
            selectedIds.push($(this).val());
        });

        if ($choices.length && !selectedIds.length) {
            showInfo(
                i18n.cancel_title || __('Cancel appointment?'),
                __('Please select at least one service to cancel.')
            );
            return;
        }

        var totalChoices = $choices.length;
        var isPartialCancel = totalChoices && selectedIds.length < totalChoices;
        var confirmBody = i18n.cancel_confirm || __('Are you sure you want to cancel this appointment? This cannot be undone.');

        if (totalChoices) {
            confirmBody = isPartialCancel
                ? 'Cancel the selected ' + selectedIds.length + ' item(s)? The remaining item(s) will stay booked.'
                : __('Cancel all selected appointment items? This cannot be undone.');
        }

        confirmAction(
            i18n.cancel_title || __('Cancel appointment?'),
            confirmBody,
            function () {
                $btn.prop('disabled', true).text(i18n.loading || __('Processing...'));

                $.post(ajaxurl, {
                    action: 'yatoon_customer_cancel',
                    nonce:  nonce,
                    token:  token,
                    booking_ids: totalChoices ? JSON.stringify(selectedIds) : ''
                }, function (resp) {
                    if (resp.success) {
                        showMsg($manageMSG, resp.data.message, 'success');
                        if (isPartialCancel) {
                            window.setTimeout(function () {
                                reloadFresh();
                            }, 900);
                        } else {
                            $actions.hide();
                            $reschedulePanel.hide();
                            showAfterCancelActions();
                        }
                    } else {
                        showMsg($manageMSG, resp.data.message, 'error');
                        $btn.prop('disabled', false).text(originalText);
                    }
                }).fail(function () {
                    showMsg($manageMSG, __('Request failed. Please try again.'), 'error');
                    $btn.prop('disabled', false).text(originalText);
                });
            }
        );
    });

    // -- Open reschedule panel ─────────────────────────────────────────────────
    $('#yatoon-reschedule-btn').on('click', function () {
        $reschedulePanel.slideDown(200);
        $(this).hide();
    });

    $('#yatoon-cancel-reschedule-btn').on('click', function () {
        $reschedulePanel.slideUp(200);
        $('#yatoon-reschedule-btn').show();
        resetSlots();
    });

    // ── Load available slots ──────────────────────────────────────────────────
    $('#yatoon-load-slots-btn').on('click', function () {
        var date = $('#yatoon-reschedule-date').val();
        if (!date) {
            showInfo(
                i18n.date_required_title || __('Select a date'),
                i18n.date_required || __('Please choose a date before loading available times.')
            );
            return;
        }

        var $btn = $(this).prop('disabled', true).text(i18n.loading || __('Loading...'));
        resetSlots();

        $.post(ajaxurl, {
            action: 'yatoon_get_reschedule_slots',
            nonce:  nonce,
            token:  token,
            date:   date,
        }, function (resp) {
            $btn.prop('disabled', false).text(__('Show Available Times'));
            if (resp.success && resp.data.slots && resp.data.slots.length) {
                renderSlots(resp.data.slots);
            } else {
                var msg = (resp.data && resp.data.message) ? resp.data.message : __('No times available on this date.');
                showMsg($slotsMSG, msg, 'info');
                $slotsMSG.show();
            }
        }).fail(function () {
            $btn.prop('disabled', false).text(__('Show Available Times'));
            showMsg($slotsMSG, __('Request failed. Please try again.'), 'error');
            $slotsMSG.show();
        });
    });

    function renderSlots(slots) {
        $slotsList.empty();
        selectedSlot = null;
        $confirmRow.hide();

        $.each(slots, function (i, slot) {
            var $chip = $('<button type="button" class="yatoon-slot-chip">')
                .text(slot.display || slot.time)
                .attr('data-time', slot.datetime)
                .on('click', function () {
                    $('.yatoon-slot-chip').removeClass('selected');
                    $(this).addClass('selected');
                    selectedSlot = slot.datetime;
                    $confirmRow.show();
                });
            $slotsList.append($chip);
        });

        $slotsWrap.show();
    }

    function resetSlots() {
        $slotsList.empty();
        $slotsWrap.hide();
        $confirmRow.hide();
        $slotsMSG.hide();
        selectedSlot = null;
    }

    // ── Confirm reschedule ────────────────────────────────────────────────────
    $('#yatoon-confirm-reschedule-btn').on('click', function () {
        if (!selectedSlot) {
            showInfo(
                i18n.slot_required_title || __('Select a time'),
                i18n.select_slot || __('Please select a new time slot.')
            );
            return;
        }

        var $btn = $(this);

        confirmAction(
            i18n.reschedule_title || __('Confirm reschedule?'),
            i18n.reschedule_confirm || __('Confirm reschedule to the selected time?'),
            function () {
                $btn.prop('disabled', true).text(i18n.loading || __('Processing...'));

                $.post(ajaxurl, {
                    action:   'yatoon_customer_reschedule',
                    nonce:    nonce,
                    token:    token,
                    new_time: selectedSlot,
                }, function (resp) {
                    if (resp.success) {
                        $actions.hide();
                        $reschedulePanel.hide();
                        showMsg($manageMSG, resp.data.message, 'success');
                        window.setTimeout(function () {
                            reloadFresh();
                        }, 600);
                    } else {
                        showMsg($manageMSG, resp.data.message, 'error');
                        $btn.prop('disabled', false).text(__('Confirm Reschedule'));
                        resetSlots();
                    }
                }).fail(function () {
                    showMsg($manageMSG, __('Request failed. Please try again.'), 'error');
                    $btn.prop('disabled', false).text(__('Confirm Reschedule'));
                });
            }
        );
    });

    // ── Helpers ───────────────────────────────────────────────────────────────
    function showMsg($el, msg, type) {
        $el.removeClass('yatoon-notice-success yatoon-notice-error yatoon-notice-info yatoon-notice-warning')
           .addClass('yatoon-notice-' + type)
           .html(msg)
           .show();
    }

    function reloadFresh() {
        var url = new URL(window.location.href);
        url.searchParams.set('yatoon_status_ts', String(Date.now()));
        window.location.href = url.toString();
    }

    $(document).on('click', '#yatoon-change-services-btn', function () {
        $reschedulePanel.slideUp(200);
        $changePanel.slideDown(200);
        $(this).hide();
        $(this).attr('aria-expanded', 'true');
        loadManageServices();
    });

    $(document).on('click', '#yatoon-cancel-services-btn', function () {
        $changePanel.slideUp(200);
        $('#yatoon-change-services-btn').show().attr('aria-expanded', 'false').trigger('focus');
    });

    $(document).on('click', '#yatoon-add-service-row-btn', function () {
        if (!manageServices.length) return;
        currentManageItems.push({
            booking_id: 0,
            service_id: manageServices[0].service_id,
            option_id: manageServices[0].option_id || 0,
            service_name: manageServices[0].name,
            staff_id: 0,
            staff_name: ''
        });
        renderChangeServices();
    });

    $(document).on('click', '#yatoon-save-services-btn', function () {
        var $btn = $(this);
        var originalText = $btn.text();
        var items = [];
        var hasUnavailableSelection = false;

        $changeList.find('.yatoon-service-change-row').each(function () {
            var bookingId = parseInt($(this).attr('data-booking-id'), 10) || 0;
            var $selected = $(this).find('.yatoon-service-change-select option:selected');
            var serviceId = parseInt($selected.attr('data-service-id'), 10) || 0;
            var optionId = parseInt($selected.attr('data-option-id'), 10) || 0;
            var $staffSelect = $(this).find('.yatoon-service-change-staff');
            var staffId = parseInt($staffSelect.val(), 10) || 0;
            if (!serviceId || !optionId) {
                hasUnavailableSelection = true;
            } else {
                items.push({
                    booking_id: bookingId,
                    service_id: serviceId,
                    option_id: optionId,
                    staff_id: staffId
                });
            }
        });

        if (hasUnavailableSelection) {
            showInfo(__('Choose a service'), __('One current service is no longer available. Please choose a real service option before saving.'));
            return;
        }

        if (!items.length) {
            showInfo(__('Choose services'), __('Please choose at least one service.'));
            return;
        }

        confirmAction(
            __('Change services?'),
            __('We will update the services for this appointment. If Square cannot safely make this change, your original appointment will stay as-is.'),
            function () {
                $btn.prop('disabled', true).text(i18n.loading || __('Processing...'));
                $.post(ajaxurl, {
                    action: 'yatoon_customer_change_services',
                    nonce: nonce,
                    token: token,
                    items: JSON.stringify(items)
                }, function (resp) {
                    if (resp && resp.success) {
                        showMsg($manageMSG, resp.data.message || __('Services updated.'), 'success');
                        window.setTimeout(function () {
                            reloadFresh();
                        }, 900);
                    } else {
                        var msg = resp && resp.data && resp.data.message ? resp.data.message : __('Could not update services.');
                        showMsg($manageMSG, msg, 'error');
                        $btn.prop('disabled', false).text(originalText);
                    }
                }).fail(function () {
                    showMsg($manageMSG, __('Request failed. Please try again.'), 'error');
                    $btn.prop('disabled', false).text(originalText);
                });
            }
        );
    });

    function loadManageServices() {
        if (manageServices.length) {
            renderChangeServices();
            return;
        }

        $changeList.html('<p class="yatoon-change-services-help">Loading services...</p>');
        $.post(ajaxurl, {
            action: 'yatoon_get_manage_services',
            nonce: nonce,
            token: token
        }, function (resp) {
            if (resp && resp.success && resp.data) {
                manageServices = resp.data.services || [];
                currentManageItems = resp.data.current || [];
                renderChangeServices();
            } else {
                var msg = resp && resp.data && resp.data.message ? resp.data.message : __('Could not load services.');
                $changeList.html('<p class="yatoon-manage-error">' + escapeHtml(msg) + '</p>');
            }
        }).fail(function () {
            $changeList.html('<p class="yatoon-manage-error">Request failed. Please try again.</p>');
        });
    }

    function renderChangeServices() {
        $changeList.empty();
        if (!manageServices.length) {
            $changeList.html('<p class="yatoon-manage-error">No services are available right now.</p>');
            return;
        }
        $.each(currentManageItems, function (idx, item) {
            var $row = $('<div class="yatoon-service-change-row">')
                .attr('data-booking-id', item.booking_id || 0);
            var selectId = 'yatoon-service-change-' + idx;
            $('<label>')
                .attr('for', selectId)
                .text(item.booking_id ? ('Service ' + (idx + 1)) : __('New service'))
                .appendTo($row);
            var $select = $('<select class="yatoon-service-change-select">').attr('id', selectId);
            var groups = {};
            var hasSelectedOption = false;
            $.each(manageServices, function (_, service) {
                var groupName = service.group || service.name;
                if (!groups[groupName]) {
                    groups[groupName] = $('<optgroup>').attr('label', groupName).appendTo($select);
                }
                var label = service.name;
                if (service.duration) label += ' - ' + service.duration + ' min';
                var isSelected = parseInt(service.service_id, 10) === parseInt(item.service_id, 10)
                    && parseInt(service.option_id || 0, 10) === parseInt(item.option_id || 0, 10);
                if (isSelected) hasSelectedOption = true;
                $('<option>')
                    .val(service.value || (service.service_id + ':' + (service.option_id || 0)))
                    .attr('data-service-id', service.service_id)
                    .attr('data-option-id', service.option_id || 0)
                    .text(label)
                    .prop('selected', isSelected)
                    .appendTo(groups[groupName]);
            });
            if (item.booking_id && !hasSelectedOption) {
                $('<option>')
                    .val('')
                    .text(__('Current service unavailable - choose a service'))
                    .prop('disabled', true)
                    .prop('selected', true)
                    .prependTo($select);
            }
            $select.appendTo($row);
            $('<label>').attr('for', selectId + '-staff').text(__('Available staff')).appendTo($row);
            $('<select class="yatoon-service-change-staff" disabled>')
                .attr('id', selectId + '-staff')
                .append($('<option>').val('').text(__('Checking live availability...')))
                .appendTo($row);
            $('<span class="yatoon-service-change-staff-note" role="status">').appendTo($row);
            if (!item.booking_id) {
                $('<button type="button" class="yatoon-service-remove-row">Remove</button>')
                    .on('click', function () {
                        currentManageItems.splice(idx, 1);
                        renderChangeServices();
                    })
                    .appendTo($row);
            }
            $changeList.append($row);
        });
        refreshManageStaff();
    }

    $(document).on('change', '.yatoon-service-change-select', function () {
        var index = $changeList.find('.yatoon-service-change-select').index(this);
        var $option = $(this).find('option:selected');
        if (currentManageItems[index]) {
            currentManageItems[index].service_id = parseInt($option.attr('data-service-id'), 10) || 0;
            currentManageItems[index].option_id = parseInt($option.attr('data-option-id'), 10) || 0;
            currentManageItems[index].staff_id = 0;
        }
        refreshManageStaff();
    });

    $(document).on('change', '.yatoon-service-change-staff', function () {
        var index = $changeList.find('.yatoon-service-change-staff').index(this);
        if (currentManageItems[index]) currentManageItems[index].staff_id = parseInt($(this).val(), 10) || 0;
    });

    function refreshManageStaff() {
        var requestId = ++manageStaffRequestId;
        var draft = [];
        $changeList.find('.yatoon-service-change-row').each(function () {
            var $service = $(this).find('.yatoon-service-change-select option:selected');
            draft.push({
                booking_id: parseInt($(this).attr('data-booking-id'), 10) || 0,
                service_id: parseInt($service.attr('data-service-id'), 10) || 0,
                option_id: parseInt($service.attr('data-option-id'), 10) || 0
            });
        });
        if (!draft.length) return;
        $('#yatoon-save-services-btn').prop('disabled', true);
        $('.yatoon-service-change-staff').prop('disabled', true).empty().append($('<option>').text(__('Checking live availability...')));
        $.post(ajaxurl, {
            action: 'yatoon_get_manage_service_staff', nonce: nonce, token: token, items: JSON.stringify(draft)
        }, function (resp) {
            if (requestId !== manageStaffRequestId) return;
            if (!resp || !resp.success) {
                var error = resp && resp.data && resp.data.message ? resp.data.message : __('Could not check staff availability.');
                $('.yatoon-service-change-staff-note').text(error);
                return;
            }
            var allAvailable = true;
            $.each(resp.data.rows || [], function (_, row) {
                var $select = $changeList.find('.yatoon-service-change-staff').eq(row.index);
                var $note = $changeList.find('.yatoon-service-change-staff-note').eq(row.index);
                var preferred = currentManageItems[row.index] ? parseInt(currentManageItems[row.index].staff_id, 10) || 0 : 0;
                $select.empty().append($('<option>').val('0').text(__('Any staff')));
                $.each(row.staff || [], function (_, staff) {
                    $select.append($('<option>').val(staff.id).text(staff.name));
                });
                if (preferred && $select.find('option[value="' + preferred + '"]').length) $select.val(String(preferred));
                else $select.val('0');
                $select.prop('disabled', !(row.staff || []).length);
                if (!(row.staff || []).length) allAvailable = false;
                $note.text(row.message || ((row.staff || []).length + ' available'));
            });
            $('#yatoon-save-services-btn').prop('disabled', !allAvailable);
        }).fail(function () {
            if (requestId === manageStaffRequestId) $('.yatoon-service-change-staff-note').text(__('Could not check staff availability. Please try again.'));
        });
    }

    function escapeHtml(value) {
        return String(value || '').replace(/[&<>"']/g, function (ch) {
            return {
                '&': '&amp;',
                '<': '&lt;',
                '>': '&gt;',
                '"': '&quot;',
                "'": '&#039;'
            }[ch];
        });
    }

})(jQuery);

})();
