/* Copyright (c) 2004-2012, The Dojo Foundation All Rights Reserved. Available via Academic Free License >= 2.1 OR the modified BSD license. see: http://dojotoolkit.org/license for details */ if(!dojo._hasResource["dojox.charting.plot2d.Grid"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. dojo._hasResource["dojox.charting.plot2d.Grid"] = true; dojo.provide("dojox.charting.plot2d.Grid"); dojo.require("dojox.charting.Element"); dojo.require("dojox.charting.plot2d.common"); dojo.require("dojox.lang.functional"); dojo.require("dojox.lang.utils"); /*===== dojo.declare("dojox.charting.plot2d.__GridCtorArgs", dojox.charting.plot2d.__DefaultCtorArgs, { // summary: // A special keyword arguments object that is specific to a grid "plot". // hMajorLines: Boolean? // Whether to show lines at the major ticks along the horizontal axis. Default is true. hMajorLines: true, // hMinorLines: Boolean? // Whether to show lines at the minor ticks along the horizontal axis. Default is false. hMinorLines: false, // vMajorLines: Boolean? // Whether to show lines at the major ticks along the vertical axis. Default is true. vMajorLines: true, // vMinorLines: Boolean? // Whether to show lines at the major ticks along the vertical axis. Default is false. vMinorLines: false, // hStripes: String? // Whether or not to show stripes (alternating fills) along the horizontal axis. Default is "none". hStripes: "none", // vStripes: String? // Whether or not to show stripes (alternating fills) along the vertical axis. Default is "none". vStripes: "none" }); =====*/ (function(){ var du = dojox.lang.utils, dc = dojox.charting.plot2d.common; dojo.declare("dojox.charting.plot2d.Grid", dojox.charting.Element, { // summary: // A "faux" plot that can be placed behind other plots to represent // a grid against which other plots can be easily measured. defaultParams: { hAxis: "x", // use a horizontal axis named "x" vAxis: "y", // use a vertical axis named "y" hMajorLines: true, // draw horizontal major lines hMinorLines: false, // draw horizontal minor lines vMajorLines: true, // draw vertical major lines vMinorLines: false, // draw vertical minor lines hStripes: "none", // TBD vStripes: "none", // TBD animate: null // animate bars into place }, optionalParams: {}, // no optional parameters constructor: function(chart, kwArgs){ // summary: // Create the faux Grid plot. // chart: dojox.charting.Chart2D // The chart this plot belongs to. // kwArgs: dojox.charting.plot2d.__GridCtorArgs? // An optional keyword arguments object to help define the parameters of the underlying grid. this.opt = dojo.clone(this.defaultParams); du.updateWithObject(this.opt, kwArgs); this.hAxis = this.opt.hAxis; this.vAxis = this.opt.vAxis; this.dirty = true; this.animate = this.opt.animate; this.zoom = null, this.zoomQueue = []; // zooming action task queue this.lastWindow = {vscale: 1, hscale: 1, xoffset: 0, yoffset: 0}; }, clear: function(){ // summary: // Clear out any parameters set on this plot. // returns: dojox.charting.plot2d.Grid // The reference to this plot for functional chaining. this._hAxis = null; this._vAxis = null; this.dirty = true; return this; // dojox.charting.plot2d.Grid }, setAxis: function(axis){ // summary: // Set an axis for this plot. // returns: dojox.charting.plot2d.Grid // The reference to this plot for functional chaining. if(axis){ this[axis.vertical ? "_vAxis" : "_hAxis"] = axis; } return this; // dojox.charting.plot2d.Grid }, addSeries: function(run){ // summary: // Ignored but included as a dummy method. // returns: dojox.charting.plot2d.Grid // The reference to this plot for functional chaining. return this; // dojox.charting.plot2d.Grid }, getSeriesStats: function(){ // summary: // Returns default stats (irrelevant for this type of plot). // returns: Object // {hmin, hmax, vmin, vmax} min/max in both directions. return dojo.delegate(dc.defaultStats); }, initializeScalers: function(){ // summary: // Does nothing (irrelevant for this type of plot). return this; }, isDirty: function(){ // summary: // Return whether or not this plot needs to be redrawn. // returns: Boolean // If this plot needs to be rendered, this will return true. return this.dirty || this._hAxis && this._hAxis.dirty || this._vAxis && this._vAxis.dirty; // Boolean }, performZoom: function(dim, offsets){ // summary: // Create/alter any zooming windows on this plot. // dim: Object // An object of the form { width, height }. // offsets: Object // An object of the form { l, r, t, b }. // returns: dojox.charting.plot2d.Grid // A reference to this plot for functional chaining. // get current zooming various var vs = this._vAxis.scale || 1, hs = this._hAxis.scale || 1, vOffset = dim.height - offsets.b, hBounds = this._hAxis.getScaler().bounds, xOffset = (hBounds.from - hBounds.lower) * hBounds.scale, vBounds = this._vAxis.getScaler().bounds, yOffset = (vBounds.from - vBounds.lower) * vBounds.scale; // get incremental zooming various rVScale = vs / this.lastWindow.vscale, rHScale = hs / this.lastWindow.hscale, rXOffset = (this.lastWindow.xoffset - xOffset)/ ((this.lastWindow.hscale == 1)? hs : this.lastWindow.hscale), rYOffset = (yOffset - this.lastWindow.yoffset)/ ((this.lastWindow.vscale == 1)? vs : this.lastWindow.vscale), shape = this.group, anim = dojox.gfx.fx.animateTransform(dojo.delegate({ shape: shape, duration: 1200, transform:[ {name:"translate", start:[0, 0], end: [offsets.l * (1 - rHScale), vOffset * (1 - rVScale)]}, {name:"scale", start:[1, 1], end: [rHScale, rVScale]}, {name:"original"}, {name:"translate", start: [0, 0], end: [rXOffset, rYOffset]} ]}, this.zoom)); dojo.mixin(this.lastWindow, {vscale: vs, hscale: hs, xoffset: xOffset, yoffset: yOffset}); //add anim to zooming action queue, //in order to avoid several zooming action happened at the same time this.zoomQueue.push(anim); //perform each anim one by one in zoomQueue dojo.connect(anim, "onEnd", this, function(){ this.zoom = null; this.zoomQueue.shift(); if(this.zoomQueue.length > 0){ this.zoomQueue[0].play(); } }); if(this.zoomQueue.length == 1){ this.zoomQueue[0].play(); } return this; // dojox.charting.plot2d.Grid }, getRequiredColors: function(){ // summary: // Ignored but included as a dummy method. // returns: Number // Returns 0, since there are no series associated with this plot type. return 0; // Number }, render: function(dim, offsets){ // summary: // Render the plot on the chart. // dim: Object // An object of the form { width, height }. // offsets: Object // An object of the form { l, r, t, b }. // returns: dojox.charting.plot2d.Grid // A reference to this plot for functional chaining. if(this.zoom){ return this.performZoom(dim, offsets); } this.dirty = this.isDirty(); if(!this.dirty){ return this; } this.cleanGroup(); var s = this.group, ta = this.chart.theme.axis; // draw horizontal stripes and lines try{ var vScaler = this._vAxis.getScaler(), vt = vScaler.scaler.getTransformerFromModel(vScaler), ticks = this._vAxis.getTicks(); if(this.opt.hMinorLines){ dojo.forEach(ticks.minor, function(tick){ var y = dim.height - offsets.b - vt(tick.value); var hMinorLine = s.createLine({ x1: offsets.l, y1: y, x2: dim.width - offsets.r, y2: y }).setStroke(ta.minorTick); if(this.animate){ this._animateGrid(hMinorLine, "h", offsets.l, offsets.r + offsets.l - dim.width); } }, this); } if(this.opt.hMajorLines){ dojo.forEach(ticks.major, function(tick){ var y = dim.height - offsets.b - vt(tick.value); var hMajorLine = s.createLine({ x1: offsets.l, y1: y, x2: dim.width - offsets.r, y2: y }).setStroke(ta.majorTick); if(this.animate){ this._animateGrid(hMajorLine, "h", offsets.l, offsets.r + offsets.l - dim.width); } }, this); } }catch(e){ // squelch } // draw vertical stripes and lines try{ var hScaler = this._hAxis.getScaler(), ht = hScaler.scaler.getTransformerFromModel(hScaler), ticks = this._hAxis.getTicks(); if(ticks && this.opt.vMinorLines){ dojo.forEach(ticks.minor, function(tick){ var x = offsets.l + ht(tick.value); var vMinorLine = s.createLine({ x1: x, y1: offsets.t, x2: x, y2: dim.height - offsets.b }).setStroke(ta.minorTick); if(this.animate){ this._animateGrid(vMinorLine, "v", dim.height - offsets.b, dim.height - offsets.b - offsets.t); } }, this); } if(ticks && this.opt.vMajorLines){ dojo.forEach(ticks.major, function(tick){ var x = offsets.l + ht(tick.value); var vMajorLine = s.createLine({ x1: x, y1: offsets.t, x2: x, y2: dim.height - offsets.b }).setStroke(ta.majorTick); if(this.animate){ this._animateGrid(vMajorLine, "v", dim.height - offsets.b, dim.height - offsets.b - offsets.t); } }, this); } }catch(e){ // squelch } this.dirty = false; return this; // dojox.charting.plot2d.Grid }, _animateGrid: function(shape, type, offset, size){ var transStart = type == "h" ? [offset, 0] : [0, offset]; var scaleStart = type == "h" ? [1/size, 1] : [1, 1/size]; dojox.gfx.fx.animateTransform(dojo.delegate({ shape: shape, duration: 1200, transform: [ {name: "translate", start: transStart, end: [0, 0]}, {name: "scale", start: scaleStart, end: [1, 1]}, {name: "original"} ] }, this.animate)).play(); } }); })(); }