/**
 * @file
 * Admin Icons behaviors.
 *
 * Provides a selected icons group at the top, search filtering, and page-size dropdown.
 */
(function (Drupal, drupalSettings, once) {
  Drupal.behaviors.bootstrapUiKitAdminIcons = {
    attach(context) {
      const wrapper = context.querySelector('#iconography-selection-wrapper')
      if (!wrapper) {
        return
      }

      const icons = drupalSettings.bootstrap_ui_kit.icons || []

      once('bootstrap-ui-kit-admin-icons', '#iconography-selection-wrapper', context).forEach(() => {
        const selectedSet = new Set(drupalSettings.bootstrap_ui_kit.selected_icons || [])

        // Hidden inputs — carries selected-but-off-screen icons through the POST.
        const hiddenContainer = document.createElement('div')
        hiddenContainer.id = 'admin-icons-hidden-inputs'
        hiddenContainer.setAttribute('aria-hidden', 'true')
        hiddenContainer.style.cssText = 'display:none!important'
        wrapper.parentNode.insertBefore(hiddenContainer, wrapper)

        // Selected section sits between the toolbar and the main grid.
        const selectedSection = document.createElement('div')
        selectedSection.id = 'admin-icons-selected-section'
        selectedSection.classList.add('admin-icons-selected-section')
        selectedSection.hidden = true
        wrapper.parentNode.insertBefore(selectedSection, wrapper)

        const searchInput = document.getElementById('admin-icons-search')
        const pageSizeSelect = document.getElementById('admin-icons-page-size')

        function getPageSize() {
          const val = pageSizeSelect?.value || '25'
          return val === 'all' ? Infinity : parseInt(val, 10)
        }

        function getFilteredUnselected() {
          const query = (searchInput?.value || '').toLowerCase().trim()
          return icons.filter((icon) => {
            if (selectedSet.has(icon)) return false
            if (query && !icon.toLowerCase().includes(query)) return false
            return true
          })
        }

        function createIconCheckbox(icon, checked) {
          const div = document.createElement('div')
          div.classList.add(
            'admin-icon-checkbox',
            'js-form-item',
            'form-item',
            'js-form-type-checkbox',
            'form-type--checkbox',
            'form-type--boolean',
          )

          div.innerHTML = `
            <input
              type="checkbox"
              id="edit-${icon}"
              name="${icon}"
              data-drupal-selector="edit-${icon}"
              value="1"
              class="form-checkbox form-boolean form-boolean--type-checkbox"
              ${checked ? 'checked' : ''}
            >
            <label for="edit-${icon}" class="form-item__label option">
              <div class="d-flex flex-column text-center gap-3" data-icon-name="${icon}" style="width: 100px;">
                <i class="icon icon-${icon} icon-lg mx-auto" role="presentation">
                  <svg role="img" xmlns:xlink="http://www.w3.org/1999/xlink" fill="currentColor" viewBox="0 0 20 20">
                    <use xlink:href="#${icon}"></use>
                  </svg>
                </i>
                <span class="py-2 badge text-bg-light fw-normal text-truncate" role="presentation">${icon}</span>
              </div>
            </label>`

          div.querySelector('input[type="checkbox"]').addEventListener('change', (e) => {
            if (e.target.checked) {
              selectedSet.add(icon)
            }
            else {
              selectedSet.delete(icon)
            }
            refresh()
          })

          return div
        }

        function renderSelectedSection() {
          selectedSection.innerHTML = ''

          if (selectedSet.size === 0) {
            selectedSection.hidden = true
            return
          }

          selectedSection.hidden = false

          const header = document.createElement('div')
          header.classList.add('admin-icons-selected-header')
          header.innerHTML = `<h4 class="admin-icons-selected-heading">${Drupal.t('Selected')} <span class="admin-icons-selected-count">${selectedSet.size}</span></h4>`
          selectedSection.appendChild(header)

          const grid = document.createElement('div')
          grid.classList.add('admin-icons-selected-grid')
          selectedSet.forEach((icon) => grid.appendChild(createIconCheckbox(icon, true)))
          selectedSection.appendChild(grid)
        }

        function renderMainGrid() {
          wrapper.innerHTML = ''
          const filtered = getFilteredUnselected()
          const pageSize = getPageSize()
          filtered.slice(0, pageSize).forEach((icon) => wrapper.appendChild(createIconCheckbox(icon, false)))
        }

        function syncHiddenInputs() {
          // Selected icons are always in the selected section,
          // so hidden inputs are only a safety net for any edge cases.
          const visibleNames = new Set(
            [...document.querySelectorAll('#admin-icons-selected-section input[type="checkbox"]')].map(cb => cb.name),
          )
          hiddenContainer.innerHTML = ''
          selectedSet.forEach((icon) => {
            if (!visibleNames.has(icon)) {
              const input = document.createElement('input')
              input.type = 'hidden'
              input.name = icon
              input.value = '1'
              hiddenContainer.appendChild(input)
            }
          })
        }

        function refresh() {
          renderSelectedSection()
          renderMainGrid()
          syncHiddenInputs()
        }

        let debounceTimer
        function onSearchInput() {
          clearTimeout(debounceTimer)
          debounceTimer = setTimeout(refresh, 200)
        }

        if (searchInput) {
          searchInput.addEventListener('input', onSearchInput)
        }
        if (pageSizeSelect) {
          pageSizeSelect.addEventListener('change', refresh)
        }

        refresh()
      })
    },
  }
})(Drupal, drupalSettings, once)