fix #8056 - more refinements to checking data
[g.raphael] / g.bar.js
index dffe42e..85b77d0 100644 (file)
--- a/g.bar.js
+++ b/g.bar.js
@@ -4,6 +4,11 @@
  * Copyright (c) 2009 Dmitry Baranovskiy (http://g.raphaeljs.com)
  * Licensed under the MIT (http://www.opensource.org/licenses/mit-license.php) license.
  */
+imports = typeof(imports) == 'undefined' ? false : imports;
+Raphael = typeof(Raphael) != 'undefined' ? Raphael :  (imports ? imports.seed.Raphael.Raphael : {});
+Roo = typeof(Roo) != 'undefined' ? Roo:  (imports ? imports.seed.Roo.Roo: {});
+
+
 (function () {
     var mmin = Math.min,
         mmax = Math.max;
      *    axis: {String} eg. "top right bottom left" - which sides to show an axis eg. "0 0 1 1"
      *    axisxstep
      *    axisystep
-     *    axisxlabels
+     *    axisxlabels: {Array} - note - first element appears left of first bar..
      *    stacked
      *    to
      *    stretch
      */
     function VBarchart(paper, x, y, width, height, values, opts) {
         opts = opts || {};
-        opts.xvalues 
-        
+         
         var chartinst = this,
             type = opts.type || "square",
             gutter = parseFloat(opts.gutter || "20%"),
             chart = paper.set(),
             bars = paper.set(),
-//            covers = paper.set(),
-//            covers2 = paper.set(),
+            covers = paper.set(),
+            covers2 = paper.set(),
             total = Math.max.apply(Math, values),
             stacktotal = [],
             multi = 0,
         
         var allx = Array.prototype.concat.apply([], opts.xvalues),
             ally = Array.prototype.concat.apply([], opts.yvalues),
+            
             xdim = chartinst.snapEnds(
                 Math.min.apply(Math, allx),
                 Math.max.apply(Math, allx),
             kx = (width - gutter * 2) / ((maxx - minx) || 1),
             ky = (height - gutter * 2) / ((maxy - miny) || 1);
             
-       
+       //Roo.log({ally : ally});
         
-        if (Raphael.is(values[0], "array") && values.length > 1) {
+        if (Raphael.is(values[0], "array")) { // && values.length > 1) {
             total = [];
             multi = len;
             len = 0;
                 total.push(Math.max.apply(Math, values[i]));
                 len = Math.max(len, values[i].length);
             }
+            if (opts.stacked) {
+                for (var i = len; i--;) {
+                    var tot = 0;
+                    for (var j = values.length; j--;) {
+                        tot +=+ values[j][i] || 0;
+                    }
+                    stacktotal.push(tot);
+                }
+            }
 
             for (var i = values.length; i--;) {
                 if (values[i].length < len) {
         }
         
         total = (opts.to) || total;
-        Roo.log([width, len, gutter]);
+        //Roo.log([width, len, gutter]);
         var barwidth = width / (len * (90 + gutter) + gutter) * 100,
             barhgutter = barwidth * (gutter) / 100,
             barvgutter = opts.vgutter == null ? 20 : opts.vgutter,
             stack = [],
             X = x + barhgutter,
             Y = (height - 2 * barvgutter) / total;
-        Roo.log([barwidth, X, barhgutter]);
+        //Roo.log([barwidth, X, barhgutter]);
         if (!opts.stretch) {
             barhgutter = Math.round(barhgutter);
             barwidth = Math.floor(barwidth);
                         paper
                     ));
             // bottom axis
+            opts.axisxlabels = opts.axisxlabels || [];
+            // add elements at beginning and end of array...
+            opts.axisxlabels.unshift(' ');
+            opts.axisxlabels.push(' ');
+            opts.axisxstep  = opts.axisxstep  || (opts.axisxlabels ? opts.axisxlabels.length  -1    : false ) || len;
+            
+            
             +ax[2] && axis.push(
                 // bottom
                 // x, y, length, from, to, steps, orientation, labels, type, dashsize, paper
                 chartinst.axis(
-                    x + gutter + barwidth,
+                    x + gutter ,
                     y + height - gutter,
-                    width - (gutter + barwidth), // total width
+                    width - (gutter + barhgutter), // total width
                     minx ,  // from
                     maxx, //to
-                    opts.axisxstep || len - 3, // steps
+                    opts.axisxstep ,
                     0, // orientation
                     opts.axisxlabels || false, // labels
                     "-", // type
                     paper
                 ));
             // left axis
+            
+             // x, y, length, from, to, steps, orientation, labels, type, dashsize, paper
+            
+            // vertical steps (eg. number of Lables) - should be related to the range.
+            // eg. around 10? 
+            opts.axisystep = opts.axisystep  || Math.floor((height - 2 * gutter) / 20);
+            var yrangedivs = Math.ceil((maxy - miny) / opts.axisystep) 
+            var yrange = yrangedivs * opts.axisystep;
+            if (yrange < (maxy - miny) ) {
+                opts.axisystep++;
+                maxy = miny + (yrangedivs * opts.axisystep);
+            }
+            //Roo.log(opts.axisystep);
+            
+            
+            
             +ax[3] && axis.push(
                     chartinst.axis(
                         x + gutter,
                         height - 2 * gutter,
                         miny,
                         maxy ,
-//                        opts.axisystep || Math.floor((height - 2 * gutter) / 20),
-                        10,
+                        opts.axisystep, 
+                        
                         1,
                         paper
             ));
             if(i == 0){
                 X += barwidth;
             }
-            Roo.log( {X : X});
+            
+            //Roo.log( {X : X});
             for (var j = 0; j < (multi || 1); j++) {
                 var h = Math.round((multi ? values[j][i] : values[i]) * Y),
                     top = y + height - barvgutter - h,
-                    bar = finger(Math.round(X + barwidth / 2), top + h, barwidth, h, true, type, null, paper).attr({ stroke: "none", fill: colors[multi ? j : i] });
+                    bar = finger(Math.round(X + barwidth / 2), top + h, barwidth, h, true, type, null, paper).attr({
+                            stroke: "none",
+                            fill: colors[multi ? j : i]
+                    });
+                    
                     
-//                    bar = finger(x, Y + barwidth / 2, Math.round(8 * X), barwidth - 1, false, type, null, paper).attr({stroke: "none", fill: colors[multi ? j : i]});
                 
                 
-                if (multi && bars[j]) { // bars[j] did not appear to exist?
+                if (multi) { // bars[j] did not appear to exist?
                     bars[j].push(bar);
                 } else {
                     bars.push(bar);
                     var qtyLbl = paper.text(
                             bar.x - 10,
                             (bar.y - 10),
-                            opts.labels[i])
-                            .attr({
+                            opts.labels[i]).attr({
                                 fill : '#000',
                                 'text-anchor' : 'start',
                                 font : '10px Arial'
 
             //X += barhgutter + 25; -- why add 25??
             X += barhgutter;
+            if (opts.stacked) {
+               var cvr;
+
+               covers2.push(cvr = paper.rect(stack[0].x - stack[0].w / 2, y, barwidth, height).attr(chartinst.shim));
+               cvr.bars = paper.set();
+
+               var size = 0;
+
+               for (var s = stack.length; s--;) {
+                   stack[s].toFront();
+               }
+
+               for (var s = 0, ss = stack.length; s < ss; s++) {
+                   var bar = stack[s],
+                       cover,
+                       h = (size + bar.value) * Y,
+                       path = finger(bar.x, y + height - barvgutter - !!size * .5, barwidth, h, true, type, 1, paper);
+
+                   cvr.bars.push(bar);
+                   size && bar.attr({path: path});
+                   bar.h = h;
+                   bar.y = y + height - barvgutter - !!size * .5 - h;
+                   covers.push(cover = paper.rect(bar.x - bar.w / 2, bar.y, barwidth, bar.value * Y).attr(chartinst.shim));
+                   cover.bar = bar;
+                   cover.value = bar.value;
+                   size += bar.value;
+               }
+
+               X += barwidth;
+           }
+
+
         }
         X = x + barhgutter;
         
 //            return this;
 //        };
         
-//        chart.push(bars, covers, covers2);
+//        chart.push(bars, covers, covers2);+
+        if (!opts.stacked) {
+            for (var i = 0; i < len; i++) {
+                for (var j = 0; j < (multi || 1); j++) {
+                    var cover;
+
+                    covers.push(cover = paper.rect(Math.round(X), y + barvgutter, barwidth, height - barvgutter).attr(chartinst.shim));
+                    cover.bar = multi ? bars[j][i] : bars[i];
+                    cover.value = cover.bar.value;
+                    X += barwidth;
+                }
+
+                X += barhgutter;
+            }
+        }
+
         chart.bars = bars;
 //        chart.covers = covers;
         return chart;