selectify-1.0.3/js/selectify-dropdown-checkbox.js

js/selectify-dropdown-checkbox.js
/**
 * @file
 * Contains utility functions for Selectify module multi-select.
 *
 * Filename: selectify-dropdown-checkbod.js
 * Website: https://www.flashwebcenter.com
 * Developer: Alaa Haddad https://www.alaahaddad.com.
 */
((Drupal, once) => {
  'use strict';
  const type = 'checkbox';
  Drupal.behaviors.selectifySelectCheckbox = {
    attach: (context) => {
      once('selectifyMultiSelectCheckbox', '.selectify-dropdown-checkbox-widget', context).forEach((selectifySelect) => {
        setTimeout(() => {
          // Retrieve the target ID from data attribute.
          const targetId = selectifySelect.getAttribute('data-target-id');
          if (!targetId) {
            console.error('Selectify: Missing data-target-id on dropdown element', selectifySelect);
            return;
          }
          // Locate the corresponding hidden <select> element by its ID.
          const nativeSelect = document.getElementById(targetId);
          if (!nativeSelect || nativeSelect.tagName !== 'SELECT') {
            console.error(`Selectify: No matching <select> found for data-target-id="${targetId}"`, selectifySelect);
            return;
          }
          initializeSelectifyCheckbox(selectifySelect, nativeSelect);
          let maxSelections = selectifySelect.getAttribute('data-max-selections');
          maxSelections = maxSelections === 'null' ? null : parseInt(maxSelections, 10);
          Drupal.selectify.handleSelectionLimit(
            type
            , selectifySelect
            , nativeSelect
            , maxSelections
            , '.selectify-available-one-option'
          );
          const dropdownMenu = selectifySelect.querySelector('.selectify-available-display');
          if (dropdownMenu) {
            // Generate a unique ID for the dropdown if not already set.
            const dropdownId = `${targetId}-dropdown`;
            dropdownMenu.setAttribute('id', dropdownId);
            // Set aria-controls on selectifySelect
            selectifySelect.setAttribute('aria-controls', dropdownId);
          }
        }, 10);
      });
    }
  };
  /**
   * Initializes the checkbox-based Selectify component.
   *
   * @param {HTMLElement} selectifySelect
   *   The Selectify wrapper element.
   * @param {HTMLElement} nativeSelect
   *   The hidden native <select> element.
   */
  function initializeSelectifyCheckbox(selectifySelect, nativeSelect) {
    const selectedDisplay = selectifySelect.querySelector('.selectify-selected-display');
    const dropdownMenu = selectifySelect.querySelector('.selectify-available-display');
    const options = selectifySelect.querySelectorAll('.selectify-available-one-option input[type="checkbox"]');
    const clearAllButton = selectifySelect.querySelector('.selectify-clear-all');
    if (!nativeSelect || nativeSelect.tagName !== 'SELECT') {
      console.error('Selectify: Could not find the corresponding hidden <select> for', selectifySelect);
      return;
    }
    if (!selectedDisplay || !dropdownMenu || options.length === 0) {
      return;
    }
    // Handle dropdown toggle on click.
    selectedDisplay.addEventListener('click', (event) => {
      event.preventDefault();
      event.stopPropagation();
      if (dropdownMenu.classList.contains('toggled')) {
        Drupal.selectify.closeDropdown(dropdownMenu, selectedDisplay);
      } else {
        Drupal.selectify.adjustDropdownHeight(selectifySelect, dropdownMenu);
        Drupal.selectify.openDropdown(dropdownMenu, selectedDisplay);
      }
    });
    // Handle checkbox selection within the dropdown.
    dropdownMenu.addEventListener('change', (event) => {
      if (event.target.matches('.selectify-available-one-option input[type="checkbox"]')) {
        const optionValue = event.target.value;
        const correspondingOption = nativeSelect.querySelector(`option[value="${optionValue}"]`);
        const parentOption = event.target.closest('.selectify-available-one-option');

        // Update aria-activedescendant
        if (parentOption && parentOption.id) {
          selectifySelect.setAttribute('aria-activedescendant', parentOption.id);
        }

        if (correspondingOption) {
          correspondingOption.selected = event.target.checked;
        }
        // **Add or remove .selected and .s-hidden on the parent div**
        if (parentOption) {
          if (event.target.checked) {
            parentOption.classList.add('s-selected');
          } else {
            parentOption.classList.remove('s-selected');
          }
        }
        Drupal.selectify.syncHiddenSelect(nativeSelect, Drupal.selectify.getSelectedValues(nativeSelect));
        Drupal.selectify.updateSelectedDisplay(type, nativeSelect, selectedDisplay, clearAllButton);
        nativeSelect.dispatchEvent(new Event('change'));
      }
    });
    // Handle "Clear All" functionality.
    if (clearAllButton) {
      clearAllButton.addEventListener('click', () => {
        // Unselect all options in the hidden select
        nativeSelect.querySelectorAll('option').forEach(option => option.selected = false);
        // Uncheck all checkboxes
        options.forEach(opt => {
          opt.checked = false;
          opt.disabled = false;
        });
        // Remove .selected and .s-hidden from parent elements
        options.forEach(opt => {
          const parentOption = opt.closest('.selectify-available-one-option');
          if (parentOption) {
            parentOption.classList.remove('s-selected');
          }
        });
        // Sync hidden select and update UI
        Drupal.selectify.syncHiddenSelect(nativeSelect, []);
        Drupal.selectify.updateSelectedDisplay(type, nativeSelect, selectedDisplay, clearAllButton);
        nativeSelect.dispatchEvent(new Event('change'));

        // Return focus to the main trigger
        if (selectedDisplay && typeof selectedDisplay.focus === 'function') {
          setTimeout(() => selectedDisplay.focus(), 100);
        }
      });
    }
    // Close dropdown when clicking outside.
    document.addEventListener('click', (event) => {
      if (!selectifySelect.contains(event.target)) {
        Drupal.selectify.closeDropdown(dropdownMenu, selectedDisplay);
      }
    });
    // Enable keyboard navigation.
    Drupal.selectify.handleKeyboardNavigation(selectifySelect, dropdownMenu, selectedDisplay, type);
    Drupal.selectify.updateSelectedDisplay(type, nativeSelect, selectedDisplay, clearAllButton);
    const selectedValues = Drupal.selectify.getSelectedValues(nativeSelect);
    options.forEach(checkbox => {
      checkbox.checked = selectedValues.includes(checkbox.value);
    });
  }
})(Drupal, once);

Главная | Обратная связь

drupal hosting | друпал хостинг | it patrol .inc