<commit_before>Ext.namespace('Kwc.Abstract.Image');
Kwc.Abstract.Image.DimensionWindow = Ext.extend(Ext.Window, {

    dimensions: null,
    value: null, //contains width, height, cropdata

    title: trlKwf('Image Size'),
    closeAction: 'close',
    modal: true,
    width: 850,
    height: 350,
    layout: 'fit',
    resizable: false,

    initComponent: function() {
        var radios = [];
        for (var i in this.dimensions) {
            radios.push({
                inputValue: i,
                boxLabel: Kwc.Abstract.Image.DimensionField.getDimensionString(this.dimensions, {dimension: i}),
                name: 'dimension',
                listeners: {
                    check: this._enableDisableFields,
                    scope: this
                }
            });
        }
        this.dimensionField = new Kwf.Form.RadioGroup({
            columns: 1,
            hideLabel: true,
            vertical: false,
            items: radios
        });
        this.widthField = new Ext.form.NumberField({
            fieldLabel: trlKwf('Width'),
            width: 50,
            enableKeyEvents: true,
            validateOnBlur: false,
            validationEvent: false,
            allowNegative: false
        });
        this.heightField = new Ext.form.NumberField({
            fieldLabel: trlKwf('Height'),
            width: 50,
            enableKeyEvents: true,
            validateOnBlur: false,
            validationEvent: false,
            allowNegative: false
        });

        this.widthField.on('blur', this._validateSizes, this);
        this.widthField.on('keyup', this._validateSizes, this);
        this.heightField.on('blur', this._validateSizes, this);
        this.heightField.on('keyup', this._validateSizes, this);
        this.dimensionField.on('change', this._validateSizes, this);
        this.dimensionField.on('change', this._resetCropRegion, this);

        // Has to be initialised before cropRegion because cropRegion needs dimensionValue
        if (this.value && this.value.dimension) {
            this.dimensionField.setValue(this.value.dimension);
            this.widthField.setValue(this.value.width);
            this.heightField.setValue(this.value.height);
        } else {
            for (var i in this.dimensions) {
                break;
            }
            this.dimensionField.setValue(i);
        }
        this._enableDisableFields();

        this._initCropRegion();

        this._configPane = new Ext.FormPanel({
            region: 'west',
            layout: 'fit',
            width: 250,
            items: [
                {
                    xtype: 'fieldset',
                    autoHeight: true,
                    title: trlKwf('Size'),
                    items: [
                        this.widthField,
                        this.heightField
                    ]
                },
                this.dimensionField
            ]
        });

        this._cropPane = new Ext.Panel({
            region: 'center',
            layout: 'fit',
            width: 600,
            height: 200,
            items: [
                this._cropImage
            ]
        });

        this.items = new Ext.FormPanel({
            bodyStyle: 'padding: 10px',
            layout: 'border',
            items: [
                this._configPane,
                this._cropPane
            ]
        });
        this.buttons = [
            {
                text: trlKwf('OK'),
                handler: function() {
                    if (this._validateSizes()) {
                        this.value.cropData = this.cropData;
                        this.value = {
                            dimension: this.dimensionField.getValue(),
                            width: this.widthField.getValue(),
                            height: this.heightField.getValue(),
                            cropData: this.value.cropData
                        };
                        this.fireEvent('save', this.value);
                        this.close();
                    } else {
                        Ext.Msg.alert(trlKwf('Error'), trlKwf('Please fill the marked fields correctly.'));
                    }
                },
                scope: this
            },{
                text: trlKwf('Cancel'),
                handler: function() {
                    this.close();
                },
                scope: this
            }
        ];

        Kwc.Abstract.Image.DimensionWindow.superclass.initComponent.call(this);
        this._validateSizes();
    },

    _initCropRegion: function ()
    {
        var cropData = null;
        if (this.dimensionField.getValue() == this.value.dimension) {
            // load saved crop-values if not 0
            if (this.value.cropData && this.value.cropData.width > 0 && this.value.cropData.height > 0) {
                cropData = this.value.cropData;
            }
        }

        var outWidth = this._getWidth();
        var outHeight = this._getHeight();
        if (outWidth == -1 || outHeight == -1) {
            return;
        }

        var preserveRatio = this._getPreserveRatio();

        this._cropImage = new Kwc.Abstract.Image.CropImage({
            // call controller to create image with nice size to work with
            src: '/kwf/media/upload/download-handy?uploadId='+this.imageData.uploadId+'&hashKey='+this.imageData.hashKey,
            preserveRatio: preserveRatio,
            width: 500,
            height: 300,
            outWidth: outWidth,
            outHeight: outHeight,
            cropData: cropData
        });

        this._cropImage.on('changeCrop', function(cropImageElement, x) {
            this.cropData = x;
        }, this);
        this._cropImage.on('finishedLoading', function (dimensions) {
            this._cropPane.width = dimensions.width;
            this._cropPane.height = dimensions.height;
            this.setSize(250 + 18 + dimensions.width, dimensions.height + 73);
            //TODO handle image height smaller than dimensions-radios
        }, this);
    },

    _getPreserveRatio: function()
    {
        var preserveRatio = false;
        var outWidth = this._getWidth();
        var outHeight = this._getHeight();
        var dimension = this.dimensions[this.dimensionField.getValue()];
        if (dimension.cover == true && !(outWidth == 0 || outHeight == 0)) {
            preserveRatio = true;
        }
        return preserveRatio;
    },

    _getHeight: function ()
    {
        var outHeight = -1;
        var dimension = this.dimensions[this.dimensionField.getValue()];
        if (dimension.height == 'user' && this.heightField.getValue() != '') {
            outHeight = this.heightField.getValue();
        } else if (dimension.height >= 0) {
            outHeight = dimension.height;
        } else if (typeof dimension.height === 'undefined') {
            outHeight = 0;
        } else {
            Ext.Msg.alert(trlKwf('Error'), trlKwf('No height value was set'));
        }
        return outHeight;
    },

    _getWidth: function ()
    {
        var outWidth = -1;
        var dimension = this.dimensions[this.dimensionField.getValue()];
        if (dimension.width == 'user' && this.widthField.getValue() != '') {
            outWidth = this.widthField.getValue();
        } else if (dimension.width == 'contentWidth') {
            outWidth = 0;
        } else if (dimension.width >= 0) {
            outWidth = dimension.width;
        } else if (typeof dimension.width === 'undefined') {
            outWidth = 0;
        } else {
            Ext.Msg.alert(trlKwf('Error'), trlKwf('No width value was set'));
        }
        return outWidth;
    },

    _resetCropRegion: function (element, value)
    {
        var cropData = null;
        if (value.inputValue == this.value.dimension) {
            cropData = this.value.cropData;
        }
        this.value = {
            dimension: this.dimensionField.getValue(),
            width: this.widthField.getValue(),
            height: this.heightField.getValue(),
            cropData: cropData
        };
        var outWidth = this._getWidth();
        var outHeight = this._getHeight();
        if (outWidth == -1 || outHeight == -1) {
            return;
        }
        this._cropImage.outWidth = outWidth;
        this._cropImage.outHeight = outHeight;
        this._cropImage.setCropData(cropData, this._getPreserveRatio());
    },

    _validateSizes: function()
    {
        var dim = this.dimensionField.getValue();
        if (this.widthField.getValue() < 1 && this.dimensions[dim].width == 'user'
            && this.heightField.getValue() < 1 && this.dimensions[dim].height == 'user'
        ) {
            if (this.widthField.getValue() < 1) {
                this.widthField.markInvalid(trlKwf('Width or height must be higher than 0 when using crop or cover.'));
            }
            if (this.heightField.getValue() < 1) {
                this.heightField.markInvalid(trlKwf('Width or height must be higher than 0 when using crop or cover.'));
            }
            return false;
        }

        this.widthField.clearInvalid();
        this.heightField.clearInvalid();

        return true;
    },

    _enableDisableFields: function()
    {
        var dim = this.dimensions[this.dimensionField.getValue()];
        this.widthField.setDisabled(!(dim && dim.width == 'user'));
        this.heightField.setDisabled(!(dim && dim.height == 'user'));
    }
});

Ext.reg('kwc.image.dimensionwindow', Kwc.Abstract.Image.DimensionWindow);
<commit_msg>Change variables to match private-field code-style<commit_after>Ext.namespace('Kwc.Abstract.Image');
Kwc.Abstract.Image.DimensionWindow = Ext.extend(Ext.Window, {

    dimensions: null,
    value: null, //contains width, height, cropdata

    title: trlKwf('Image Size'),
    closeAction: 'close',
    modal: true,
    width: 850,
    height: 350,
    layout: 'fit',
    resizable: false,

    initComponent: function() {
        var radios = [];
        for (var i in this.dimensions) {
            radios.push({
                inputValue: i,
                boxLabel: Kwc.Abstract.Image.DimensionField.getDimensionString(this.dimensions, {dimension: i}),
                name: 'dimension',
                listeners: {
                    check: this._enableDisableFields,
                    scope: this
                }
            });
        }
        this._dimensionField = new Kwf.Form.RadioGroup({
            columns: 1,
            hideLabel: true,
            vertical: false,
            items: radios
        });
        this._widthField = new Ext.form.NumberField({
            fieldLabel: trlKwf('Width'),
            width: 50,
            enableKeyEvents: true,
            validateOnBlur: false,
            validationEvent: false,
            allowNegative: false
        });
        this._heightField = new Ext.form.NumberField({
            fieldLabel: trlKwf('Height'),
            width: 50,
            enableKeyEvents: true,
            validateOnBlur: false,
            validationEvent: false,
            allowNegative: false
        });

        this._widthField.on('blur', this._validateSizes, this);
        this._widthField.on('keyup', this._validateSizes, this);
        this._heightField.on('blur', this._validateSizes, this);
        this._heightField.on('keyup', this._validateSizes, this);
        this._dimensionField.on('change', this._validateSizes, this);
        this._dimensionField.on('change', this._resetCropRegion, this);

        // Has to be initialised before cropRegion because cropRegion needs dimensionValue
        if (this.value && this.value.dimension) {
            this._dimensionField.setValue(this.value.dimension);
            this._widthField.setValue(this.value.width);
            this._heightField.setValue(this.value.height);
        } else {
            for (var i in this.dimensions) {
                break;
            }
            this._dimensionField.setValue(i);
        }
        this._enableDisableFields();

        this._initCropRegion();

        this._configPane = new Ext.FormPanel({
            region: 'west',
            layout: 'fit',
            width: 250,
            items: [
                {
                    xtype: 'fieldset',
                    autoHeight: true,
                    title: trlKwf('Size'),
                    items: [
                        this._widthField,
                        this._heightField
                    ]
                },
                this._dimensionField
            ]
        });

        this._cropPane = new Ext.Panel({
            region: 'center',
            layout: 'fit',
            width: 600,
            height: 200,
            items: [
                this._cropImage
            ]
        });

        this.items = new Ext.FormPanel({
            bodyStyle: 'padding: 10px',
            layout: 'border',
            items: [
                this._configPane,
                this._cropPane
            ]
        });
        this.buttons = [
            {
                text: trlKwf('OK'),
                handler: function() {
                    if (this._validateSizes()) {
                        this.value.cropData = this.cropData;
                        this.value = {
                            dimension: this._dimensionField.getValue(),
                            width: this._widthField.getValue(),
                            height: this._heightField.getValue(),
                            cropData: this.value.cropData
                        };
                        this.fireEvent('save', this.value);
                        this.close();
                    } else {
                        Ext.Msg.alert(trlKwf('Error'), trlKwf('Please fill the marked fields correctly.'));
                    }
                },
                scope: this
            },{
                text: trlKwf('Cancel'),
                handler: function() {
                    this.close();
                },
                scope: this
            }
        ];

        Kwc.Abstract.Image.DimensionWindow.superclass.initComponent.call(this);
        this._validateSizes();
    },

    _initCropRegion: function ()
    {
        var cropData = null;
        if (this._dimensionField.getValue() == this.value.dimension) {
            // load saved crop-values if not 0
            if (this.value.cropData && this.value.cropData.width > 0 && this.value.cropData.height > 0) {
                cropData = this.value.cropData;
            }
        }

        var outWidth = this._getWidth();
        var outHeight = this._getHeight();
        if (outWidth == -1 || outHeight == -1) {
            return;
        }

        var preserveRatio = this._getPreserveRatio();

        this._cropImage = new Kwc.Abstract.Image.CropImage({
            // call controller to create image with nice size to work with
            src: '/kwf/media/upload/download-handy?uploadId='+this.imageData.uploadId+'&hashKey='+this.imageData.hashKey,
            preserveRatio: preserveRatio,
            width: 500,
            height: 300,
            outWidth: outWidth,
            outHeight: outHeight,
            cropData: cropData
        });

        this._cropImage.on('changeCrop', function(cropImageElement, x) {
            this.cropData = x;
        }, this);
        this._cropImage.on('finishedLoading', function (dimensions) {
            this._cropPane.width = dimensions.width;
            this._cropPane.height = dimensions.height;
            this.setSize(250 + 18 + dimensions.width, dimensions.height + 73);
            //TODO handle image height smaller than dimensions-radios
        }, this);
    },

    _getPreserveRatio: function()
    {
        var preserveRatio = false;
        var outWidth = this._getWidth();
        var outHeight = this._getHeight();
        var dimension = this.dimensions[this._dimensionField.getValue()];
        if (dimension.cover == true && !(outWidth == 0 || outHeight == 0)) {
            preserveRatio = true;
        }
        return preserveRatio;
    },

    _getHeight: function ()
    {
        var outHeight = -1;
        var dimension = this.dimensions[this._dimensionField.getValue()];
        if (dimension.height == 'user' && this._heightField.getValue() != '') {
            outHeight = this._heightField.getValue();
        } else if (dimension.height >= 0) {
            outHeight = dimension.height;
        } else if (typeof dimension.height === 'undefined') {
            outHeight = 0;
        } else {
            Ext.Msg.alert(trlKwf('Error'), trlKwf('No height value was set'));
        }
        return outHeight;
    },

    _getWidth: function ()
    {
        var outWidth = -1;
        var dimension = this.dimensions[this._dimensionField.getValue()];
        if (dimension.width == 'user' && this._widthField.getValue() != '') {
            outWidth = this._widthField.getValue();
        } else if (dimension.width == 'contentWidth') {
            outWidth = 0;
        } else if (dimension.width >= 0) {
            outWidth = dimension.width;
        } else if (typeof dimension.width === 'undefined') {
            outWidth = 0;
        } else {
            Ext.Msg.alert(trlKwf('Error'), trlKwf('No width value was set'));
        }
        return outWidth;
    },

    _resetCropRegion: function (element, value)
    {
        var cropData = null;
        if (value.inputValue == this.value.dimension) {
            cropData = this.value.cropData;
        }
        this.value = {
            dimension: this._dimensionField.getValue(),
            width: this._widthField.getValue(),
            height: this._heightField.getValue(),
            cropData: cropData
        };
        var outWidth = this._getWidth();
        var outHeight = this._getHeight();
        if (outWidth == -1 || outHeight == -1) {
            return;
        }
        this._cropImage.outWidth = outWidth;
        this._cropImage.outHeight = outHeight;
        this._cropImage.setCropData(cropData, this._getPreserveRatio());
    },

    _validateSizes: function()
    {
        var dim = this._dimensionField.getValue();
        if (this._widthField.getValue() < 1 && this.dimensions[dim].width == 'user'
            && this._heightField.getValue() < 1 && this.dimensions[dim].height == 'user'
        ) {
            if (this._widthField.getValue() < 1) {
                this._widthField.markInvalid(trlKwf('Width or height must be higher than 0 when using crop or cover.'));
            }
            if (this._heightField.getValue() < 1) {
                this._heightField.markInvalid(trlKwf('Width or height must be higher than 0 when using crop or cover.'));
            }
            return false;
        }

        this._widthField.clearInvalid();
        this._heightField.clearInvalid();

        return true;
    },

    _enableDisableFields: function()
    {
        var dim = this.dimensions[this._dimensionField.getValue()];
        this._widthField.setDisabled(!(dim && dim.width == 'user'));
        this._heightField.setDisabled(!(dim && dim.height == 'user'));
    }
});

Ext.reg('kwc.image.dimensionwindow', Kwc.Abstract.Image.DimensionWindow);
<|endoftext|>


<commit_before>var filter = options.register(new Option("filter", "f", "SpciMsm", "[S]ource, constant[p]ool, [c]lasses, [i]nstances, [M]etadata, [s]cripts, [m]ethods"));

var IndentingWriter = (function () {
  function indentingWriter(suppressOutput, out) {
    this.tab = "  ";
    this.padding = "";
    this.suppressOutput = suppressOutput;
    this.out = out || console;
  }

  indentingWriter.prototype.writeLn = function writeLn(str) {
    if (!this.suppressOutput) {
      this.out.info(this.padding + str);
    }
  };

  indentingWriter.prototype.enter = function enter(str) {
    if (!this.suppressOutput) {
      this.out.info(this.padding + str);
    }
    this.indent();
  };

  indentingWriter.prototype.leave = function leave(str) {
    this.outdent();
    if (!this.suppressOutput) {
      this.out.info(this.padding + str);
    }
  };

  indentingWriter.prototype.indent = function indent() {
    this.padding += this.tab;
  };

  indentingWriter.prototype.outdent = function outdent() {
    if (this.padding.length > 0) {
      this.padding = this.padding.substring(0, this.padding.length - this.tab.length);
    }
  };

  indentingWriter.prototype.writeArray = function writeArray(arr, detailed) {
    detailed = detailed || false;
    for (var i = 0, j = arr.length; i < j; i++) {
      var prefix = "";
      if (detailed) {
        if (arr[i] === null) {
          prefix = "null";
        } else if (arr[i] === undefined) {
          prefix = "undefined";
        } else {
          prefix = arr[i].constructor.name;
        }
        prefix += " ";
      }
      this.writeLn(("" + i).padRight(' ', 4) + prefix + arr[i]);
    }
  };

  return indentingWriter;
})();

function traceArray(writer, name, array, abc) {
  if (array.length === 0) {
    return;
  }
  writer.enter(name + " {");
  array.forEach(function (a, idx) {
    a.trace(writer, abc);
  });
  writer.leave("}");
}

AbcFile.prototype.trace = function trace(writer) {
  if (filter.value.indexOf("p") >= 0) {
    this.constantPool.trace(writer);
  }
  if (filter.value.indexOf("c") >= 0) {
    traceArray(writer, "classes", this.classes);
  }
  if (filter.value.indexOf("i") >= 0) {
    traceArray(writer, "instances", this.instances);
  }
  if (filter.value.indexOf("M") >= 0) {
    traceArray(writer, "metadata", this.metadata);
  }
  if (filter.value.indexOf("s") >= 0) {
    traceArray(writer, "scripts", this.scripts);
  }
  if (filter.value.indexOf("m") >= 0) {
    traceArray(writer, "methods", this.methods, this);
  }
  if (filter.value.indexOf("S") >= 0) {
    traceSource(writer, this);
  }
};

ConstantPool.prototype.trace = function (writer) {
  writer.enter("constantPool {");
  for (var key in this) {
    /* Special-case namespaces to print out full names. */
    if (key === "namespaces") {
      writer.enter("namespaces {");
      this.namespaces.forEach(function (ns, i) {
        writer.writeLn(("" + i).padRight(' ', 3) +
                 (ns ? ns.toString() : "*"));
      });
      writer.leave("}");
    } else if (this[key] instanceof Array) {
      writer.enter(key + " " + this[key].length + " {");
      writer.writeArray(this[key]);
      writer.leave("}");
    }
  }
  writer.leave("}");
};

Traits.prototype.trace = function (writer) {
  traceArray(writer, "traits", this.traits);
};

ClassInfo.prototype.trace = function (writer) {
  writer.enter("class " + this + " {");
  this.traits.trace(writer);
  writer.leave("}");
};

MetaDataInfo.prototype.trace = function (writer) {
  writer.enter(this + " {");
  this.items.forEach(function (item) {
    writer.writeLn((item.key ? item.key + ": " : "") + "\"" + item.value + "\"");
  });
  writer.leave("}");
};

InstanceInfo.prototype.trace = function (writer) {
  writer.enter("instance " + this + " {");
  this.traits.trace(writer);
  writer.leave("}");
};

ScriptInfo.prototype.trace = function (writer) {
  writer.enter("script " + this + " {");
  this.traits.trace(writer);
  writer.leave("}");
};

Trait.prototype.trace = function (writer) {
  if (this.metadata) {
    for (var key in this.metadata) {
      this.metadata[key].trace(writer);
    }
  }
  writer.writeLn(this);
};

function traceAbc(writer, abc) {
  abc.trace(writer);
}

function traceOperand(operand, abc, code) {
  var value = 0;
  switch(operand.size) {
    case "s08": value = code.readS8(); break;
    case "u08": value = code.readU8(); break;
    case "s16": value = code.readS16(); break;
    case "s24": value = code.readS24(); break;
    case "u30": value = code.readU30(); break;
    case "u32": value = code.readU32(); break;
    default: assert (false); break;
  }
  var description = "";
  switch(operand.type) {
    case "": break;
    case "I": description = abc.constantPool.ints[value]; break;
    case "U": description = abc.constantPool.uints[value]; break;
    case "D": description = abc.constantPool.doubles[value]; break;
    case "S": description = abc.constantPool.strings[value]; break;
    case "N": description = abc.constantPool.namespaces[value]; break;
    case "CI": description = abc.classes[value]; break;
    case "M":
      return abc.constantPool.multinames[value];
    default: description = "?"; break;
  }
  return operand.name + ":" + value + (description === "" ? "" : " (" + description + ")");
}

function traceOperands(opcode, abc, code, rewind) {
  rewind = rewind || false;
  var old = code.position;
  var str = "";
  if (opcode.operands === null) {
    str = "null";
  } else {
    opcode.operands.forEach(function (op, i) {
      str += traceOperand(op, abc, code);
      if (i < opcode.operands.length - 1) {
        str += ", ";
      }
    });
  }
  if (rewind) {
    code.seek(old);
  }
  return str;
}

MethodInfo.prototype.trace = function trace(writer, abc) {
  writer.enter("method" + (this.name ? " " + this.name : "") + " {");
  writer.writeLn("flags: " + getFlags(this.flags, "NEED_ARGUMENTS|NEED_ACTIVATION|NEED_REST|HAS_OPTIONAL||NATIVE|SET_DXN|HAS_PARAM_NAMES".split("|")));

  if (!this.code) {
    writer.leave("}");
    return;
  }

  var code = new AbcStream(this.code);

  this.traits.trace(writer);

  writer.enter("code {");
  while (code.remaining() > 0) {
    var bc = code.readU8();
    var opcode = opcodeTable[bc];
    var str, defaultOffset, offset, count;
    str = ("" + code.position).padRight(' ', 6);
    switch (bc) {
      case OP_lookupswitch:
        str += opcode.name + ": defaultOffset: " + code.readS24();
        var caseCount = code.readU30();
        str += ", caseCount: " + caseCount;
        for (var i = 0; i < caseCount + 1; i++) {
          str += " offset: " + code.readS24();
        }
        writer.writeLn(str);
        break;
      default:
        if (opcode) {
          str += opcode.name.padRight(' ', 20);
          if (!opcode.operands) {
            assert(false, "Opcode: " + opcode.name + " has undefined operands.");
          } else {
            if (opcode.operands.length > 0) {
              str += traceOperands(opcode, abc, code);
            }
            writer.writeLn(str);
          }
        } else {
          assert(false, "Opcode: " + bc + " is not implemented.");
        }
        break;
    }
  }
  writer.leave("}");
  writer.leave("}");
}

function traceSource(writer, abc) {
  function literal(value) {
    if (value === undefined) {
      return "undefined";
    } else if (value === null) {
      return "null";
    } else if (typeof (value) === "string") {
      return "\"" + value + "\"";
    } else {
      return String(value);
    }
  }

  function getSignature(method, excludeTypesAndDefaultValues) {
    return method.parameters.map(function (x) {
      var str = x.name;
      if (!excludeTypesAndDefaultValues) {
        if (x.type) {
          str += ":" + x.type.getName();
        }
        if (x.value !== undefined) {
          str += "=" + literal(x.value);
        }
      }
      return str;
    }).join(", ");
  }

  abc.scripts.forEach(function (script) {
    traceTraits(script.traits);
    function traceTraits(traits, isStatic) {
      traits.traits.forEach(function (trait) {
        var str;
        var accessModifier = trait.name.getAccessModifier();
        var namespaceName = trait.name.namespaces[0].originalURI;
        if (namespaceName) {
          if (namespaceName === "http://adobe.com/AS3/2006/builtin") {
            namespaceName = "AS3";
          }
          if (accessModifier === "public") {
            str = namespaceName;
          } else {
            str = accessModifier;
          }
        } else {
          str = accessModifier;
        }
        if (isStatic) {
          str += " static";
        }
        if (trait.isSlot() || trait.isConst()) {
          traceMetadata(trait.metadata);
          if (trait.isConst()) {
            str += " const";
          }
          str += " " + trait.name.getName();
          if (trait.typeName) {
            str += ":" + trait.typeName.getName();
          }
          if (trait.value) {
            str += " = " + literal(trait.value);
          }
          writer.writeLn(str + ";");
        } else if (trait.isMethod() || trait.isGetter() || trait.isSetter()) {
          traceMetadata(trait.metadata);
          var method = trait.method;
          if (method.isNative()) {
            str += " native";
          }
          str += " function";
          str += trait.isGetter() ? " get" : (trait.isSetter() ? " set" : "");
          str += " " + trait.name.getName();
          str += "(" + getSignature(method) + ")";
          str += method.returnType ? ":" + method.returnType.getName() : "";
          if (method.isNative()) {
            writer.writeLn(str + ";");
          } else {
            writer.writeLn(str + " { notImplemented(\"" + trait.name.getName() + "\"); }");
          }
        } else if (trait.isClass()) {
          var className = trait.class.instance.name;
          writer.enter("package " + className.namespaces[0].originalURI + " {");
          traceMetadata(trait.metadata);
          traceClass(trait.class);
          writer.leave("}");
          traceClassStub(trait);
        } else {
          notImplemented();
        }
      });
    }

    function traceClassStub(trait) {
      var cls = trait.class;
      var name = cls.instance.name;
      var native = trait.metadata.native;
      if (!native) {
        return;
      }
      writer.enter("Shumway Stub {");
      writer.enter("function " + native.dict.cls + "(scope, instance) {");
      writer.writeLn("function " + name.getName() + "() {};");
      writer.writeLn("var c = new Class(\"" + name.getName() + "\", " +
                     name.getName() + ", C(" + name.getName() + "));");

      function traceTraits(traits, isStatic) {
        traits.traits.forEach(function (trait) {
          var traitName = trait.name.getName();
          if (trait.isMethod() || trait.isGetter() || trait.isSetter()) {
            var method = trait.method;
            if (method.isNative()) {
              var str = "";
              if (isStatic) {
                str += "statics";
              } else if (trait.isGetter()) {
                str += "getters";
              } else if (trait.isSetter()) {
                str += "setters";
              } else if (trait.isMethod()) {
                str += "methods";
              }
              if (trait.method.parameters.length) {
                writer.writeLn("// Signature: " + getSignature(trait.method) + " -> " + trait.method.returnType.getName());
              }
              str += "." + traitName + " = function " + traitName + "(" + getSignature(trait.method, true) + ") {";
              writer.enter(str);
              writer.leave("}");
            }
          }
        });
      }

      writer.writeLn("var statics = c.statics = {};");
      writer.writeLn("var getters = c.getters = {};");
      writer.writeLn("var setters = c.setters = {};");
      writer.writeLn("var methods = instance.prototype;");
      traceTraits(cls.traits, true);
      traceTraits(cls.instance.traits);

      writer.writeLn("return c;");
      writer.leave("}");
      writer.leave("}");
    }

    function traceClass(cls) {
      var name = cls.instance.name;
      var str = name.getAccessModifier();
      if (cls.instance.isFinal()) {
        str += " final";
      }
      if (!cls.instance.isSealed()) {
        str += " dynamic";
      }
      str += cls.instance.isInterface() ? " interface " : " class ";
      str += name.getName();
      if (cls.instance.superName) {
        str += " extends " + cls.instance.superName.getName();
      }
      if (cls.instance.interfaces.length) {
        str += " implements " + cls.instance.interfaces.map(function (x) {
          return x.getName();
        }).join(", ");
      }
      writer.enter(str + " {");
      writer.writeLn("public function " + name.getName() + "(" + getSignature(cls.instance.init) + ") {}");
      traceTraits(cls.traits, true);
      traceTraits(cls.instance.traits);
      writer.leave("}");
    }

    function traceMetadata(metadata) {
      for (var key in metadata) {
        if (key.indexOf("__") === 0) {
          continue;
        }
        writer.writeLn("[" + key + "(" + metadata[key].items.map(function (m) {
          var str = m.key ? m.key + "=" : "";
          return str + "\"" + m.value + "\"";
        }).join(", ") + ")]");
      }
    }

  });
}
<commit_msg>Update stub generator to use static getters/setters.<commit_after>var filter = options.register(new Option("filter", "f", "SpciMsm", "[S]ource, constant[p]ool, [c]lasses, [i]nstances, [M]etadata, [s]cripts, [m]ethods"));

var IndentingWriter = (function () {
  function indentingWriter(suppressOutput, out) {
    this.tab = "  ";
    this.padding = "";
    this.suppressOutput = suppressOutput;
    this.out = out || console;
  }

  indentingWriter.prototype.writeLn = function writeLn(str) {
    if (!this.suppressOutput) {
      this.out.info(this.padding + str);
    }
  };

  indentingWriter.prototype.enter = function enter(str) {
    if (!this.suppressOutput) {
      this.out.info(this.padding + str);
    }
    this.indent();
  };

  indentingWriter.prototype.leave = function leave(str) {
    this.outdent();
    if (!this.suppressOutput) {
      this.out.info(this.padding + str);
    }
  };

  indentingWriter.prototype.indent = function indent() {
    this.padding += this.tab;
  };

  indentingWriter.prototype.outdent = function outdent() {
    if (this.padding.length > 0) {
      this.padding = this.padding.substring(0, this.padding.length - this.tab.length);
    }
  };

  indentingWriter.prototype.writeArray = function writeArray(arr, detailed) {
    detailed = detailed || false;
    for (var i = 0, j = arr.length; i < j; i++) {
      var prefix = "";
      if (detailed) {
        if (arr[i] === null) {
          prefix = "null";
        } else if (arr[i] === undefined) {
          prefix = "undefined";
        } else {
          prefix = arr[i].constructor.name;
        }
        prefix += " ";
      }
      this.writeLn(("" + i).padRight(' ', 4) + prefix + arr[i]);
    }
  };

  return indentingWriter;
})();

function traceArray(writer, name, array, abc) {
  if (array.length === 0) {
    return;
  }
  writer.enter(name + " {");
  array.forEach(function (a, idx) {
    a.trace(writer, abc);
  });
  writer.leave("}");
}

AbcFile.prototype.trace = function trace(writer) {
  if (filter.value.indexOf("p") >= 0) {
    this.constantPool.trace(writer);
  }
  if (filter.value.indexOf("c") >= 0) {
    traceArray(writer, "classes", this.classes);
  }
  if (filter.value.indexOf("i") >= 0) {
    traceArray(writer, "instances", this.instances);
  }
  if (filter.value.indexOf("M") >= 0) {
    traceArray(writer, "metadata", this.metadata);
  }
  if (filter.value.indexOf("s") >= 0) {
    traceArray(writer, "scripts", this.scripts);
  }
  if (filter.value.indexOf("m") >= 0) {
    traceArray(writer, "methods", this.methods, this);
  }
  if (filter.value.indexOf("S") >= 0) {
    traceSource(writer, this);
  }
};

ConstantPool.prototype.trace = function (writer) {
  writer.enter("constantPool {");
  for (var key in this) {
    /* Special-case namespaces to print out full names. */
    if (key === "namespaces") {
      writer.enter("namespaces {");
      this.namespaces.forEach(function (ns, i) {
        writer.writeLn(("" + i).padRight(' ', 3) +
                 (ns ? ns.toString() : "*"));
      });
      writer.leave("}");
    } else if (this[key] instanceof Array) {
      writer.enter(key + " " + this[key].length + " {");
      writer.writeArray(this[key]);
      writer.leave("}");
    }
  }
  writer.leave("}");
};

Traits.prototype.trace = function (writer) {
  traceArray(writer, "traits", this.traits);
};

ClassInfo.prototype.trace = function (writer) {
  writer.enter("class " + this + " {");
  this.traits.trace(writer);
  writer.leave("}");
};

MetaDataInfo.prototype.trace = function (writer) {
  writer.enter(this + " {");
  this.items.forEach(function (item) {
    writer.writeLn((item.key ? item.key + ": " : "") + "\"" + item.value + "\"");
  });
  writer.leave("}");
};

InstanceInfo.prototype.trace = function (writer) {
  writer.enter("instance " + this + " {");
  this.traits.trace(writer);
  writer.leave("}");
};

ScriptInfo.prototype.trace = function (writer) {
  writer.enter("script " + this + " {");
  this.traits.trace(writer);
  writer.leave("}");
};

Trait.prototype.trace = function (writer) {
  if (this.metadata) {
    for (var key in this.metadata) {
      this.metadata[key].trace(writer);
    }
  }
  writer.writeLn(this);
};

function traceAbc(writer, abc) {
  abc.trace(writer);
}

function traceOperand(operand, abc, code) {
  var value = 0;
  switch(operand.size) {
    case "s08": value = code.readS8(); break;
    case "u08": value = code.readU8(); break;
    case "s16": value = code.readS16(); break;
    case "s24": value = code.readS24(); break;
    case "u30": value = code.readU30(); break;
    case "u32": value = code.readU32(); break;
    default: assert (false); break;
  }
  var description = "";
  switch(operand.type) {
    case "": break;
    case "I": description = abc.constantPool.ints[value]; break;
    case "U": description = abc.constantPool.uints[value]; break;
    case "D": description = abc.constantPool.doubles[value]; break;
    case "S": description = abc.constantPool.strings[value]; break;
    case "N": description = abc.constantPool.namespaces[value]; break;
    case "CI": description = abc.classes[value]; break;
    case "M":
      return abc.constantPool.multinames[value];
    default: description = "?"; break;
  }
  return operand.name + ":" + value + (description === "" ? "" : " (" + description + ")");
}

function traceOperands(opcode, abc, code, rewind) {
  rewind = rewind || false;
  var old = code.position;
  var str = "";
  if (opcode.operands === null) {
    str = "null";
  } else {
    opcode.operands.forEach(function (op, i) {
      str += traceOperand(op, abc, code);
      if (i < opcode.operands.length - 1) {
        str += ", ";
      }
    });
  }
  if (rewind) {
    code.seek(old);
  }
  return str;
}

MethodInfo.prototype.trace = function trace(writer, abc) {
  writer.enter("method" + (this.name ? " " + this.name : "") + " {");
  writer.writeLn("flags: " + getFlags(this.flags, "NEED_ARGUMENTS|NEED_ACTIVATION|NEED_REST|HAS_OPTIONAL||NATIVE|SET_DXN|HAS_PARAM_NAMES".split("|")));

  if (!this.code) {
    writer.leave("}");
    return;
  }

  var code = new AbcStream(this.code);

  this.traits.trace(writer);

  writer.enter("code {");
  while (code.remaining() > 0) {
    var bc = code.readU8();
    var opcode = opcodeTable[bc];
    var str, defaultOffset, offset, count;
    str = ("" + code.position).padRight(' ', 6);
    switch (bc) {
      case OP_lookupswitch:
        str += opcode.name + ": defaultOffset: " + code.readS24();
        var caseCount = code.readU30();
        str += ", caseCount: " + caseCount;
        for (var i = 0; i < caseCount + 1; i++) {
          str += " offset: " + code.readS24();
        }
        writer.writeLn(str);
        break;
      default:
        if (opcode) {
          str += opcode.name.padRight(' ', 20);
          if (!opcode.operands) {
            assert(false, "Opcode: " + opcode.name + " has undefined operands.");
          } else {
            if (opcode.operands.length > 0) {
              str += traceOperands(opcode, abc, code);
            }
            writer.writeLn(str);
          }
        } else {
          assert(false, "Opcode: " + bc + " is not implemented.");
        }
        break;
    }
  }
  writer.leave("}");
  writer.leave("}");
}

function traceSource(writer, abc) {
  function literal(value) {
    if (value === undefined) {
      return "undefined";
    } else if (value === null) {
      return "null";
    } else if (typeof (value) === "string") {
      return "\"" + value + "\"";
    } else {
      return String(value);
    }
  }

  function getSignature(method, excludeTypesAndDefaultValues) {
    return method.parameters.map(function (x) {
      var str = x.name;
      if (!excludeTypesAndDefaultValues) {
        if (x.type) {
          str += ":" + x.type.getName();
        }
        if (x.value !== undefined) {
          str += "=" + literal(x.value);
        }
      }
      return str;
    }).join(", ");
  }

  abc.scripts.forEach(function (script) {
    traceTraits(script.traits);
    function traceTraits(traits, isStatic) {
      traits.traits.forEach(function (trait) {
        var str;
        var accessModifier = trait.name.getAccessModifier();
        var namespaceName = trait.name.namespaces[0].originalURI;
        if (namespaceName) {
          if (namespaceName === "http://adobe.com/AS3/2006/builtin") {
            namespaceName = "AS3";
          }
          if (accessModifier === "public") {
            str = namespaceName;
          } else {
            str = accessModifier;
          }
        } else {
          str = accessModifier;
        }
        if (isStatic) {
          str += " static";
        }
        if (trait.isSlot() || trait.isConst()) {
          traceMetadata(trait.metadata);
          if (trait.isConst()) {
            str += " const";
          }
          str += " " + trait.name.getName();
          if (trait.typeName) {
            str += ":" + trait.typeName.getName();
          }
          if (trait.value) {
            str += " = " + literal(trait.value);
          }
          writer.writeLn(str + ";");
        } else if (trait.isMethod() || trait.isGetter() || trait.isSetter()) {
          traceMetadata(trait.metadata);
          var method = trait.method;
          if (method.isNative()) {
            str += " native";
          }
          str += " function";
          str += trait.isGetter() ? " get" : (trait.isSetter() ? " set" : "");
          str += " " + trait.name.getName();
          str += "(" + getSignature(method) + ")";
          str += method.returnType ? ":" + method.returnType.getName() : "";
          if (method.isNative()) {
            writer.writeLn(str + ";");
          } else {
            writer.writeLn(str + " { notImplemented(\"" + trait.name.getName() + "\"); }");
          }
        } else if (trait.isClass()) {
          var className = trait.class.instance.name;
          writer.enter("package " + className.namespaces[0].originalURI + " {");
          traceMetadata(trait.metadata);
          traceClass(trait.class);
          writer.leave("}");
          traceClassStub(trait);
        } else {
          notImplemented();
        }
      });
    }

    function traceClassStub(trait) {
      var cls = trait.class;
      var name = cls.instance.name;
      var native = trait.metadata.native;
      if (!native) {
        return;
      }
      writer.enter("Shumway Stub {");
      writer.enter("function " + native.dict.cls + "(scope, instance) {");
      writer.writeLn("function " + name.getName() + "() {};");
      writer.writeLn("var c = new Class(\"" + name.getName() + "\", " +
                     name.getName() + ", C(" + name.getName() + "));");

      function traceTraits(traits, isStatic) {
        traits.traits.forEach(function (trait) {
          var traitName = trait.name.getName();
          if (trait.isMethod() || trait.isGetter() || trait.isSetter()) {
            var method = trait.method;
            if (method.isNative()) {
              var str = "";
              if (isStatic) {
                str += "s";
              }
              if (trait.isGetter()) {
                str += "g";
              } else if (trait.isSetter()) {
                str += "s";
              } else if (trait.isMethod()) {
                str += "m";
              }
              if (trait.method.parameters.length) {
                writer.writeLn("// Signature: " + getSignature(trait.method) + " -> " + trait.method.returnType.getName());
              }
              str += "." + traitName + " = function " + traitName + "(" + getSignature(trait.method, true) + ") {";
              writer.enter(str);
              writer.leave("}");
            }
          }
        });
      }

      writer.writeLn("var m = instance.prototype;");
      writer.writeLn("var g = c.getters = {};");
      writer.writeLn("var s = c.setters = {};");

      writer.writeLn("var sm = c.statics = {};");
      writer.writeLn("var sg = c.staticGetters = {};");
      writer.writeLn("var ss = c.staticSetters = {};");

      traceTraits(cls.traits, true);
      traceTraits(cls.instance.traits);

      writer.writeLn("return c;");
      writer.leave("}");
      writer.leave("}");
    }

    function traceClass(cls) {
      var name = cls.instance.name;
      var str = name.getAccessModifier();
      if (cls.instance.isFinal()) {
        str += " final";
      }
      if (!cls.instance.isSealed()) {
        str += " dynamic";
      }
      str += cls.instance.isInterface() ? " interface " : " class ";
      str += name.getName();
      if (cls.instance.superName) {
        str += " extends " + cls.instance.superName.getName();
      }
      if (cls.instance.interfaces.length) {
        str += " implements " + cls.instance.interfaces.map(function (x) {
          return x.getName();
        }).join(", ");
      }
      writer.enter(str + " {");
      writer.writeLn("public function " + name.getName() + "(" + getSignature(cls.instance.init) + ") {}");
      traceTraits(cls.traits, true);
      traceTraits(cls.instance.traits);
      writer.leave("}");
    }

    function traceMetadata(metadata) {
      for (var key in metadata) {
        if (key.indexOf("__") === 0) {
          continue;
        }
        writer.writeLn("[" + key + "(" + metadata[key].items.map(function (m) {
          var str = m.key ? m.key + "=" : "";
          return str + "\"" + m.value + "\"";
        }).join(", ") + ")]");
      }
    }

  });
}
<|endoftext|>


<commit_before>/*window['Autocompleter'] = Autocompleter;
window['Autocompleter.prototype'] = Autocompleter.prototype;
window['AutocompleteOnSelected'] = AutocompleteOnSelected;*/

$(function() { $('#form input[type=text]').keypress(function(e) { return e.which != 13 }) })

/*window['Autocompleter'] = Autocompleter;
window['Autocompleter.prototype'] = Autocompleter.prototype;
window['AutocompleteOnSelected'] = AutocompleteOnSelected;*/
Autocompleter = function(controlId, url, _options) {
    var self = this;
    self.options = $.extend({
        minChars: 1,
        limit: 5,
        delay: 200,
        process: null,
        onSuccess: null,
        entityIdFieldName: null,
        textField: "text",
        extraParams: {},

        extraResult: null,
        extraResultClick: null,

        cacheResults: true
    }, _options);

    self.timerID = 10;
    self.$dd = self.currentText = self.request = undefined;
    self.$control = $("#" + controlId);
    self.controlId = controlId;
    self.url = url;
    self.cacheResults = [];
    self.currentResults = [];
    self.currentInput = undefined;
    self.resultClass = "ddlAuto";
    self.resultSelectedClass = "ddlAutoOn";
    self.$resultDiv = $("

");
    self.create();
};

Autocompleter.prototype = {
    create: function() {
        var self = this;

        this.$control.bind({
            keyup: function(e) {
                self.clear(e.which ? e.which : e.keyCode);
            },
            keydown: function(e) {
                self.keydown(e);
            },
            click: function(e) {
                if (e.preventDefault) e.preventDefault();
                if (e.stopPropagation) e.stopPropagation();
            },
            focusin: function(e) {
                if (self.currentResults.length) {
                    self.$dd.show();
                }
            }
        });

        $("body").click(function() {
            self.$dd.hide();
        });

        this.$dd = $("
").addClass("AutoCompleteMainDiv");
        this.$dd.click(function(e) {
            self.click(e);
        });

        this.$dd.insertAfter(this.$control);
        this.$dd.delegate("." + this.resultClass, "mouseenter", function() {
            self.selectIndex($(this));
        });

    },
    clear: function(e) {
        clearTimeout(this.timerID);
        var self = this;
        this.timerID = setTimeout(function() { self.keyup(e) }, (self.options.cacheResults && self.cacheResults[self.$control.val().toLowerCase()] != null) ? 0 : self.options.delay);
    },
    keyup: function(key) {
    if (key == 37 || key == 39 || key == 38 || key == 40 || key == 13) return;
        var input = this.$control.val();
        if (this.currentText == input) return;

        if (input != null && input.length < this.options.minChars) {
            this.$dd.html("").hide(); this.currentResults = [];
            return;
        }
        //if (this.currentResults.length < this.options.limit && input.indexOf(this.currentInput) != -1)
        //process cached results

        var data = $.extend({
            q: input, l: this.options.limit
        }, this.options.extraParams);

        var self = this;

        if (self.currentResults == [] && self.currentInput != null && input.indexOf(self.currentInput) == 0) {
            self.showResults([], input);
            return;
        }

        if (self.options.cacheResults && self.cacheResults[input.toLowerCase()] != null) {
            self.showResults(self.cacheResults[input.toLowerCase()], input);
            return;
        }

        if (self.request) self.request.abort();
        self.$control.addClass('loading');
        self.request = $.getJSON(
            self.url, data,
            function(results) {
                if (results) {
                    self.showResults(results, input);
                }
            });
    },

    showResults: function(results, input) {
        var self = this;
        self.currentInput = input;
        self.request = undefined;
        self.currentText = self.$control.val();

        var prevCount = self.currentResults.length;
        var newCount = results.length;
        if (prevCount == 0) self.$dd.hide();
        var $divsCurrentResults = self.$dd.children("." + self.resultClass);

        var i = 0;
        for (var l = results.length; i < l; i++) {
            if (i < prevCount) {
                $divsCurrentResults.eq(i).html(self.process(input, results[i])).data("data", results[i]);
            }
            else {
                var $rD = self.$resultDiv.clone();
                $rD.append(self.process(input, results[i])).data("data", results[i]);
                self.$dd.append($rD);
            }
        }

        var j;
        for (j = i; j < prevCount; j++) {
            $divsCurrentResults.eq(j).remove();
        }

        self.currentResults = results;
        if (self.options.cacheResults)
            self.cacheResults[input.toLowerCase()] = results;

        var $previousExtra = self.$dd.find(".extra");

        //add extra result
        if (self.options.extraResult != null) {
            var $rD = self.$resultDiv.clone();
            var obj = {};
            obj.input = input;
            obj.results = newCount;

            var $rD = self.$resultDiv.clone()
                            .addClass("extra")
                            .data("data", obj)
                            .click(function() {
                                if (self.options.extraResultClick != null)
                                    self.options.extraResultClick(obj);
                            });

            $rD.append(self.options.extraResult(obj));
            if ($previousExtra.length) $previousExtra.remove();
            self.$dd.append($rD);

        }

        var offset = self.$control.position();
        self.$dd.css({
            left: offset.left,
            top: offset.top + self.$control.outerHeight(),
            width: self.$control.width()
        });

        self.$control.removeClass('loading');

        if (prevCount == 0 && !$previousExtra.length)
            self.$dd.slideDown("fast");
        else
            self.$dd.show();

    },
    keydown: function(e) {
    var key = e.which ? e.which : e.keyCode;
    if (key == 13 || key == 9) {    //enter or tab
            var selectedOption = this.$dd.find("." + this.resultSelectedClass);
            if (selectedOption.length > 0) {
                if (selectedOption.hasClass("extra")) selectedOption.click();
                else this.onOk(selectedOption.data("data"));
            }
            if (key == 9) {
                this.$dd.hide();
            }
            if (key == 13) {    //no bubble for enter
                if (e.preventDefault) e.preventDefault();
                if (e.stopPropagation) e.stopPropagation();
            }
            return;
        }
        if (key == 38) { //Arrow up
            if (this.currentText != "") { //autocomplete dropdown is shown
                this.moveUp();
                return;
            }
        }
        if (key == 40) { //Arrow down
            if (this.currentText != "") { //autocomplete dropdown is shown
                this.moveDown();
                return;
            }
        }
    },
    moveUp: function() {
        var current = this.$dd.children("." + this.resultSelectedClass).first();
        if (!current.length) { //Not yet in the DDL, select the last one
            this.selectIndex(this.$dd.children().last());
            return;
        }
        this.selectIndex(current.prev());
    },
    moveDown: function() {
        var current = this.$dd.children("." + this.resultSelectedClass).first();
        if (!current.length) { //Not yet in the DDL, select the first one
            this.selectIndex(this.$dd.children());
            return;
        }
        this.selectIndex(current.next());
    },
    click: function(e) {
        var target = e.srcElement || e.target;
        if (target != null) {
            if (!$(target).closest(".extra").length)
                this.onOk($(target).closest("." + this.resultSelectedClass).data("data"));
            this.$dd.hide();
        }
    },
    process: function(i, s) {
        if (this.options.process != null) return this.options.process(i, s);
        return this.highlight(i, s[this.options.textField]);
    },
    highlight: function(i, s) {
        var pre_s = s;
        s = s.replace(new RegExp("(" + i + ")", "gi"), '$1');

        if (pre_s == s) {
            //look if there are non-bolded strings
            var nd_i = replaceDiacritics(i).toLowerCase();
            var nd_s = replaceDiacritics(s).toLowerCase();

            var index = nd_s.indexOf(nd_i), l = i.length;
            if (index != -1) s = s.substring(0, index) + "" + s.substring(index, l) + "" + s.substring(index + l);
        }
        return s;
    },
    onOk: function(data) {
        this.$dd.hide();
        this.$control.val(data[this.options.textField]);

        if (this.options.onSuccess != null) {
            this.options.onSuccess(this.$control, data);
            return;
        }
        var id = data.id;
        if (this.options.entityIdFieldName != null) {
            $('#' + this.options.entityIdFieldName).val(id);
            AutocompleteOnSelected(this.controlId, data);
        }
    },
    selectIndex: function($option) {
        this.$dd.children("." + this.resultSelectedClass).removeClass(this.resultSelectedClass);
        if ($option == null || $option == undefined) {
            this.$control.val(this.currentText).focus();
            return;
        }
        $option.first().addClass(this.resultSelectedClass);
        this.$control.focus();
    }
};

function replaceDiacritics(s) {
    var diacritics = [
        /[\300-\306]/g, /[\340-\346]/g,  // A, a
        /[\310-\313]/g, /[\350-\353]/g,  // E, e
        /[\314-\317]/g, /[\354-\357]/g,  // I, i
        /[\322-\330]/g, /[\362-\370]/g,  // O, o
        /[\331-\334]/g, /[\371-\374]/g,  // U, u
        /[\321]/g, /[\361]/g, // N, n
        /[\307]/g, /[\347]/g // C, c
    ];
    var chars = ['A', 'a', 'E', 'e', 'I', 'i', 'O', 'o', 'U', 'u', 'N', 'n', 'C', 'c'];

    for (var i = 0; i < diacritics.length; i++) {
        s = s.replace(diacritics[i], chars[i]);
    }
    return (s);
}
<commit_msg>(TFS CS 5497)<commit_after>/*window['Autocompleter'] = Autocompleter;
window['Autocompleter.prototype'] = Autocompleter.prototype;
window['AutocompleteOnSelected'] = AutocompleteOnSelected;*/

$(function() { $('#form input[type=text]').keypress(function(e) { return e.which != 13 }) })

/*window['Autocompleter'] = Autocompleter;
window['Autocompleter.prototype'] = Autocompleter.prototype;
window['AutocompleteOnSelected'] = AutocompleteOnSelected;*/
Autocompleter = function(controlId, url, _options) {
    var self = this;
    self.options = $.extend({
        minChars: 1,
        limit: 5,
        delay: 200,
        process: null,
        onSuccess: null,
        entityIdFieldName: null,
        textField: "text",
        extraParams: {},

        extraResult: null,
        extraResultClick: null,

        cacheResults: true
    }, _options);

    self.timerID = 10;
    self.$dd = self.currentText = self.request = undefined;
    self.$control = $("#" + controlId);
    self.controlId = controlId;
    self.url = url;
    self.cacheResults = [];
    self.currentResults = [];
    self.currentInput = undefined;
    self.resultClass = "ddlAuto";
    self.resultSelectedClass = "ddlAutoOn";
    self.$resultDiv = $("

");
    self.create();
};

Autocompleter.prototype = {
    create: function() {
        var self = this;

        this.$control.bind({
            keyup: function(e) {
                self.clear(e.which ? e.which : e.keyCode);
            },
            keydown: function(e) {
                self.keydown(e);
            },
            click: function(e) {
                if (e.preventDefault) e.preventDefault();
                if (e.stopPropagation) e.stopPropagation();
            },
            focusin: function(e) {
                if (self.currentResults.length) {
                    self.$dd.show();
                }
            }
        });

        $("body").click(function() {
            self.$dd.hide();
        });

        this.$dd = $("
").addClass("AutoCompleteMainDiv");
        this.$dd.click(function(e) {
            self.click(e);
        });

        this.$dd.insertAfter(this.$control);
        this.$dd.delegate("." + this.resultClass, "mouseenter", function() {
            self.selectIndex($(this));
        });

    },
    clear: function(e) {
        clearTimeout(this.timerID);
        var self = this;
        this.timerID = setTimeout(function() { self.keyup(e) }, (self.options.cacheResults && self.cacheResults[self.$control.val().toLowerCase()] != null) ? 0 : self.options.delay);
    },
    keyup: function(key) {
        if (key == 37 || key == 39 || key == 38 || key == 40 || key == 13) return;
        var input = this.$control.val();
        if (this.currentText == input) return;

        if (input != null && input.length < this.options.minChars) {
            this.$dd.html("").hide(); this.currentResults = [];
            return;
        }
        //if (this.currentResults.length < this.options.limit && input.indexOf(this.currentInput) != -1)
        //process cached results

        var data = $.extend({
            q: input, l: this.options.limit
        }, this.options.extraParams);

        var self = this;

        if (self.currentResults == [] && self.currentInput != null && input.indexOf(self.currentInput) == 0) {
            self.showResults([], input);
            return;
        }

        if (self.options.cacheResults && self.cacheResults[input.toLowerCase()] != null) {
            self.showResults(self.cacheResults[input.toLowerCase()], input);
            return;
        }

        if (self.request) self.request.abort();
        self.$control.addClass('loading');
        self.request = $.getJSON(
            self.url, data,
            function(results) {
                if (results) {
                    self.showResults(results, input);
                }
            });
    },

    showResults: function(results, input) {
        var self = this;
        self.currentInput = input;
        self.request = undefined;
        self.currentText = self.$control.val();

        var prevCount = self.currentResults.length;
        var newCount = results.length;
        if (prevCount == 0) self.$dd.hide();
        var $divsCurrentResults = self.$dd.children("." + self.resultClass);

        var i = 0;
        for (var l = results.length; i < l; i++) {
            if (i < prevCount) {
                $divsCurrentResults.eq(i).html(self.process(input, results[i])).data("data", results[i]);
            }
            else {
                var $rD = self.$resultDiv.clone();
                $rD.append(self.process(input, results[i])).data("data", results[i]);
                self.$dd.append($rD);
            }
        }

        var j;
        for (j = i; j < prevCount; j++) {
            $divsCurrentResults.eq(j).remove();
        }

        self.currentResults = results;
        if (self.options.cacheResults)
            self.cacheResults[input.toLowerCase()] = results;

        var $previousExtra = self.$dd.find(".extra");

        //add extra result
        if (self.options.extraResult != null) {
            var $rD = self.$resultDiv.clone();
            var obj = {};
            obj.input = input;
            obj.results = newCount;

            var $rD = self.$resultDiv.clone()
                            .addClass("extra")
                            .data("data", obj)
                            .click(function() {
                                if (self.options.extraResultClick != null)
                                    self.options.extraResultClick(obj);
                            });

            $rD.append(self.options.extraResult(obj));
            if ($previousExtra.length) $previousExtra.remove();
            self.$dd.append($rD);

        }

        var offset = self.$control.position();
        self.$dd.css({
            left: offset.left,
            top: offset.top + self.$control.outerHeight(),
            width: self.$control.width()
        });

        self.$control.removeClass('loading');

        if (prevCount == 0 && !$previousExtra.length)
            self.$dd.slideDown("fast");
        else
            self.$dd.show();

    },
    keydown: function(e) {
        var key = e.which ? e.which : e.keyCode;
        if (key == 13 || key == 9) {    //enter or tab
            var selectedOption = this.$dd.find("." + this.resultSelectedClass);
            if (selectedOption.length > 0) {
                if (selectedOption.hasClass("extra")) selectedOption.click();
                else this.onOk(selectedOption.data("data"));
            }
            if (key == 9) {
                this.$dd.hide();
            }
            if (key == 13) {    //no bubble for enter
                if (e.preventDefault) e.preventDefault();
                if (e.stopPropagation) e.stopPropagation();
            }
            return;
        }
        if (key == 38) { //Arrow up
            if (this.currentText != "") { //autocomplete dropdown is shown
                this.moveUp();
                return;
            }
        }
        if (key == 40) { //Arrow down
            if (this.currentText != "") { //autocomplete dropdown is shown
                this.moveDown();
                return;
            }
        }
    },
    moveUp: function() {
        var current = this.$dd.children("." + this.resultSelectedClass).first();
        if (!current.length) { //Not yet in the DDL, select the last one
            this.selectIndex(this.$dd.children().last());
            return;
        }
        this.selectIndex(current.prev());
    },
    moveDown: function() {
        var current = this.$dd.children("." + this.resultSelectedClass).first();
        if (!current.length) { //Not yet in the DDL, select the first one
            this.selectIndex(this.$dd.children());
            return;
        }
        this.selectIndex(current.next());
    },
    click: function(e) {
        var target = e.srcElement || e.target;
        if (target != null) {
            if (!$(target).closest(".extra").length)
                this.onOk($(target).closest("." + this.resultSelectedClass).data("data"));
            this.$dd.hide();
        }
    },
    process: function(i, s) {
        if (this.options.process != null) return this.options.process(i, s);
        return this.highlight(i, s[this.options.textField]);
    },
    highlight: function(i, s) {
        var pre_s = s;
        s = s.replace(new RegExp("(" + i + ")", "gi"), '$1');

        if (pre_s == s) {
            //look if there are non-bolded strings
            var nd_i = replaceDiacritics(i).toLowerCase();
            var nd_s = replaceDiacritics(s).toLowerCase();
            console.log("nd_i " + nd_i);
            console.log("nd_s " + nd_s);

            var index = nd_s.indexOf(nd_i), l = i.length;
            if (index != -1) s = s.substr(0, index) + "" + s.substr(index, i.length) + "" + s.substr(index + i.length);
        }
        return s;
    },
    onOk: function(data) {
        this.$dd.hide();
        this.$control.val(data[this.options.textField]);

        if (this.options.onSuccess != null) {
            this.options.onSuccess(this.$control, data);
            return;
        }
        var id = data.id;
        if (this.options.entityIdFieldName != null) {
            $('#' + this.options.entityIdFieldName).val(id);
            AutocompleteOnSelected(this.controlId, data);
        }
    },
    selectIndex: function($option) {
        this.$dd.children("." + this.resultSelectedClass).removeClass(this.resultSelectedClass);
        if ($option == null || $option == undefined) {
            this.$control.val(this.currentText).focus();
            return;
        }
        $option.first().addClass(this.resultSelectedClass);
        this.$control.focus();
    }
};

function replaceDiacritics(s) {
    var diacritics = [
        /[\300-\306]/g, /[\340-\346]/g,  // A, a
        /[\310-\313]/g, /[\350-\353]/g,  // E, e
        /[\314-\317]/g, /[\354-\357]/g,  // I, i
        /[\322-\330]/g, /[\362-\370]/g,  // O, o
        /[\331-\334]/g, /[\371-\374]/g,  // U, u
        /[\321]/g, /[\361]/g, // N, n
        /[\307]/g, /[\347]/g // C, c
    ];
    var chars = ['A', 'a', 'E', 'e', 'I', 'i', 'O', 'o', 'U', 'u', 'N', 'n', 'C', 'c'];

    for (var i = 0; i < diacritics.length; i++) {
        s = s.replace(diacritics[i], chars[i]);
    }
    return (s);
}
<|endoftext|>


<commit_before>const sleep = require('system-sleep');
const Logging = require('disnode-logger');

class OwnerPlugin {
    constructor() {
        this.ownerName = "Insert Name"; //Insert Name so that users that do [p]owner will know who the owner of the bot is
        this.owner = "Insert ID"; //Insert ID so that only you can run these commands
    }

    default (command) {
        var self = this;
        self.disnode.bot.SendEmbed(command.msg.channel, {
            color: 3447003,
            author: {},
            fields: [{
                name: "Owner",
                inline: false,
                value: this.ownerName + "\n" + this.owner,
            }],
            footer: {}
        });
    }
    commandRestart(command) {
        var self = this;
        if (command.msg.userID == this.owner) {
            self.disnode.bot.SendMessage(command.msg.channel, "I am restarting");
            self.disnode.Restart();
        } else {
            self.disnode.bot.SendEmbed(command.msg.channel, {
                color: 15158332,
                author: {},
                fields: [{
                    name: "Stop",
                    inline: false,
                    value: "**You're not my Owner**",
                }],
                footer: {}
            });
            Logging.Warning(command.msg.user, command.msg.userID, "Tried using " + self.disnode.botConfig.prefix + "" + command.command.cmd)
        };
    }
    commandShutdown(command) {
        var self = this;
        if (command.msg.userID == this.owner) {
            self.disnode.bot.SendMessage(command.msg.channel, "I am shutting down");
            self.disnode.bot.Disconnect();
            sleep(1000);
            process.exit();
        } else {
            self.disnode.bot.SendEmbed(command.msg.channel, {
                color: 15158332,
                author: {},
                fields: [{
                    name: "Stop",
                    inline: false,
                    value: "**You're not my Owner**",
                }],
                footer: {}
            });
            Logging.Warning(command.msg.user, command.msg.userID, "Tried using " + self.disnode.botConfig.prefix + "" + command.command.cmd)
        };
    }
    commandStatus(command) {
        var self = this;
        if (command.msg.userID == this.owner) {
            self.disnode.bot.SetStatus(command.params[0]);
            self.disnode.bot.SendMessage(command.msg.channel, "Status Set To - **Playing " + command.params[0] + "**");
        } else {
            self.disnode.bot.SendEmbed(command.msg.channel, {
                color: 15158332,
                author: {},
                fields: [{
                    name: "Stop",
                    inline: false,
                    value: "**You're not my Owner**",
                }],
                footer: {}
            });
            Logging.Warning(command.msg.user, command.msg.userID, "Tried using " + self.disnode.botConfig.prefix + "" + command.command.cmd)
        };
    }
    commandUsername(command) {
        var self = this;
        if (command.msg.userID == this.owner) {
            self.disnode.bot.SetUsername(command.params[0]);
            self.disnode.bot.SendMessage(command.msg.channel, "Username set to - **" + command.params[0] + "**");
        } else {
            self.disnode.bot.SendEmbed(command.msg.channel, {
                color: 15158332,
                author: {},
                fields: [{
                    name: "Stop",
                    inline: false,
                    value: "**You're not my Owner**",
                }],
                footer: {}
            });
            Logging.Warning(command.msg.user, command.msg.userID, "Tried using " + self.disnode.botConfig.prefix + "" + command.command.cmd)
        };
    }
    commandServers(command) {
        var self = this;
        if (command.msg.userID == this.owner) {
            var serverids = Object.keys(self.disnode.bot.client.servers);
            var servers = '';
            for (var i = 0; i < serverids.length; i++) {
                var amount = i + 1;
                if (servers == '') {
                    servers += amount + ". " + self.disnode.bot.client.servers[serverids[i]].name + "\n";
                } else if (i == serverids.length) {
                    serers += amount + ". " + self.disnode.bot.client.servers[serverids[i]].name;
                } else {
                    servers += amount + ". " + self.disnode.bot.client.servers[serverids[i]].name + "\n";
                }
            }
            var results = "```\n" + servers + "```\n**Servers:** " + serverids.length + "\n**Users:** " + Object.keys(self.disnode.bot.client.users).length;
            self.disnode.bot.SendCompactEmbed(command.msg.channel, "Servers List", results);
        } else {
            self.disnode.bot.SendEmbed(command.msg.channel, {
                color: 15158332,
                author: {},
                fields: [{
                    name: "Stop",
                    inline: false,
                    value: "**You're not my Owner**",
                }],
                footer: {}
            });
            Logging.Warning(command.msg.user, command.msg.userID, "Tried using " + self.disnode.botConfig.prefix + "" + command.command.cmd)
        };
    }

}
module.exports = OwnerPlugin
// Made by Hazed SPaCE✘#2574 & God of _.#6075
<commit_msg>Changed status params <commit_after>const sleep = require('system-sleep');
const Logging = require('disnode-logger');

class OwnerPlugin {
    constructor() {
        this.ownerName = "Insert Name"; //Insert Name so that users that do [p]owner will know who the owner of the bot is
        this.owner = "Insert ID"; //Insert ID so that only you can run these commands
    }

    default (command) {
        var self = this;
        self.disnode.bot.SendEmbed(command.msg.channel, {
            color: 3447003,
            author: {},
            fields: [{
                name: "Owner",
                inline: false,
                value: this.ownerName + "\n" + this.owner,
            }],
            footer: {}
        });
    }
    commandRestart(command) {
        var self = this;
        if (command.msg.userID == this.owner) {
            self.disnode.bot.SendMessage(command.msg.channel, "I am restarting");
            self.disnode.Restart();
        } else {
            self.disnode.bot.SendEmbed(command.msg.channel, {
                color: 15158332,
                author: {},
                fields: [{
                    name: "Stop",
                    inline: false,
                    value: "**You're not my Owner**",
                }],
                footer: {}
            });
            Logging.Warning(command.msg.user, command.msg.userID, "Tried using " + self.disnode.botConfig.prefix + "" + command.command.cmd)
        };
    }
    commandShutdown(command) {
        var self = this;
        if (command.msg.userID == this.owner) {
            self.disnode.bot.SendMessage(command.msg.channel, "I am shutting down");
            self.disnode.bot.Disconnect();
            sleep(1000);
            process.exit();
        } else {
            self.disnode.bot.SendEmbed(command.msg.channel, {
                color: 15158332,
                author: {},
                fields: [{
                    name: "Stop",
                    inline: false,
                    value: "**You're not my Owner**",
                }],
                footer: {}
            });
            Logging.Warning(command.msg.user, command.msg.userID, "Tried using " + self.disnode.botConfig.prefix + "" + command.command.cmd)
        };
    }
    commandStatus(command) {
        var self = this;
        var status = command.params.join(" ");
        if (command.msg.userID == this.owner) {
            self.disnode.bot.SetStatus(status);
            self.disnode.bot.SendMessage(command.msg.channel, "Status Set To - **Playing " + status + "**");
        } else {
            self.disnode.bot.SendEmbed(command.msg.channel, {
                color: 15158332,
                author: {},
                fields: [{
                    name: "Stop",
                    inline: false,
                    value: "**You're not my Owner**",
                }],
                footer: {}
            });
            Logging.Warning(command.msg.user, command.msg.userID, "Tried using " + self.disnode.botConfig.prefix + "" + command.command.cmd)
        };
    }
    commandUsername(command) {
        var self = this;
        if (command.msg.userID == this.owner) {
            self.disnode.bot.SetUsername(command.params[0]);
            self.disnode.bot.SendMessage(command.msg.channel, "Username set to - **" + command.params[0] + "**");
        } else {
            self.disnode.bot.SendEmbed(command.msg.channel, {
                color: 15158332,
                author: {},
                fields: [{
                    name: "Stop",
                    inline: false,
                    value: "**You're not my Owner**",
                }],
                footer: {}
            });
            Logging.Warning(command.msg.user, command.msg.userID, "Tried using " + self.disnode.botConfig.prefix + "" + command.command.cmd)
        };
    }
    commandServers(command) {
        var self = this;
        if (command.msg.userID == this.owner) {
            var serverids = Object.keys(self.disnode.bot.client.servers);
            var servers = '';
            for (var i = 0; i < serverids.length; i++) {
                var amount = i + 1;
                if (servers == '') {
                    servers += amount + ". " + self.disnode.bot.client.servers[serverids[i]].name + "\n";
                } else if (i == serverids.length) {
                    serers += amount + ". " + self.disnode.bot.client.servers[serverids[i]].name;
                } else {
                    servers += amount + ". " + self.disnode.bot.client.servers[serverids[i]].name + "\n";
                }
            }
            var results = "```\n" + servers + "```\n**Servers:** " + serverids.length + "\n**Users:** " + Object.keys(self.disnode.bot.client.users).length;
            self.disnode.bot.SendCompactEmbed(command.msg.channel, "Servers List", results);
        } else {
            self.disnode.bot.SendEmbed(command.msg.channel, {
                color: 15158332,
                author: {},
                fields: [{
                    name: "Stop",
                    inline: false,
                    value: "**You're not my Owner**",
                }],
                footer: {}
            });
            Logging.Warning(command.msg.user, command.msg.userID, "Tried using " + self.disnode.botConfig.prefix + "" + command.command.cmd)
        };
    }

}
module.exports = OwnerPlugin
// Made by Hazed SPaCE✘#2574 & God of _.#6075
<|endoftext|>


<commit_before>
// Enable ajax based navigation

// flow

// click internal link
// updates hash
// hash envokes navigate
// if 1st level is changed tells #content navigation has been invoked
// if 2nd level is changed tells .scene navigation has been invoked

u.navigation = function(page, options) {

//	u.bug("set up navigation")

	// this._nav_navigate_callback = null;
	//
	// // additional info passed to function as JSON object
	// if(typeof(options) == "object") {
	// 	var argument;
	// 	for(argument in options) {
	//
	// 		switch(argument) {
	// 			case "navigate_callback"	: this._nav_navigate_callback		= options[argument]; break;
	// 		}
	//
	// 	}
	// }

	// default starting path
	page._nav_path = page._nav_path ? page._nav_path : "/";
	page._nav_history = page._nav_history ? page._nav_history : [];

	// internal hash change distribution - content or scene level
	page._navigate = function() {

		// no url or invalid path
		// update hash, triggering new _navigate request
		if(!location.hash || !location.hash.match(/^#\//)) {
			location.hash = "#/"
			return;
		}

		var url = u.h.getCleanHash(location.hash);

		page._nav_history.unshift(url);
//		u.bug("navigate:" + url + "("+ (this._nav_path) + ")")

		// stats
		// TODO: this.hash_node add to stats
		u.stats.pageView(url);

		// direct navigation callback to correct level
		// first request or new base-level
		if(!this._nav_path || this._nav_path != u.h.getCleanHash(location.hash, 1)) {

			// forward navigation event to #content
			if(this.cN && typeof(this.cN.navigate) == "function") {
				this.cN.navigate(url);
			}

		}
		else {

			// forward navigation event to .scene if it has navigate function
			if(this.cN.scene && this.cN.scene.parentNode && typeof(this.cN.scene.navigate) == "function") {
				this.cN.scene.navigate(url);
			}
			// else forward to content
			else if(this.cN && typeof(this.cN.navigate) == "function") {
				this.cN.navigate(url);
			}

		}

		// remember base-level
		this._nav_path = u.h.getCleanHash(location.hash, 1);
	}

	// update hash and set hash back node if any
	page.navigate = function(url, node) {
//		u.bug("url:" + url + ", " + u.nodeId(node))

		this.hash_node = node ? node : false;
		location.hash = u.h.getCleanUrl(url);

	}

	// sharing via social media (linkedin) might add hashbang
	// remove invalid hash value
	if(location.hash.length && location.hash.match(/^#!/)) {
		location.hash = location.hash.replace(/!/, "");
	}

	// set default hash if no hash value is present
	// no further navigation - initialize content
	if(location.hash.length < 2) {
//		u.bug("set hash + init content")

		// update hash
		page.navigate(location.href, page);
		// update internal value, so navigation doesn't mess up
		page._nav_path = u.h.getCleanUrl(location.href);
		// init content
		u.init(page.cN);
	}
	// if different hash and url, hash value starts with /
	// load content based on hash
	else if(u.h.getCleanHash(location.hash) != u.h.getCleanUrl(location.href) && location.hash.match(/^#\//)) {
//		u.bug("init navigate:" + u.h.getCleanHash(location.hash) + "!=" + u.h.getCleanUrl(location.href) + "; ")

		// update internal value, so navigation doesn't mess up
		page._nav_path = u.h.getCleanUrl(location.href);
		// manually invoke navigation to load correct page
		page._navigate();
	}
	// hash and url is aligned, or unusable value
	// init existing content
	else {
//		u.bug("init content")

		// just go for it
		u.init(page.cN);
	}

	page._initHash = function() {
//		u.bug("enable HASH navigation")

		u.h.catchEvent(page._navigate, page);
	}

	// set hash event handler with small delay to avoid redirecting when actually just trying to update HASH
	u.t.setTimer(page, page._initHash, 100);

	page.historyBack = function() {
		if(this._nav_history.length > 1) {
			this._nav_history.shift();
			return this._nav_history.shift();
		}
		else {
			return "/";
		}
	}
}

<commit_msg>debugging<commit_after>
// Enable ajax based navigation

// flow

// click internal link
// updates hash
// hash envokes navigate
// if 1st level is changed tells #content navigation has been invoked
// if 2nd level is changed tells .scene navigation has been invoked

u.navigation = function(page, options) {

//	u.bug("set up navigation")

	// this._nav_navigate_callback = null;
	//
	// // additional info passed to function as JSON object
	// if(typeof(options) == "object") {
	// 	var argument;
	// 	for(argument in options) {
	//
	// 		switch(argument) {
	// 			case "navigate_callback"	: this._nav_navigate_callback		= options[argument]; break;
	// 		}
	//
	// 	}
	// }

	// default starting path
	page._nav_path = page._nav_path ? page._nav_path : "/";
	page._nav_history = page._nav_history ? page._nav_history : [];

	// internal hash change distribution - content or scene level
	page._navigate = function() {

		// no url or invalid path
		// update hash, triggering new _navigate request
		if(!location.hash || !location.hash.match(/^#\//)) {
			location.hash = "#/"
			return;
		}

		var url = u.h.getCleanHash(location.hash);

		page._nav_history.unshift(url);
//		u.bug("page._navigate:" + url + "("+ (this._nav_path) + ")")

		// stats
		// TODO: this.hash_node add to stats
		u.stats.pageView(url);

		// direct navigation callback to correct level
		// first request or new base-level
		if(!this._nav_path || this._nav_path != u.h.getCleanHash(location.hash, 1)) {

			// forward navigation event to #content
			if(this.cN && typeof(this.cN.navigate) == "function") {
				this.cN.navigate(url);
			}

		}
		else {

			// forward navigation event to .scene if it has navigate function
			if(this.cN.scene && this.cN.scene.parentNode && typeof(this.cN.scene.navigate) == "function") {
				this.cN.scene.navigate(url);
			}
			// else forward to content
			else if(this.cN && typeof(this.cN.navigate) == "function") {
				this.cN.navigate(url);
			}

		}

		// remember base-level
		this._nav_path = u.h.getCleanHash(location.hash, 1);
	}

	// update hash and set hash back node if any
	page.navigate = function(url, node) {
//		u.bug("url:" + url + ", " + u.nodeId(node))

		this.hash_node = node ? node : false;
		location.hash = u.h.getCleanUrl(url);

	}

	// sharing via social media (linkedin) might add hashbang
	// remove invalid hash value
	if(location.hash.length && location.hash.match(/^#!/)) {
		location.hash = location.hash.replace(/!/, "");
	}

	// set default hash if no hash value is present
	// no further navigation - initialize content
	if(location.hash.length < 2) {
//		u.bug("set hash + init content")

		// update hash
		page.navigate(location.href, page);
		// update internal value, so navigation doesn't mess up
		page._nav_path = u.h.getCleanUrl(location.href);
		// init content
		u.init(page.cN);
	}
	// if different hash and url, hash value starts with /
	// load content based on hash
	else if(u.h.getCleanHash(location.hash) != u.h.getCleanUrl(location.href) && location.hash.match(/^#\//)) {
//		u.bug("init navigate:" + u.h.getCleanHash(location.hash) + "!=" + u.h.getCleanUrl(location.href) + "; ")

		// update internal value, so navigation doesn't mess up
		page._nav_path = u.h.getCleanUrl(location.href);
		// manually invoke navigation to load correct page
		page._navigate();
	}
	// hash and url is aligned, or unusable value
	// init existing content
	else {
//		u.bug("init content")

		// just go for it
		u.init(page.cN);
	}

	page._initHash = function() {
//		u.bug("enable HASH navigation")

		u.h.catchEvent(page._navigate, page);
	}

	// set hash event handler with small delay to avoid redirecting when actually just trying to update HASH
	u.t.setTimer(page, page._initHash, 100);
//	page._initHash();

	page.historyBack = function() {
		if(this._nav_history.length > 1) {
			this._nav_history.shift();
			return this._nav_history.shift();
		}
		else {
			return "/";
		}
	}
}

<|endoftext|>