<commit_before>// Texpand
// Unobtrusively resize textarea's height as content is added.
//
// Copyright (c) 2008, <NAME> - gianni[at]runlevel6[dot]org
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the
// "Software"), to deal in the Software without restriction, including
// without limitation the rights to use, copy, modify, merge, publish,
// distribute, sublicense, and/or sell copies of the Software, and to
// permit persons to whom the Software is furnished to do so, subject to
// the following conditions:
// 
// The above copyright notice and this permission notice shall be
// included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

// Texpand Class
//------------------------------------------------------------------------------
var Texpand = Class.create();
Texpand.version = 0.8;
Texpand.prototype = {
  initialize: function(el, options) {
    // INIT
    this.options = {
      increment: 15,
      autoShrink: false,
      expandOnLoad: false,
	  expandOnFocus: true,
	  shrinkOnBlur: true,
      onExpand: Prototype.emptyFunction
    };
    Object.extend(this.options, options || {});
    this.element = $(el);
    
    // Requirements
    if (this.element.tagName.toLowerCase() != 'textarea') {
      throw (new Error('Texpand: can only be initialized with a <textarea> but got <' + this.element.tagName.toLowerCase() + '>'));
    }
    if (typeof Prototype == 'undefined' || (parseFloat(Prototype.Version.split(".")[0] + "." + Prototype.Version.split(".")[1]) < 1.6)) {
      throw (new Error('Texpand: requires Prototype 1.6.0+'));
    }
    if (typeof Effect == 'undefined') {
      throw (new Error('Textpand: requires Script.aculo.us, specifically Effects'));
    }
    
    // Setup Textarea & mimic
    this.element.insert({after: '<div id="texpand-mimic-' + this.element.identify() + '"></div>'}).setStyle({
      resize: 'none',
      overflow: 'hidden'
    });
    this.mimic = this.element.next();
    this.mimic.update(this.element.value);
    
    // Fix default font size if in em's, based on a 10px em unit (This is an IE thing mainly)
    var fontSize = this.element.getStyle('fontSize');
    if (fontSize.search(/em/) >= 0) {
      var pixelSize = parseFloat(fontSize.replace(/em/, '')) * 10;
      this.element.setStyle({
        fontSize: pixelSize + 'px'
      });
    }
    
    // Duplicate style
    var style = {};
    var properties = $w('borderBottomColor borderBottomStyle borderBottomWidth borderTopColor borderTopStyle borderTopWidth borderRightColor borderRightStyle borderRightWidth borderLeftColor borderLeftStyle borderLeftWidth fontSize fontFamily fontWeight letterSpacing lineHeight marginTop marginRight marginBottom marginLeft paddingTop paddingRight paddingBottom paddingLeft textAlign textIndent width wordSpacing');
    for (var i = 0, length = properties.length; i < length; i++) {
      style[properties[i]] = this.element.getStyle(properties[i]);
    }
    this.mimic.setStyle(Object.extend(style, {
      display: 'block',
      whiteSpace: 'pre-wrap',
      position: 'absolute',
      left: '-9999px',
      top: '-9999px'
    }));
    
    // Reset font-family (IE7 & IE8 issue)
    this.element.setStyle({fontFamily: this.mimic.getStyle('fontFamily')});
    
    // Fix width for browser inconsistencies (Again an IE thing mainly) [Thanks tfluehr]
    var estimatedWidth = this.element.getWidth();
    if (estimatedWidth != this.mimic.getWidth()) {
      var tmpInt;
      estimatedWidth -= isNaN(tmpInt = parseInt(this.element.getStyle('marginLeft'), 10)) ? 0 : tmpInt;
      estimatedWidth -= isNaN(tmpInt = parseInt(this.element.getStyle('marginRight'), 10)) ? 0 : tmpInt;
      estimatedWidth -= isNaN(tmpInt = parseInt(this.element.getStyle('borderLeftWidth'), 10)) ? 0 : tmpInt;
      estimatedWidth -= isNaN(tmpInt = parseInt(this.element.getStyle('borderRightWidth'), 10)) ? 0 : tmpInt;
      estimatedWidth -= isNaN(tmpInt = parseInt(this.element.getStyle('paddingLeft'), 10)) ? 0 : tmpInt;
      estimatedWidth -= isNaN(tmpInt = parseInt(this.element.getStyle('paddingRight'), 10)) ? 0 : tmpInt;
      estimatedWidth += 'px';
      this.mimic.setStyle({width: estimatedWidth});
    }
    
    // Listen
    this.element.observe("keyup", this._autoExpand.bind(this));
	if (this.options.expandOnFocus) this.element.observe("focus", this._autoExpand.bind(this));
	if (this.options.shrinkOnBlur) this.element.observe("blur", this._shrinkToInitial.bind(this));
    this.initialHeight = this.element.getHeight();
    if (this.options.expandOnLoad) this._autoExpand();
    return this.element;
  },
  _effect: function(h) {
      // Shrink
      this.element.morph('height: ' + h + 'px;', {
        duration: 0.05,
        queue: {
          position: 'end',
          scope: 'texpand' + this.element.identify(),
          limit: 2
        }
      });
  },
  // shrink to Initial height
  _shrinkToInitial: function(ev) {
      // Shrink
	  this._effect(this.initialHeight);
  },
  // Auto expand height if required
  _autoExpand: function(ev) {
    if (ev) {
      // Keeps the keyboard from slowing down ie by only running the 
      // morph if the keyboard hasnt been touched for 0.1 seconds
      clearTimeout(this.keypressDelay);
      this.keypressDelay = this.doExpand.bind(this).delay(0.1, ev);
    }
    else this.doExpand();
  },
  
  doExpand: function(ev) {
    // Code to actually do the heavy lifting
    this.mimic.update(this.element.value.replace(/\n/gm, '<br />') + '<br />');
    var mimicCurrentHeight = this.mimic.getHeight();
    var elementCurrentHeight = this.element.getHeight();
    var differenceHeight = elementCurrentHeight - mimicCurrentHeight;
    var targetHeight;
    // If the elements value == '' then we want the target height to be the inital height 
    // set when the texpand was created, usually a one line text box.
    if (this.element.value === '') targetHeight = this.initialHeight;
    else targetHeight = elementCurrentHeight + (this.options.increment - differenceHeight);
    
    if ((this.options.autoShrink && (differenceHeight > this.options.increment) || this.element.value === '') || differenceHeight < this.options.increment) {
      // Clear queue
      var queue = Effect.Queues.get('texpand' + this.element.identify());
      queue.each(function(effect) {
        effect.cancel();
      });
      
      // Expand
	  this._effect(targetHeight);
      this.options.onExpand.call(ev);
    }
  },
  
  // Add text and resize
  appendText: function(text) {
    this.element.value += text;
    this._autoExpand();
  },
  
  // Replace text and resize
  setValue: function(text) {
    this.element.value = text;
    this._autoExpand();
  }
};<commit_msg>initial changes for ie/opera fixes.<commit_after>﻿// Texpand
// Unobtrusively resize textarea's height as content is added.
//
// Copyright (c) 2008, <NAME> - gianni[at]runlevel6[dot]org
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the
// "Software"), to deal in the Software without restriction, including
// without limitation the rights to use, copy, modify, merge, publish,
// distribute, sublicense, and/or sell copies of the Software, and to
// permit persons to whom the Software is furnished to do so, subject to
// the following conditions:
// 
// The above copyright notice and this permission notice shall be
// included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

// Texpand Class
//------------------------------------------------------------------------------
var Texpand = Class.create();
Texpand.version = 0.8;
Texpand.prototype = {
  initialize: function(el, options) {
    // INIT
    this.options = {
      increment: 15,
      autoShrink: false,
      expandOnLoad: false,
      expandOnFocus: true,
      shrinkOnBlur: true,
      onExpand: Prototype.emptyFunction
    };
    Object.extend(this.options, options || {});
    this.element = $(el);
    
    // Requirements
    if (this.element.tagName.toLowerCase() != 'textarea') {
      throw (new Error('Texpand: can only be initialized with a <textarea> but got <' + this.element.tagName.toLowerCase() + '>'));
    }
    if (typeof Prototype == 'undefined' || (parseFloat(Prototype.Version.split(".")[0] + "." + Prototype.Version.split(".")[1]) < 1.6)) {
      throw (new Error('Texpand: requires Prototype 1.6.0+'));
    }
    if (typeof Effect == 'undefined') {
      throw (new Error('Textpand: requires Script.aculo.us, specifically Effects'));
    }
    this.c = typeof(opera) != 'undefined' ? opera.postError : typeof(console) != 'undefined' ? console.log : Prototype.emptyFunction;
    // Setup Textarea & mimic
    this.element.insert({after: '<div id="texpand-mimic-' + this.element.identify() + 'Parent"><div id="texpand-mimic-' + this.element.identify() + '">' + this.element.value + '</div></div>'}).setStyle({
      resize: 'none',
      overflow: 'hidden'
    });
    this.mimic = this.element.next().down();
    
    this._setWhitespaceAndUpdate();
        
    this._setMimicStyles();
    // Listen
    this.element.observe("keyup", this._autoExpand.bind(this));
    if (this.options.expandOnFocus) this.element.observe("focus", this._autoExpand.bind(this));
    if (this.options.shrinkOnBlur) this.element.observe("blur", this._shrinkToInitial.bind(this));
    this.initialHeight = this.element.getHeight();
    if (this.options.expandOnLoad) this._autoExpand();
    return this.element;
  },
  _setMimicStyles: function(){
    if (!this.elementStyles && !this.mimicStyles) {
      this.elementStyles = {};
      this.mimicStyles = {};
      // Fix default font size if in em's, based on a 10px em unit (This is an IE thing mainly)
      var fontSize = this.element.getStyle('fontSize');
      this.elementStyles.fontSize = fontSize;
      if (fontSize.search(/em/) >= 0) {
        var pixelSize = parseFloat(fontSize.replace(/em/, '')) * 10;
        this.elementStyles.fontSize = pixelSize + 'px';
      }
      
      // Duplicate style
      var properties = $w('borderBottomColor borderBottomStyle borderBottomWidth borderTopColor borderTopStyle borderTopWidth borderRightColor borderRightStyle borderRightWidth borderLeftColor borderLeftStyle borderLeftWidth fontSize fontFamily fontWeight letterSpacing lineHeight marginTop marginRight marginBottom marginLeft paddingTop paddingRight paddingBottom paddingLeft textAlign textIndent width wordSpacing');
      for (var i = 0, length = properties.length; i < length; i++) {
        this.mimicStyles[properties[i]] = this.element.getStyle(properties[i]);
      }
      this.mimicStyles.display = 'block';
      this.mimicStyles.border = '1px solid red';
      
      // Reset font-family (IE7 & IE8 issue)
      this.elementStyles.fontFamily = this.mimic.getStyle('fontFamily');
      this.mimicStyles.fontSize = this.elementStyles.fontSize;
      
      // Fix width for browser inconsistencies (Again an IE thing mainly) [Thanks tfluehr]
      var estimatedWidth = this.element.getWidth();
      if (estimatedWidth != this.mimic.getWidth()){
        var tmpInt;
        estimatedWidth -= isNaN(tmpInt = parseInt(this.element.getStyle('marginLeft'), 10)) ? 0 : tmpInt;
        estimatedWidth -= isNaN(tmpInt = parseInt(this.element.getStyle('marginRight'), 10)) ? 0 : tmpInt;
        estimatedWidth -= isNaN(tmpInt = parseInt(this.element.getStyle('borderLeftWidth'), 10)) ? 0 : tmpInt;
        estimatedWidth -= isNaN(tmpInt = parseInt(this.element.getStyle('borderRightWidth'), 10)) ? 0 : tmpInt;
        estimatedWidth -= isNaN(tmpInt = parseInt(this.element.getStyle('paddingLeft'), 10)) ? 0 : tmpInt;
        estimatedWidth -= isNaN(tmpInt = parseInt(this.element.getStyle('paddingRight'), 10)) ? 0 : tmpInt;
        estimatedWidth += 'px';
        this.mimicStyles.width = estimatedWidth;
      }
    }
    this.mimic.setStyle(this.mimicStyles);
    this.element.setStyle(this.elementStyles);
  },
  // ugly, ugly, ugly hack because of IE not supporting white-space: pre-wrap
  // plus an even uglier hack because IE has another bug where if you dynamically update a <pre> tag
  // or any element that has white-space: pre then the pre formatting is lost.
  _setWhitespaceAndUpdate: function(){
    if (!this.whiteSpaceChecked) {
      // list of possible pre values
      var vals = $w('pre-wrap -moz-pre-wrap -pre-wrap -o-pre-wrap pre');
      var cVal;
      vals.each(function(item){
        try{
          this.mimic.setStyle({
            'whiteSpace': item
          });
          if (this.mimic.getStyle('whiteSpace') != item) throw 'error';
        } 
        catch (e){
          // browser error or our own telling us that the value wasn't accepted
          return;
        }
        cVal = item;
        // value was accepted to we're done
        throw $break;
      }.bind(this));
      // if IE "pre" value then activate hack
      if (cVal == 'pre') this.wsHack = true;
      // cache that we did the check so it is only done once
      this.whiteSpaceChecked = true;
    }
    // values the same, skip updating
    if (this.mimic.innerHTML == this.element.value) return;
    
    // need to do the following because of IE losing pre formatting.
    // I couldn't come up with an eash way to detect it without browser sniffing
    var mParent = this.mimic.up();
    mParent.update('<pre id="texpand-mimic-' + this.element.identify() + '">'+ this.element.value + '</pre>');
    // reset this.mimic to proper new element
    this.mimic = mParent.down();
    // reset styles on mimic
    this._setMimicStyles();
    
    if (this.wsHack) {
      // IE hack for white-space: pre to make word wrap function
      this.mimic.setStyle(
      {
        wordWrap: 'break-word'
      });
    }
  },
  _effect: function(h) {
    // Clear queue
    var queue = Effect.Queues.get('texpand' + this.element.identify());
    queue.each(function(effect) {
      effect.cancel();
    });
	  // Shrink or Expand according to value of h
	  this.element.morph('height: ' + h + 'px;', {
	  	duration: 0.05,
	  	queue: {
	  		position: 'end',
	  		scope: 'texpand' + this.element.identify(),
	  		limit: 2
	  	}
	  });
  },
  // shrink to Initial height
  _shrinkToInitial: function(ev) {
      // Shrink
	  this._effect(this.initialHeight);
  },
  // Auto expand height if required
  _autoExpand: function(ev) {
    if (ev) {
      // Keeps the keyboard from slowing down ie by only running the 
      // morph if the keyboard hasnt been touched for 0.1 seconds
      clearTimeout(this.keypressDelay);
      this.keypressDelay = this.doExpand.bind(this).delay(0.1, ev);
    }
    else this.doExpand();
  },
  
  doExpand: function(ev) {
    // Code to actually do the heavy lifting
    this._setWhitespaceAndUpdate();
    var mimicCurrentHeight = this.mimic.getHeight();
    var elementCurrentHeight = this.element.getHeight();
    var differenceHeight = elementCurrentHeight - mimicCurrentHeight;
    var targetHeight;
    // If the elements value == '' then we want the target height to be the inital height 
    // set when the texpand was created, usually a one line text box.
    if (this.element.value === '') targetHeight = this.initialHeight;
    else targetHeight = elementCurrentHeight + (this.options.increment - differenceHeight);
    
    if ((this.options.autoShrink && (differenceHeight > this.options.increment) || this.element.value === '') || differenceHeight < this.options.increment) {
      // Expand
      this._effect(targetHeight);
      this.options.onExpand.call(ev);
    }
  },
  
  // Add text and resize
  appendText: function(text) {
    this.element.value += text;
    this._autoExpand();
  },
  
  // Replace text and resize
  setValue: function(text) {
    this.element.value = text;
    this._autoExpand();
  }
};
{'fraction_non_alphanumeric': 0.13468273283077106, 'fraction_numerical': 0.006469994657802576, 'mean_word_length': 2.9670355545090654, 'pattern_counts': {'":': 0, '<': 26, '<?xml version=': 0, '>': 24, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '1946513', 'n_tokens_mistral': 5075, 'n_tokens_neox': 4915, 'n_words': 1405}