1
+ ( function ( $ ) {
2
+
3
+ // Class: $.jqplot.LinDifferentColorMarkerLineRenderereRenderer
4
+ // Line renderer for jqPlot, this class has one
5
+ // markerColors: []
6
+ // Draws series as a line.
7
+ $ . jqplot . DifferentColorMarkerLineRenderer = function ( options ) {
8
+ this . markerColors = [ ] ;
9
+ this . shapeRenderer = new $ . jqplot . ShapeRenderer ( ) ;
10
+ this . shadowRenderer = new $ . jqplot . ShadowRenderer ( ) ;
11
+ $ . extend ( true , this , options ) ;
12
+ } ;
13
+
14
+ // called with scope of series.
15
+ $ . jqplot . DifferentColorMarkerLineRenderer . prototype . init = function ( options ) {
16
+ //$.extend(true, this, options);
17
+ // set the shape renderer options
18
+ this . markerColors = options . markerColors || this . markerColors ;
19
+ var opts = {
20
+ lineJoin :'round' ,
21
+ lineCap :'round' ,
22
+ fill :this . fill ,
23
+ isarc :false ,
24
+ strokeStyle :this . color ,
25
+ fillStyle :this . fillColor ,
26
+ lineWidth :this . lineWidth ,
27
+ closePath :this . fill
28
+
29
+ } ;
30
+ this . renderer . shapeRenderer . init ( opts ) ;
31
+ // set the shadow renderer options
32
+ // scale the shadowOffset to the width of the line.
33
+ if ( this . lineWidth > 2.5 ) {
34
+ var shadow_offset = this . shadowOffset * ( 1 + ( Math . atan ( ( this . lineWidth / 2.5 ) ) / 0.785398163 - 1 ) * 0.6 ) ;
35
+ // var shadow_offset = this.shadowOffset;
36
+ }
37
+ // for skinny lines, don't make such a big shadow.
38
+ else {
39
+ var shadow_offset = this . shadowOffset * Math . atan ( ( this . lineWidth / 2.5 ) ) / 0.785398163 ;
40
+ }
41
+ var sopts = {
42
+ lineJoin :'round' ,
43
+ lineCap :'round' ,
44
+ fill :this . fill ,
45
+ isarc :false ,
46
+ angle :this . shadowAngle ,
47
+ offset :shadow_offset ,
48
+ alpha :this . shadowAlpha ,
49
+ depth :this . shadowDepth ,
50
+ lineWidth :this . lineWidth ,
51
+ closePath :this . fill
52
+ } ;
53
+ this . renderer . shadowRenderer . init ( sopts ) ;
54
+ } ;
55
+
56
+ // Method: setGridData
57
+ // converts the user data values to grid coordinates and stores them
58
+ // in the gridData array.
59
+ // Called with scope of a series.
60
+ $ . jqplot . DifferentColorMarkerLineRenderer . prototype . setGridData = function ( plot ) {
61
+ // recalculate the grid data
62
+ var xp = this . _xaxis . series_u2p ;
63
+ var yp = this . _yaxis . series_u2p ;
64
+ var data = this . _plotData ;
65
+ var pdata = this . _prevPlotData ;
66
+ this . gridData = [ ] ;
67
+ this . _prevGridData = [ ] ;
68
+ for ( var i = 0 ; i < this . data . length ; i ++ ) {
69
+ if ( data [ i ] != null ) {
70
+ this . gridData . push ( [ xp . call ( this . _xaxis , data [ i ] [ 0 ] ) , yp . call ( this . _yaxis , data [ i ] [ 1 ] ) ] ) ;
71
+ }
72
+ if ( pdata [ i ] != null ) {
73
+ this . _prevGridData . push ( [ xp . call ( this . _xaxis , pdata [ i ] [ 0 ] ) , yp . call ( this . _yaxis , pdata [ i ] [ 1 ] ) ] ) ;
74
+ }
75
+ }
76
+ } ;
77
+
78
+ // Method: makeGridData
79
+ // converts any arbitrary data values to grid coordinates and
80
+ // returns them. This method exists so that plugins can use a series'
81
+ // linerenderer to generate grid data points without overwriting the
82
+ // grid data associated with that series.
83
+ // Called with scope of a series.
84
+ $ . jqplot . DifferentColorMarkerLineRenderer . prototype . makeGridData = function ( data , plot ) {
85
+ // recalculate the grid data
86
+ var xp = this . _xaxis . series_u2p ;
87
+ var yp = this . _yaxis . series_u2p ;
88
+ var gd = [ ] ;
89
+ var pgd = [ ] ;
90
+ for ( var i = 0 ; i < data . length ; i ++ ) {
91
+ if ( data [ i ] != null ) {
92
+ gd . push ( [ xp . call ( this . _xaxis , data [ i ] [ 0 ] ) , yp . call ( this . _yaxis , data [ i ] [ 1 ] ) ] ) ;
93
+ }
94
+ }
95
+ return gd ;
96
+ } ;
97
+
98
+
99
+ // called within scope of series.
100
+ $ . jqplot . DifferentColorMarkerLineRenderer . prototype . draw = function ( ctx , gd , options ) {
101
+ var i ;
102
+ var opts = ( options != undefined ) ? options : { } ;
103
+ var shadow = ( opts . shadow != undefined ) ? opts . shadow : this . shadow ;
104
+ var showLine = ( opts . showLine != undefined ) ? opts . showLine : this . showLine ;
105
+ var fill = ( opts . fill != undefined ) ? opts . fill : this . fill ;
106
+ var fillAndStroke = ( opts . fillAndStroke != undefined ) ? opts . fillAndStroke : this . fillAndStroke ;
107
+ ctx . save ( ) ;
108
+ if ( gd . length ) {
109
+ if ( showLine ) {
110
+ // if we fill, we'll have to add points to close the curve.
111
+ if ( fill ) {
112
+ if ( this . fillToZero ) {
113
+ // have to break line up into shapes at axis crossings
114
+ var negativeColors = new $ . jqplot . ColorGenerator ( this . negativeSeriesColors ) ;
115
+ var negativeColor = negativeColors . get ( this . index ) ;
116
+ if ( ! this . useNegativeColors ) {
117
+ negativeColor = opts . fillStyle ;
118
+ }
119
+ var isnegative = false ;
120
+ var posfs = opts . fillStyle ;
121
+
122
+ // if stoking line as well as filling, get a copy of line data.
123
+ if ( fillAndStroke ) {
124
+ var fasgd = gd . slice ( 0 ) ;
125
+ }
126
+ // if not stacked, fill down to axis
127
+ if ( this . index == 0 || ! this . _stack ) {
128
+
129
+ var tempgd = [ ] ;
130
+ var pyzero = this . _yaxis . series_u2p ( 0 ) ;
131
+ var pxzero = this . _xaxis . series_u2p ( 0 ) ;
132
+
133
+ if ( this . fillAxis == 'y' ) {
134
+ tempgd . push ( [ gd [ 0 ] [ 0 ] , pyzero ] ) ;
135
+
136
+ for ( var i = 0 ; i < gd . length - 1 ; i ++ ) {
137
+ tempgd . push ( gd [ i ] ) ;
138
+ // do we have an axis crossing?
139
+ if ( this . _plotData [ i ] [ 1 ] * this . _plotData [ i + 1 ] [ 1 ] < 0 ) {
140
+ if ( this . _plotData [ i ] [ 1 ] < 0 ) {
141
+ isnegative = true ;
142
+ opts . fillStyle = negativeColor ;
143
+ }
144
+ else {
145
+ isnegative = false ;
146
+ opts . fillStyle = posfs ;
147
+ }
148
+
149
+ var xintercept = gd [ i ] [ 0 ] + ( gd [ i + 1 ] [ 0 ] - gd [ i ] [ 0 ] ) * ( pyzero - gd [ i ] [ 1 ] ) / ( gd [ i + 1 ] [ 1 ] - gd [ i ] [ 1 ] ) ;
150
+ tempgd . push ( [ xintercept , pyzero ] ) ;
151
+ // now draw this shape and shadow.
152
+ if ( shadow ) {
153
+ this . renderer . shadowRenderer . draw ( ctx , tempgd , opts ) ;
154
+ }
155
+ this . renderer . shapeRenderer . draw ( ctx , tempgd , opts ) ;
156
+ // now empty temp array and continue
157
+ tempgd = [ [ xintercept , pyzero ] ] ;
158
+ }
159
+ }
160
+ if ( this . _plotData [ gd . length - 1 ] [ 1 ] < 0 ) {
161
+ isnegative = true ;
162
+ opts . fillStyle = negativeColor ;
163
+ }
164
+ else {
165
+ isnegative = false ;
166
+ opts . fillStyle = posfs ;
167
+ }
168
+ tempgd . push ( gd [ gd . length - 1 ] ) ;
169
+ tempgd . push ( [ gd [ gd . length - 1 ] [ 0 ] , pyzero ] ) ;
170
+ }
171
+ // now draw this shape and shadow.
172
+ if ( shadow ) {
173
+ this . renderer . shadowRenderer . draw ( ctx , tempgd , opts ) ;
174
+ }
175
+ this . renderer . shapeRenderer . draw ( ctx , tempgd , opts ) ;
176
+
177
+
178
+ // var gridymin = this._yaxis.series_u2p(0);
179
+ // // IE doesn't return new length on unshift
180
+ // gd.unshift([gd[0][0], gridymin]);
181
+ // len = gd.length;
182
+ // gd.push([gd[len - 1][0], gridymin]);
183
+ }
184
+ // if stacked, fill to line below
185
+ else {
186
+ var prev = this . _prevGridData ;
187
+ for ( var i = prev . length ; i > 0 ; i -- ) {
188
+ gd . push ( prev [ i - 1 ] ) ;
189
+ }
190
+ if ( shadow ) {
191
+ this . renderer . shadowRenderer . draw ( ctx , gd , opts ) ;
192
+ }
193
+
194
+ this . renderer . shapeRenderer . draw ( ctx , gd , opts ) ;
195
+ }
196
+ }
197
+ else {
198
+ // if stoking line as well as filling, get a copy of line data.
199
+ if ( fillAndStroke ) {
200
+ var fasgd = gd . slice ( 0 ) ;
201
+ }
202
+ // if not stacked, fill down to axis
203
+ if ( this . index == 0 || ! this . _stack ) {
204
+ // var gridymin = this._yaxis.series_u2p(this._yaxis.min) - this.gridBorderWidth / 2;
205
+ var gridymin = ctx . canvas . height ;
206
+ // IE doesn't return new length on unshift
207
+ gd . unshift ( [ gd [ 0 ] [ 0 ] , gridymin ] ) ;
208
+ len = gd . length ;
209
+ gd . push ( [ gd [ len - 1 ] [ 0 ] , gridymin ] ) ;
210
+ }
211
+ // if stacked, fill to line below
212
+ else {
213
+ var prev = this . _prevGridData ;
214
+ for ( var i = prev . length ; i > 0 ; i -- ) {
215
+ gd . push ( prev [ i - 1 ] ) ;
216
+ }
217
+ }
218
+ if ( shadow ) {
219
+ this . renderer . shadowRenderer . draw ( ctx , gd , opts ) ;
220
+ }
221
+
222
+ this . renderer . shapeRenderer . draw ( ctx , gd , opts ) ;
223
+ }
224
+ if ( fillAndStroke ) {
225
+ var fasopts = $ . extend ( true , { } , opts , {
226
+ fill :false ,
227
+ closePath :false
228
+ } ) ;
229
+ this . renderer . shapeRenderer . draw ( ctx , fasgd , fasopts ) ;
230
+ //////////
231
+ // TODO: figure out some way to do shadows nicely
232
+ // if (shadow) {
233
+ // this.renderer.shadowRenderer.draw(ctx, fasgd, fasopts);
234
+ // }
235
+ // now draw the markers
236
+ if ( this . markerRenderer . show ) {
237
+ for ( i = 0 ; i < fasgd . length ; i ++ ) {
238
+ this . markerRenderer . draw ( fasgd [ i ] [ 0 ] , fasgd [ i ] [ 1 ] , ctx , opts . markerOptions ) ;
239
+ }
240
+ }
241
+ }
242
+ }
243
+ else {
244
+ if ( shadow ) {
245
+ this . renderer . shadowRenderer . draw ( ctx , gd , opts ) ;
246
+ }
247
+ this . renderer . shapeRenderer . draw ( ctx , gd , opts ) ;
248
+ }
249
+ }
250
+
251
+
252
+ // now draw the markers
253
+ if ( this . markerRenderer . show && ! fill ) {
254
+ for ( i = 0 ; i < gd . length ; i ++ ) {
255
+ // Grab each color and send it to a new markerRenderer.
256
+ opts . markerOptions = {
257
+ color : this . markerColors [ i ]
258
+ } ;
259
+ this . markerRenderer = new $ . jqplot . MarkerRenderer
260
+ this . markerRenderer . init ( opts . markerOptions ) ;
261
+ this . markerRenderer . draw ( gd [ i ] [ 0 ] , gd [ i ] [ 1 ] , ctx , opts . markerOptions ) ;
262
+ }
263
+ }
264
+ }
265
+
266
+ ctx . restore ( ) ;
267
+ } ;
268
+
269
+ $ . jqplot . DifferentColorMarkerLineRenderer . prototype . drawShadow = function ( ctx , gd , options ) {
270
+ // This is a no-op, shadows drawn with lines.
271
+ } ;
272
+
273
+ } ) ( jQuery ) ;
0 commit comments