StackGenVis: Alignment of Data, Algorithms, and Models for Stacking Ensemble Learning Using Performance Metrics https://doi.org/10.1109/TVCG.2020.3030352
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
StackGenVis/frontend/node_modules/templates/lib/list.js

474 lines
10 KiB

'use strict';
var Base = require('base');
var debug = require('debug')('base:templates:list');
var plugin = require('./plugins');
var Group = require('./group');
var utils = require('./utils');
/**
* Expose `List`
*/
module.exports = exports = List;
/**
* Create an instance of `List` with the given `options`.
* Lists differ from collections in that items are stored
* as an array, allowing items to be paginated, sorted,
* and grouped.
*
* ```js
* var list = new List();
* list.addItem('foo', {content: 'bar'});
* ```
* @param {Object} `options`
* @api public
*/
function List(options) {
if (!(this instanceof List)) {
return new List(options);
}
Base.call(this);
this.is('list');
this.define('isCollection', true);
this.use(utils.option());
this.use(utils.plugin());
this.init(options || {});
}
/**
* Inherit `Base` and load static plugins
*/
plugin.static(Base, List, 'List');
/**
* Initalize `List` defaults
*/
List.prototype.init = function(opts) {
debug('initalizing');
// add constructors to the instance
this.define('Item', opts.Item || List.Item);
this.define('View', opts.View || List.View);
// decorate the instance
this.use(plugin.init);
this.use(plugin.renameKey());
this.use(plugin.context);
this.use(utils.engines());
this.use(utils.helpers());
this.use(utils.routes());
this.use(plugin.item('item', 'Item', {emit: false}));
this.use(plugin.item('view', 'View', {emit: false}));
// decorate `isItem` and `isView`, in case custom class is passed
plugin.is(this.Item);
plugin.is(this.View);
this.queue = [];
this.items = [];
this.keys = [];
// if an instance of `List` of `Views` is passed, load it now
if (Array.isArray(opts) || opts.isList) {
this.options = opts.options || {};
this.addList(opts.items || opts);
} else if (opts.isCollection) {
this.options = opts.options;
this.addItems(opts.views);
} else {
this.options = opts;
}
};
/**
* Add an item to `list.items`. This is identical to [setItem](#setItem)
* except `addItem` returns the `item`, add `setItem` returns the instance
* of `List`.
*
* ```js
* collection.addItem('foo', {content: 'bar'});
* ```
*
* @param {String|Object} `key` Item key or object
* @param {Object} `value` If key is a string, value is the item object.
* @developer The `item` method is decorated onto the collection using the `item` plugin
* @return {Object} returns the `item` instance.
* @api public
*/
List.prototype.addItem = function(key, value) {
var item = this.item(key, value);
utils.setInstanceNames(item, 'Item');
debug('adding item "%s"', item.key);
if (this.options.pager === true) {
List.addPager(item, this.items);
}
this.keys.push(item.key);
if (typeof item.use === 'function') {
this.run(item);
}
this.extendItem(item);
this.emit('load', item, this);
this.emit('item', item, this);
this.items.push(item);
return item;
};
/**
* Add an item to `list.items`. This is identical to [addItem](#addItem)
* except `addItem` returns the `item`, add `setItem` returns the instance
* of `List`.
*
* ```js
* var items = new Items(...);
* items.setItem('a.html', {path: 'a.html', contents: '...'});
* ```
* @param {String} `key`
* @param {Object} `value`
* @return {Object} Returns the instance of `List` to support chaining.
* @api public
*/
List.prototype.setItem = function(/*key, value*/) {
this.addItem.apply(this, arguments);
return this;
};
/**
* Load multiple items onto the collection.
*
* ```js
* collection.addItems({
* 'a.html': {content: '...'},
* 'b.html': {content: '...'},
* 'c.html': {content: '...'}
* });
* ```
* @param {Object|Array} `items`
* @return {Object} returns the instance for chaining
* @api public
*/
List.prototype.addItems = function(items) {
if (Array.isArray(items)) {
return this.addList.apply(this, arguments);
}
this.emit('addItems', items);
if (this.loaded) {
this.loaded = false;
return this;
}
this.visit('addItem', items);
return this;
};
/**
* Load an array of items or the items from another instance of `List`.
*
* ```js
* var foo = new List(...);
* var bar = new List(...);
* bar.addList(foo);
* ```
* @param {Array} `items` or an instance of `List`
* @param {Function} `fn` Optional sync callback function that is called on each item.
* @return {Object} returns the List instance for chaining
* @api public
*/
List.prototype.addList = function(list, fn) {
this.emit.call(this, 'addList', list);
if (this.loaded) {
this.loaded = false;
return this;
}
if (!Array.isArray(list)) {
throw new TypeError('expected list to be an array.');
}
if (typeof fn !== 'function') {
fn = utils.identity;
}
var len = list.length, i = -1;
while (++i < len) {
var item = list[i];
fn(item);
this.addItem(item.path, item);
}
return this;
};
/**
* Return true if the list has the given item (name).
*
* ```js
* list.addItem('foo.html', {content: '...'});
* list.hasItem('foo.html');
* //=> true
* ```
* @param {String} `key`
* @return {Object}
* @api public
*/
List.prototype.hasItem = function(key) {
return this.getIndex(key) !== -1;
};
/**
* Get a the index of a specific item from the list by `key`.
*
* ```js
* list.getIndex('foo.html');
* //=> 1
* ```
* @param {String} `key`
* @return {Object}
* @api public
*/
List.prototype.getIndex = function(key) {
if (typeof key === 'undefined') {
throw new Error('expected a string or instance of Item');
}
if (List.isItem(key)) {
key = key.key;
}
var idx = this.keys.indexOf(key);
if (idx !== -1) {
return idx;
}
idx = this.keys.indexOf(this.renameKey(key));
if (idx !== -1) {
return idx;
}
var items = this.items;
var len = items.length;
while (len--) {
var item = items[len];
var prop = this.renameKey(key, item);
if (utils.matchFile(prop, item)) {
return len;
}
}
return -1;
};
/**
* Get a specific item from the list by `key`.
*
* ```js
* list.getItem('foo.html');
* //=> '<Item <foo.html>>'
* ```
* @param {String} `key` The item name/key.
* @return {Object}
* @api public
*/
List.prototype.getItem = function(key) {
var idx = this.getIndex(key);
if (idx !== -1) {
return this.items[idx];
}
};
/**
* Proxy for `getItem`
*
* ```js
* list.getItem('foo.html');
* //=> '<Item "foo.html" <buffer e2 e2 e2>>'
* ```
* @param {String} `key` Pass the key of the `item` to get.
* @return {Object}
* @api public
*/
List.prototype.getView = function() {
return this.getItem.apply(this, arguments);
};
/**
* Remove an item from the list.
*
* ```js
* list.deleteItem('a.html');
* ```
* @param {Object|String} `key` Pass an `item` instance (object) or `item.key` (string).
* @api public
*/
List.prototype.deleteItem = function(item) {
var idx = this.getIndex(item);
if (idx !== -1) {
this.items.splice(idx, 1);
this.keys.splice(idx, 1);
}
return this;
};
/**
* Decorate each item on the list with additional methods
* and properties. This provides a way of easily overriding
* defaults.
*
* @param {Object} `item`
* @return {Object} Instance of item for chaining
* @api public
*/
List.prototype.extendItem = function(item) {
plugin.view(this, item);
return this;
};
/**
* Group all list `items` using the given property,
* properties or compare functions. See [group-array][]
* for the full range of available features and options.
*
* ```js
* var list = new List();
* list.addItems(...);
* var groups = list.groupBy('data.date', 'data.slug');
* ```
* @return {Object} Returns the grouped items.
* @api public
*/
List.prototype.groupBy = function() {
var args = [].slice.call(arguments);
var fn = utils.groupBy;
// Make `items` the first argument for group-array
args.unshift(this.items.slice());
// group the `items` and return the result
return new Group(fn.apply(fn, args));
};
/**
* Sort all list `items` using the given property,
* properties or compare functions. See [array-sort][]
* for the full range of available features and options.
*
* ```js
* var list = new List();
* list.addItems(...);
* var result = list.sortBy('data.date');
* //=> new sorted list
* ```
* @return {Object} Returns a new `List` instance with sorted items.
* @api public
*/
List.prototype.sortBy = function() {
var args = [].slice.call(arguments);
var last = args[args.length - 1];
var opts = this.options.sort || {};
// extend `list.options.sort` global options with local options
if (last && typeof last === 'object' && !Array.isArray(last)) {
opts = utils.extend({}, opts, args.pop());
}
// create the args to pass to array-sort
args.unshift(this.items.slice());
args.push(opts);
// sort the `items` array, then sort `keys`
var items = utils.sortBy.apply(utils.sortBy, args);
var list = new List(this.options);
list.addItems(items);
return list;
};
/**
* Resolve the layout to use for the given `item`
*
* @param {Object} `item`
* @return {String} Returns the name of the layout to use.
*/
List.prototype.resolveLayout = function(item) {
if (utils.isRenderable(item) && typeof item.layout === 'undefined') {
return this.option('layout');
}
return item.layout;
};
/**
* Paginate all `items` in the list with the given options,
* See [paginationator][] for the full range of available
* features and options.
*
* ```js
* var list = new List(items);
* var pages = list.paginate({limit: 5});
* ```
* @return {Object} Returns the paginated items.
* @api public
*/
List.prototype.paginate = function() {
var args = [].slice.call(arguments);
var fn = utils.paginationator;
// Make `items` the first argument for paginationator
args.unshift(this.items.slice());
// paginate the `items` and return the pages
var items = fn.apply(fn, args);
return items.pages;
};
/**
* Add paging (`prev`/`next`) information to the
* `data` object of an item.
*
* @param {Object} `item`
* @param {Array} `items` instance items.
*/
List.addPager = function addPager(item, items) {
item.data.pager = {};
item.data.pager.index = items.length;
utils.define(item.data.pager, 'current', item);
if (items.length) {
var prev = items[items.length - 1];
utils.define(item.data.pager, 'prev', prev);
utils.define(prev.data.pager, 'next', item);
}
};
/**
* Expose static properties
*/
utils.define(List, 'Item', require('vinyl-item'));
utils.define(List, 'View', require('vinyl-view'));