// Generated by CoffeeScript 1.12.7
(function() {
  var HandlerStack, root;

  root = typeof exports !== "undefined" && exports !== null ? exports : (window.root != null ? window.root : window.root = {});

  HandlerStack = (function() {
    function HandlerStack() {
      this.debug = false;
      this.eventNumber = 0;
      this.stack = [];
      this.counter = 0;
      this.passEventToPage = new Object();
      this.suppressPropagation = new Object();
      this.restartBubbling = new Object();
      this.continueBubbling = true;
      this.suppressEvent = false;
    }

    HandlerStack.prototype.push = function(handler) {
      handler._name || (handler._name = "anon-" + this.counter);
      this.stack.push(handler);
      return handler.id = ++this.counter;
    };

    HandlerStack.prototype.unshift = function(handler) {
      handler._name || (handler._name = "anon-" + this.counter);
      handler._name += "/unshift";
      this.stack.unshift(handler);
      return handler.id = ++this.counter;
    };

    HandlerStack.prototype.bubbleEvent = function(type, event) {
      var eventNumber, handler, j, len, ref, result;
      this.eventNumber += 1;
      eventNumber = this.eventNumber;
      ref = this.stack.slice(0).reverse();
      for (j = 0, len = ref.length; j < len; j++) {
        handler = ref[j];
        if (!((handler != null ? handler.id : void 0) && handler[type])) {
          if (this.debug) {
            this.logResult(eventNumber, type, event, handler, "skip [" + (handler[type] != null) + "]");
          }
        } else {
          this.currentId = handler.id;
          result = handler[type].call(this, event);
          if (this.debug) {
            this.logResult(eventNumber, type, event, handler, result);
          }
          if (result === this.passEventToPage) {
            return true;
          } else if (result === this.suppressPropagation) {
            DomUtils.suppressPropagation(event);
            return false;
          } else if (result === this.restartBubbling) {
            return this.bubbleEvent(type, event);
          } else if (result === this.continueBubbling || (result && result !== this.suppressEvent)) {
            true;
          } else {
            if (this.isChromeEvent(event)) {
              DomUtils.suppressEvent(event);
            }
            return false;
          }
        }
      }
      return true;
    };

    HandlerStack.prototype.remove = function(id) {
      var handler, i, j, ref, results;
      if (id == null) {
        id = this.currentId;
      }
      results = [];
      for (i = j = ref = this.stack.length - 1; j >= 0; i = j += -1) {
        handler = this.stack[i];
        if (handler.id === id) {
          handler.id = null;
          this.stack.splice(i, 1);
          break;
        } else {
          results.push(void 0);
        }
      }
      return results;
    };

    HandlerStack.prototype.isChromeEvent = function(event) {
      return ((event != null ? event.preventDefault : void 0) != null) || ((event != null ? event.stopImmediatePropagation : void 0) != null);
    };

    HandlerStack.prototype.alwaysContinueBubbling = function(handler) {
      if (handler == null) {
        handler = null;
      }
      if (typeof handler === "function") {
        handler();
      }
      return this.continueBubbling;
    };

    HandlerStack.prototype.alwaysSuppressPropagation = function(handler) {
      if (handler == null) {
        handler = null;
      }
      if ((typeof handler === "function" ? handler() : void 0) === this.suppressEvent) {
        return this.suppressEvent;
      } else {
        return this.suppressPropagation;
      }
    };

    HandlerStack.prototype.logResult = function(eventNumber, type, event, handler, result) {
      var label;
      if ((event != null ? event.type : void 0) === "keydown") {
        label = (function() {
          switch (result) {
            case this.passEventToPage:
              return "passEventToPage";
            case this.suppressEvent:
              return "suppressEvent";
            case this.suppressPropagation:
              return "suppressPropagation";
            case this.restartBubbling:
              return "restartBubbling";
            case "skip":
              return "skip";
            case true:
              return "continue";
          }
        }).call(this);
        label || (label = result ? "continue/truthy" : "suppress");
        return console.log("" + eventNumber, type, handler._name, label);
      }
    };

    HandlerStack.prototype.show = function() {
      var handler, j, len, ref, results;
      console.log(this.eventNumber + ":");
      ref = this.stack.slice(0).reverse();
      results = [];
      for (j = 0, len = ref.length; j < len; j++) {
        handler = ref[j];
        results.push(console.log("  ", handler._name));
      }
      return results;
    };

    HandlerStack.prototype.reset = function() {
      return this.stack = [];
    };

    return HandlerStack;

  })();

  root.HandlerStack = HandlerStack;

  root.handlerStack = new HandlerStack();

  if (typeof exports === "undefined" || exports === null) {
    extend(window, root);
  }

}).call(this);
