/**
 * @license
 * Copyright (C) 2017 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
import {PolymerElement} from '@polymer/polymer/polymer-element.js';

/** @constructor */
export function GrDomHooksManager(plugin) {
  this._plugin = plugin;
  this._hooks = {};
}

GrDomHooksManager.prototype._getHookName = function(endpointName,
    opt_moduleName) {
  if (opt_moduleName) {
    return endpointName + ' ' + opt_moduleName;
  } else {
    // lowercase in case plugin's name contains uppercase letters
    // TODO: this still can not prevent if plugin has invalid char
    // other than uppercase, but is the first step
    // https://html.spec.whatwg.org/multipage/custom-elements.html#valid-custom-element-name
    const pluginName = this._plugin.getPluginName() || 'unknown_plugin';
    return pluginName.toLowerCase() + '-autogenerated-' + endpointName;
  }
};

GrDomHooksManager.prototype.getDomHook = function(endpointName,
    opt_moduleName) {
  const hookName = this._getHookName(endpointName, opt_moduleName);
  if (!this._hooks[hookName]) {
    this._hooks[hookName] = new GrDomHook(hookName, opt_moduleName);
  }
  return this._hooks[hookName];
};

/** @constructor */
export function GrDomHook(hookName, opt_moduleName) {
  this._instances = [];
  this._attachCallbacks = [];
  this._detachCallbacks = [];
  if (opt_moduleName) {
    this._moduleName = opt_moduleName;
  } else {
    this._moduleName = hookName;
    this._createPlaceholder(hookName);
  }
}

GrDomHook.prototype._createPlaceholder = function(hookName) {
  class HookPlaceholder extends PolymerElement {
    static get is() { return hookName; }

    static get properties() {
      return {
        plugin: Object,
        content: Object,
      };
    }
  }

  customElements.define(HookPlaceholder.is, HookPlaceholder);
};

GrDomHook.prototype.handleInstanceDetached = function(instance) {
  const index = this._instances.indexOf(instance);
  if (index !== -1) {
    this._instances.splice(index, 1);
  }
  this._detachCallbacks.forEach(callback => callback(instance));
};

GrDomHook.prototype.handleInstanceAttached = function(instance) {
  this._instances.push(instance);
  this._attachCallbacks.forEach(callback => callback(instance));
};

/**
 * Get instance of last DOM hook element attached into the endpoint.
 * Returns a Promise, that's resolved when attachment is done.
 *
 * @return {!Promise<!Element>}
 */
GrDomHook.prototype.getLastAttached = function() {
  if (this._instances.length) {
    return Promise.resolve(this._instances.slice(-1)[0]);
  }
  if (!this._lastAttachedPromise) {
    let resolve;
    const promise = new Promise(r => resolve = r);
    this._attachCallbacks.push(resolve);
    this._lastAttachedPromise = promise.then(element => {
      this._lastAttachedPromise = null;
      const index = this._attachCallbacks.indexOf(resolve);
      if (index !== -1) {
        this._attachCallbacks.splice(index, 1);
      }
      return element;
    });
  }
  return this._lastAttachedPromise;
};

/**
 * Get all DOM hook elements.
 */
GrDomHook.prototype.getAllAttached = function() {
  return this._instances;
};

/**
 * Install a new callback to invoke when a new instance of DOM hook element
 * is attached.
 *
 * @param {function(Element)} callback
 */
GrDomHook.prototype.onAttached = function(callback) {
  this._attachCallbacks.push(callback);
  return this;
};

/**
 * Install a new callback to invoke when an instance of DOM hook element
 * is detached.
 *
 * @param {function(Element)} callback
 */
GrDomHook.prototype.onDetached = function(callback) {
  this._detachCallbacks.push(callback);
  return this;
};

/**
 * Name of DOM hook element that will be installed into the endpoint.
 */
GrDomHook.prototype.getModuleName = function() {
  return this._moduleName;
};

GrDomHook.prototype.getPublicAPI = function() {
  const result = {};
  const exposedMethods = [
    'onAttached',
    'onDetached',
    'getLastAttached',
    'getAllAttached',
    'getModuleName',
  ];
  for (const p of exposedMethods) {
    result[p] = this[p].bind(this);
  }
  return result;
};
