vega-encode
Advanced tools
Comparing version 2.0.8 to 3.0.0
(function (global, factory) { | ||
typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('vega-scale'), require('vega-util'), require('d3-format'), require('vega-dataflow'), require('d3-array'), require('d3-interpolate')) : | ||
typeof define === 'function' && define.amd ? define(['exports', 'vega-scale', 'vega-util', 'd3-format', 'vega-dataflow', 'd3-array', 'd3-interpolate'], factory) : | ||
(factory((global.vega = global.vega || {}, global.vega.transforms = global.vega.transforms || {}),global.vega,global.vega,global.d3,global.vega,global.d3,global.d3)); | ||
typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('vega-scale'), require('vega-util'), require('d3-format'), require('vega-dataflow'), require('d3-array'), require('d3-interpolate')) : | ||
typeof define === 'function' && define.amd ? define(['exports', 'vega-scale', 'vega-util', 'd3-format', 'vega-dataflow', 'd3-array', 'd3-interpolate'], factory) : | ||
(factory((global.vega = global.vega || {}, global.vega.transforms = {}),global.vega,global.vega,global.d3,global.vega,global.d3,global.d3)); | ||
}(this, (function (exports,vegaScale,vegaUtil,d3Format,vegaDataflow,d3Array,d3Interpolate) { 'use strict'; | ||
var Log = 'log'; | ||
var Pow = 'pow'; | ||
var Utc = 'utc'; | ||
var Sqrt = 'sqrt'; | ||
var Band = 'band'; | ||
var Time = 'time'; | ||
var Point = 'point'; | ||
var Linear = 'linear'; | ||
var Ordinal = 'ordinal'; | ||
var Quantile = 'quantile'; | ||
var Quantize = 'quantize'; | ||
var Threshold = 'threshold'; | ||
var BinLinear = 'bin-linear'; | ||
var BinOrdinal = 'bin-ordinal'; | ||
var Sequential = 'sequential'; | ||
var Log = 'log'; | ||
var Pow = 'pow'; | ||
var Utc = 'utc'; | ||
var Sqrt = 'sqrt'; | ||
var Band = 'band'; | ||
var Time = 'time'; | ||
var Point = 'point'; | ||
var Linear = 'linear'; | ||
var Ordinal = 'ordinal'; | ||
var Quantile = 'quantile'; | ||
var Quantize = 'quantize'; | ||
var Threshold = 'threshold'; | ||
var BinLinear = 'bin-linear'; | ||
var BinOrdinal = 'bin-ordinal'; | ||
var Sequential = 'sequential'; | ||
/** | ||
* Determine the tick count or interval function. | ||
* @param {Scale} scale - The scale for which to generate tick values. | ||
* @param {*} count - The desired tick count or interval specifier. | ||
* @return {*} - The tick count or interval function. | ||
*/ | ||
function tickCount(scale$$1, count) { | ||
var step; | ||
/** | ||
* Determine the tick count or interval function. | ||
* @param {Scale} scale - The scale for which to generate tick values. | ||
* @param {*} count - The desired tick count or interval specifier. | ||
* @return {*} - The tick count or interval function. | ||
*/ | ||
function tickCount(scale, count) { | ||
var step; | ||
if (vegaUtil.isObject(count)) { | ||
step = count.step; | ||
count = count.interval; | ||
if (vegaUtil.isObject(count)) { | ||
step = count.step; | ||
count = count.interval; | ||
} | ||
if (vegaUtil.isString(count)) { | ||
count = scale.type === 'time' ? vegaScale.timeInterval(count) | ||
: scale.type === 'utc' ? vegaScale.utcInterval(count) | ||
: vegaUtil.error('Only time and utc scales accept interval strings.'); | ||
if (step) count = count.every(step); | ||
} | ||
return count; | ||
} | ||
if (vegaUtil.isString(count)) { | ||
count = scale$$1.type === 'time' ? vegaScale.timeInterval(count) | ||
: scale$$1.type === 'utc' ? vegaScale.utcInterval(count) | ||
: vegaUtil.error('Only time and utc scales accept interval strings.'); | ||
if (step) count = count.every(step); | ||
/** | ||
* Filter a set of candidate tick values, ensuring that only tick values | ||
* that lie within the scale range are included. | ||
* @param {Scale} scale - The scale for which to generate tick values. | ||
* @param {Array<*>} ticks - The candidate tick values. | ||
* @param {*} count - The tick count or interval function. | ||
* @return {Array<*>} - The filtered tick values. | ||
*/ | ||
function validTicks(scale, ticks, count) { | ||
var range = scale.range(), | ||
lo = range[0], | ||
hi = vegaUtil.peek(range); | ||
if (lo > hi) { | ||
range = hi; | ||
hi = lo; | ||
lo = range; | ||
} | ||
ticks = ticks.filter(function(v) { | ||
v = scale(v); | ||
return !(v < lo || v > hi) | ||
}); | ||
if (count > 0 && ticks.length > 1) { | ||
var endpoints = [ticks[0], vegaUtil.peek(ticks)]; | ||
while (ticks.length > count && ticks.length >= 3) { | ||
ticks = ticks.filter(function(_, i) { return !(i % 2); }); | ||
} | ||
if (ticks.length < 3) { | ||
ticks = endpoints; | ||
} | ||
} | ||
return ticks; | ||
} | ||
return count; | ||
} | ||
/** | ||
* Generate tick values for the given scale and approximate tick count or | ||
* interval value. If the scale has a 'ticks' method, it will be used to | ||
* generate the ticks, with the count argument passed as a parameter. If the | ||
* scale lacks a 'ticks' method, the full scale domain will be returned. | ||
* @param {Scale} scale - The scale for which to generate tick values. | ||
* @param {*} [count] - The approximate number of desired ticks. | ||
* @return {Array<*>} - The generated tick values. | ||
*/ | ||
function tickValues(scale, count) { | ||
return scale.ticks ? scale.ticks(count) : scale.domain(); | ||
} | ||
/** | ||
* Filter a set of candidate tick values, ensuring that only tick values | ||
* that lie within the scale range are included. | ||
* @param {Scale} scale - The scale for which to generate tick values. | ||
* @param {Array<*>} ticks - The candidate tick values. | ||
* @param {*} count - The tick count or interval function. | ||
* @return {Array<*>} - The filtered tick values. | ||
*/ | ||
function validTicks(scale$$1, ticks, count) { | ||
var range$$1 = scale$$1.range(), | ||
lo = range$$1[0], | ||
hi = vegaUtil.peek(range$$1); | ||
if (lo > hi) { | ||
range$$1 = hi; | ||
hi = lo; | ||
lo = range$$1; | ||
/** | ||
* Generate a label format function for a scale. If the scale has a | ||
* 'tickFormat' method, it will be used to generate the formatter, with the | ||
* count and specifier arguments passed as parameters. If the scale lacks a | ||
* 'tickFormat' method, the returned formatter performs simple string coercion. | ||
* If the input scale is a logarithmic scale and the format specifier does not | ||
* indicate a desired decimal precision, a special variable precision formatter | ||
* that automatically trims trailing zeroes will be generated. | ||
* @param {Scale} scale - The scale for which to generate the label formatter. | ||
* @param {*} [count] - The approximate number of desired ticks. | ||
* @param {string} [specifier] - The format specifier. Must be a legal d3 4.0 | ||
* specifier string (see https://github.com/d3/d3-format#formatSpecifier). | ||
* @return {function(*):string} - The generated label formatter. | ||
*/ | ||
function tickFormat(scale, count, specifier) { | ||
var format = scale.tickFormat ? scale.tickFormat(count, specifier) | ||
: specifier ? d3Format.format(specifier) | ||
: String; | ||
return (scale.type === Log) | ||
? filter(format, variablePrecision(specifier)) | ||
: format; | ||
} | ||
ticks = ticks.filter(function(v) { | ||
v = scale$$1(v); | ||
return !(v < lo || v > hi) | ||
}); | ||
function filter(sourceFormat, targetFormat) { | ||
return function(_) { | ||
return sourceFormat(_) ? targetFormat(_) : ''; | ||
}; | ||
} | ||
if (count > 0 && ticks.length > 1) { | ||
var endpoints = [ticks[0], vegaUtil.peek(ticks)]; | ||
while (ticks.length > count && ticks.length >= 3) { | ||
ticks = ticks.filter(function(_, i) { return !(i % 2); }); | ||
function variablePrecision(specifier) { | ||
var s = d3Format.formatSpecifier(specifier || ','); | ||
if (s.precision == null) { | ||
s.precision = 12; | ||
switch (s.type) { | ||
case '%': s.precision -= 2; break; | ||
case 'e': s.precision -= 1; break; | ||
} | ||
return trimZeroes( | ||
d3Format.format(s), // number format | ||
d3Format.format('.1f')(1)[1] // decimal point character | ||
); | ||
} else { | ||
return d3Format.format(s); | ||
} | ||
if (ticks.length < 3) { | ||
ticks = endpoints; | ||
} | ||
} | ||
return ticks; | ||
} | ||
function trimZeroes(format, decimalChar) { | ||
return function(x) { | ||
var str = format(x), | ||
dec = str.indexOf(decimalChar), | ||
idx, end; | ||
/** | ||
* Generate tick values for the given scale and approximate tick count or | ||
* interval value. If the scale has a 'ticks' method, it will be used to | ||
* generate the ticks, with the count argument passed as a parameter. If the | ||
* scale lacks a 'ticks' method, the full scale domain will be returned. | ||
* @param {Scale} scale - The scale for which to generate tick values. | ||
* @param {*} [count] - The approximate number of desired ticks. | ||
* @return {Array<*>} - The generated tick values. | ||
*/ | ||
function tickValues(scale$$1, count) { | ||
return scale$$1.ticks ? scale$$1.ticks(count) : scale$$1.domain(); | ||
} | ||
if (dec < 0) return str; | ||
/** | ||
* Generate a label format function for a scale. If the scale has a | ||
* 'tickFormat' method, it will be used to generate the formatter, with the | ||
* count and specifier arguments passed as parameters. If the scale lacks a | ||
* 'tickFormat' method, the returned formatter performs simple string coercion. | ||
* If the input scale is a logarithmic scale and the format specifier does not | ||
* indicate a desired decimal precision, a special variable precision formatter | ||
* that automatically trims trailing zeroes will be generated. | ||
* @param {Scale} scale - The scale for which to generate the label formatter. | ||
* @param {*} [count] - The approximate number of desired ticks. | ||
* @param {string} [specifier] - The format specifier. Must be a legal d3 4.0 | ||
* specifier string (see https://github.com/d3/d3-format#formatSpecifier). | ||
* @return {function(*):string} - The generated label formatter. | ||
*/ | ||
function tickFormat(scale$$1, count, specifier) { | ||
var format$$1 = scale$$1.tickFormat | ||
? scale$$1.tickFormat(count, specifier) | ||
: String; | ||
idx = rightmostDigit(str, dec); | ||
end = idx < str.length ? str.slice(idx) : ''; | ||
while (--idx > dec) if (str[idx] !== '0') { ++idx; break; } | ||
return (scale$$1.type === Log) | ||
? filter(format$$1, variablePrecision(specifier)) | ||
: format$$1; | ||
} | ||
return str.slice(0, idx) + end; | ||
}; | ||
} | ||
function filter(sourceFormat, targetFormat) { | ||
return function(_) { | ||
return sourceFormat(_) ? targetFormat(_) : ''; | ||
}; | ||
} | ||
function rightmostDigit(str, dec) { | ||
var i = str.lastIndexOf('e'), c; | ||
if (i > 0) return i; | ||
for (i=str.length; --i > dec;) { | ||
c = str.charCodeAt(i); | ||
if (c >= 48 && c <= 57) return i + 1; // is digit | ||
} | ||
} | ||
function variablePrecision(specifier) { | ||
var s = d3Format.formatSpecifier(specifier || ','); | ||
/** | ||
* Generates axis ticks for visualizing a spatial scale. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
* @param {Scale} params.scale - The scale to generate ticks for. | ||
* @param {*} [params.count=10] - The approximate number of ticks, or | ||
* desired tick interval, to use. | ||
* @param {Array<*>} [params.values] - The exact tick values to use. | ||
* These must be legal domain values for the provided scale. | ||
* If provided, the count argument is ignored. | ||
* @param {function(*):string} [params.formatSpecifier] - A format specifier | ||
* to use in conjunction with scale.tickFormat. Legal values are | ||
* any valid d3 4.0 format specifier. | ||
* @param {function(*):string} [params.format] - The format function to use. | ||
* If provided, the formatSpecifier argument is ignored. | ||
*/ | ||
function AxisTicks(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
} | ||
if (s.precision == null) { | ||
s.precision = 12; | ||
switch (s.type) { | ||
case '%': s.precision -= 2; break; | ||
case 'e': s.precision -= 1; break; | ||
var prototype = vegaUtil.inherits(AxisTicks, vegaDataflow.Transform); | ||
prototype.transform = function(_, pulse) { | ||
if (this.value && !_.modified()) { | ||
return pulse.StopPropagation; | ||
} | ||
return trimZeroes( | ||
d3Format.format(s), // number format | ||
d3Format.format('.1f')(1)[1] // decimal point character | ||
); | ||
} else { | ||
return d3Format.format(s); | ||
} | ||
} | ||
function trimZeroes(format$$1, decimalChar) { | ||
return function(x) { | ||
var str = format$$1(x), | ||
dec = str.indexOf(decimalChar), | ||
idx, end; | ||
var out = pulse.fork(pulse.NO_SOURCE | pulse.NO_FIELDS), | ||
ticks = this.value, | ||
scale = _.scale, | ||
count = _.count == null ? (_.values ? _.values.length : 10) : tickCount(scale, _.count), | ||
format = _.format || tickFormat(scale, count, _.formatSpecifier), | ||
values = _.values ? validTicks(scale, _.values, count) : tickValues(scale, count); | ||
if (dec < 0) return str; | ||
if (ticks) out.rem = ticks; | ||
idx = rightmostDigit(str, dec); | ||
end = idx < str.length ? str.slice(idx) : ''; | ||
while (--idx > dec) if (str[idx] !== '0') { ++idx; break; } | ||
ticks = values.map(function(value, i) { | ||
return vegaDataflow.ingest({ | ||
index: i / (values.length - 1), | ||
value: value, | ||
label: format(value) | ||
}); | ||
}); | ||
return str.slice(0, idx) + end; | ||
if (_.extra) { | ||
// add an extra tick pegged to the initial domain value | ||
// this is used to generate axes with 'binned' domains | ||
ticks.push(vegaDataflow.ingest({ | ||
index: -1, | ||
extra: {value: ticks[0].value}, | ||
label: '' | ||
})); | ||
} | ||
out.source = ticks; | ||
out.add = ticks; | ||
this.value = ticks; | ||
return out; | ||
}; | ||
} | ||
function rightmostDigit(str, dec) { | ||
var i = str.lastIndexOf('e'), c; | ||
if (i > 0) return i; | ||
for (i=str.length; --i > dec;) { | ||
c = str.charCodeAt(i); | ||
if (c >= 48 && c <= 57) return i + 1; // is digit | ||
/** | ||
* Joins a set of data elements against a set of visual items. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
* @param {function(object): object} [params.item] - An item generator function. | ||
* @param {function(object): *} [params.key] - The key field associating data and visual items. | ||
*/ | ||
function DataJoin(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
} | ||
} | ||
/** | ||
* Generates axis ticks for visualizing a spatial scale. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
* @param {Scale} params.scale - The scale to generate ticks for. | ||
* @param {*} [params.count=10] - The approximate number of ticks, or | ||
* desired tick interval, to use. | ||
* @param {Array<*>} [params.values] - The exact tick values to use. | ||
* These must be legal domain values for the provided scale. | ||
* If provided, the count argument is ignored. | ||
* @param {function(*):string} [params.formatSpecifier] - A format specifier | ||
* to use in conjunction with scale.tickFormat. Legal values are | ||
* any valid d3 4.0 format specifier. | ||
* @param {function(*):string} [params.format] - The format function to use. | ||
* If provided, the formatSpecifier argument is ignored. | ||
*/ | ||
function AxisTicks(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
} | ||
var prototype$1 = vegaUtil.inherits(DataJoin, vegaDataflow.Transform); | ||
var prototype = vegaUtil.inherits(AxisTicks, vegaDataflow.Transform); | ||
function defaultItemCreate() { | ||
return vegaDataflow.ingest({}); | ||
} | ||
prototype.transform = function(_, pulse) { | ||
if (this.value && !_.modified()) { | ||
return pulse.StopPropagation; | ||
function isExit(t) { | ||
return t.exit; | ||
} | ||
var out = pulse.fork(pulse.NO_SOURCE | pulse.NO_FIELDS), | ||
ticks = this.value, | ||
scale$$1 = _.scale, | ||
count = _.count == null ? (_.values ? _.values.length : 10) : tickCount(scale$$1, _.count), | ||
format$$1 = _.format || tickFormat(scale$$1, count, _.formatSpecifier), | ||
values = _.values ? validTicks(scale$$1, _.values, count) : tickValues(scale$$1, count); | ||
prototype$1.transform = function(_, pulse) { | ||
var df = pulse.dataflow, | ||
out = pulse.fork(pulse.NO_SOURCE | pulse.NO_FIELDS), | ||
item = _.item || defaultItemCreate, | ||
key = _.key || vegaDataflow.tupleid, | ||
map = this.value; | ||
if (ticks) out.rem = ticks; | ||
// prevent transient (e.g., hover) requests from | ||
// cascading across marks derived from marks | ||
if (vegaUtil.isArray(out.encode)) { | ||
out.encode = null; | ||
} | ||
ticks = values.map(function(value, i) { | ||
return vegaDataflow.ingest({ | ||
index: i / (values.length - 1), | ||
value: value, | ||
label: format$$1(value) | ||
}); | ||
}); | ||
if (map && (_.modified('key') || pulse.modified(key))) { | ||
vegaUtil.error('DataJoin does not support modified key function or fields.'); | ||
} | ||
if (_.extra) { | ||
// add an extra tick pegged to the initial domain value | ||
// this is used to generate axes with 'binned' domains | ||
ticks.push(vegaDataflow.ingest({ | ||
index: -1, | ||
extra: {value: ticks[0].value}, | ||
label: '' | ||
})); | ||
} | ||
if (!map) { | ||
pulse = pulse.addAll(); | ||
this.value = map = vegaUtil.fastmap().test(isExit); | ||
map.lookup = function(t) { return map.get(key(t)); }; | ||
} | ||
out.source = ticks; | ||
out.add = ticks; | ||
this.value = ticks; | ||
pulse.visit(pulse.ADD, function(t) { | ||
var k = key(t), | ||
x = map.get(k); | ||
return out; | ||
}; | ||
if (x) { | ||
if (x.exit) { | ||
map.empty--; | ||
out.add.push(x); | ||
} else { | ||
out.mod.push(x); | ||
} | ||
} else { | ||
map.set(k, (x = item(t))); | ||
out.add.push(x); | ||
} | ||
/** | ||
* Joins a set of data elements against a set of visual items. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
* @param {function(object): object} [params.item] - An item generator function. | ||
* @param {function(object): *} [params.key] - The key field associating data and visual items. | ||
*/ | ||
function DataJoin(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
} | ||
x.datum = t; | ||
x.exit = false; | ||
}); | ||
var prototype$1 = vegaUtil.inherits(DataJoin, vegaDataflow.Transform); | ||
pulse.visit(pulse.MOD, function(t) { | ||
var k = key(t), | ||
x = map.get(k); | ||
function defaultItemCreate() { | ||
return vegaDataflow.ingest({}); | ||
} | ||
if (x) { | ||
x.datum = t; | ||
out.mod.push(x); | ||
} | ||
}); | ||
function isExit(t) { | ||
return t.exit; | ||
} | ||
pulse.visit(pulse.REM, function(t) { | ||
var k = key(t), | ||
x = map.get(k); | ||
prototype$1.transform = function(_, pulse) { | ||
var df = pulse.dataflow, | ||
out = pulse.fork(pulse.NO_SOURCE | pulse.NO_FIELDS), | ||
item = _.item || defaultItemCreate, | ||
key = _.key || vegaDataflow.tupleid, | ||
map = this.value; | ||
if (t === x.datum && !x.exit) { | ||
out.rem.push(x); | ||
x.exit = true; | ||
++map.empty; | ||
} | ||
}); | ||
// prevent transient (e.g., hover) requests from | ||
// cascading across marks derived from marks | ||
if (vegaUtil.isArray(out.encode)) { | ||
out.encode = null; | ||
} | ||
if (pulse.changed(pulse.ADD_MOD)) out.modifies('datum'); | ||
if (map && (_.modified('key') || pulse.modified(key))) { | ||
vegaUtil.error('DataJoin does not support modified key function or fields.'); | ||
} | ||
if (_.clean && map.empty > df.cleanThreshold) df.runAfter(map.clean); | ||
if (!map) { | ||
pulse = pulse.addAll(); | ||
this.value = map = vegaUtil.fastmap().test(isExit); | ||
map.lookup = function(t) { return map.get(key(t)); }; | ||
return out; | ||
}; | ||
/** | ||
* Invokes encoding functions for visual items. | ||
* @constructor | ||
* @param {object} params - The parameters to the encoding functions. This | ||
* parameter object will be passed through to all invoked encoding functions. | ||
* @param {object} param.encoders - The encoding functions | ||
* @param {function(object, object): boolean} [param.encoders.update] - Update encoding set | ||
* @param {function(object, object): boolean} [param.encoders.enter] - Enter encoding set | ||
* @param {function(object, object): boolean} [param.encoders.exit] - Exit encoding set | ||
*/ | ||
function Encode(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
} | ||
pulse.visit(pulse.ADD, function(t) { | ||
var k = key(t), | ||
x = map.get(k); | ||
var prototype$2 = vegaUtil.inherits(Encode, vegaDataflow.Transform); | ||
if (x) { | ||
if (x.exit) { | ||
map.empty--; | ||
out.add.push(x); | ||
prototype$2.transform = function(_, pulse) { | ||
var out = pulse.fork(pulse.ADD_REM), | ||
encoders = _.encoders, | ||
encode = pulse.encode; | ||
// if an array, the encode directive includes additional sets | ||
// that must be defined in order for the primary set to be invoked | ||
// e.g., only run the update set if the hover set is defined | ||
if (vegaUtil.isArray(encode)) { | ||
if (out.changed() || encode.every(function(e) { return encoders[e]; })) { | ||
encode = encode[0]; | ||
out.encode = null; // consume targeted encode directive | ||
} else { | ||
out.mod.push(x); | ||
return pulse.StopPropagation; | ||
} | ||
} else { | ||
map.set(k, (x = item(t))); | ||
out.add.push(x); | ||
} | ||
x.datum = t; | ||
x.exit = false; | ||
}); | ||
// marshall encoder functions | ||
var reenter = encode === 'enter', | ||
update = encoders.update || vegaUtil.falsy, | ||
enter = encoders.enter || vegaUtil.falsy, | ||
exit = encoders.exit || vegaUtil.falsy, | ||
set = (encode && !reenter ? encoders[encode] : update) || vegaUtil.falsy; | ||
pulse.visit(pulse.MOD, function(t) { | ||
var k = key(t), | ||
x = map.get(k); | ||
if (pulse.changed(pulse.ADD)) { | ||
pulse.visit(pulse.ADD, function(t) { | ||
enter(t, _); | ||
update(t, _); | ||
if (set !== vegaUtil.falsy && set !== update) set(t, _); | ||
}); | ||
out.modifies(enter.output); | ||
out.modifies(update.output); | ||
if (set !== vegaUtil.falsy && set !== update) out.modifies(set.output); | ||
} | ||
if (x) { | ||
x.datum = t; | ||
out.mod.push(x); | ||
if (pulse.changed(pulse.REM) && exit !== vegaUtil.falsy) { | ||
pulse.visit(pulse.REM, function(t) { exit(t, _); }); | ||
out.modifies(exit.output); | ||
} | ||
}); | ||
pulse.visit(pulse.REM, function(t) { | ||
var k = key(t), | ||
x = map.get(k); | ||
if (t === x.datum && !x.exit) { | ||
out.rem.push(x); | ||
x.exit = true; | ||
++map.empty; | ||
if (reenter || set !== vegaUtil.falsy) { | ||
var flag = pulse.MOD | (_.modified() ? pulse.REFLOW : 0); | ||
if (reenter) { | ||
pulse.visit(flag, function(t) { | ||
var mod = enter(t, _); | ||
if (set(t, _) || mod) out.mod.push(t); | ||
}); | ||
if (out.mod.length) out.modifies(enter.output); | ||
} else { | ||
pulse.visit(flag, function(t) { | ||
if (set(t, _)) out.mod.push(t); | ||
}); | ||
} | ||
if (out.mod.length) out.modifies(set.output); | ||
} | ||
}); | ||
if (pulse.changed(pulse.ADD_MOD)) out.modifies('datum'); | ||
return out.changed() ? out : pulse.StopPropagation; | ||
}; | ||
if (_.clean && map.empty > df.cleanThreshold) df.runAfter(map.clean); | ||
var Symbols = 'symbol'; | ||
var Discrete = 'discrete'; | ||
var Gradient = 'gradient'; | ||
return out; | ||
}; | ||
var symbols = {}; | ||
symbols[Quantile] = quantileSymbols; | ||
symbols[Quantize] = quantizeSymbols; | ||
symbols[Threshold] = thresholdSymbols; | ||
symbols[BinLinear] = symbols[BinOrdinal] = binSymbols; | ||
/** | ||
* Invokes encoding functions for visual items. | ||
* @constructor | ||
* @param {object} params - The parameters to the encoding functions. This | ||
* parameter object will be passed through to all invoked encoding functions. | ||
* @param {object} param.encoders - The encoding functions | ||
* @param {function(object, object): boolean} [param.encoders.update] - Update encoding set | ||
* @param {function(object, object): boolean} [param.encoders.enter] - Enter encoding set | ||
* @param {function(object, object): boolean} [param.encoders.exit] - Exit encoding set | ||
*/ | ||
function Encode(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
} | ||
function labelValues(scale, count) { | ||
var values = symbols[scale.type]; | ||
return values ? values(scale) : tickValues(scale, count); | ||
} | ||
var prototype$2 = vegaUtil.inherits(Encode, vegaDataflow.Transform); | ||
function quantizeSymbols(scale) { | ||
var domain = scale.domain(), | ||
x0 = domain[0], | ||
x1 = vegaUtil.peek(domain), | ||
n = scale.range().length, | ||
values = new Array(n), | ||
i = 0; | ||
prototype$2.transform = function(_, pulse) { | ||
var out = pulse.fork(pulse.ADD_REM), | ||
encoders = _.encoders, | ||
encode = pulse.encode; | ||
values[0] = -Infinity; | ||
while (++i < n) values[i] = (i * x1 - (i - n) * x0) / n; | ||
values.max = +Infinity; | ||
// if an array, the encode directive includes additional sets | ||
// that must be defined in order for the primary set to be invoked | ||
// e.g., only run the update set if the hover set is defined | ||
if (vegaUtil.isArray(encode)) { | ||
if (out.changed() || encode.every(function(e) { return encoders[e]; })) { | ||
encode = encode[0]; | ||
out.encode = null; // consume targeted encode directive | ||
} else { | ||
return pulse.StopPropagation; | ||
} | ||
return values; | ||
} | ||
// marshall encoder functions | ||
var reenter = encode === 'enter', | ||
update = encoders.update || vegaUtil.falsy, | ||
enter = encoders.enter || vegaUtil.falsy, | ||
exit = encoders.exit || vegaUtil.falsy, | ||
set = (encode && !reenter ? encoders[encode] : update) || vegaUtil.falsy; | ||
function quantileSymbols(scale) { | ||
var values = [-Infinity].concat(scale.quantiles()); | ||
values.max = +Infinity; | ||
if (pulse.changed(pulse.ADD)) { | ||
pulse.visit(pulse.ADD, function(t) { | ||
enter(t, _); | ||
update(t, _); | ||
if (set !== vegaUtil.falsy && set !== update) set(t, _); | ||
}); | ||
out.modifies(enter.output); | ||
out.modifies(update.output); | ||
if (set !== vegaUtil.falsy && set !== update) out.modifies(set.output); | ||
return values; | ||
} | ||
if (pulse.changed(pulse.REM) && exit !== vegaUtil.falsy) { | ||
pulse.visit(pulse.REM, function(t) { exit(t, _); }); | ||
out.modifies(exit.output); | ||
function thresholdSymbols(scale) { | ||
var values = [-Infinity].concat(scale.domain()); | ||
values.max = +Infinity; | ||
return values; | ||
} | ||
if (reenter || set !== vegaUtil.falsy) { | ||
var flag = pulse.MOD | (_.modified() ? pulse.REFLOW : 0); | ||
if (reenter) { | ||
pulse.visit(flag, function(t) { | ||
var mod = enter(t, _); | ||
if (set(t, _) || mod) out.mod.push(t); | ||
}); | ||
if (out.mod.length) out.modifies(enter.output); | ||
} else { | ||
pulse.visit(flag, function(t) { | ||
if (set(t, _)) out.mod.push(t); | ||
}); | ||
function binSymbols(scale) { | ||
var values = scale.domain(); | ||
values.max = values.pop(); | ||
return values; | ||
} | ||
function labelFormat(scale, format, type) { | ||
return type === Symbols && symbols[scale.type] ? formatRange(format) | ||
: type === Discrete ? formatDiscrete(format) | ||
: formatPoint(format); | ||
} | ||
function formatRange(format) { | ||
return function(value, index, array) { | ||
var limit = array[index + 1] || array.max || +Infinity, | ||
lo = formatValue(value, format), | ||
hi = formatValue(limit, format); | ||
return lo && hi ? lo + '\u2013' + hi : hi ? '< ' + hi : '\u2265 ' + lo; | ||
}; | ||
} | ||
function formatDiscrete(format) { | ||
return function(value, index) { | ||
return index ? format(value) : null; | ||
} | ||
if (out.mod.length) out.modifies(set.output); | ||
} | ||
return out.changed() ? out : pulse.StopPropagation; | ||
}; | ||
function formatPoint(format) { | ||
return function(value) { | ||
return format(value); | ||
}; | ||
} | ||
var discrete = {}; | ||
discrete[Quantile] = quantile; | ||
discrete[Quantize] = quantize; | ||
discrete[Threshold] = threshold; | ||
discrete[BinLinear] = bin; | ||
discrete[BinOrdinal] = bin; | ||
function formatValue(value, format) { | ||
return isFinite(value) ? format(value) : null; | ||
} | ||
function labelValues(scale$$1, count, gradient) { | ||
if (gradient) return scale$$1.domain(); | ||
var values = discrete[scale$$1.type]; | ||
return values ? values(scale$$1) : tickValues(scale$$1, count); | ||
} | ||
function labelFraction(scale) { | ||
var domain = scale.domain(), | ||
count = domain.length - 1, | ||
lo = +domain[0], | ||
hi = +vegaUtil.peek(domain), | ||
span = hi - lo; | ||
function quantize(scale$$1) { | ||
var domain = scale$$1.domain(), | ||
x0 = domain[0], | ||
x1 = vegaUtil.peek(domain), | ||
n = scale$$1.range().length, | ||
values = new Array(n), | ||
i = 0; | ||
if (scale.type === Threshold) { | ||
var adjust = count ? span / count : 0.1; | ||
lo -= adjust; | ||
hi += adjust; | ||
span = hi - lo; | ||
} | ||
values[0] = -Infinity; | ||
while (++i < n) values[i] = (i * x1 - (i - n) * x0) / n; | ||
values.max = +Infinity; | ||
return function(value) { | ||
return (value - lo) / span; | ||
}; | ||
} | ||
return values; | ||
} | ||
/** | ||
* Generates legend entries for visualizing a scale. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
* @param {Scale} params.scale - The scale to generate items for. | ||
* @param {*} [params.count=5] - The approximate number of items, or | ||
* desired tick interval, to use. | ||
* @param {Array<*>} [params.values] - The exact tick values to use. | ||
* These must be legal domain values for the provided scale. | ||
* If provided, the count argument is ignored. | ||
* @param {string} [params.formatSpecifier] - A format specifier | ||
* to use in conjunction with scale.tickFormat. Legal values are | ||
* any valid D3 format specifier string. | ||
* @param {function(*):string} [params.format] - The format function to use. | ||
* If provided, the formatSpecifier argument is ignored. | ||
*/ | ||
function LegendEntries(params) { | ||
vegaDataflow.Transform.call(this, [], params); | ||
} | ||
function quantile(scale$$1) { | ||
var values = [-Infinity].concat(scale$$1.quantiles()); | ||
values.max = +Infinity; | ||
var prototype$3 = vegaUtil.inherits(LegendEntries, vegaDataflow.Transform); | ||
return values; | ||
} | ||
prototype$3.transform = function(_, pulse) { | ||
if (this.value != null && !_.modified()) { | ||
return pulse.StopPropagation; | ||
} | ||
function threshold(scale$$1) { | ||
var values = [-Infinity].concat(scale$$1.domain()); | ||
values.max = +Infinity; | ||
var out = pulse.fork(pulse.NO_SOURCE | pulse.NO_FIELDS), | ||
items = this.value, | ||
type = _.type || Symbols, | ||
scale = _.scale, | ||
count = _.count == null ? 5 : tickCount(scale, _.count), | ||
format = _.format || tickFormat(scale, count, _.formatSpecifier), | ||
values = _.values || labelValues(scale, count, type), | ||
domain, fraction, size, offset; | ||
return values; | ||
} | ||
format = labelFormat(scale, format, type); | ||
if (items) out.rem = items; | ||
function bin(scale$$1) { | ||
var values = scale$$1.domain(); | ||
values.max = values.pop(); | ||
if (type === Symbols) { | ||
if (vegaUtil.isFunction(size = _.size)) { | ||
// if first value maps to size zero, remove from list (vega#717) | ||
if (!_.values && scale(values[0]) === 0) { | ||
values = values.slice(1); | ||
} | ||
// compute size offset for legend entries | ||
offset = values.reduce(function(max, value) { | ||
return Math.max(max, size(value, _)); | ||
}, 0); | ||
} else { | ||
size = vegaUtil.constant(offset = size || 8); | ||
} | ||
return values; | ||
} | ||
items = values.map(function(value, index) { | ||
return vegaDataflow.ingest({ | ||
index: index, | ||
label: format(value, index, values), | ||
value: value, | ||
offset: offset, | ||
size: size(value, _) | ||
}); | ||
}); | ||
} | ||
function labelFormat(scale$$1, format$$1) { | ||
return discrete[scale$$1.type] ? formatRange(format$$1) : formatPoint(format$$1); | ||
} | ||
else if (type === Gradient) { | ||
domain = _.values ? scale.domain() : values, | ||
fraction = vegaScale.scaleFraction(scale, domain[0], vegaUtil.peek(domain)); | ||
function formatRange(format$$1) { | ||
return function(value, index, array) { | ||
var limit = array[index + 1] || array.max || +Infinity, | ||
lo = formatValue(value, format$$1), | ||
hi = formatValue(limit, format$$1); | ||
return lo && hi ? lo + '\u2013' + hi : hi ? '< ' + hi : '\u2265 ' + lo; | ||
}; | ||
} | ||
items = values.map(function(value, index) { | ||
return vegaDataflow.ingest({ | ||
index: index, | ||
label: format(value, index, values), | ||
value: value, | ||
perc: fraction(value) | ||
}); | ||
}); | ||
} | ||
function formatValue(value, format$$1) { | ||
return isFinite(value) ? format$$1(value) : null; | ||
} | ||
else { | ||
size = values.length - 1; | ||
fraction = labelFraction(scale); | ||
function formatPoint(format$$1) { | ||
return function(value) { | ||
return format$$1(value); | ||
items = values.map(function(value, index) { | ||
return vegaDataflow.ingest({ | ||
index: index, | ||
label: format(value, index, values), | ||
value: value, | ||
perc: index ? fraction(value) : 0, | ||
perc2: index === size ? 1 : fraction(values[index+1]) | ||
}); | ||
}); | ||
} | ||
out.source = items; | ||
out.add = items; | ||
this.value = items; | ||
return out; | ||
}; | ||
} | ||
/** | ||
* Generates legend entries for visualizing a scale. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
* @param {Scale} params.scale - The scale to generate items for. | ||
* @param {*} [params.count=10] - The approximate number of items, or | ||
* desired tick interval, to use. | ||
* @param {Array<*>} [params.values] - The exact tick values to use. | ||
* These must be legal domain values for the provided scale. | ||
* If provided, the count argument is ignored. | ||
* @param {function(*):string} [params.formatSpecifier] - A format specifier | ||
* to use in conjunction with scale.tickFormat. Legal values are | ||
* any valid d3 4.0 format specifier. | ||
* @param {function(*):string} [params.format] - The format function to use. | ||
* If provided, the formatSpecifier argument is ignored. | ||
*/ | ||
function LegendEntries(params) { | ||
vegaDataflow.Transform.call(this, [], params); | ||
} | ||
var Paths = vegaUtil.fastmap({ | ||
'line': line, | ||
'line-radial': lineR, | ||
'arc': arc, | ||
'arc-radial': arcR, | ||
'curve': curve, | ||
'curve-radial': curveR, | ||
'orthogonal-horizontal': orthoX, | ||
'orthogonal-vertical': orthoY, | ||
'orthogonal-radial': orthoR, | ||
'diagonal-horizontal': diagonalX, | ||
'diagonal-vertical': diagonalY, | ||
'diagonal-radial': diagonalR | ||
}); | ||
var prototype$3 = vegaUtil.inherits(LegendEntries, vegaDataflow.Transform); | ||
function sourceX(t) { return t.source.x; } | ||
function sourceY(t) { return t.source.y; } | ||
function targetX(t) { return t.target.x; } | ||
function targetY(t) { return t.target.y; } | ||
prototype$3.transform = function(_, pulse) { | ||
if (this.value != null && !_.modified()) { | ||
return pulse.StopPropagation; | ||
/** | ||
* Layout paths linking source and target elements. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
*/ | ||
function LinkPath(params) { | ||
vegaDataflow.Transform.call(this, {}, params); | ||
} | ||
var out = pulse.fork(pulse.NO_SOURCE | pulse.NO_FIELDS), | ||
total = 0, | ||
items = this.value, | ||
grad = _.type === 'gradient', | ||
scale$$1 = _.scale, | ||
count = _.count == null ? 5 : tickCount(scale$$1, _.count), | ||
format$$1 = _.format || tickFormat(scale$$1, count, _.formatSpecifier), | ||
values = _.values || labelValues(scale$$1, count, grad); | ||
LinkPath.Definition = { | ||
"type": "LinkPath", | ||
"metadata": {"modifies": true}, | ||
"params": [ | ||
{ "name": "sourceX", "type": "field", "default": "source.x" }, | ||
{ "name": "sourceY", "type": "field", "default": "source.y" }, | ||
{ "name": "targetX", "type": "field", "default": "target.x" }, | ||
{ "name": "targetY", "type": "field", "default": "target.y" }, | ||
{ "name": "orient", "type": "enum", "default": "vertical", | ||
"values": ["horizontal", "vertical", "radial"] }, | ||
{ "name": "shape", "type": "enum", "default": "line", | ||
"values": ["line", "arc", "curve", "diagonal", "orthogonal"] }, | ||
{ "name": "as", "type": "string", "default": "path" } | ||
] | ||
}; | ||
format$$1 = labelFormat(scale$$1, format$$1); | ||
if (items) out.rem = items; | ||
var prototype$4 = vegaUtil.inherits(LinkPath, vegaDataflow.Transform); | ||
if (grad) { | ||
var domain = _.values ? scale$$1.domain() : values, | ||
fraction = vegaScale.scaleFraction(scale$$1, domain[0], vegaUtil.peek(domain)); | ||
} else { | ||
var size = _.size, | ||
offset; | ||
if (vegaUtil.isFunction(size)) { | ||
// if first value maps to size zero, remove from list (vega#717) | ||
if (!_.values && scale$$1(values[0]) === 0) { | ||
values = values.slice(1); | ||
} | ||
// compute size offset for legend entries | ||
offset = values.reduce(function(max, value) { | ||
return Math.max(max, size(value, _)); | ||
}, 0); | ||
} else { | ||
size = vegaUtil.constant(offset = size || 8); | ||
prototype$4.transform = function(_, pulse) { | ||
var sx = _.sourceX || sourceX, | ||
sy = _.sourceY || sourceY, | ||
tx = _.targetX || targetX, | ||
ty = _.targetY || targetY, | ||
as = _.as || 'path', | ||
orient = _.orient || 'vertical', | ||
shape = _.shape || 'line', | ||
path = Paths.get(shape + '-' + orient) || Paths.get(shape); | ||
if (!path) { | ||
vegaUtil.error('LinkPath unsupported type: ' + _.shape | ||
+ (_.orient ? '-' + _.orient : '')); | ||
} | ||
} | ||
items = values.map(function(value, index) { | ||
var t = vegaDataflow.ingest({ | ||
index: index, | ||
label: format$$1(value, index, values), | ||
value: value | ||
pulse.visit(pulse.SOURCE, function(t) { | ||
t[as] = path(sx(t), sy(t), tx(t), ty(t)); | ||
}); | ||
if (grad) { | ||
t.perc = fraction(value); | ||
} else { | ||
t.offset = offset; | ||
t.size = size(value, _); | ||
t.total = Math.round(total); | ||
total += t.size; | ||
} | ||
return t; | ||
}); | ||
return pulse.reflow(_.modified()).modifies(as); | ||
}; | ||
out.source = items; | ||
out.add = items; | ||
this.value = items; | ||
// -- Link Path Generation Methods ----- | ||
return out; | ||
}; | ||
function line(sx, sy, tx, ty) { | ||
return 'M' + sx + ',' + sy + | ||
'L' + tx + ',' + ty; | ||
} | ||
var Paths = vegaUtil.fastmap({ | ||
'line': line, | ||
'line-radial': lineR, | ||
'arc': arc, | ||
'arc-radial': arcR, | ||
'curve': curve, | ||
'curve-radial': curveR, | ||
'orthogonal-horizontal': orthoX, | ||
'orthogonal-vertical': orthoY, | ||
'orthogonal-radial': orthoR, | ||
'diagonal-horizontal': diagonalX, | ||
'diagonal-vertical': diagonalY, | ||
'diagonal-radial': diagonalR | ||
}); | ||
function lineR(sa, sr, ta, tr) { | ||
return line( | ||
sr * Math.cos(sa), sr * Math.sin(sa), | ||
tr * Math.cos(ta), tr * Math.sin(ta) | ||
); | ||
} | ||
function sourceX(t) { return t.source.x; } | ||
function sourceY(t) { return t.source.y; } | ||
function targetX(t) { return t.target.x; } | ||
function targetY(t) { return t.target.y; } | ||
function arc(sx, sy, tx, ty) { | ||
var dx = tx - sx, | ||
dy = ty - sy, | ||
rr = Math.sqrt(dx * dx + dy * dy) / 2, | ||
ra = 180 * Math.atan2(dy, dx) / Math.PI; | ||
return 'M' + sx + ',' + sy + | ||
'A' + rr + ',' + rr + | ||
' ' + ra + ' 0 1' + | ||
' ' + tx + ',' + ty; | ||
} | ||
/** | ||
* Layout paths linking source and target elements. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
*/ | ||
function LinkPath(params) { | ||
vegaDataflow.Transform.call(this, {}, params); | ||
} | ||
function arcR(sa, sr, ta, tr) { | ||
return arc( | ||
sr * Math.cos(sa), sr * Math.sin(sa), | ||
tr * Math.cos(ta), tr * Math.sin(ta) | ||
); | ||
} | ||
LinkPath.Definition = { | ||
"type": "LinkPath", | ||
"metadata": {"modifies": true}, | ||
"params": [ | ||
{ "name": "sourceX", "type": "field", "default": "source.x" }, | ||
{ "name": "sourceY", "type": "field", "default": "source.y" }, | ||
{ "name": "targetX", "type": "field", "default": "target.x" }, | ||
{ "name": "targetY", "type": "field", "default": "target.y" }, | ||
{ "name": "orient", "type": "enum", "default": "vertical", | ||
"values": ["horizontal", "vertical", "radial"] }, | ||
{ "name": "shape", "type": "enum", "default": "line", | ||
"values": ["line", "arc", "curve", "diagonal", "orthogonal"] }, | ||
{ "name": "as", "type": "string", "default": "path" } | ||
] | ||
}; | ||
function curve(sx, sy, tx, ty) { | ||
var dx = tx - sx, | ||
dy = ty - sy, | ||
ix = 0.2 * (dx + dy), | ||
iy = 0.2 * (dy - dx); | ||
return 'M' + sx + ',' + sy + | ||
'C' + (sx+ix) + ',' + (sy+iy) + | ||
' ' + (tx+iy) + ',' + (ty-ix) + | ||
' ' + tx + ',' + ty; | ||
} | ||
var prototype$4 = vegaUtil.inherits(LinkPath, vegaDataflow.Transform); | ||
function curveR(sa, sr, ta, tr) { | ||
return curve( | ||
sr * Math.cos(sa), sr * Math.sin(sa), | ||
tr * Math.cos(ta), tr * Math.sin(ta) | ||
); | ||
} | ||
prototype$4.transform = function(_, pulse) { | ||
var sx = _.sourceX || sourceX, | ||
sy = _.sourceY || sourceY, | ||
tx = _.targetX || targetX, | ||
ty = _.targetY || targetY, | ||
as = _.as || 'path', | ||
orient = _.orient || 'vertical', | ||
shape = _.shape || 'line', | ||
path = Paths.get(shape + '-' + orient) || Paths.get(shape); | ||
function orthoX(sx, sy, tx, ty) { | ||
return 'M' + sx + ',' + sy + | ||
'V' + ty + 'H' + tx; | ||
} | ||
if (!path) { | ||
vegaUtil.error('LinkPath unsupported type: ' + _.shape | ||
+ (_.orient ? '-' + _.orient : '')); | ||
function orthoY(sx, sy, tx, ty) { | ||
return 'M' + sx + ',' + sy + | ||
'H' + tx + 'V' + ty; | ||
} | ||
pulse.visit(pulse.SOURCE, function(t) { | ||
t[as] = path(sx(t), sy(t), tx(t), ty(t)); | ||
}); | ||
function orthoR(sa, sr, ta, tr) { | ||
var sc = Math.cos(sa), | ||
ss = Math.sin(sa), | ||
tc = Math.cos(ta), | ||
ts = Math.sin(ta), | ||
sf = Math.abs(ta - sa) > Math.PI ? ta <= sa : ta > sa; | ||
return 'M' + (sr*sc) + ',' + (sr*ss) + | ||
'A' + sr + ',' + sr + ' 0 0,' + (sf?1:0) + | ||
' ' + (sr*tc) + ',' + (sr*ts) + | ||
'L' + (tr*tc) + ',' + (tr*ts); | ||
} | ||
return pulse.reflow(_.modified()).modifies(as); | ||
}; | ||
function diagonalX(sx, sy, tx, ty) { | ||
var m = (sx + tx) / 2; | ||
return 'M' + sx + ',' + sy + | ||
'C' + m + ',' + sy + | ||
' ' + m + ',' + ty + | ||
' ' + tx + ',' + ty; | ||
} | ||
// -- Link Path Generation Methods ----- | ||
function diagonalY(sx, sy, tx, ty) { | ||
var m = (sy + ty) / 2; | ||
return 'M' + sx + ',' + sy + | ||
'C' + sx + ',' + m + | ||
' ' + tx + ',' + m + | ||
' ' + tx + ',' + ty; | ||
} | ||
function line(sx, sy, tx, ty) { | ||
return 'M' + sx + ',' + sy + | ||
'L' + tx + ',' + ty; | ||
} | ||
function diagonalR(sa, sr, ta, tr) { | ||
var sc = Math.cos(sa), | ||
ss = Math.sin(sa), | ||
tc = Math.cos(ta), | ||
ts = Math.sin(ta), | ||
mr = (sr + tr) / 2; | ||
return 'M' + (sr*sc) + ',' + (sr*ss) + | ||
'C' + (mr*sc) + ',' + (mr*ss) + | ||
' ' + (mr*tc) + ',' + (mr*ts) + | ||
' ' + (tr*tc) + ',' + (tr*ts); | ||
} | ||
function lineR(sa, sr, ta, tr) { | ||
return line( | ||
sr * Math.cos(sa), sr * Math.sin(sa), | ||
tr * Math.cos(ta), tr * Math.sin(ta) | ||
); | ||
} | ||
/** | ||
* Pie and donut chart layout. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
* @param {function(object): *} params.field - The value field to size pie segments. | ||
* @param {number} [params.startAngle=0] - The start angle (in radians) of the layout. | ||
* @param {number} [params.endAngle=2π] - The end angle (in radians) of the layout. | ||
* @param {boolean} [params.sort] - Boolean flag for sorting sectors by value. | ||
*/ | ||
function Pie(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
} | ||
function arc(sx, sy, tx, ty) { | ||
var dx = tx - sx, | ||
dy = ty - sy, | ||
rr = Math.sqrt(dx * dx + dy * dy) / 2, | ||
ra = 180 * Math.atan2(dy, dx) / Math.PI; | ||
return 'M' + sx + ',' + sy + | ||
'A' + rr + ',' + rr + | ||
' ' + ra + ' 0 1' + | ||
' ' + tx + ',' + ty; | ||
} | ||
Pie.Definition = { | ||
"type": "Pie", | ||
"metadata": {"modifies": true}, | ||
"params": [ | ||
{ "name": "field", "type": "field" }, | ||
{ "name": "startAngle", "type": "number", "default": 0 }, | ||
{ "name": "endAngle", "type": "number", "default": 6.283185307179586 }, | ||
{ "name": "sort", "type": "boolean", "default": false }, | ||
{ "name": "as", "type": "string", "array": true, "length": 2, "default": ["startAngle", "endAngle"] } | ||
] | ||
}; | ||
function arcR(sa, sr, ta, tr) { | ||
return arc( | ||
sr * Math.cos(sa), sr * Math.sin(sa), | ||
tr * Math.cos(ta), tr * Math.sin(ta) | ||
); | ||
} | ||
var prototype$5 = vegaUtil.inherits(Pie, vegaDataflow.Transform); | ||
function curve(sx, sy, tx, ty) { | ||
var dx = tx - sx, | ||
dy = ty - sy, | ||
ix = 0.2 * (dx + dy), | ||
iy = 0.2 * (dy - dx); | ||
return 'M' + sx + ',' + sy + | ||
'C' + (sx+ix) + ',' + (sy+iy) + | ||
' ' + (tx+iy) + ',' + (ty-ix) + | ||
' ' + tx + ',' + ty; | ||
} | ||
prototype$5.transform = function(_, pulse) { | ||
var as = _.as || ['startAngle', 'endAngle'], | ||
startAngle = as[0], | ||
endAngle = as[1], | ||
field = _.field || vegaUtil.one, | ||
start = _.startAngle || 0, | ||
stop = _.endAngle != null ? _.endAngle : 2 * Math.PI, | ||
data = pulse.source, | ||
values = data.map(field), | ||
n = values.length, | ||
a = start, | ||
k = (stop - start) / d3Array.sum(values), | ||
index = d3Array.range(n), | ||
i, t, v; | ||
function curveR(sa, sr, ta, tr) { | ||
return curve( | ||
sr * Math.cos(sa), sr * Math.sin(sa), | ||
tr * Math.cos(ta), tr * Math.sin(ta) | ||
); | ||
} | ||
if (_.sort) { | ||
index.sort(function(a, b) { | ||
return values[a] - values[b]; | ||
}); | ||
} | ||
function orthoX(sx, sy, tx, ty) { | ||
return 'M' + sx + ',' + sy + | ||
'V' + ty + 'H' + tx; | ||
} | ||
for (i=0; i<n; ++i) { | ||
v = values[index[i]]; | ||
t = data[index[i]]; | ||
t[startAngle] = a; | ||
t[endAngle] = (a += v * k); | ||
} | ||
function orthoY(sx, sy, tx, ty) { | ||
return 'M' + sx + ',' + sy + | ||
'H' + tx + 'V' + ty; | ||
} | ||
this.value = values; | ||
return pulse.reflow(_.modified()).modifies(as); | ||
}; | ||
function orthoR(sa, sr, ta, tr) { | ||
var sc = Math.cos(sa), | ||
ss = Math.sin(sa), | ||
tc = Math.cos(ta), | ||
ts = Math.sin(ta), | ||
sf = Math.abs(ta - sa) > Math.PI ? ta <= sa : ta > sa; | ||
return 'M' + (sr*sc) + ',' + (sr*ss) + | ||
'A' + sr + ',' + sr + ' 0 0,' + (sf?1:0) + | ||
' ' + (sr*tc) + ',' + (sr*ts) + | ||
'L' + (tr*tc) + ',' + (tr*ts); | ||
} | ||
var DEFAULT_COUNT = 5; | ||
function diagonalX(sx, sy, tx, ty) { | ||
var m = (sx + tx) / 2; | ||
return 'M' + sx + ',' + sy + | ||
'C' + m + ',' + sy + | ||
' ' + m + ',' + ty + | ||
' ' + tx + ',' + ty; | ||
} | ||
var INCLUDE_ZERO = vegaUtil.toSet([Linear, Pow, Sqrt]); | ||
function diagonalY(sx, sy, tx, ty) { | ||
var m = (sy + ty) / 2; | ||
return 'M' + sx + ',' + sy + | ||
'C' + sx + ',' + m + | ||
' ' + tx + ',' + m + | ||
' ' + tx + ',' + ty; | ||
} | ||
var INCLUDE_PAD = vegaUtil.toSet([Linear, Log, Pow, Sqrt, Time, Utc]); | ||
function diagonalR(sa, sr, ta, tr) { | ||
var sc = Math.cos(sa), | ||
ss = Math.sin(sa), | ||
tc = Math.cos(ta), | ||
ts = Math.sin(ta), | ||
mr = (sr + tr) / 2; | ||
return 'M' + (sr*sc) + ',' + (sr*ss) + | ||
'C' + (mr*sc) + ',' + (mr*ss) + | ||
' ' + (mr*tc) + ',' + (mr*ts) + | ||
' ' + (tr*tc) + ',' + (tr*ts); | ||
} | ||
var SKIP = vegaUtil.toSet([ | ||
'set', 'modified', 'clear', 'type', 'scheme', 'schemeExtent', 'schemeCount', | ||
'domain', 'domainMin', 'domainMid', 'domainMax', 'domainRaw', 'nice', 'zero', | ||
'range', 'rangeStep', 'round', 'reverse', 'interpolate', 'interpolateGamma' | ||
]); | ||
/** | ||
* Pie and donut chart layout. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
* @param {function(object): *} params.field - The value field to size pie segments. | ||
* @param {number} [params.startAngle=0] - The start angle (in radians) of the layout. | ||
* @param {number} [params.endAngle=2π] - The end angle (in radians) of the layout. | ||
* @param {boolean} [params.sort] - Boolean flag for sorting sectors by value. | ||
*/ | ||
function Pie(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
} | ||
/** | ||
* Maintains a scale function mapping data values to visual channels. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
*/ | ||
function Scale(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
this.modified(true); // always treat as modified | ||
} | ||
Pie.Definition = { | ||
"type": "Pie", | ||
"metadata": {"modifies": true}, | ||
"params": [ | ||
{ "name": "field", "type": "field" }, | ||
{ "name": "startAngle", "type": "number", "default": 0 }, | ||
{ "name": "endAngle", "type": "number", "default": 6.283185307179586 }, | ||
{ "name": "sort", "type": "boolean", "default": false }, | ||
{ "name": "as", "type": "string", "array": true, "length": 2, "default": ["startAngle", "endAngle"] } | ||
] | ||
}; | ||
var prototype$6 = vegaUtil.inherits(Scale, vegaDataflow.Transform); | ||
var prototype$5 = vegaUtil.inherits(Pie, vegaDataflow.Transform); | ||
prototype$6.transform = function(_, pulse) { | ||
var df = pulse.dataflow, | ||
scale = this.value, | ||
prop; | ||
prototype$5.transform = function(_, pulse) { | ||
var as = _.as || ['startAngle', 'endAngle'], | ||
startAngle = as[0], | ||
endAngle = as[1], | ||
field = _.field || vegaUtil.one, | ||
start = _.startAngle || 0, | ||
stop = _.endAngle != null ? _.endAngle : 2 * Math.PI, | ||
data = pulse.source, | ||
values = data.map(field), | ||
n = values.length, | ||
a = start, | ||
k = (stop - start) / d3Array.sum(values), | ||
index = d3Array.range(n), | ||
i, t, v; | ||
if (!scale || _.modified('type')) { | ||
this.value = scale = vegaScale.scale((_.type || Linear).toLowerCase())(); | ||
} | ||
if (_.sort) { | ||
index.sort(function(a, b) { | ||
return values[a] - values[b]; | ||
}); | ||
} | ||
for (prop in _) if (!SKIP[prop]) { | ||
// padding is a scale property for band/point but not others | ||
if (prop === 'padding' && INCLUDE_PAD[scale.type]) continue; | ||
// invoke scale property setter, raise warning if not found | ||
vegaUtil.isFunction(scale[prop]) | ||
? scale[prop](_[prop]) | ||
: df.warn('Unsupported scale property: ' + prop); | ||
} | ||
for (i=0; i<n; ++i) { | ||
v = values[index[i]]; | ||
t = data[index[i]]; | ||
t[startAngle] = a; | ||
t[endAngle] = (a += v * k); | ||
} | ||
configureRange(scale, _, configureDomain(scale, _, df)); | ||
this.value = values; | ||
return pulse.reflow(_.modified()).modifies(as); | ||
}; | ||
return pulse.fork(pulse.NO_SOURCE | pulse.NO_FIELDS); | ||
}; | ||
var DEFAULT_COUNT = 5; | ||
function configureDomain(scale, _, df) { | ||
// check raw domain, if provided use that and exit early | ||
var raw = rawDomain(scale, _.domainRaw); | ||
if (raw > -1) return raw; | ||
var INCLUDE_ZERO = vegaUtil.toSet([Linear, Pow, Sqrt]); | ||
var domain = _.domain, | ||
type = scale.type, | ||
zero = _.zero || (_.zero === undefined && INCLUDE_ZERO[type]), | ||
n, mid; | ||
var INCLUDE_PAD = vegaUtil.toSet([Linear, Log, Pow, Sqrt, Time, Utc]); | ||
if (!domain) return 0; | ||
var SKIP = vegaUtil.toSet([ | ||
'set', 'modified', 'clear', 'type', 'scheme', 'schemeExtent', 'schemeCount', | ||
'domain', 'domainMin', 'domainMid', 'domainMax', 'domainRaw', 'nice', 'zero', | ||
'range', 'rangeStep', 'round', 'reverse', 'interpolate', 'interpolateGamma' | ||
]); | ||
// adjust continuous domain for minimum pixel padding | ||
if (INCLUDE_PAD[type] && _.padding && domain[0] !== vegaUtil.peek(domain)) { | ||
domain = padDomain(type, domain, _.range, _.padding, _.exponent); | ||
} | ||
/** | ||
* Maintains a scale function mapping data values to visual channels. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
*/ | ||
function Scale(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
this.modified(true); // always treat as modified | ||
} | ||
// adjust domain based on zero, min, max settings | ||
if (zero || _.domainMin != null || _.domainMax != null || _.domainMid != null) { | ||
n = ((domain = domain.slice()).length - 1) || 1; | ||
if (zero) { | ||
if (domain[0] > 0) domain[0] = 0; | ||
if (domain[n] < 0) domain[n] = 0; | ||
} | ||
if (_.domainMin != null) domain[0] = _.domainMin; | ||
if (_.domainMax != null) domain[n] = _.domainMax; | ||
var prototype$6 = vegaUtil.inherits(Scale, vegaDataflow.Transform); | ||
if (_.domainMid != null) { | ||
mid = _.domainMid; | ||
if (mid < domain[0] || mid > domain[n]) { | ||
df.warn('Scale domainMid exceeds domain min or max.', mid); | ||
} | ||
domain.splice(n, 0, mid); | ||
} | ||
} | ||
prototype$6.transform = function(_, pulse) { | ||
var df = pulse.dataflow, | ||
scale$$1 = this.value, | ||
prop; | ||
// set the scale domain | ||
scale.domain(domain); | ||
if (!scale$$1 || _.modified('type')) { | ||
this.value = scale$$1 = vegaScale.scale((_.type || Linear).toLowerCase())(); | ||
// if ordinal scale domain is defined, prevent implicit | ||
// domain construction as side-effect of scale lookup | ||
if (type === Ordinal) { | ||
scale.unknown(undefined); | ||
} | ||
// perform 'nice' adjustment as requested | ||
if (_.nice && scale.nice) { | ||
scale.nice((_.nice !== true && tickCount(scale, _.nice)) || null); | ||
} | ||
// return the cardinality of the domain | ||
return domain.length; | ||
} | ||
for (prop in _) if (!SKIP[prop]) { | ||
// padding is a scale property for band/point but not others | ||
if (prop === 'padding' && INCLUDE_PAD[scale$$1.type]) continue; | ||
// invoke scale property setter, raise warning if not found | ||
vegaUtil.isFunction(scale$$1[prop]) | ||
? scale$$1[prop](_[prop]) | ||
: df.warn('Unsupported scale property: ' + prop); | ||
function rawDomain(scale, raw) { | ||
if (raw) { | ||
scale.domain(raw); | ||
return raw.length; | ||
} else { | ||
return -1; | ||
} | ||
} | ||
configureRange(scale$$1, _, configureDomain(scale$$1, _, df)); | ||
function padDomain(type, domain, range, pad, exponent) { | ||
var span = Math.abs(vegaUtil.peek(range) - range[0]), | ||
frac = span / (span - 2 * pad), | ||
d = type === Log ? vegaUtil.zoomLog(domain, null, frac) | ||
: type === Sqrt ? vegaUtil.zoomPow(domain, null, frac, 0.5) | ||
: type === Pow ? vegaUtil.zoomPow(domain, null, frac, exponent) | ||
: vegaUtil.zoomLinear(domain, null, frac); | ||
return pulse.fork(pulse.NO_SOURCE | pulse.NO_FIELDS); | ||
}; | ||
domain = domain.slice(); | ||
domain[0] = d[0]; | ||
domain[domain.length-1] = d[1]; | ||
return domain; | ||
} | ||
function configureDomain(scale$$1, _, df) { | ||
// check raw domain, if provided use that and exit early | ||
var raw = rawDomain(scale$$1, _.domainRaw); | ||
if (raw > -1) return raw; | ||
function configureRange(scale, _, count) { | ||
var round = _.round || false, | ||
range = _.range; | ||
var domain = _.domain, | ||
type = scale$$1.type, | ||
zero = _.zero || (_.zero === undefined && INCLUDE_ZERO[type]), | ||
n, mid; | ||
// if range step specified, calculate full range extent | ||
if (_.rangeStep != null) { | ||
range = configureRangeStep(scale.type, _, count); | ||
} | ||
if (!domain) return 0; | ||
// else if a range scheme is defined, use that | ||
else if (_.scheme) { | ||
range = configureScheme(scale.type, _, count); | ||
if (vegaUtil.isFunction(range)) return scale.interpolator(range); | ||
} | ||
// adjust continuous domain for minimum pixel padding | ||
if (INCLUDE_PAD[type] && _.padding && domain[0] !== vegaUtil.peek(domain)) { | ||
domain = padDomain(type, domain, _.range, _.padding, _.exponent); | ||
} | ||
// adjust domain based on zero, min, max settings | ||
if (zero || _.domainMin != null || _.domainMax != null || _.domainMid != null) { | ||
n = ((domain = domain.slice()).length - 1) || 1; | ||
if (zero) { | ||
if (domain[0] > 0) domain[0] = 0; | ||
if (domain[n] < 0) domain[n] = 0; | ||
// given a range array for a sequential scale, convert to interpolator | ||
else if (range && scale.type === Sequential) { | ||
return scale.interpolator(d3Interpolate.interpolateRgbBasis(flip(range, _.reverse))); | ||
} | ||
if (_.domainMin != null) domain[0] = _.domainMin; | ||
if (_.domainMax != null) domain[n] = _.domainMax; | ||
if (_.domainMid != null) { | ||
mid = _.domainMid; | ||
if (mid < domain[0] || mid > domain[n]) { | ||
df.warn('Scale domainMid exceeds domain min or max.', mid); | ||
} | ||
domain.splice(n, 0, mid); | ||
// configure rounding / interpolation | ||
if (range && _.interpolate && scale.interpolate) { | ||
scale.interpolate(vegaScale.interpolate(_.interpolate, _.interpolateGamma)); | ||
} else if (vegaUtil.isFunction(scale.round)) { | ||
scale.round(round); | ||
} else if (vegaUtil.isFunction(scale.rangeRound)) { | ||
scale.interpolate(round ? d3Interpolate.interpolateRound : d3Interpolate.interpolate); | ||
} | ||
} | ||
// set the scale domain | ||
scale$$1.domain(domain); | ||
// if ordinal scale domain is defined, prevent implicit | ||
// domain construction as side-effect of scale lookup | ||
if (type === Ordinal) { | ||
scale$$1.unknown(undefined); | ||
if (range) scale.range(flip(range, _.reverse)); | ||
} | ||
// perform 'nice' adjustment as requested | ||
if (_.nice && scale$$1.nice) { | ||
scale$$1.nice((_.nice !== true && tickCount(scale$$1, _.nice)) || null); | ||
} | ||
function configureRangeStep(type, _, count) { | ||
if (type !== Band && type !== Point) { | ||
vegaUtil.error('Only band and point scales support rangeStep.'); | ||
} | ||
// return the cardinality of the domain | ||
return domain.length; | ||
} | ||
function rawDomain(scale$$1, raw) { | ||
if (raw) { | ||
scale$$1.domain(raw); | ||
return raw.length; | ||
} else { | ||
return -1; | ||
// calculate full range based on requested step size and padding | ||
var outer = (_.paddingOuter != null ? _.paddingOuter : _.padding) || 0, | ||
inner = type === Point ? 1 | ||
: ((_.paddingInner != null ? _.paddingInner : _.padding) || 0); | ||
return [0, _.rangeStep * vegaScale.bandSpace(count, inner, outer)]; | ||
} | ||
} | ||
function padDomain(type, domain, range$$1, pad, exponent) { | ||
var span = Math.abs(vegaUtil.peek(range$$1) - range$$1[0]), | ||
frac = span / (span - 2 * pad), | ||
d = type === Log ? vegaUtil.zoomLog(domain, null, frac) | ||
: type === Sqrt ? vegaUtil.zoomPow(domain, null, frac, 0.5) | ||
: type === Pow ? vegaUtil.zoomPow(domain, null, frac, exponent) | ||
: vegaUtil.zoomLinear(domain, null, frac); | ||
function configureScheme(type, _, count) { | ||
var name = _.scheme.toLowerCase(), | ||
scheme = vegaScale.scheme(name), | ||
extent = _.schemeExtent, | ||
discrete; | ||
domain = domain.slice(); | ||
domain[0] = d[0]; | ||
domain[domain.length-1] = d[1]; | ||
return domain; | ||
} | ||
if (!scheme) { | ||
vegaUtil.error('Unrecognized scheme name: ' + _.scheme); | ||
} | ||
function configureRange(scale$$1, _, count) { | ||
var round = _.round || false, | ||
range$$1 = _.range; | ||
// determine size for potential discrete range | ||
count = (type === Threshold) ? count + 1 | ||
: (type === BinOrdinal) ? count - 1 | ||
: (type === Quantile || type === Quantize) ? (+_.schemeCount || DEFAULT_COUNT) | ||
: count; | ||
// if range step specified, calculate full range extent | ||
if (_.rangeStep != null) { | ||
range$$1 = configureRangeStep(scale$$1.type, _, count); | ||
// adjust and/or quantize scheme as appropriate | ||
return type === Sequential ? adjustScheme(scheme, extent, _.reverse) | ||
: !extent && (discrete = vegaScale.scheme(name + '-' + count)) ? discrete | ||
: vegaUtil.isFunction(scheme) ? quantize(adjustScheme(scheme, extent), count) | ||
: type === Ordinal ? scheme : scheme.slice(0, count); | ||
} | ||
// else if a range scheme is defined, use that | ||
else if (_.scheme) { | ||
range$$1 = configureScheme(scale$$1.type, _, count); | ||
if (vegaUtil.isFunction(range$$1)) return scale$$1.interpolator(range$$1); | ||
function adjustScheme(scheme, extent, reverse) { | ||
return (vegaUtil.isFunction(scheme) && (extent || reverse)) | ||
? vegaScale.interpolateRange(scheme, flip(extent || [0, 1], reverse)) | ||
: scheme; | ||
} | ||
// given a range array for a sequential scale, convert to interpolator | ||
else if (range$$1 && scale$$1.type === Sequential) { | ||
return scale$$1.interpolator(d3Interpolate.interpolateRgbBasis(flip(range$$1, _.reverse))); | ||
function flip(array, reverse) { | ||
return reverse ? array.slice().reverse() : array; | ||
} | ||
// configure rounding / interpolation | ||
if (range$$1 && _.interpolate && scale$$1.interpolate) { | ||
scale$$1.interpolate(vegaScale.interpolate(_.interpolate, _.interpolateGamma)); | ||
} else if (vegaUtil.isFunction(scale$$1.round)) { | ||
scale$$1.round(round); | ||
} else if (vegaUtil.isFunction(scale$$1.rangeRound)) { | ||
scale$$1.interpolate(round ? d3Interpolate.interpolateRound : d3Interpolate.interpolate); | ||
function quantize(interpolator, count) { | ||
var samples = new Array(count), | ||
n = count + 2; | ||
for (var i = 0; i < count;) samples[i] = interpolator(++i / n); | ||
return samples; | ||
} | ||
if (range$$1) scale$$1.range(flip(range$$1, _.reverse)); | ||
} | ||
function configureRangeStep(type, _, count) { | ||
if (type !== Band && type !== Point) { | ||
vegaUtil.error('Only band and point scales support rangeStep.'); | ||
/** | ||
* Sorts scenegraph items in the pulse source array. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
* @param {function(*,*): number} [params.sort] - A comparator | ||
* function for sorting tuples. | ||
*/ | ||
function SortItems(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
} | ||
// calculate full range based on requested step size and padding | ||
var outer = (_.paddingOuter != null ? _.paddingOuter : _.padding) || 0, | ||
inner = type === Point ? 1 | ||
: ((_.paddingInner != null ? _.paddingInner : _.padding) || 0); | ||
return [0, _.rangeStep * vegaScale.bandSpace(count, inner, outer)]; | ||
} | ||
var prototype$7 = vegaUtil.inherits(SortItems, vegaDataflow.Transform); | ||
function configureScheme(type, _, count) { | ||
var name = _.scheme.toLowerCase(), | ||
scheme$$1 = vegaScale.scheme(name), | ||
extent = _.schemeExtent, | ||
discrete; | ||
prototype$7.transform = function(_, pulse) { | ||
var mod = _.modified('sort') | ||
|| pulse.changed(pulse.ADD) | ||
|| pulse.modified(_.sort.fields) | ||
|| pulse.modified('datum'); | ||
if (!scheme$$1) { | ||
vegaUtil.error('Unrecognized scheme name: ' + _.scheme); | ||
} | ||
if (mod) pulse.source.sort(_.sort); | ||
// determine size for potential discrete range | ||
count = (type === Threshold) ? count + 1 | ||
: (type === BinOrdinal) ? count - 1 | ||
: (type === Quantile || type === Quantize) ? (+_.schemeCount || DEFAULT_COUNT) | ||
: count; | ||
this.modified(mod); | ||
return pulse; | ||
}; | ||
// adjust and/or quantize scheme as appropriate | ||
return type === Sequential ? adjustScheme(scheme$$1, extent, _.reverse) | ||
: !extent && (discrete = vegaScale.scheme(name + '-' + count)) ? discrete | ||
: vegaUtil.isFunction(scheme$$1) ? quantize$1(adjustScheme(scheme$$1, extent), count) | ||
: type === Ordinal ? scheme$$1 : scheme$$1.slice(0, count); | ||
} | ||
var Center = 'center', | ||
Normalize = 'normalize'; | ||
function adjustScheme(scheme$$1, extent, reverse) { | ||
return (vegaUtil.isFunction(scheme$$1) && (extent || reverse)) | ||
? vegaScale.interpolateRange(scheme$$1, flip(extent || [0, 1], reverse)) | ||
: scheme$$1; | ||
} | ||
/** | ||
* Stack layout for visualization elements. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
* @param {function(object): *} params.field - The value field to stack. | ||
* @param {Array<function(object): *>} [params.groupby] - An array of accessors to groupby. | ||
* @param {function(object,object): number} [params.sort] - A comparator for stack sorting. | ||
* @param {string} [offset='zero'] - One of 'zero', 'center', 'normalize'. | ||
*/ | ||
function Stack(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
} | ||
function flip(array, reverse) { | ||
return reverse ? array.slice().reverse() : array; | ||
} | ||
Stack.Definition = { | ||
"type": "Stack", | ||
"metadata": {"modifies": true}, | ||
"params": [ | ||
{ "name": "field", "type": "field" }, | ||
{ "name": "groupby", "type": "field", "array": true }, | ||
{ "name": "sort", "type": "compare" }, | ||
{ "name": "offset", "type": "enum", "default": "zero", "values": ["zero", "center", "normalize"] }, | ||
{ "name": "as", "type": "string", "array": true, "length": 2, "default": ["y0", "y1"] } | ||
] | ||
}; | ||
function quantize$1(interpolator, count) { | ||
var samples = new Array(count), | ||
n = (count - 1) || 1; | ||
for (var i = 0; i < count; ++i) samples[i] = interpolator(i / n); | ||
return samples; | ||
} | ||
var prototype$8 = vegaUtil.inherits(Stack, vegaDataflow.Transform); | ||
/** | ||
* Sorts scenegraph items in the pulse source array. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
* @param {function(*,*): number} [params.sort] - A comparator | ||
* function for sorting tuples. | ||
*/ | ||
function SortItems(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
} | ||
prototype$8.transform = function(_, pulse) { | ||
var as = _.as || ['y0', 'y1'], | ||
y0 = as[0], | ||
y1 = as[1], | ||
field = _.field || vegaUtil.one, | ||
stack = _.offset === Center ? stackCenter | ||
: _.offset === Normalize ? stackNormalize | ||
: stackZero, | ||
groups, i, n, max; | ||
var prototype$7 = vegaUtil.inherits(SortItems, vegaDataflow.Transform); | ||
// partition, sum, and sort the stack groups | ||
groups = partition(pulse.source, _.groupby, _.sort, field); | ||
prototype$7.transform = function(_, pulse) { | ||
var mod = _.modified('sort') | ||
|| pulse.changed(pulse.ADD) | ||
|| pulse.modified(_.sort.fields) | ||
|| pulse.modified('datum'); | ||
// compute stack layouts per group | ||
for (i=0, n=groups.length, max=groups.max; i<n; ++i) { | ||
stack(groups[i], max, field, y0, y1); | ||
} | ||
if (mod) pulse.source.sort(_.sort); | ||
return pulse.reflow(_.modified()).modifies(as); | ||
}; | ||
this.modified(mod); | ||
return pulse; | ||
}; | ||
function stackCenter(group, max, field, y0, y1) { | ||
var last = (max - group.sum) / 2, | ||
m = group.length, | ||
j = 0, t; | ||
var Center = 'center'; | ||
var Normalize = 'normalize'; | ||
/** | ||
* Stack layout for visualization elements. | ||
* @constructor | ||
* @param {object} params - The parameters for this operator. | ||
* @param {function(object): *} params.field - The value field to stack. | ||
* @param {Array<function(object): *>} [params.groupby] - An array of accessors to groupby. | ||
* @param {function(object,object): number} [params.sort] - A comparator for stack sorting. | ||
* @param {string} [offset='zero'] - One of 'zero', 'center', 'normalize'. | ||
*/ | ||
function Stack(params) { | ||
vegaDataflow.Transform.call(this, null, params); | ||
} | ||
Stack.Definition = { | ||
"type": "Stack", | ||
"metadata": {"modifies": true}, | ||
"params": [ | ||
{ "name": "field", "type": "field" }, | ||
{ "name": "groupby", "type": "field", "array": true }, | ||
{ "name": "sort", "type": "compare" }, | ||
{ "name": "offset", "type": "enum", "default": "zero", "values": ["zero", "center", "normalize"] }, | ||
{ "name": "as", "type": "string", "array": true, "length": 2, "default": ["y0", "y1"] } | ||
] | ||
}; | ||
var prototype$8 = vegaUtil.inherits(Stack, vegaDataflow.Transform); | ||
prototype$8.transform = function(_, pulse) { | ||
var as = _.as || ['y0', 'y1'], | ||
y0 = as[0], | ||
y1 = as[1], | ||
field = _.field || vegaUtil.one, | ||
stack = _.offset === Center ? stackCenter | ||
: _.offset === Normalize ? stackNormalize | ||
: stackZero, | ||
groups, i, n, max; | ||
// partition, sum, and sort the stack groups | ||
groups = partition(pulse.source, _.groupby, _.sort, field); | ||
// compute stack layouts per group | ||
for (i=0, n=groups.length, max=groups.max; i<n; ++i) { | ||
stack(groups[i], max, field, y0, y1); | ||
for (; j<m; ++j) { | ||
t = group[j]; | ||
t[y0] = last; | ||
t[y1] = (last += Math.abs(field(t))); | ||
} | ||
} | ||
return pulse.reflow(_.modified()).modifies(as); | ||
}; | ||
function stackNormalize(group, max, field, y0, y1) { | ||
var scale = 1 / group.sum, | ||
last = 0, | ||
m = group.length, | ||
j = 0, v = 0, t; | ||
function stackCenter(group, max, field, y0, y1) { | ||
var last = (max - group.sum) / 2, | ||
m = group.length, | ||
j = 0, t; | ||
for (; j<m; ++j) { | ||
t = group[j]; | ||
t[y0] = last; | ||
t[y1] = (last += Math.abs(field(t))); | ||
for (; j<m; ++j) { | ||
t = group[j]; | ||
t[y0] = last; | ||
t[y1] = last = scale * (v += Math.abs(field(t))); | ||
} | ||
} | ||
} | ||
function stackNormalize(group, max, field, y0, y1) { | ||
var scale$$1 = 1 / group.sum, | ||
last = 0, | ||
m = group.length, | ||
j = 0, v = 0, t; | ||
function stackZero(group, max, field, y0, y1) { | ||
var lastPos = 0, | ||
lastNeg = 0, | ||
m = group.length, | ||
j = 0, v, t; | ||
for (; j<m; ++j) { | ||
t = group[j]; | ||
t[y0] = last; | ||
t[y1] = last = scale$$1 * (v += Math.abs(field(t))); | ||
for (; j<m; ++j) { | ||
t = group[j]; | ||
v = field(t); | ||
if (v < 0) { | ||
t[y0] = lastNeg; | ||
t[y1] = (lastNeg += v); | ||
} else { | ||
t[y0] = lastPos; | ||
t[y1] = (lastPos += v); | ||
} | ||
} | ||
} | ||
} | ||
function stackZero(group, max, field, y0, y1) { | ||
var lastPos = 0, | ||
lastNeg = 0, | ||
m = group.length, | ||
j = 0, v, t; | ||
function partition(data, groupby, sort, field) { | ||
var groups = [], | ||
get = function(f) { return f(t); }, | ||
map, i, n, m, t, k, g, s, max; | ||
for (; j<m; ++j) { | ||
t = group[j]; | ||
v = field(t); | ||
if (v < 0) { | ||
t[y0] = lastNeg; | ||
t[y1] = (lastNeg += v); | ||
// partition data points into stack groups | ||
if (groupby == null) { | ||
groups.push(data.slice()); | ||
} else { | ||
t[y0] = lastPos; | ||
t[y1] = (lastPos += v); | ||
for (map={}, i=0, n=data.length; i<n; ++i) { | ||
t = data[i]; | ||
k = groupby.map(get); | ||
g = map[k]; | ||
if (!g) { | ||
map[k] = (g = []); | ||
groups.push(g); | ||
} | ||
g.push(t); | ||
} | ||
} | ||
} | ||
} | ||
function partition(data, groupby, sort, field) { | ||
var groups = [], | ||
get = function(f) { return f(t); }, | ||
map, i, n, m, t, k, g, s, max; | ||
// partition data points into stack groups | ||
if (groupby == null) { | ||
groups.push(data.slice()); | ||
} else { | ||
for (map={}, i=0, n=data.length; i<n; ++i) { | ||
t = data[i]; | ||
k = groupby.map(get); | ||
g = map[k]; | ||
if (!g) { | ||
map[k] = (g = []); | ||
groups.push(g); | ||
// compute sums of groups, sort groups as needed | ||
for (k=0, max=0, m=groups.length; k<m; ++k) { | ||
g = groups[k]; | ||
for (i=0, s=0, n=g.length; i<n; ++i) { | ||
s += Math.abs(field(g[i])); | ||
} | ||
g.push(t); | ||
g.sum = s; | ||
if (s > max) max = s; | ||
if (sort) g.sort(sort); | ||
} | ||
} | ||
groups.max = max; | ||
// compute sums of groups, sort groups as needed | ||
for (k=0, max=0, m=groups.length; k<m; ++k) { | ||
g = groups[k]; | ||
for (i=0, s=0, n=g.length; i<n; ++i) { | ||
s += Math.abs(field(g[i])); | ||
} | ||
g.sum = s; | ||
if (s > max) max = s; | ||
if (sort) g.sort(sort); | ||
return groups; | ||
} | ||
groups.max = max; | ||
return groups; | ||
} | ||
exports.axisticks = AxisTicks; | ||
exports.datajoin = DataJoin; | ||
exports.encode = Encode; | ||
exports.legendentries = LegendEntries; | ||
exports.linkpath = LinkPath; | ||
exports.pie = Pie; | ||
exports.scale = Scale; | ||
exports.sortitems = SortItems; | ||
exports.stack = Stack; | ||
exports.validTicks = validTicks; | ||
exports.axisticks = AxisTicks; | ||
exports.datajoin = DataJoin; | ||
exports.encode = Encode; | ||
exports.legendentries = LegendEntries; | ||
exports.linkpath = LinkPath; | ||
exports.pie = Pie; | ||
exports.scale = Scale; | ||
exports.sortitems = SortItems; | ||
exports.stack = Stack; | ||
exports.validTicks = validTicks; | ||
Object.defineProperty(exports, '__esModule', { value: true }); | ||
Object.defineProperty(exports, '__esModule', { value: true }); | ||
}))); |
@@ -1,1 +0,1 @@ | ||
!function(e,n){"object"==typeof exports&&"undefined"!=typeof module?n(exports,require("vega-scale"),require("vega-util"),require("d3-format"),require("vega-dataflow"),require("d3-array"),require("d3-interpolate")):"function"==typeof define&&define.amd?define(["exports","vega-scale","vega-util","d3-format","vega-dataflow","d3-array","d3-interpolate"],n):n((e.vega=e.vega||{},e.vega.transforms=e.vega.transforms||{}),e.vega,e.vega,e.d3,e.vega,e.d3,e.d3)}(this,function(e,p,M,u,h,g,i){"use strict";var x="log",k="pow",S="sqrt",o="band",s="point",l="linear",O="ordinal",f="quantile",c="quantize",d="threshold",m="bin-ordinal",v="sequential";function b(e,n){var t;return M.isObject(n)&&(t=n.step,n=n.interval),M.isString(n)&&(n="time"===e.type?p.timeInterval(n):"utc"===e.type?p.utcInterval(n):M.error("Only time and utc scales accept interval strings."),t&&(n=n.every(t))),n}function y(n,e,t){var r=n.range(),a=r[0],i=M.peek(r);if(i<a&&(r=i,i=a,a=r),e=e.filter(function(e){return!((e=n(e))<a||i<e)}),0<t&&1<e.length){for(var o=[e[0],M.peek(e)];e.length>t&&3<=e.length;)e=e.filter(function(e,n){return!(n%2)});e.length<3&&(e=o)}return e}function A(e,n){return e.ticks?e.ticks(n):e.domain()}function D(e,n,t){var r,a,i=e.tickFormat?e.tickFormat(n,t):String;return e.type===x?(r=i,a=function(e){var n=u.formatSpecifier(e||",");{if(null==n.precision){switch(n.precision=12,n.type){case"%":n.precision-=2;break;case"e":n.precision-=1}return i=u.format(n),o=u.format(".1f")(1)[1],function(e){var n,t,r=i(e),a=r.indexOf(o);if(a<0)return r;for(n=function(e,n){var t,r=e.lastIndexOf("e");if(0<r)return r;for(r=e.length;--r>n;)if(48<=(t=e.charCodeAt(r))&&t<=57)return r+1}(r,a),t=n<r.length?r.slice(n):"";--n>a;)if("0"!==r[n]){++n;break}return r.slice(0,n)+t}}return u.format(n)}var i,o}(t),function(e){return r(e)?a(e):""}):i}function n(e){h.Transform.call(this,null,e)}function t(e){h.Transform.call(this,null,e)}function w(){return h.ingest({})}function T(e){return e.exit}function r(e){h.Transform.call(this,null,e)}M.inherits(n,h.Transform).transform=function(e,n){if(this.value&&!e.modified())return n.StopPropagation;var t=n.fork(n.NO_SOURCE|n.NO_FIELDS),r=this.value,a=e.scale,i=null==e.count?e.values?e.values.length:10:b(a,e.count),o=e.format||D(a,i,e.formatSpecifier),u=e.values?y(a,e.values,i):A(a,i);return r&&(t.rem=r),r=u.map(function(e,n){return h.ingest({index:n/(u.length-1),value:e,label:o(e)})}),e.extra&&r.push(h.ingest({index:-1,extra:{value:r[0].value},label:""})),t.source=r,t.add=r,this.value=r,t},M.inherits(t,h.Transform).transform=function(e,n){var t=n.dataflow,r=n.fork(n.NO_SOURCE|n.NO_FIELDS),a=e.item||w,i=e.key||h.tupleid,o=this.value;return M.isArray(r.encode)&&(r.encode=null),o&&(e.modified("key")||n.modified(i))&&M.error("DataJoin does not support modified key function or fields."),o||(n=n.addAll(),this.value=o=M.fastmap().test(T),o.lookup=function(e){return o.get(i(e))}),n.visit(n.ADD,function(e){var n=i(e),t=o.get(n);t?t.exit?(o.empty--,r.add.push(t)):r.mod.push(t):(o.set(n,t=a(e)),r.add.push(t)),t.datum=e,t.exit=!1}),n.visit(n.MOD,function(e){var n=i(e),t=o.get(n);t&&(t.datum=e,r.mod.push(t))}),n.visit(n.REM,function(e){var n=i(e),t=o.get(n);e!==t.datum||t.exit||(r.rem.push(t),t.exit=!0,++o.empty)}),n.changed(n.ADD_MOD)&&r.modifies("datum"),e.clean&&o.empty>t.cleanThreshold&&t.runAfter(o.clean),r},M.inherits(r,h.Transform).transform=function(t,e){var r=e.fork(e.ADD_REM),n=t.encoders,a=e.encode;if(M.isArray(a)){if(!r.changed()&&!a.every(function(e){return n[e]}))return e.StopPropagation;a=a[0],r.encode=null}var i="enter"===a,o=n.update||M.falsy,u=n.enter||M.falsy,s=n.exit||M.falsy,l=(a&&!i?n[a]:o)||M.falsy;if(e.changed(e.ADD)&&(e.visit(e.ADD,function(e){u(e,t),o(e,t),l!==M.falsy&&l!==o&&l(e,t)}),r.modifies(u.output),r.modifies(o.output),l!==M.falsy&&l!==o&&r.modifies(l.output)),e.changed(e.REM)&&s!==M.falsy&&(e.visit(e.REM,function(e){s(e,t)}),r.modifies(s.output)),i||l!==M.falsy){var f=e.MOD|(t.modified()?e.REFLOW:0);i?(e.visit(f,function(e){var n=u(e,t);(l(e,t)||n)&&r.mod.push(e)}),r.mod.length&&r.modifies(u.output)):e.visit(f,function(e){l(e,t)&&r.mod.push(e)}),r.mod.length&&r.modifies(l.output)}return r.changed()?r:e.StopPropagation};var z={};function a(e){var n=e.domain();return n.max=n.pop(),n}function E(e,n){return z[e.type]?(o=n,function(e,n,t){var r=t[n+1]||t.max||1/0,a=F(e,o),i=F(r,o);return a&&i?a+"–"+i:i?"< "+i:"≥ "+a}):(t=n,function(e){return t(e)});var t,o}function F(e,n){return isFinite(e)?n(e):null}function R(e){h.Transform.call(this,[],e)}z[f]=function(e){var n=[-1/0].concat(e.quantiles());return n.max=1/0,n},z[c]=function(e){var n=e.domain(),t=n[0],r=M.peek(n),a=e.range().length,i=new Array(a),o=0;i[0]=-1/0;for(;++o<a;)i[o]=(o*r-(o-a)*t)/a;return i.max=1/0,i},z[d]=function(e){var n=[-1/0].concat(e.domain());return n.max=1/0,n},z["bin-linear"]=a,z[m]=a,M.inherits(R,h.Transform).transform=function(r,e){if(null!=this.value&&!r.modified())return e.StopPropagation;var n=e.fork(e.NO_SOURCE|e.NO_FIELDS),a=0,t=this.value,i="gradient"===r.type,o=r.scale,u=null==r.count?5:b(o,r.count),s=r.format||D(o,u,r.formatSpecifier),l=r.values||function(e,n,t){if(t)return e.domain();var r=z[e.type];return r?r(e):A(e,n)}(o,u,i);if(s=E(o,s),t&&(n.rem=t),i)var f=r.values?o.domain():l,c=p.scaleFraction(o,f[0],M.peek(f));else{var d,m=r.size;M.isFunction(m)?(r.values||0!==o(l[0])||(l=l.slice(1)),d=l.reduce(function(e,n){return Math.max(e,m(n,r))},0)):m=M.constant(d=m||8)}return t=l.map(function(e,n){var t=h.ingest({index:n,label:s(e,n,l),value:e});return i?t.perc=c(e):(t.offset=d,t.size=m(e,r),t.total=Math.round(a),a+=t.size),t}),n.source=t,n.add=t,this.value=t,n};var C=M.fastmap({line:N,"line-radial":function(e,n,t,r){return N(n*Math.cos(e),n*Math.sin(e),r*Math.cos(t),r*Math.sin(t))},arc:U,"arc-radial":function(e,n,t,r){return U(n*Math.cos(e),n*Math.sin(e),r*Math.cos(t),r*Math.sin(t))},curve:j,"curve-radial":function(e,n,t,r){return j(n*Math.cos(e),n*Math.sin(e),r*Math.cos(t),r*Math.sin(t))},"orthogonal-horizontal":function(e,n,t,r){return"M"+e+","+n+"V"+r+"H"+t},"orthogonal-vertical":function(e,n,t,r){return"M"+e+","+n+"H"+t+"V"+r},"orthogonal-radial":function(e,n,t,r){var a=Math.cos(e),i=Math.sin(e),o=Math.cos(t),u=Math.sin(t),s=Math.abs(t-e)>Math.PI?t<=e:e<t;return"M"+n*a+","+n*i+"A"+n+","+n+" 0 0,"+(s?1:0)+" "+n*o+","+n*u+"L"+r*o+","+r*u},"diagonal-horizontal":function(e,n,t,r){var a=(e+t)/2;return"M"+e+","+n+"C"+a+","+n+" "+a+","+r+" "+t+","+r},"diagonal-vertical":function(e,n,t,r){var a=(n+r)/2;return"M"+e+","+n+"C"+e+","+a+" "+t+","+a+" "+t+","+r},"diagonal-radial":function(e,n,t,r){var a=Math.cos(e),i=Math.sin(e),o=Math.cos(t),u=Math.sin(t),s=(n+r)/2;return"M"+n*a+","+n*i+"C"+s*a+","+s*i+" "+s*o+","+s*u+" "+r*o+","+r*u}});function L(e){return e.source.x}function P(e){return e.source.y}function q(e){return e.target.x}function I(e){return e.target.y}function _(e){h.Transform.call(this,{},e)}function N(e,n,t,r){return"M"+e+","+n+"L"+t+","+r}function U(e,n,t,r){var a=t-e,i=r-n,o=Math.sqrt(a*a+i*i)/2;return"M"+e+","+n+"A"+o+","+o+" "+180*Math.atan2(i,a)/Math.PI+" 0 1 "+t+","+r}function j(e,n,t,r){var a=t-e,i=r-n,o=.2*(a+i),u=.2*(i-a);return"M"+e+","+n+"C"+(e+o)+","+(n+u)+" "+(t+u)+","+(r-o)+" "+t+","+r}function X(e){h.Transform.call(this,null,e)}_.Definition={type:"LinkPath",metadata:{modifies:!0},params:[{name:"sourceX",type:"field",default:"source.x"},{name:"sourceY",type:"field",default:"source.y"},{name:"targetX",type:"field",default:"target.x"},{name:"targetY",type:"field",default:"target.y"},{name:"orient",type:"enum",default:"vertical",values:["horizontal","vertical","radial"]},{name:"shape",type:"enum",default:"line",values:["line","arc","curve","diagonal","orthogonal"]},{name:"as",type:"string",default:"path"}]},M.inherits(_,h.Transform).transform=function(e,n){var t=e.sourceX||L,r=e.sourceY||P,a=e.targetX||q,i=e.targetY||I,o=e.as||"path",u=e.orient||"vertical",s=e.shape||"line",l=C.get(s+"-"+u)||C.get(s);return l||M.error("LinkPath unsupported type: "+e.shape+(e.orient?"-"+e.orient:"")),n.visit(n.SOURCE,function(e){e[o]=l(t(e),r(e),a(e),i(e))}),n.reflow(e.modified()).modifies(o)},X.Definition={type:"Pie",metadata:{modifies:!0},params:[{name:"field",type:"field"},{name:"startAngle",type:"number",default:0},{name:"endAngle",type:"number",default:6.283185307179586},{name:"sort",type:"boolean",default:!1},{name:"as",type:"string",array:!0,length:2,default:["startAngle","endAngle"]}]},M.inherits(X,h.Transform).transform=function(e,n){var t,r,a,i=e.as||["startAngle","endAngle"],o=i[0],u=i[1],s=e.field||M.one,l=e.startAngle||0,f=null!=e.endAngle?e.endAngle:2*Math.PI,c=n.source,d=c.map(s),m=d.length,p=l,h=(f-l)/g.sum(d),v=g.range(m);for(e.sort&&v.sort(function(e,n){return d[e]-d[n]}),t=0;t<m;++t)a=d[v[t]],(r=c[v[t]])[o]=p,r[u]=p+=a*h;return this.value=d,n.reflow(e.modified()).modifies(i)};var Y=5,G=M.toSet([l,k,S]),H=M.toSet([l,x,k,S,"time","utc"]),V=M.toSet(["set","modified","clear","type","scheme","schemeExtent","schemeCount","domain","domainMin","domainMid","domainMax","domainRaw","nice","zero","range","rangeStep","round","reverse","interpolate","interpolateGamma"]);function B(e){h.Transform.call(this,null,e),this.modified(!0)}function J(e,n,t){return M.isFunction(e)&&(n||t)?p.interpolateRange(e,W(n||[0,1],t)):e}function W(e,n){return n?e.slice().reverse():e}function K(e){h.Transform.call(this,null,e)}M.inherits(B,h.Transform).transform=function(e,n){var t,r=n.dataflow,a=this.value;for(t in a&&!e.modified("type")||(this.value=a=p.scale((e.type||l).toLowerCase())()),e)if(!V[t]){if("padding"===t&&H[a.type])continue;M.isFunction(a[t])?a[t](e[t]):r.warn("Unsupported scale property: "+t)}return function(e,n,t){var r=n.round||!1,a=n.range;if(null!=n.rangeStep)a=function(e,n,t){e!==o&&e!==s&&M.error("Only band and point scales support rangeStep.");var r=(null!=n.paddingOuter?n.paddingOuter:n.padding)||0,a=e===s?1:(null!=n.paddingInner?n.paddingInner:n.padding)||0;return[0,n.rangeStep*p.bandSpace(t,a,r)]}(e.type,n,t);else if(n.scheme){if(a=function(e,n,t){var r,a=n.scheme.toLowerCase(),i=p.scheme(a),o=n.schemeExtent;i||M.error("Unrecognized scheme name: "+n.scheme);return t=e===d?t+1:e===m?t-1:e===f||e===c?+n.schemeCount||Y:t,e===v?J(i,o,n.reverse):!o&&(r=p.scheme(a+"-"+t))?r:M.isFunction(i)?function(e,n){for(var t=new Array(n),r=n-1||1,a=0;a<n;++a)t[a]=e(a/r);return t}(J(i,o),t):e===O?i:i.slice(0,t)}(e.type,n,t),M.isFunction(a))return e.interpolator(a)}else if(a&&e.type===v)return e.interpolator(i.interpolateRgbBasis(W(a,n.reverse)));a&&n.interpolate&&e.interpolate?e.interpolate(p.interpolate(n.interpolate,n.interpolateGamma)):M.isFunction(e.round)?e.round(r):M.isFunction(e.rangeRound)&&e.interpolate(r?i.interpolateRound:i.interpolate);a&&e.range(W(a,n.reverse))}(a,e,function(e,n,t){var r=(a=e,i=n.domainRaw,i?(a.domain(i),i.length):-1);var a,i;if(-1<r)return r;var o,u,s=n.domain,l=e.type,f=n.zero||void 0===n.zero&&G[l];if(!s)return 0;H[l]&&n.padding&&s[0]!==M.peek(s)&&(c=l,d=s,m=n.range,p=n.padding,h=n.exponent,v=Math.abs(M.peek(m)-m[0]),g=v/(v-2*p),y=c===x?M.zoomLog(d,null,g):c===S?M.zoomPow(d,null,g,.5):c===k?M.zoomPow(d,null,g,h):M.zoomLinear(d,null,g),(d=d.slice())[0]=y[0],d[d.length-1]=y[1],s=d);var c,d,m,p,h,v,g,y;(f||null!=n.domainMin||null!=n.domainMax||null!=n.domainMid)&&(o=(s=s.slice()).length-1||1,f&&(0<s[0]&&(s[0]=0),s[o]<0&&(s[o]=0)),null!=n.domainMin&&(s[0]=n.domainMin),null!=n.domainMax&&(s[o]=n.domainMax),null!=n.domainMid&&(((u=n.domainMid)<s[0]||u>s[o])&&t.warn("Scale domainMid exceeds domain min or max.",u),s.splice(o,0,u)));e.domain(s),l===O&&e.unknown(void 0);n.nice&&e.nice&&e.nice(!0!==n.nice&&b(e,n.nice)||null);return s.length}(a,e,r)),n.fork(n.NO_SOURCE|n.NO_FIELDS)},M.inherits(K,h.Transform).transform=function(e,n){var t=e.modified("sort")||n.changed(n.ADD)||n.modified(e.sort.fields)||n.modified("datum");return t&&n.source.sort(e.sort),this.modified(t),n};function Q(e){h.Transform.call(this,null,e)}function Z(e,n,t,r,a){for(var i,o=(n-e.sum)/2,u=e.length,s=0;s<u;++s)(i=e[s])[r]=o,i[a]=o+=Math.abs(t(i))}function $(e,n,t,r,a){for(var i,o=1/e.sum,u=0,s=e.length,l=0,f=0;l<s;++l)(i=e[l])[r]=u,i[a]=u=o*(f+=Math.abs(t(i)))}function ee(e,n,t,r,a){for(var i,o,u=0,s=0,l=e.length,f=0;f<l;++f)(i=t(o=e[f]))<0?(o[r]=s,o[a]=s+=i):(o[r]=u,o[a]=u+=i)}Q.Definition={type:"Stack",metadata:{modifies:!0},params:[{name:"field",type:"field"},{name:"groupby",type:"field",array:!0},{name:"sort",type:"compare"},{name:"offset",type:"enum",default:"zero",values:["zero","center","normalize"]},{name:"as",type:"string",array:!0,length:2,default:["y0","y1"]}]},M.inherits(Q,h.Transform).transform=function(e,n){var t,r,a,i,o=e.as||["y0","y1"],u=o[0],s=o[1],l=e.field||M.one,f="center"===e.offset?Z:"normalize"===e.offset?$:ee;for(r=0,a=(t=function(e,n,t,r){var a,i,o,u,s,l,f,c,d,m=[],p=function(e){return e(s)};if(null==n)m.push(e.slice());else for(a={},i=0,o=e.length;i<o;++i)s=e[i],l=n.map(p),(f=a[l])||(a[l]=f=[],m.push(f)),f.push(s);for(d=l=0,u=m.length;l<u;++l){for(f=m[l],c=i=0,o=f.length;i<o;++i)c+=Math.abs(r(f[i]));f.sum=c,d<c&&(d=c),t&&f.sort(t)}return m.max=d,m}(n.source,e.groupby,e.sort,l)).length,i=t.max;r<a;++r)f(t[r],i,l,u,s);return n.reflow(e.modified()).modifies(o)},e.axisticks=n,e.datajoin=t,e.encode=r,e.legendentries=R,e.linkpath=_,e.pie=X,e.scale=B,e.sortitems=K,e.stack=Q,e.validTicks=y,Object.defineProperty(e,"__esModule",{value:!0})}); | ||
!function(e,n){"object"==typeof exports&&"undefined"!=typeof module?n(exports,require("vega-scale"),require("vega-util"),require("d3-format"),require("vega-dataflow"),require("d3-array"),require("d3-interpolate")):"function"==typeof define&&define.amd?define(["exports","vega-scale","vega-util","d3-format","vega-dataflow","d3-array","d3-interpolate"],n):n((e.vega=e.vega||{},e.vega.transforms={}),e.vega,e.vega,e.d3,e.vega,e.d3,e.d3)}(this,function(e,v,M,u,g,y,i){"use strict";var x="log",k="pow",S="sqrt",o="band",l="point",s="linear",b="ordinal",f="quantile",c="quantize",O="threshold",d="bin-ordinal",m="sequential";function A(e,n){var t;return M.isObject(n)&&(t=n.step,n=n.interval),M.isString(n)&&(n="time"===e.type?v.timeInterval(n):"utc"===e.type?v.utcInterval(n):M.error("Only time and utc scales accept interval strings."),t&&(n=n.every(t))),n}function p(n,e,t){var r=n.range(),a=r[0],i=M.peek(r);if(i<a&&(r=i,i=a,a=r),e=e.filter(function(e){return!((e=n(e))<a||i<e)}),0<t&&1<e.length){for(var o=[e[0],M.peek(e)];e.length>t&&3<=e.length;)e=e.filter(function(e,n){return!(n%2)});e.length<3&&(e=o)}return e}function D(e,n){return e.ticks?e.ticks(n):e.domain()}function w(e,n,t){var r,a,i=e.tickFormat?e.tickFormat(n,t):t?u.format(t):String;return e.type===x?(r=i,a=function(e){var n=u.formatSpecifier(e||",");{if(null==n.precision){switch(n.precision=12,n.type){case"%":n.precision-=2;break;case"e":n.precision-=1}return i=u.format(n),o=u.format(".1f")(1)[1],function(e){var n,t,r=i(e),a=r.indexOf(o);if(a<0)return r;for(n=function(e,n){var t,r=e.lastIndexOf("e");if(0<r)return r;for(r=e.length;--r>n;)if(48<=(t=e.charCodeAt(r))&&t<=57)return r+1}(r,a),t=n<r.length?r.slice(n):"";--n>a;)if("0"!==r[n]){++n;break}return r.slice(0,n)+t}}return u.format(n)}var i,o}(t),function(e){return r(e)?a(e):""}):i}function n(e){g.Transform.call(this,null,e)}function t(e){g.Transform.call(this,null,e)}function h(){return g.ingest({})}function T(e){return e.exit}function r(e){g.Transform.call(this,null,e)}M.inherits(n,g.Transform).transform=function(e,n){if(this.value&&!e.modified())return n.StopPropagation;var t=n.fork(n.NO_SOURCE|n.NO_FIELDS),r=this.value,a=e.scale,i=null==e.count?e.values?e.values.length:10:A(a,e.count),o=e.format||w(a,i,e.formatSpecifier),u=e.values?p(a,e.values,i):D(a,i);return r&&(t.rem=r),r=u.map(function(e,n){return g.ingest({index:n/(u.length-1),value:e,label:o(e)})}),e.extra&&r.push(g.ingest({index:-1,extra:{value:r[0].value},label:""})),t.source=r,t.add=r,this.value=r,t},M.inherits(t,g.Transform).transform=function(e,n){var t=n.dataflow,r=n.fork(n.NO_SOURCE|n.NO_FIELDS),a=e.item||h,i=e.key||g.tupleid,o=this.value;return M.isArray(r.encode)&&(r.encode=null),o&&(e.modified("key")||n.modified(i))&&M.error("DataJoin does not support modified key function or fields."),o||(n=n.addAll(),this.value=o=M.fastmap().test(T),o.lookup=function(e){return o.get(i(e))}),n.visit(n.ADD,function(e){var n=i(e),t=o.get(n);t?t.exit?(o.empty--,r.add.push(t)):r.mod.push(t):(o.set(n,t=a(e)),r.add.push(t)),t.datum=e,t.exit=!1}),n.visit(n.MOD,function(e){var n=i(e),t=o.get(n);t&&(t.datum=e,r.mod.push(t))}),n.visit(n.REM,function(e){var n=i(e),t=o.get(n);e!==t.datum||t.exit||(r.rem.push(t),t.exit=!0,++o.empty)}),n.changed(n.ADD_MOD)&&r.modifies("datum"),e.clean&&o.empty>t.cleanThreshold&&t.runAfter(o.clean),r},M.inherits(r,g.Transform).transform=function(t,e){var r=e.fork(e.ADD_REM),n=t.encoders,a=e.encode;if(M.isArray(a)){if(!r.changed()&&!a.every(function(e){return n[e]}))return e.StopPropagation;a=a[0],r.encode=null}var i="enter"===a,o=n.update||M.falsy,u=n.enter||M.falsy,l=n.exit||M.falsy,s=(a&&!i?n[a]:o)||M.falsy;if(e.changed(e.ADD)&&(e.visit(e.ADD,function(e){u(e,t),o(e,t),s!==M.falsy&&s!==o&&s(e,t)}),r.modifies(u.output),r.modifies(o.output),s!==M.falsy&&s!==o&&r.modifies(s.output)),e.changed(e.REM)&&l!==M.falsy&&(e.visit(e.REM,function(e){l(e,t)}),r.modifies(l.output)),i||s!==M.falsy){var f=e.MOD|(t.modified()?e.REFLOW:0);i?(e.visit(f,function(e){var n=u(e,t);(s(e,t)||n)&&r.mod.push(e)}),r.mod.length&&r.modifies(u.output)):e.visit(f,function(e){s(e,t)&&r.mod.push(e)}),r.mod.length&&r.modifies(s.output)}return r.changed()?r:e.StopPropagation};var z="symbol",E="discrete",F={};function R(e,n,t){return t===z&&F[e.type]?(o=n,function(e,n,t){var r=t[n+1]||t.max||1/0,a=C(e,o),i=C(r,o);return a&&i?a+"–"+i:i?"< "+i:"≥ "+a}):t===E?(a=n,function(e,n){return n?a(e):null}):(r=n,function(e){return r(e)});var r,a,o}function C(e,n){return isFinite(e)?n(e):null}function a(e){g.Transform.call(this,[],e)}F[f]=function(e){var n=[-1/0].concat(e.quantiles());return n.max=1/0,n},F[c]=function(e){var n=e.domain(),t=n[0],r=M.peek(n),a=e.range().length,i=new Array(a),o=0;i[0]=-1/0;for(;++o<a;)i[o]=(o*r-(o-a)*t)/a;return i.max=1/0,i},F[O]=function(e){var n=[-1/0].concat(e.domain());return n.max=1/0,n},F["bin-linear"]=F[d]=function(e){var n=e.domain();return n.max=n.pop(),n},M.inherits(a,g.Transform).transform=function(t,e){if(null!=this.value&&!t.modified())return e.StopPropagation;var n,r,a,i,o,u,l,s=e.fork(e.NO_SOURCE|e.NO_FIELDS),f=this.value,c=t.type||z,d=t.scale,m=null==t.count?5:A(d,t.count),p=t.format||w(d,m,t.formatSpecifier),h=t.values||(u=m,(l=F[(o=d).type])?l(o):D(o,u));return p=R(d,p,c),f&&(s.rem=f),c===z?(M.isFunction(a=t.size)?(t.values||0!==d(h[0])||(h=h.slice(1)),i=h.reduce(function(e,n){return Math.max(e,a(n,t))},0)):a=M.constant(i=a||8),f=h.map(function(e,n){return g.ingest({index:n,label:p(e,n,h),value:e,offset:i,size:a(e,t)})})):"gradient"===c?(n=t.values?d.domain():h,r=v.scaleFraction(d,n[0],M.peek(n)),f=h.map(function(e,n){return g.ingest({index:n,label:p(e,n,h),value:e,perc:r(e)})})):(a=h.length-1,r=function(e){var n=e.domain(),t=n.length-1,r=+n[0],a=+M.peek(n),i=a-r;if(e.type===O){var o=t?i/t:.1;i=(a+=o)-(r-=o)}return function(e){return(e-r)/i}}(d),f=h.map(function(e,n){return g.ingest({index:n,label:p(e,n,h),value:e,perc:n?r(e):0,perc2:n===a?1:r(h[n+1])})})),s.source=f,s.add=f,this.value=f,s};var L=M.fastmap({line:U,"line-radial":function(e,n,t,r){return U(n*Math.cos(e),n*Math.sin(e),r*Math.cos(t),r*Math.sin(t))},arc:j,"arc-radial":function(e,n,t,r){return j(n*Math.cos(e),n*Math.sin(e),r*Math.cos(t),r*Math.sin(t))},curve:X,"curve-radial":function(e,n,t,r){return X(n*Math.cos(e),n*Math.sin(e),r*Math.cos(t),r*Math.sin(t))},"orthogonal-horizontal":function(e,n,t,r){return"M"+e+","+n+"V"+r+"H"+t},"orthogonal-vertical":function(e,n,t,r){return"M"+e+","+n+"H"+t+"V"+r},"orthogonal-radial":function(e,n,t,r){var a=Math.cos(e),i=Math.sin(e),o=Math.cos(t),u=Math.sin(t),l=Math.abs(t-e)>Math.PI?t<=e:e<t;return"M"+n*a+","+n*i+"A"+n+","+n+" 0 0,"+(l?1:0)+" "+n*o+","+n*u+"L"+r*o+","+r*u},"diagonal-horizontal":function(e,n,t,r){var a=(e+t)/2;return"M"+e+","+n+"C"+a+","+n+" "+a+","+r+" "+t+","+r},"diagonal-vertical":function(e,n,t,r){var a=(n+r)/2;return"M"+e+","+n+"C"+e+","+a+" "+t+","+a+" "+t+","+r},"diagonal-radial":function(e,n,t,r){var a=Math.cos(e),i=Math.sin(e),o=Math.cos(t),u=Math.sin(t),l=(n+r)/2;return"M"+n*a+","+n*i+"C"+l*a+","+l*i+" "+l*o+","+l*u+" "+r*o+","+r*u}});function P(e){return e.source.x}function q(e){return e.source.y}function I(e){return e.target.x}function _(e){return e.target.y}function N(e){g.Transform.call(this,{},e)}function U(e,n,t,r){return"M"+e+","+n+"L"+t+","+r}function j(e,n,t,r){var a=t-e,i=r-n,o=Math.sqrt(a*a+i*i)/2;return"M"+e+","+n+"A"+o+","+o+" "+180*Math.atan2(i,a)/Math.PI+" 0 1 "+t+","+r}function X(e,n,t,r){var a=t-e,i=r-n,o=.2*(a+i),u=.2*(i-a);return"M"+e+","+n+"C"+(e+o)+","+(n+u)+" "+(t+u)+","+(r-o)+" "+t+","+r}function Y(e){g.Transform.call(this,null,e)}N.Definition={type:"LinkPath",metadata:{modifies:!0},params:[{name:"sourceX",type:"field",default:"source.x"},{name:"sourceY",type:"field",default:"source.y"},{name:"targetX",type:"field",default:"target.x"},{name:"targetY",type:"field",default:"target.y"},{name:"orient",type:"enum",default:"vertical",values:["horizontal","vertical","radial"]},{name:"shape",type:"enum",default:"line",values:["line","arc","curve","diagonal","orthogonal"]},{name:"as",type:"string",default:"path"}]},M.inherits(N,g.Transform).transform=function(e,n){var t=e.sourceX||P,r=e.sourceY||q,a=e.targetX||I,i=e.targetY||_,o=e.as||"path",u=e.orient||"vertical",l=e.shape||"line",s=L.get(l+"-"+u)||L.get(l);return s||M.error("LinkPath unsupported type: "+e.shape+(e.orient?"-"+e.orient:"")),n.visit(n.SOURCE,function(e){e[o]=s(t(e),r(e),a(e),i(e))}),n.reflow(e.modified()).modifies(o)},Y.Definition={type:"Pie",metadata:{modifies:!0},params:[{name:"field",type:"field"},{name:"startAngle",type:"number",default:0},{name:"endAngle",type:"number",default:6.283185307179586},{name:"sort",type:"boolean",default:!1},{name:"as",type:"string",array:!0,length:2,default:["startAngle","endAngle"]}]},M.inherits(Y,g.Transform).transform=function(e,n){var t,r,a,i=e.as||["startAngle","endAngle"],o=i[0],u=i[1],l=e.field||M.one,s=e.startAngle||0,f=null!=e.endAngle?e.endAngle:2*Math.PI,c=n.source,d=c.map(l),m=d.length,p=s,h=(f-s)/y.sum(d),v=y.range(m);for(e.sort&&v.sort(function(e,n){return d[e]-d[n]}),t=0;t<m;++t)a=d[v[t]],(r=c[v[t]])[o]=p,r[u]=p+=a*h;return this.value=d,n.reflow(e.modified()).modifies(i)};var G=5,H=M.toSet([s,k,S]),V=M.toSet([s,x,k,S,"time","utc"]),B=M.toSet(["set","modified","clear","type","scheme","schemeExtent","schemeCount","domain","domainMin","domainMid","domainMax","domainRaw","nice","zero","range","rangeStep","round","reverse","interpolate","interpolateGamma"]);function J(e){g.Transform.call(this,null,e),this.modified(!0)}function W(e,n,t){return M.isFunction(e)&&(n||t)?v.interpolateRange(e,K(n||[0,1],t)):e}function K(e,n){return n?e.slice().reverse():e}function Q(e){g.Transform.call(this,null,e)}M.inherits(J,g.Transform).transform=function(e,n){var t,r=n.dataflow,a=this.value;for(t in a&&!e.modified("type")||(this.value=a=v.scale((e.type||s).toLowerCase())()),e)if(!B[t]){if("padding"===t&&V[a.type])continue;M.isFunction(a[t])?a[t](e[t]):r.warn("Unsupported scale property: "+t)}return function(e,n,t){var r=n.round||!1,a=n.range;if(null!=n.rangeStep)a=function(e,n,t){e!==o&&e!==l&&M.error("Only band and point scales support rangeStep.");var r=(null!=n.paddingOuter?n.paddingOuter:n.padding)||0,a=e===l?1:(null!=n.paddingInner?n.paddingInner:n.padding)||0;return[0,n.rangeStep*v.bandSpace(t,a,r)]}(e.type,n,t);else if(n.scheme){if(a=function(e,n,t){var r,a=n.scheme.toLowerCase(),i=v.scheme(a),o=n.schemeExtent;i||M.error("Unrecognized scheme name: "+n.scheme);return t=e===O?t+1:e===d?t-1:e===f||e===c?+n.schemeCount||G:t,e===m?W(i,o,n.reverse):!o&&(r=v.scheme(a+"-"+t))?r:M.isFunction(i)?function(e,n){for(var t=new Array(n),r=n+2,a=0;a<n;)t[a]=e(++a/r);return t}(W(i,o),t):e===b?i:i.slice(0,t)}(e.type,n,t),M.isFunction(a))return e.interpolator(a)}else if(a&&e.type===m)return e.interpolator(i.interpolateRgbBasis(K(a,n.reverse)));a&&n.interpolate&&e.interpolate?e.interpolate(v.interpolate(n.interpolate,n.interpolateGamma)):M.isFunction(e.round)?e.round(r):M.isFunction(e.rangeRound)&&e.interpolate(r?i.interpolateRound:i.interpolate);a&&e.range(K(a,n.reverse))}(a,e,function(e,n,t){var r=(a=e,i=n.domainRaw,i?(a.domain(i),i.length):-1);var a,i;if(-1<r)return r;var o,u,l=n.domain,s=e.type,f=n.zero||void 0===n.zero&&H[s];if(!l)return 0;V[s]&&n.padding&&l[0]!==M.peek(l)&&(c=s,d=l,m=n.range,p=n.padding,h=n.exponent,v=Math.abs(M.peek(m)-m[0]),g=v/(v-2*p),y=c===x?M.zoomLog(d,null,g):c===S?M.zoomPow(d,null,g,.5):c===k?M.zoomPow(d,null,g,h):M.zoomLinear(d,null,g),(d=d.slice())[0]=y[0],d[d.length-1]=y[1],l=d);var c,d,m,p,h,v,g,y;(f||null!=n.domainMin||null!=n.domainMax||null!=n.domainMid)&&(o=(l=l.slice()).length-1||1,f&&(0<l[0]&&(l[0]=0),l[o]<0&&(l[o]=0)),null!=n.domainMin&&(l[0]=n.domainMin),null!=n.domainMax&&(l[o]=n.domainMax),null!=n.domainMid&&(((u=n.domainMid)<l[0]||u>l[o])&&t.warn("Scale domainMid exceeds domain min or max.",u),l.splice(o,0,u)));e.domain(l),s===b&&e.unknown(void 0);n.nice&&e.nice&&e.nice(!0!==n.nice&&A(e,n.nice)||null);return l.length}(a,e,r)),n.fork(n.NO_SOURCE|n.NO_FIELDS)},M.inherits(Q,g.Transform).transform=function(e,n){var t=e.modified("sort")||n.changed(n.ADD)||n.modified(e.sort.fields)||n.modified("datum");return t&&n.source.sort(e.sort),this.modified(t),n};function Z(e){g.Transform.call(this,null,e)}function $(e,n,t,r,a){for(var i,o=(n-e.sum)/2,u=e.length,l=0;l<u;++l)(i=e[l])[r]=o,i[a]=o+=Math.abs(t(i))}function ee(e,n,t,r,a){for(var i,o=1/e.sum,u=0,l=e.length,s=0,f=0;s<l;++s)(i=e[s])[r]=u,i[a]=u=o*(f+=Math.abs(t(i)))}function ne(e,n,t,r,a){for(var i,o,u=0,l=0,s=e.length,f=0;f<s;++f)(i=t(o=e[f]))<0?(o[r]=l,o[a]=l+=i):(o[r]=u,o[a]=u+=i)}Z.Definition={type:"Stack",metadata:{modifies:!0},params:[{name:"field",type:"field"},{name:"groupby",type:"field",array:!0},{name:"sort",type:"compare"},{name:"offset",type:"enum",default:"zero",values:["zero","center","normalize"]},{name:"as",type:"string",array:!0,length:2,default:["y0","y1"]}]},M.inherits(Z,g.Transform).transform=function(e,n){var t,r,a,i,o=e.as||["y0","y1"],u=o[0],l=o[1],s=e.field||M.one,f="center"===e.offset?$:"normalize"===e.offset?ee:ne;for(r=0,a=(t=function(e,n,t,r){var a,i,o,u,l,s,f,c,d,m=[],p=function(e){return e(l)};if(null==n)m.push(e.slice());else for(a={},i=0,o=e.length;i<o;++i)l=e[i],s=n.map(p),(f=a[s])||(a[s]=f=[],m.push(f)),f.push(l);for(d=s=0,u=m.length;s<u;++s){for(f=m[s],c=i=0,o=f.length;i<o;++i)c+=Math.abs(r(f[i]));f.sum=c,d<c&&(d=c),t&&f.sort(t)}return m.max=d,m}(n.source,e.groupby,e.sort,s)).length,i=t.max;r<a;++r)f(t[r],i,s,u,l);return n.reflow(e.modified()).modifies(o)},e.axisticks=n,e.datajoin=t,e.encode=r,e.legendentries=a,e.linkpath=N,e.pie=Y,e.scale=J,e.sortitems=Q,e.stack=Z,e.validTicks=p,Object.defineProperty(e,"__esModule",{value:!0})}); |
{ | ||
"name": "vega-encode", | ||
"version": "2.0.8", | ||
"version": "3.0.0", | ||
"description": "Visual encoding transforms for Vega dataflows.", | ||
@@ -31,16 +31,16 @@ "keywords": [ | ||
"dependencies": { | ||
"d3-array": "1", | ||
"d3-format": "1", | ||
"d3-interpolate": "1", | ||
"vega-dataflow": "3", | ||
"vega-scale": "^2.1", | ||
"vega-util": "1" | ||
"d3-array": "^1.2.1", | ||
"d3-format": "^1.2.2", | ||
"d3-interpolate": "^1.1.6", | ||
"vega-dataflow": "^4.0.0", | ||
"vega-scale": "^2.1.1", | ||
"vega-util": "^1.7.0" | ||
}, | ||
"devDependencies": { | ||
"eslint": "4", | ||
"rollup": "0.43", | ||
"rollup": "0.58.2", | ||
"tape": "4", | ||
"uglify-js": "3", | ||
"vega-transforms": "1" | ||
"vega-transforms": "^2.0.0" | ||
} | ||
} |
@@ -0,1 +1,2 @@ | ||
import {Symbols, Discrete} from './legend-types'; | ||
import {Quantile, Quantize, Threshold, BinLinear, BinOrdinal} from './scale-types'; | ||
@@ -5,16 +6,14 @@ import {tickValues} from './ticks'; | ||
var discrete = {}; | ||
discrete[Quantile] = quantile; | ||
discrete[Quantize] = quantize; | ||
discrete[Threshold] = threshold; | ||
discrete[BinLinear] = bin; | ||
discrete[BinOrdinal] = bin; | ||
var symbols = {}; | ||
symbols[Quantile] = quantileSymbols; | ||
symbols[Quantize] = quantizeSymbols; | ||
symbols[Threshold] = thresholdSymbols; | ||
symbols[BinLinear] = symbols[BinOrdinal] = binSymbols; | ||
export function labelValues(scale, count, gradient) { | ||
if (gradient) return scale.domain(); | ||
var values = discrete[scale.type]; | ||
export function labelValues(scale, count) { | ||
var values = symbols[scale.type]; | ||
return values ? values(scale) : tickValues(scale, count); | ||
} | ||
function quantize(scale) { | ||
function quantizeSymbols(scale) { | ||
var domain = scale.domain(), | ||
@@ -34,3 +33,3 @@ x0 = domain[0], | ||
function quantile(scale) { | ||
function quantileSymbols(scale) { | ||
var values = [-Infinity].concat(scale.quantiles()); | ||
@@ -42,3 +41,3 @@ values.max = +Infinity; | ||
function threshold(scale) { | ||
function thresholdSymbols(scale) { | ||
var values = [-Infinity].concat(scale.domain()); | ||
@@ -50,3 +49,3 @@ values.max = +Infinity; | ||
function bin(scale) { | ||
function binSymbols(scale) { | ||
var values = scale.domain(); | ||
@@ -58,4 +57,6 @@ values.max = values.pop(); | ||
export function labelFormat(scale, format) { | ||
return discrete[scale.type] ? formatRange(format) : formatPoint(format); | ||
export function labelFormat(scale, format, type) { | ||
return type === Symbols && symbols[scale.type] ? formatRange(format) | ||
: type === Discrete ? formatDiscrete(format) | ||
: formatPoint(format); | ||
} | ||
@@ -72,4 +73,6 @@ | ||
function formatValue(value, format) { | ||
return isFinite(value) ? format(value) : null; | ||
function formatDiscrete(format) { | ||
return function(value, index) { | ||
return index ? format(value) : null; | ||
} | ||
} | ||
@@ -82,1 +85,24 @@ | ||
} | ||
function formatValue(value, format) { | ||
return isFinite(value) ? format(value) : null; | ||
} | ||
export function labelFraction(scale) { | ||
var domain = scale.domain(), | ||
count = domain.length - 1, | ||
lo = +domain[0], | ||
hi = +peek(domain), | ||
span = hi - lo; | ||
if (scale.type === Threshold) { | ||
var adjust = count ? span / count : 0.1; | ||
lo -= adjust; | ||
hi += adjust; | ||
span = hi - lo; | ||
} | ||
return function(value) { | ||
return (value - lo) / span; | ||
}; | ||
} |
@@ -1,2 +0,3 @@ | ||
import {labelFormat, labelValues} from './labels'; | ||
import {labelFormat, labelFraction, labelValues} from './labels'; | ||
import {Symbols, Gradient} from './legend-types'; | ||
import {tickCount, tickFormat} from './ticks'; | ||
@@ -12,3 +13,3 @@ import {Transform, ingest} from 'vega-dataflow'; | ||
* @param {Scale} params.scale - The scale to generate items for. | ||
* @param {*} [params.count=10] - The approximate number of items, or | ||
* @param {*} [params.count=5] - The approximate number of items, or | ||
* desired tick interval, to use. | ||
@@ -18,5 +19,5 @@ * @param {Array<*>} [params.values] - The exact tick values to use. | ||
* If provided, the count argument is ignored. | ||
* @param {function(*):string} [params.formatSpecifier] - A format specifier | ||
* @param {string} [params.formatSpecifier] - A format specifier | ||
* to use in conjunction with scale.tickFormat. Legal values are | ||
* any valid d3 4.0 format specifier. | ||
* any valid D3 format specifier string. | ||
* @param {function(*):string} [params.format] - The format function to use. | ||
@@ -37,20 +38,15 @@ * If provided, the formatSpecifier argument is ignored. | ||
var out = pulse.fork(pulse.NO_SOURCE | pulse.NO_FIELDS), | ||
total = 0, | ||
items = this.value, | ||
grad = _.type === 'gradient', | ||
type = _.type || Symbols, | ||
scale = _.scale, | ||
count = _.count == null ? 5 : tickCount(scale, _.count), | ||
format = _.format || tickFormat(scale, count, _.formatSpecifier), | ||
values = _.values || labelValues(scale, count, grad); | ||
values = _.values || labelValues(scale, count, type), | ||
domain, fraction, size, offset; | ||
format = labelFormat(scale, format); | ||
format = labelFormat(scale, format, type); | ||
if (items) out.rem = items; | ||
if (grad) { | ||
var domain = _.values ? scale.domain() : values, | ||
fraction = scaleFraction(scale, domain[0], peek(domain)); | ||
} else { | ||
var size = _.size, | ||
offset; | ||
if (isFunction(size)) { | ||
if (type === Symbols) { | ||
if (isFunction(size = _.size)) { | ||
// if first value maps to size zero, remove from list (vega#717) | ||
@@ -67,22 +63,43 @@ if (!_.values && scale(values[0]) === 0) { | ||
} | ||
items = values.map(function(value, index) { | ||
return ingest({ | ||
index: index, | ||
label: format(value, index, values), | ||
value: value, | ||
offset: offset, | ||
size: size(value, _) | ||
}); | ||
}); | ||
} | ||
items = values.map(function(value, index) { | ||
var t = ingest({ | ||
index: index, | ||
label: format(value, index, values), | ||
value: value | ||
else if (type === Gradient) { | ||
domain = _.values ? scale.domain() : values, | ||
fraction = scaleFraction(scale, domain[0], peek(domain)); | ||
items = values.map(function(value, index) { | ||
return ingest({ | ||
index: index, | ||
label: format(value, index, values), | ||
value: value, | ||
perc: fraction(value) | ||
}); | ||
}); | ||
} | ||
if (grad) { | ||
t.perc = fraction(value); | ||
} else { | ||
t.offset = offset; | ||
t.size = size(value, _); | ||
t.total = Math.round(total); | ||
total += t.size; | ||
} | ||
return t; | ||
}); | ||
else { | ||
size = values.length - 1; | ||
fraction = labelFraction(scale); | ||
items = values.map(function(value, index) { | ||
return ingest({ | ||
index: index, | ||
label: format(value, index, values), | ||
value: value, | ||
perc: index ? fraction(value) : 0, | ||
perc2: index === size ? 1 : fraction(values[index+1]) | ||
}); | ||
}); | ||
} | ||
out.source = items; | ||
@@ -89,0 +106,0 @@ out.add = items; |
@@ -232,5 +232,5 @@ import {tickCount} from './ticks'; | ||
var samples = new Array(count), | ||
n = (count - 1) || 1; | ||
for (var i = 0; i < count; ++i) samples[i] = interpolator(i / n); | ||
n = count + 2; | ||
for (var i = 0; i < count;) samples[i] = interpolator(++i / n); | ||
return samples; | ||
} |
@@ -97,4 +97,4 @@ import {Log} from './scale-types'; | ||
export function tickFormat(scale, count, specifier) { | ||
var format = scale.tickFormat | ||
? scale.tickFormat(count, specifier) | ||
var format = scale.tickFormat ? scale.tickFormat(count, specifier) | ||
: specifier ? numberFormat(specifier) | ||
: String; | ||
@@ -101,0 +101,0 @@ |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
90821
20
2090
+ Addednode-fetch@2.7.0(transitive)
+ Addedtr46@0.0.3(transitive)
+ Addedvega-dataflow@4.1.0(transitive)
+ Addedvega-loader@3.1.0(transitive)
+ Addedwebidl-conversions@3.0.1(transitive)
+ Addedwhatwg-url@5.0.0(transitive)
- Removedd3-dispatch@1.0.6(transitive)
- Removedd3-request@1.0.6(transitive)
- Removedvega-dataflow@3.1.0(transitive)
- Removedvega-loader@2.1.0(transitive)
- Removedxmlhttprequest@1.8.0(transitive)
Updatedd3-array@^1.2.1
Updatedd3-format@^1.2.2
Updatedd3-interpolate@^1.1.6
Updatedvega-dataflow@^4.0.0
Updatedvega-scale@^2.1.1
Updatedvega-util@^1.7.0