import { VegaButtonClickStrategy } from './vega-button-click-strategy';
import { VegaCheckboxChangeStrategy } from './vega-checkbox-change-strategy';
import { VegaInputSelectChangeStrategy } from './vega-input-select-change-strategy';
import { VegaInputStrategy } from './vega-input-strategy';
import { VegaRadioChangeStrategy } from './vega-radio-change-strategy';
import { VegaTextareaChangeStrategy } from './vega-textarea-change-strategy';
/** The `JQueryDelegatedStrategyController` class manages delegated event strategies for different HTML elements in a TypeScript application. */
class JQueryDelegatedStrategyController {
  /**
   * The constructor initializes a registry of update strategies for various input events in a Vega application.
   */
  constructor() {
    this.strategyRegistry = new Map();
    this.updateStrategyRegistry([
      new VegaButtonClickStrategy(),
      new VegaInputStrategy('change'),
      new VegaInputStrategy('focus'),
      new VegaInputStrategy('blur'),
      new VegaInputSelectChangeStrategy(),
      new VegaTextareaChangeStrategy(),
      new VegaCheckboxChangeStrategy(),
      new VegaRadioChangeStrategy(),
    ]);
  }
  /**
   * The function checks if a given event on a specific HTML element is supported for delegation.
   *
   * @param {HTMLElement} host - The `host` parameter is an HTMLElement, which represents the element on which the event listener is attached.
   * @param {VegaEventID} eventId - The `eventName` parameter is a string that represents the name of the event.
   * @returns {boolean} a boolean value.
   */
  isSupportDelegated(host, eventId) {
    let result = false;
    const componentName = host.tagName.toLowerCase();
    if (!!this.strategyRegistry.get(componentName) &&
      !!this.strategyRegistry.get(componentName).get(eventId.getNativeName())) {
      result = true;
    }
    return result;
  }
  /**
   * The function updates the strategy registry with custom strategies based on the event semantics configuration.
   *
   * @param {EventSemanticsConfig} eventSemantics - The parameter `eventSemantics` is of type `EventSemanticsConfig`. It is an object that contains two properties: `global` and `components`.
   */
  updateRegistryFromEventSemantics(eventSemantics) {
    let customStrategies = [];
    const { global, components } = eventSemantics;
    if (global && Array.isArray(global.jqueryDelegatedEvent)) {
      customStrategies = customStrategies.concat(global.jqueryDelegatedEvent);
    }
    if (components) {
      for (const name in components) {
        if (Array.isArray(components[name].jqueryDelegatedEvent)) {
          customStrategies = customStrategies.concat(components[name].jqueryDelegatedEvent);
        }
      }
    }
    if (customStrategies.length) {
      this.updateStrategyRegistry(customStrategies);
    }
  }
  /**
   * The function returns a delegated event strategy based on the host element and event name.
   *
   * @param {HTMLElement} host - The `host` parameter is an HTMLElement that represents the element on
   * which the event strategy is being applied. It is the element to which the event listener is attached.
   * @param {VegaEventID} eventId - The `eventName` parameter is a string that represents the name of the event for which you want to retrieve the strategy.
   * @returns {Nullable<JQueryDelegatedEventStrategy>} a Nullable<JQueryDelegatedEventStrategy>.
   */
  getStrategy(host, eventId) {
    const componentName = host.tagName.toLowerCase();
    if (this.strategyRegistry && this.strategyRegistry.get(componentName)) {
      return this.strategyRegistry.get(componentName).get(eventId.getNativeName());
    }
  }
  /**
   * The function `overrideCurrentStrategy` updates the strategy registry with a new strategy for a specific host and event.
   *
   * @param {JQueryDelegatedEventStrategy[]} strategies - The parameter "strategy" is of type "JQueryDelegatedEventStrategy".
   */
  updateStrategyRegistry(strategies) {
    strategies.forEach((strategy) => {
      const hostName = strategy.getHostName();
      const eventName = strategy.getEventName();
      if (!this.strategyRegistry.get(hostName)) {
        const map = new Map();
        map.set(eventName, strategy);
        this.strategyRegistry.set(hostName, map);
      }
      else {
        this.strategyRegistry.get(hostName).set(eventName, strategy);
      }
    });
  }
}
export default new JQueryDelegatedStrategyController();
