<commit_before>/*globals jml */

/**
* @class ExpandableInputs
* @requires jamilih
*/
var ExpandableInputs = (function () {'use strict';

// STATIC VARS
var ns = 0; // Used to prevent conflicts if the user does not supply their own namespace

// POLYFILLS
Array.from = function (arg) {
    return [].slice.call(arg);
};

// UTILITIES

/**
* @static
* @private
*/
function $ (sel) {
    return document.querySelector(sel);
}
/**
* @static
* @private
*/
function $$ (sel) {
    return document.querySelectorAll(sel);
}

/**
* 
* @constructor
* @param {object} cfg Configuration object
* @param {string} cfg.table The ID of the table.
* @param {string} [cfg.prefix="ei-"] Prefix to denote expandable inputs. Should not need to be changed
* @param {string} [cfg.namespace] Namespace for this set
    of expandable inputs. If none is supplied, an incrementing value will be used.
* @param {string} [cfg.label="%s:"] The label to be shown. (See cfg.pattern for the regular expression used to do substitutions.)
* @param {string} [cfg.pattern=/%s/g] The regular expression for finding numbers within labels.
* @param {string} [cfg.inputType="text"] The type for text inputs
* @param {boolean} [cfg.selects=false] Whether to include a select menu for preset file paths or directories
* @param {number} [cfg.inputSize=50] The size for text inputs
* @param {number} [cfg.rows] The number of rows; auto-changes input to a textarea (even if set to 1)
* @param {string} [cfg.locale] A locale. Default to an English locale. (Note that the label property ought to also be localized.)
*/
function ExpandableInputs (cfg) {
    if (!(this instanceof ExpandableInputs)) {
        return new ExpandableInputs(cfg);
    }
    if (!cfg || typeof cfg !== 'object' || !cfg.table) {
        throw 'A config object with a table ID must be supplied to ExpandableInputs';
    }
    this.table = cfg.table;
    this.prefix = ((cfg.prefix && cfg.prefix.replace(/-$/, '')) || 'ei') + '-';
    this.ns = ((cfg.namespace && cfg.namespace.replace(/-$/, '')) || (ns++).toString()) + '-';
    this.label = cfg.label || "%s:";
    this.pattern = cfg.pattern || /%s/g;
    this.inputType = cfg.inputType && cfg.inputType !== 'file' ? cfg.inputType : 'text';
    this.selects = cfg.selects || false;
    this.inputSize = cfg.inputSize || 50;
    this.rows = cfg.rows;
    this.locale = cfg.locale || {
        browse: "Browse\u2026",
        directory: "Directory?",
        plus: "+",
        minus: "-",
        reveal: "" // We use a background-image of a folder instead of text
    };

    // State variables
    this.fileType = cfg.inputType === 'file';
    this.id = 1;
    this.num = 1;
}

ExpandableInputs.prototype.getLabel = function (num) {
    return this.label.replace(this.pattern, num);
};

ExpandableInputs.prototype.getPrefixedNamespace = function () {
    return this.prefix + this.ns;
};

ExpandableInputs.prototype.remove = function (id) {
    var prefixedNS = this.getPrefixedNamespace(),
        that = this,
        rowIDSel = '#' + prefixedNS + 'row-' + id;
    if ($$('.' + prefixedNS + 'row').length === 1) { // Don't delete if only one remaining
        return;
    }
    $(rowIDSel).parentNode.removeChild($(rowIDSel));
    // Renumber to ensure inputs remain incrementing by one
    this.num = 1;
    Array.from($$('.' + prefixedNS + 'number')).forEach(function (numHolder) {
        numHolder.replaceChild(document.createTextNode(that.getLabel(that.num++)), numHolder.firstChild);
    });
};

ExpandableInputs.prototype.add = function () {
    var that = this,
        prefixedNS = this.getPrefixedNamespace();
    $('#' + this.table).appendChild(jml(
        'tr', {
            'id': prefixedNS + 'row-' + this.id,
            'class': prefixedNS + 'row'
        }, [
                ['td', [
                    ['label', {
                        'for': prefixedNS + 'input-' + this.id,
                        'class': prefixedNS + 'number'
                    }, [this.getLabel(this.num)]]
                ]],
                ['td', [
                    (this.fileType && this.selects ?
                        ($$('.' + prefixedNS + 'presets').length > 0 ?
                            (function () {
                                var select = $('.' + prefixedNS + 'presets').cloneNode(true);
                                select.id = prefixedNS + 'select-' + that.id;
                                select.dataset.sel = '#' + prefixedNS + 'input-' + that.id;
                                return select;
                            }()) :
                            ['select', {
                                id: prefixedNS + 'select-' + this.id,
                                'class': prefixedNS + 'presets',
                                dataset: {sel: '#' + prefixedNS + 'input-' + this.id}
                            }]
                        ) :
                        ''
                    ),
                    [(this.rows ? 'textarea' : 'input'), (function () {
                        var atts = {
                            id: prefixedNS + 'input-' + that.id,
                            'class': prefixedNS + 'input ' + prefixedNS + 'path'
                        };
                        if (that.hasOwnProperty('rows')) { // textarea
                            atts.cols = that.inputSize;
                            atts.rows = that.rows;
                        }
                        else { // input<commit_msg>Fix textarea check<commit_after>/*globals jml */

/**
* @class ExpandableInputs
* @requires jamilih
*/
var ExpandableInputs = (function (undef) {'use strict';

// STATIC VARS
var ns = 0; // Used to prevent conflicts if the user does not supply their own namespace

// POLYFILLS
Array.from = function (arg) {
    return [].slice.call(arg);
};

// UTILITIES

/**
* @static
* @private
*/
function $ (sel) {
    return document.querySelector(sel);
}
/**
* @static
* @private
*/
function $$ (sel) {
    return document.querySelectorAll(sel);
}

/**
* 
* @constructor
* @param {object} cfg Configuration object
* @param {string} cfg.table The ID of the table.
* @param {string} [cfg.prefix="ei-"] Prefix to denote expandable inputs. Should not need to be changed
* @param {string} [cfg.namespace] Namespace for this set
    of expandable inputs. If none is supplied, an incrementing value will be used.
* @param {string} [cfg.label="%s:"] The label to be shown. (See cfg.pattern for the regular expression used to do substitutions.)
* @param {string} [cfg.pattern=/%s/g] The regular expression for finding numbers within labels.
* @param {string} [cfg.inputType="text"] The type for text inputs
* @param {boolean} [cfg.selects=false] Whether to include a select menu for preset file paths or directories
* @param {number} [cfg.inputSize=50] The size for text inputs
* @param {number} [cfg.rows] The number of rows; auto-changes input to a textarea (even if set to 1)
* @param {string} [cfg.locale] A locale. Default to an English locale. (Note that the label property ought to also be localized.)
*/
function ExpandableInputs (cfg) {
    if (!(this instanceof ExpandableInputs)) {
        return new ExpandableInputs(cfg);
    }
    if (!cfg || typeof cfg !== 'object' || !cfg.table) {
        throw 'A config object with a table ID must be supplied to ExpandableInputs';
    }
    this.table = cfg.table;
    this.prefix = ((cfg.prefix && cfg.prefix.replace(/-$/, '')) || 'ei') + '-';
    this.ns = ((cfg.namespace && cfg.namespace.replace(/-$/, '')) || (ns++).toString()) + '-';
    this.label = cfg.label || "%s:";
    this.pattern = cfg.pattern || /%s/g;
    this.inputType = cfg.inputType && cfg.inputType !== 'file' ? cfg.inputType : 'text';
    this.selects = cfg.selects || false;
    this.inputSize = cfg.inputSize || 50;
    if (cfg.rows !== undef) {
        this.rows = cfg.rows;
    }
    this.locale = cfg.locale || {
        browse: "Browse\u2026",
        directory: "Directory?",
        plus: "+",
        minus: "-",
        reveal: "" // We use a background-image of a folder instead of text
    };

    // State variables
    this.fileType = cfg.inputType === 'file';
    this.id = 1;
    this.num = 1;
}

ExpandableInputs.prototype.getLabel = function (num) {
    return this.label.replace(this.pattern, num);
};

ExpandableInputs.prototype.getPrefixedNamespace = function () {
    return this.prefix + this.ns;
};

ExpandableInputs.prototype.remove = function (id) {
    var prefixedNS = this.getPrefixedNamespace(),
        that = this,
        rowIDSel = '#' + prefixedNS + 'row-' + id;
    if ($$('.' + prefixedNS + 'row').length === 1) { // Don't delete if only one remaining
        return;
    }
    $(rowIDSel).parentNode.removeChild($(rowIDSel));
    // Renumber to ensure inputs remain incrementing by one
    this.num = 1;
    Array.from($$('.' + prefixedNS + 'number')).forEach(function (numHolder) {
        numHolder.replaceChild(document.createTextNode(that.getLabel(that.num++)), numHolder.firstChild);
    });
};

ExpandableInputs.prototype.add = function () {
    var that = this,
        prefixedNS = this.getPrefixedNamespace();
    $('#' + this.table).appendChild(jml(
        'tr', {
            'id': prefixedNS + 'row-' + this.id,
            'class': prefixedNS + 'row'
        }, [
                ['td', [
                    ['label', {
                        'for': prefixedNS + 'input-' + this.id,
                        'class': prefixedNS + 'number'
                    }, [this.getLabel(this.num)]]
                ]],
                ['td', [
                    (this.fileType && this.selects ?
                        ($$('.' + prefixedNS + 'presets').length > 0 ?
                            (function () {
                                var select = $('.' + prefixedNS + 'presets').cloneNode(true);
                                select.id = prefixedNS + 'select-' + that.id;
                                select.dataset.sel = '#' + prefixedNS + 'input-' + that.id;
                                return select;
                            }()) :
                            ['select', {
                                id: prefixedNS + 'select-' + this.id,
                                'class': prefixedNS + 'presets',
                                dataset: {sel: '#' + prefixedNS + 'input-' + this.id}
                            }]
                        ) :
                        ''
                    ),
                    [(this.hasOwnProperty('rows') ? 'textarea' : 'input'), (function () {
                        var atts = {
                            id: prefixedNS + 'input-' + that.id,
                            'class': prefixedNS + 'input ' + prefixedNS + 'path'
                        };
                        if (that.hasOwnProperty('rows')) { // textarea
                            atts.cols = that.inputSize;
                            atts.rows = that.rows;
                        }
                        else { // input
{'fraction_non_alphanumeric': 0.14598141060688902, 'fraction_numerical': 0.002733734281027884, 'mean_word_length': 1.862545644235785, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 5, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 4, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3591736', 'n_tokens_mistral': 3205, 'n_tokens_neox': 3110, 'n_words': 835}