Snippet from https://stackoverflow.com/questions/2848462/count-bytes-in-textarea-using-javascript/12206089#12206089
194654
function getUTF8Length(s) {
  let len = 0;
  let i;
  let code;
  for (i = 0; i < s.length; i++) {
    code = s.charCodeAt(i);
    if (code <= 0x7f) {
      len += 1;
    } else if (code <= 0x7ff) {
      len += 2;
    } else if (code >= 0xd800 && code <= 0xdfff) {
      // Surrogate pair: These take 4 bytes in UTF-8 and 2 chars in UCS-2
      // (Assume next char is the other [valid] half and just skip it)
      len += 4; i++;
    } else if (code < 0xffff) {
      len += 3;
    } else {
      len += 4;
    }
  }
  return len;
}
1338466
function(byteLength) {
    pslByteLength = byteLength + 3 & ~3;
    if (
        pslBuffer32 !== undefined &&
        pslBuffer32.byteLength >= pslByteLength
    ) {
        return;
    }
    if ( wasmMemory !== undefined ) {
        const newPageCount = pslByteLength + 0xFFFF >>> 16;
        const curPageCount = wasmMemory.buffer.byteLength >>> 16;
        const delta = newPageCount - curPageCount;
        if ( delta > 0 ) {
            wasmMemory.grow(delta);
            pslBuffer32 = new Uint32Array(wasmMemory.buffer);
            pslBuffer8 = new Uint8Array(wasmMemory.buffer);
        }
    } else {
        pslBuffer8 = new Uint8Array(pslByteLength);
        pslBuffer32 = new Uint32Array(pslBuffer8.buffer);
    }
    hostnameArg = '';
    pslBuffer8[LABEL_INDICES_SLOT] = 0;
}
857192
function base64ArrayBuffer(bytes) {
    var base64    = ''
    var encodings = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/'

    var byteLength    = bytes.byteLength
    var byteRemainder = byteLength % 3
    var mainLength    = byteLength - byteRemainder
   
    var a, b, c, d
    var chunk
   
    // Main loop deals with bytes in chunks of 3
    for (var i = 0; i < mainLength; i = i + 3) {
      // Combine the three bytes into a single integer
      chunk = (bytes[i] << 16) | (bytes[i + 1] << 8) | bytes[i + 2]
   
      // Use bitmasks to extract 6-bit segments from the triplet
      a = (chunk & 16515072) >> 18 // 16515072 = (2^6 - 1) << 18
      b = (chunk & 258048)   >> 12 // 258048   = (2^6 - 1) << 12
      c = (chunk & 4032)     >>  6 // 4032     = (2^6 - 1) << 6
      d = chunk & 63               // 63       = 2^6 - 1
   
      // Convert the raw binary segments to the appropriate ASCII encoding
      base64 += encodings[a] + encodings[b] + encodings[c] + encodings[d]
    }
   
    // Deal with the remaining bytes and padding
    if (byteRemainder == 1) {
      chunk = bytes[mainLength]
   
      a = (chunk & 252) >> 2 // 252 = (2^6 - 1) << 2
   
      // Set the 4 least significant bits to zero
      b = (chunk & 3)   << 4 // 3   = 2^2 - 1
   
      base64 += encodings[a] + encodings[b] + '=='
    } else if (byteRemainder == 2) {
      chunk = (bytes[mainLength] << 8) | bytes[mainLength + 1]
   
      a = (chunk & 64512) >> 10 // 64512 = (2^6 - 1) << 10
      b = (chunk & 1008)  >>  4 // 1008  = (2^6 - 1) << 4
   
      // Set the 2 least significant bits to zero
      c = (chunk & 15)    <<  2 // 15    = 2^4 - 1
   
      base64 += encodings[a] + encodings[b] + encodings[c] + '='
    }
    
    return base64
  }
1360632
function(data) {

    var _mode = QRMode.MODE_ALPHA_NUM;
    var _data = data;

    var _this = {};

    _this.getMode = function() {
      return _mode;
    };

    _this.getLength = function(buffer) {
      return _data.length;
    };

    _this.write = function(buffer) {

      var s = _data;

      var i = 0;

      while (i + 1 < s.length) {
        buffer.put(
          getCode(s.charAt(i) ) * 45 +
          getCode(s.charAt(i + 1) ), 11);
        i += 2;
      }

      if (i < s.length) {
        buffer.put(getCode(s.charAt(i) ), 6);
      }
    };

    var getCode = function(c) {

      if ('0' <= c && c <= '9') {
        return c.charCodeAt(0) - '0'.charCodeAt(0);
      } else if ('A' <= c && c <= 'Z') {
        return c.charCodeAt(0) - 'A'.charCodeAt(0) + 10;
      } else {
        switch (c) {
        case ' ' : return 36;
        case '$' : return 37;
        case '%' : return 38;
        case '*' : return 39;
        case '+' : return 40;
        case '-' : return 41;
        case '.' : return 42;
        case '/' : return 43;
        case ':' : return 44;
        default :
          throw 'illegal char :' + c;
        }
      }
    };

    return _this;
  }
613444
function(element, content) {
    var nodeName = element.nodeName.toLowerCase(),
        type = element.hasAttribute('type') ? element.getAttribute('type') : null;

    if (nodeName === 'textarea') {
      return true;
    }
    if (nodeName === 'input' 
      && ['text', 'password', 'number', 'date'].indexOf(type) !== -1) {
      return true;
    }
    return false;
  }
694886
function getBytesWithUnit(bytes) {
        if (isNaN(bytes)) {
            return;
        }
        var units = [ ' bytes', ' KB', ' MB', ' GB', ' TB', ' PB', ' EB', ' ZB', ' YB' ];
        var amountOf2s = Math.floor(Math.log(+bytes) / Math.log(2));
        if (amountOf2s < 1) {
            amountOf2s = 0;
        }
        var i = Math.floor(amountOf2s / 10);
        bytes = +bytes / Math.pow(2, 10 * i);


        if (bytes.toString().length > bytes.toFixed(2).toString().length) {
            bytes = bytes.toFixed(2);
        }
        return bytes + units[i];
    }
1138882
function (bytes) {
			for (var str = [], i = 0; i < bytes.length; i++)
				str.push(String.fromCharCode(bytes[i]));
			return str.join("");
		}
150954
function Multipart() {

		// Internal body
		var body = [];
		var boundary = (Math.random() * 1e10).toString(32);
		var counter = 0;
		var lineBreak = '\r\n';
		var delim = lineBreak + '--' + boundary;
		var ready = function() {};

		var dataUri = /^data\:([^;,]+(\;charset=[^;,]+)?)(\;base64)?,/i;

		// Add file
		function addFile(item) {
			var fr = new FileReader();
			fr.onload = function(e) {
				addContent(btoa(e.target.result), item.type + lineBreak + 'Content-Transfer-Encoding: base64');
			};

			fr.readAsBinaryString(item);
		}

		// Add content
		function addContent(content, type) {
			body.push(lineBreak + 'Content-Type: ' + type + lineBreak + lineBreak + content);
			counter--;
			ready();
		}

		// Add new things to the object
		this.append = function(content, type) {

			// Does the content have an array
			if (typeof (content) === 'string' || !('length' in Object(content))) {
				// Converti to multiples
				content = [content];
			}

			for (var i = 0; i < content.length; i++) {

				counter++;

				var item = content[i];

				// Is this a file?
				// Files can be either Blobs or File types
				if (
					(typeof (File) !== 'undefined' && item instanceof File) ||
					(typeof (Blob) !== 'undefined' && item instanceof Blob)
				) {
					// Read the file in
					addFile(item);
				}

				// Data-URI?
				// Data:[<mime type>][;charset=<charset>][;base64],<encoded data>
				// /^data\:([^;,]+(\;charset=[^;,]+)?)(\;base64)?,/i
				else if (typeof (item) === 'string' && item.match(dataUri)) {
					var m = item.match(dataUri);
					addContent(item.replace(dataUri, ''), m[1] + lineBreak + 'Content-Transfer-Encoding: base64');
				}

				// Regular string
				else {
					addContent(item, type);
				}
			}
		};

		this.onready = function(fn) {
			ready = function() {
				if (counter === 0) {
					// Trigger ready
					body.unshift('');
					body.push('--');
					fn(body.join(delim), boundary);
					body = [];
				}
			};

			ready();
		};
	}
757044
private int parseByte()
        throws IOException
    {
        while (_chunkLength <= 0) {
            if (_isLastChunk) {
                return -1;
            }

            int code = read();

            switch (code) {
                case 'b':
                    _isLastChunk = false;

                    _chunkLength = (read() << 8) + read();
                    break;

                case 'B':
                    _isLastChunk = true;

                    _chunkLength = (read() << 8) + read();
                    break;

                default:
                    throw expect("byte[]", code);
            }
        }

        _chunkLength--;

        return read();
    }
224175
function decodeUTF8(bytes) {
  var s = '';
  var i = 0;
  while (i < bytes.length) {
    var c = bytes[i++];
    if (c > 127) {
      if (c > 191 && c < 224) {
        if (i >= bytes.length)
          throw new Error('UTF-8 decode: incomplete 2-byte sequence');
        c = ((c & 31) << 6) | (bytes[i] & 63);
      } else if (c > 223 && c < 240) {
        if (i + 1 >= bytes.length)
          throw new Error('UTF-8 decode: incomplete 3-byte sequence');
        c = ((c & 15) << 12) | ((bytes[i] & 63) << 6) | (bytes[++i] & 63);
      } else if (c > 239 && c < 248) {
        if (i + 2 >= bytes.length)
          throw new Error('UTF-8 decode: incomplete 4-byte sequence');
        c =
          ((c & 7) << 18) |
          ((bytes[i] & 63) << 12) |
          ((bytes[++i] & 63) << 6) |
          (bytes[++i] & 63);
      } else
        throw new Error(
          'UTF-8 decode: unknown multibyte start 0x' +
            c.toString(16) +
            ' at index ' +
            (i - 1)
        );
      ++i;
    }

    if (c <= 0xffff) s += String.fromCharCode(c);
    else if (c <= 0x10ffff) {
      c -= 0x10000;
      s += String.fromCharCode((c >> 10) | 0xd800);
      s += String.fromCharCode((c & 0x3ff) | 0xdc00);
    } else
      throw new Error(
        'UTF-8 decode: code point 0x' + c.toString(16) + ' exceeds UTF-16 reach'
      );
  }
  return s;
}
1087180
function(data) {

    var _mode = QRMode.MODE_NUMBER;
    var _data = data;

    var _this = {};

    _this.getMode = function() {
      return _mode;
    };

    _this.getLength = function(buffer) {
      return _data.length;
    };

    _this.write = function(buffer) {

      var data = _data;

      var i = 0;

      while (i + 2 < data.length) {
        buffer.put(strToNum(data.substring(i, i + 3) ), 10);
        i += 3;
      }

      if (i < data.length) {
        if (data.length - i == 1) {
          buffer.put(strToNum(data.substring(i, i + 1) ), 4);
        } else if (data.length - i == 2) {
          buffer.put(strToNum(data.substring(i, i + 2) ), 7);
        }
      }
    };

    var strToNum = function(s) {
      var num = 0;
      for (var i = 0; i < s.length; i += 1) {
        num = num * 10 + chatToNum(s.charAt(i) );
      }
      return num;
    };

    var chatToNum = function(c) {
      if ('0' <= c && c <= '9') {
        return c.charCodeAt(0) - '0'.charCodeAt(0);
      }
      throw 'illegal char :' + c;
    };

    return _this;
  }
641163
function () {
        var sizeInfo = {
                body: 0,
                header: 0,
                total: 0
            },

            contentEncoding = this.headers.get(CONTENT_ENCODING),
            contentLength = this.headers.get(CONTENT_LENGTH),
            isCompressed = false,
            byteLength;

        // if server sent encoded data, we should first try deriving length from headers
        if (_.isString(contentEncoding)) {
            // desensitise case of content encoding
            contentEncoding = contentEncoding.toLowerCase();
            // eslint-disable-next-line lodash/prefer-includes
            isCompressed = (contentEncoding.indexOf('gzip') > -1) || (contentEncoding.indexOf('deflate') > -1);
        }

        // if 'Content-Length' header is present and encoding is of type gzip/deflate, we take body as declared by
        // server. else we need to compute the same.
        if (contentLength && isCompressed && util.isNumeric(contentLength)) {
            sizeInfo.body = _.parseInt(contentLength, 10);
        }
        // if there is a stream defined which looks like buffer, use it's data and move on
        else if (this.stream) {
            byteLength = this.stream.byteLength;
            sizeInfo.body = util.isNumeric(byteLength) ? byteLength : 0;
        }
        // otherwise, if body is defined, we try get the true length of the body
        else if (!_.isNil(this.body)) {
            sizeInfo.body = supportsBuffer ? Buffer.byteLength(this.body.toString()) : this.body.toString().length;
        }

        // size of header is added
        // https://tools.ietf.org/html/rfc7230#section-3
        // HTTP-message   = start-line (request-line / status-line)
        //                  *( header-field CRLF )
        //                  CRLF
        //                  [ message-body ]
        // status-line = HTTP-version SP status-code SP reason-phrase CRLF
        sizeInfo.header = (HTTP_X_X + SP + this.code + SP + this.reason() + CRLF + CRLF).length +
            this.headers.contentSize();

        // compute the approximate total body size by adding size of header and body
        sizeInfo.total = (sizeInfo.body || 0) + (sizeInfo.header || 0);
        return sizeInfo;
    }
663334
function wordCount(data) {
	var pattern = /[a-zA-Z0-9_\u0392-\u03c9\u0410-\u04F9]+|[\u4E00-\u9FFF\u3400-\u4dbf\uf900-\ufaff\u3040-\u309f\uac00-\ud7af]+/g;
	var m = data.match(pattern);
	var count = 0;
	if(m === null) return count;
	for(var i = 0; i < m.length; i++) {
		if(m[i].charCodeAt(0) >= 0x4E00) {
			count += m[i].length;
		} else {
			count += 1;
		}
	}
	return count;
}
854355
function getByte(array, position, length) {
  const d = position % 8;
  const a = Math.floor(position / 8);
  const de = 8 - d;
  const ef = (position + length) - ((a + 1) * 8);
  let fg = (8 * (a + 2)) - (position + length);
  const dg = ((a + 2) * 8) - position;
  fg = Math.max(0, fg);
  if (a >= array.length) {
    console.warn('ran off the end of the buffer before finding EOI_CODE (end on input code)');
    return EOI_CODE;
  }
  let chunk1 = array[a] & ((2 ** (8 - d)) - 1);
  chunk1 <<= (length - de);
  let chunks = chunk1;
  if (a + 1 < array.length) {
    let chunk2 = array[a + 1] >>> fg;
    chunk2 <<= Math.max(0, (length - dg));
    chunks += chunk2;
  }
  if (ef > 8 && a + 2 < array.length) {
    const hi = ((a + 3) * 8) - (position + length);
    const chunk3 = array[a + 2] >>> hi;
    chunks += chunk3;
  }
  return chunks;
}
757179
function TextareaState(input) {

  // Aliases
  var stateObj = this;
  var inputArea = input;
  this.init = function () {
    this.setInputAreaSelectionStartEnd();
    this.text = inputArea.getContent();
  };

  // Sets the selected text in the input box after we've performed an
  // operation.
  this.setInputAreaSelection = function () {
    inputArea.focus();
    inputArea.setSelection(stateObj.start, stateObj.end);
  };

  this.setInputAreaSelectionStartEnd = function () {
    stateObj.start = Math.min(
      inputArea.selectionMgr.selectionStart,
      inputArea.selectionMgr.selectionEnd
    );
    stateObj.end = Math.max(
      inputArea.selectionMgr.selectionStart,
      inputArea.selectionMgr.selectionEnd
    );
  };

  // Restore this state into the input area.
  this.restore = function () {

    if (stateObj.text !== undefined && stateObj.text != inputArea.getContent()) {
      inputArea.setContent(stateObj.text);
    }
    this.setInputAreaSelection();
  };

  // Gets a collection of HTML chunks from the inptut textarea.
  this.getChunks = function () {

    var chunk = new Chunks();
    chunk.before = util.fixEolChars(stateObj.text.substring(0, stateObj.start));
    chunk.startTag = "";
    chunk.selection = util.fixEolChars(stateObj.text.substring(stateObj.start, stateObj.end));
    chunk.endTag = "";
    chunk.after = util.fixEolChars(stateObj.text.substring(stateObj.end));

    return chunk;
  };

  // Sets the TextareaState properties given a chunk of markdown.
  this.setChunks = function (chunk) {

    chunk.before = chunk.before + chunk.startTag;
    chunk.after = chunk.endTag + chunk.after;

    this.start = chunk.before.length;
    this.end = chunk.before.length + chunk.selection.length;
    this.text = chunk.before + chunk.selection + chunk.after;
  };
  this.init();
}
338245
def textarea config={}, &block
      require 'canis/rtextarea'
      # TODO confirm events many more
      events = [ :CHANGE,  :LEAVE, :ENTER ]
      block_event = events[0]
      #_process_args args, config, block_event, events
      #config[:width] = config[:display_length] unless config.has_key? :width
      # if no width given, expand to flows width
      #config[:width] ||= @stack.last.width if @stack.last
      useform = nil
      #useform = @form if @current_object.empty?
      w = TextArea.new useform, config
      w.width = :expand unless w.width
      w.height ||= 8 # TODO
      _position(w)
      # need to expand to stack's width or flows itemwidth if given
      if block
        w.bind(block_event, &block)
      end
      return w
    end
1359021
function(element) {
    if('TEXTAREA'===element.nodeName
      ||('INPUT'===element.nodeName&&element.hasAttribute('type')
        &&('text'===element.getAttribute('type')
          ||'number'===element.getAttribute('type'))
      )
    ) {
      return true;
    }
    return false;
  }