diff options
Diffstat (limited to 'js/dojo/dojox/charting/scaler/linear.js')
| -rw-r--r-- | js/dojo/dojox/charting/scaler/linear.js | 251 |
1 files changed, 251 insertions, 0 deletions
diff --git a/js/dojo/dojox/charting/scaler/linear.js b/js/dojo/dojox/charting/scaler/linear.js new file mode 100644 index 0000000..3f4c8eb --- /dev/null +++ b/js/dojo/dojox/charting/scaler/linear.js @@ -0,0 +1,251 @@ +//>>built +define("dojox/charting/scaler/linear", ["dojo/_base/lang", "./common"], + function(lang, common){ + var linear = lang.getObject("dojox.charting.scaler.linear", true); + + var deltaLimit = 3, // pixels + findString = common.findString, + getLabel = common.getNumericLabel; + + var calcTicks = function(min, max, kwArgs, majorTick, minorTick, microTick, span){ + kwArgs = lang.delegate(kwArgs); + if(!majorTick){ + if(kwArgs.fixUpper == "major"){ kwArgs.fixUpper = "minor"; } + if(kwArgs.fixLower == "major"){ kwArgs.fixLower = "minor"; } + } + if(!minorTick){ + if(kwArgs.fixUpper == "minor"){ kwArgs.fixUpper = "micro"; } + if(kwArgs.fixLower == "minor"){ kwArgs.fixLower = "micro"; } + } + if(!microTick){ + if(kwArgs.fixUpper == "micro"){ kwArgs.fixUpper = "none"; } + if(kwArgs.fixLower == "micro"){ kwArgs.fixLower = "none"; } + } + var lowerBound = findString(kwArgs.fixLower, ["major"]) ? + Math.floor(kwArgs.min / majorTick) * majorTick : + findString(kwArgs.fixLower, ["minor"]) ? + Math.floor(kwArgs.min / minorTick) * minorTick : + findString(kwArgs.fixLower, ["micro"]) ? + Math.floor(kwArgs.min / microTick) * microTick : kwArgs.min, + upperBound = findString(kwArgs.fixUpper, ["major"]) ? + Math.ceil(kwArgs.max / majorTick) * majorTick : + findString(kwArgs.fixUpper, ["minor"]) ? + Math.ceil(kwArgs.max / minorTick) * minorTick : + findString(kwArgs.fixUpper, ["micro"]) ? + Math.ceil(kwArgs.max / microTick) * microTick : kwArgs.max; + + if(kwArgs.useMin){ min = lowerBound; } + if(kwArgs.useMax){ max = upperBound; } + + var majorStart = (!majorTick || kwArgs.useMin && findString(kwArgs.fixLower, ["major"])) ? + min : Math.ceil(min / majorTick) * majorTick, + minorStart = (!minorTick || kwArgs.useMin && findString(kwArgs.fixLower, ["major", "minor"])) ? + min : Math.ceil(min / minorTick) * minorTick, + microStart = (! microTick || kwArgs.useMin && findString(kwArgs.fixLower, ["major", "minor", "micro"])) ? + min : Math.ceil(min / microTick) * microTick, + majorCount = !majorTick ? 0 : (kwArgs.useMax && findString(kwArgs.fixUpper, ["major"]) ? + Math.round((max - majorStart) / majorTick) : + Math.floor((max - majorStart) / majorTick)) + 1, + minorCount = !minorTick ? 0 : (kwArgs.useMax && findString(kwArgs.fixUpper, ["major", "minor"]) ? + Math.round((max - minorStart) / minorTick) : + Math.floor((max - minorStart) / minorTick)) + 1, + microCount = !microTick ? 0 : (kwArgs.useMax && findString(kwArgs.fixUpper, ["major", "minor", "micro"]) ? + Math.round((max - microStart) / microTick) : + Math.floor((max - microStart) / microTick)) + 1, + minorPerMajor = minorTick ? Math.round(majorTick / minorTick) : 0, + microPerMinor = microTick ? Math.round(minorTick / microTick) : 0, + majorPrecision = majorTick ? Math.floor(Math.log(majorTick) / Math.LN10) : 0, + minorPrecision = minorTick ? Math.floor(Math.log(minorTick) / Math.LN10) : 0, + scale = span / (max - min); + if(!isFinite(scale)){ scale = 1; } + + return { + bounds: { + lower: lowerBound, + upper: upperBound, + from: min, + to: max, + scale: scale, + span: span + }, + major: { + tick: majorTick, + start: majorStart, + count: majorCount, + prec: majorPrecision + }, + minor: { + tick: minorTick, + start: minorStart, + count: minorCount, + prec: minorPrecision + }, + micro: { + tick: microTick, + start: microStart, + count: microCount, + prec: 0 + }, + minorPerMajor: minorPerMajor, + microPerMinor: microPerMinor, + scaler: linear + }; + }; + + return lang.mixin(linear, { + buildScaler: function(/*Number*/ min, /*Number*/ max, /*Number*/ span, /*Object*/ kwArgs){ + var h = {fixUpper: "none", fixLower: "none", natural: false}; + if(kwArgs){ + if("fixUpper" in kwArgs){ h.fixUpper = String(kwArgs.fixUpper); } + if("fixLower" in kwArgs){ h.fixLower = String(kwArgs.fixLower); } + if("natural" in kwArgs){ h.natural = Boolean(kwArgs.natural); } + } + + // update bounds + if("min" in kwArgs){ min = kwArgs.min; } + if("max" in kwArgs){ max = kwArgs.max; } + if(kwArgs.includeZero){ + if(min > 0){ min = 0; } + if(max < 0){ max = 0; } + } + h.min = min; + h.useMin = true; + h.max = max; + h.useMax = true; + + if("from" in kwArgs){ + min = kwArgs.from; + h.useMin = false; + } + if("to" in kwArgs){ + max = kwArgs.to; + h.useMax = false; + } + + // check for erroneous condition + if(max <= min){ + return calcTicks(min, max, h, 0, 0, 0, span); // Object + } + + var mag = Math.floor(Math.log(max - min) / Math.LN10), + major = kwArgs && ("majorTickStep" in kwArgs) ? kwArgs.majorTickStep : Math.pow(10, mag), + minor = 0, micro = 0, ticks; + + // calculate minor ticks + if(kwArgs && ("minorTickStep" in kwArgs)){ + minor = kwArgs.minorTickStep; + }else{ + do{ + minor = major / 10; + if(!h.natural || minor > 0.9){ + ticks = calcTicks(min, max, h, major, minor, 0, span); + if(ticks.bounds.scale * ticks.minor.tick > deltaLimit){ break; } + } + minor = major / 5; + if(!h.natural || minor > 0.9){ + ticks = calcTicks(min, max, h, major, minor, 0, span); + if(ticks.bounds.scale * ticks.minor.tick > deltaLimit){ break; } + } + minor = major / 2; + if(!h.natural || minor > 0.9){ + ticks = calcTicks(min, max, h, major, minor, 0, span); + if(ticks.bounds.scale * ticks.minor.tick > deltaLimit){ break; } + } + return calcTicks(min, max, h, major, 0, 0, span); // Object + }while(false); + } + + // calculate micro ticks + if(kwArgs && ("microTickStep" in kwArgs)){ + micro = kwArgs.microTickStep; + ticks = calcTicks(min, max, h, major, minor, micro, span); + }else{ + do{ + micro = minor / 10; + if(!h.natural || micro > 0.9){ + ticks = calcTicks(min, max, h, major, minor, micro, span); + if(ticks.bounds.scale * ticks.micro.tick > deltaLimit){ break; } + } + micro = minor / 5; + if(!h.natural || micro > 0.9){ + ticks = calcTicks(min, max, h, major, minor, micro, span); + if(ticks.bounds.scale * ticks.micro.tick > deltaLimit){ break; } + } + micro = minor / 2; + if(!h.natural || micro > 0.9){ + ticks = calcTicks(min, max, h, major, minor, micro, span); + if(ticks.bounds.scale * ticks.micro.tick > deltaLimit){ break; } + } + micro = 0; + }while(false); + } + + return micro ? ticks : calcTicks(min, max, h, major, minor, 0, span); // Object + }, + buildTicks: function(/*Object*/ scaler, /*Object*/ kwArgs){ + var step, next, tick, + nextMajor = scaler.major.start, + nextMinor = scaler.minor.start, + nextMicro = scaler.micro.start; + if(kwArgs.microTicks && scaler.micro.tick){ + step = scaler.micro.tick, next = nextMicro; + }else if(kwArgs.minorTicks && scaler.minor.tick){ + step = scaler.minor.tick, next = nextMinor; + }else if(scaler.major.tick){ + step = scaler.major.tick, next = nextMajor; + }else{ + // no ticks + return null; + } + // make sure that we have finite bounds + var revScale = 1 / scaler.bounds.scale; + if(scaler.bounds.to <= scaler.bounds.from || isNaN(revScale) || !isFinite(revScale) || + step <= 0 || isNaN(step) || !isFinite(step)){ + // no ticks + return null; + } + // loop over all ticks + var majorTicks = [], minorTicks = [], microTicks = []; + while(next <= scaler.bounds.to + revScale){ + if(Math.abs(nextMajor - next) < step / 2){ + // major tick + tick = {value: nextMajor}; + if(kwArgs.majorLabels){ + tick.label = getLabel(nextMajor, scaler.major.prec, kwArgs); + } + majorTicks.push(tick); + nextMajor += scaler.major.tick; + nextMinor += scaler.minor.tick; + nextMicro += scaler.micro.tick; + }else if(Math.abs(nextMinor - next) < step / 2){ + // minor tick + if(kwArgs.minorTicks){ + tick = {value: nextMinor}; + if(kwArgs.minorLabels && (scaler.minMinorStep <= scaler.minor.tick * scaler.bounds.scale)){ + tick.label = getLabel(nextMinor, scaler.minor.prec, kwArgs); + } + minorTicks.push(tick); + } + nextMinor += scaler.minor.tick; + nextMicro += scaler.micro.tick; + }else{ + // micro tick + if(kwArgs.microTicks){ + microTicks.push({value: nextMicro}); + } + nextMicro += scaler.micro.tick; + } + next += step; + } + return {major: majorTicks, minor: minorTicks, micro: microTicks}; // Object + }, + getTransformerFromModel: function(/*Object*/ scaler){ + var offset = scaler.bounds.from, scale = scaler.bounds.scale; + return function(x){ return (x - offset) * scale; }; // Function + }, + getTransformerFromPlot: function(/*Object*/ scaler){ + var offset = scaler.bounds.from, scale = scaler.bounds.scale; + return function(x){ return x / scale + offset; }; // Function + } + }); +}); |
