Issues (4542)

js/flot/jquery.flot.orderBars.js (3 issues)

1
/*
2
 * Flot plugin to order bars side by side.
3
 * 
4
 * Released under the MIT license by Benjamin BUFFET, 20-Sep-2010.
5
 *
6
 * This plugin is an alpha version.
7
 *
8
 * To activate the plugin you must specify the parameter "order" for the specific serie :
9
 *
10
 *  $.plot($("#placeholder"), [{ data: [ ... ], bars :{ order = null or integer }])
11
 *
12
 * If 2 series have the same order param, they are ordered by the position in the array;
13
 *
14
 * The plugin adjust the point by adding a value depanding of the barwidth
15
 * Exemple for 3 series (barwidth : 0.1) :
16
 *
17
 *          first bar décalage : -0.15
18
 *          second bar décalage : -0.05
19
 *          third bar décalage : 0.05
20
 *
21
 */
22
23
(function($){
24
    function init(plot){
25
        var orderedBarSeries;
26
        var nbOfBarsToOrder;
27
        var borderWidth;
28
        var borderWidthInXabsWidth;
29
        var pixelInXWidthEquivalent = 1;
30
        var isHorizontal = false;
31
32
        /*
33
         * This method add shift to x values
34
         */
35
        function reOrderBars(plot, serie, datapoints){
36
            var shiftedPoints = null;
37
            
38
            if(serieNeedToBeReordered(serie)){                
39
                checkIfGraphIsHorizontal(serie);
40
                calculPixel2XWidthConvert(plot);
41
                retrieveBarSeries(plot);
42
                calculBorderAndBarWidth(serie);
43
                
44
                if(nbOfBarsToOrder >= 2){  
45
                    var position = findPosition(serie);
46
                    var decallage = 0;
47
                    
48
                    var centerBarShift = calculCenterBarShift();
49
50
                    if (isBarAtLeftOfCenter(position)){
51
                        decallage = -1*(sumWidth(orderedBarSeries,position-1,Math.floor(nbOfBarsToOrder / 2)-1)) - centerBarShift;
52
                    }else{
53
                        decallage = sumWidth(orderedBarSeries,Math.ceil(nbOfBarsToOrder / 2),position-2) + centerBarShift + borderWidthInXabsWidth*2;
54
                    }
55
56
                    shiftedPoints = shiftPoints(datapoints,serie,decallage);
57
                    datapoints.points = shiftedPoints;
58
               }
59
           }
60
           return shiftedPoints;
61
        }
62
63
        function serieNeedToBeReordered(serie){
64
            return serie.bars != null
65
                && serie.bars.show
66
                && serie.bars.order != null;
67
        }
68
69
        function calculPixel2XWidthConvert(plot){
70
            var gridDimSize = isHorizontal ? plot.getPlaceholder().innerHeight() : plot.getPlaceholder().innerWidth();
71
            var minMaxValues = isHorizontal ? getAxeMinMaxValues(plot.getData(),1) : getAxeMinMaxValues(plot.getData(),0);
72
            var AxeSize = minMaxValues[1] - minMaxValues[0];
73
            pixelInXWidthEquivalent = AxeSize / gridDimSize;
74
        }
75
76
        function getAxeMinMaxValues(series,AxeIdx){
77
            var minMaxValues = new Array();
0 ignored issues
show
Coding Style Best Practice introduced by
Using the Array constructor is generally discouraged. Consider using an array literal instead.
Loading history...
78
            for(var i = 0; i < series.length; i++){
79
                minMaxValues[0] = series[i].data[0][AxeIdx];
80
                minMaxValues[1] = series[i].data[series[i].data.length - 1][AxeIdx];
81
            }
82
            return minMaxValues;
83
        }
84
85
        function retrieveBarSeries(plot){
86
            orderedBarSeries = findOthersBarsToReOrders(plot.getData());
87
            nbOfBarsToOrder = orderedBarSeries.length;
88
        }
89
90
        function findOthersBarsToReOrders(series){
91
            var retSeries = new Array();
0 ignored issues
show
Coding Style Best Practice introduced by
Using the Array constructor is generally discouraged. Consider using an array literal instead.
Loading history...
92
93
            for(var i = 0; i < series.length; i++){
94
                if(series[i].bars.order != null && series[i].bars.show){
95
                    retSeries.push(series[i]);
96
                }
97
            }
98
99
            return retSeries.sort(sortByOrder);
100
        }
101
102
        function sortByOrder(serie1,serie2){
103
            var x = serie1.bars.order;
104
            var y = serie2.bars.order;
105
            return ((x < y) ? -1 : ((x > y) ? 1 : 0));
106
        }
107
108
        function  calculBorderAndBarWidth(serie){
109
            borderWidth = serie.bars.lineWidth ? serie.bars.lineWidth  : 2;
110
            borderWidthInXabsWidth = borderWidth * pixelInXWidthEquivalent;
111
        }
112
        
113
        function checkIfGraphIsHorizontal(serie){
114
            if(serie.bars.horizontal){
115
                isHorizontal = true;
116
            }
117
        }
118
119
        function findPosition(serie){
120
            var pos = 0
121
            for (var i = 0; i < orderedBarSeries.length; ++i) {
122
                if (serie == orderedBarSeries[i]){
123
                    pos = i;
124
                    break;
125
                }
126
            }
127
128
            return pos+1;
129
        }
130
131
        function calculCenterBarShift(){
132
            var width = 0;
133
134
            if(nbOfBarsToOrder%2 != 0)
135
                width = (orderedBarSeries[Math.ceil(nbOfBarsToOrder / 2)].bars.barWidth)/2;
0 ignored issues
show
Coding Style Best Practice introduced by
Curly braces around statements make for more readable code and help prevent bugs when you add further statements.

Consider adding curly braces around all statements when they are executed conditionally. This is optional if there is only one statement, but leaving them out can lead to unexpected behaviour if another statement is added later.

Consider:

if (a > 0)
    b = 42;

If you or someone else later decides to put another statement in, only the first statement will be executed.

if (a > 0)
    console.log("a > 0");
    b = 42;

In this case the statement b = 42 will always be executed, while the logging statement will be executed conditionally.

if (a > 0) {
    console.log("a > 0");
    b = 42;
}

ensures that the proper code will be executed conditionally no matter how many statements are added or removed.

Loading history...
136
137
            return width;
138
        }
139
140
        function isBarAtLeftOfCenter(position){
141
            return position <= Math.ceil(nbOfBarsToOrder / 2);
142
        }
143
144
        function sumWidth(series,start,end){
145
            var totalWidth = 0;
146
147
            for(var i = start; i <= end; i++){
148
                totalWidth += series[i].bars.barWidth+borderWidthInXabsWidth*2;
149
            }
150
151
            return totalWidth;
152
        }
153
154
        function shiftPoints(datapoints,serie,dx){
155
            var ps = datapoints.pointsize;
156
            var points = datapoints.points;
157
            var j = 0;           
158
            for(var i = isHorizontal ? 1 : 0;i < points.length; i += ps){
159
                points[i] += dx;
160
                //Adding the new x value in the serie to be abble to display the right tooltip value,
161
                //using the index 3 to not overide the third index.
162
                serie.data[j][3] = points[i];
163
                j++;
164
            }
165
166
            return points;
167
        }
168
169
        plot.hooks.processDatapoints.push(reOrderBars);
170
171
    }
172
173
    var options = {
174
        series : {
175
            bars: {order: null} // or number/string
176
        }
177
    };
178
179
    $.plot.plugins.push({
180
        init: init,
181
        options: options,
182
        name: "orderBars",
183
        version: "0.2"
184
    });
185
186
})(jQuery)
187
188