rgraph-rails 1.0.5 → 1.0.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +8 -8
- data/.travis.yml +0 -1
- data/README.md +3 -3
- data/lib/rgraph-rails/version.rb +1 -1
- data/vendor/assets/javascripts/RGraph.bar.js +239 -3764
- data/vendor/assets/javascripts/RGraph.bipolar.js +115 -1986
- data/vendor/assets/javascripts/RGraph.common.annotate.js +35 -399
- data/vendor/assets/javascripts/RGraph.common.context.js +30 -600
- data/vendor/assets/javascripts/RGraph.common.core.js +403 -5187
- data/vendor/assets/javascripts/RGraph.common.csv.js +19 -275
- data/vendor/assets/javascripts/RGraph.common.deprecated.js +35 -454
- data/vendor/assets/javascripts/RGraph.common.dynamic.js +84 -1189
- data/vendor/assets/javascripts/RGraph.common.effects.js +90 -1548
- data/vendor/assets/javascripts/RGraph.common.key.js +54 -755
- data/vendor/assets/javascripts/RGraph.common.resizing.js +37 -567
- data/vendor/assets/javascripts/RGraph.common.sheets.js +29 -356
- data/vendor/assets/javascripts/RGraph.common.tooltips.js +32 -614
- data/vendor/assets/javascripts/RGraph.common.zoom.js +14 -223
- data/vendor/assets/javascripts/RGraph.cornergauge.js +71 -0
- data/vendor/assets/javascripts/RGraph.drawing.background.js +35 -620
- data/vendor/assets/javascripts/RGraph.drawing.circle.js +35 -576
- data/vendor/assets/javascripts/RGraph.drawing.image.js +52 -807
- data/vendor/assets/javascripts/RGraph.drawing.marker1.js +41 -717
- data/vendor/assets/javascripts/RGraph.drawing.marker2.js +37 -668
- data/vendor/assets/javascripts/RGraph.drawing.marker3.js +36 -563
- data/vendor/assets/javascripts/RGraph.drawing.poly.js +40 -608
- data/vendor/assets/javascripts/RGraph.drawing.rect.js +35 -597
- data/vendor/assets/javascripts/RGraph.drawing.text.js +34 -642
- data/vendor/assets/javascripts/RGraph.drawing.xaxis.js +50 -809
- data/vendor/assets/javascripts/RGraph.drawing.yaxis.js +51 -856
- data/vendor/assets/javascripts/RGraph.fuel.js +58 -964
- data/vendor/assets/javascripts/RGraph.funnel.js +55 -984
- data/vendor/assets/javascripts/RGraph.gantt.js +75 -1241
- data/vendor/assets/javascripts/RGraph.gauge.js +87 -1397
- data/vendor/assets/javascripts/RGraph.hbar.js +143 -2376
- data/vendor/assets/javascripts/RGraph.hprogress.js +80 -1397
- data/vendor/assets/javascripts/RGraph.line.js +241 -4162
- data/vendor/assets/javascripts/RGraph.meter.js +74 -1278
- metadata +3 -30
- data/vendor/assets/images/bg.png +0 -0
- data/vendor/assets/images/bullet.png +0 -0
- data/vendor/assets/images/facebook-large.png +0 -0
- data/vendor/assets/images/google-plus-large.png +0 -0
- data/vendor/assets/images/logo.png +0 -0
- data/vendor/assets/images/meter-image-sd-needle.png +0 -0
- data/vendor/assets/images/meter-image-sd.png +0 -0
- data/vendor/assets/images/meter-sketch-needle.png +0 -0
- data/vendor/assets/images/meter-sketch.png +0 -0
- data/vendor/assets/images/odometer-background.png +0 -0
- data/vendor/assets/images/rgraph.jpg +0 -0
- data/vendor/assets/images/title.png +0 -0
- data/vendor/assets/images/twitter-large.png +0 -0
- data/vendor/assets/javascripts/RGraph.modaldialog.js +0 -301
- data/vendor/assets/javascripts/RGraph.odo.js +0 -1265
- data/vendor/assets/javascripts/RGraph.pie.js +0 -2272
- data/vendor/assets/javascripts/RGraph.radar.js +0 -1847
- data/vendor/assets/javascripts/RGraph.rose.js +0 -1877
- data/vendor/assets/javascripts/RGraph.rscatter.js +0 -1425
- data/vendor/assets/javascripts/RGraph.scatter.js +0 -2970
- data/vendor/assets/javascripts/RGraph.semicircularprogress.js +0 -1015
- data/vendor/assets/javascripts/RGraph.thermometer.js +0 -1129
- data/vendor/assets/javascripts/RGraph.vprogress.js +0 -1452
- data/vendor/assets/javascripts/RGraph.waterfall.js +0 -1252
- data/vendor/assets/javascripts/financial-data.js +0 -1067
- data/vendor/assets/stylesheets/ModalDialog.css +0 -90
- data/vendor/assets/stylesheets/animations.css +0 -3347
- data/vendor/assets/stylesheets/website.css +0 -446
@@ -1,985 +1,56 @@
|
|
1
|
-
// version: 2016-06-04
|
2
|
-
/**
|
3
|
-
* o--------------------------------------------------------------------------------o
|
4
|
-
* | This file is part of the RGraph package - you can learn more at: |
|
5
|
-
* | |
|
6
|
-
* | http://www.rgraph.net |
|
7
|
-
* | |
|
8
|
-
* | RGraph is dual licensed under the Open Source GPL (General Public License) |
|
9
|
-
* | v2.0 license and a commercial license which means that you're not bound by |
|
10
|
-
* | the terms of the GPL. The commercial license is just 99 GBP and you can |
|
11
|
-
* | read about it here: |
|
12
|
-
* | http://www.rgraph.net/license |
|
13
|
-
* o--------------------------------------------------------------------------------o
|
14
|
-
*/
|
15
1
|
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
{
|
72
|
-
'chart.strokestyle': 'rgba(0,0,0,0)',
|
73
|
-
'chart.gutter.left': 25,
|
74
|
-
'chart.gutter.right': 25,
|
75
|
-
'chart.gutter.top': 25,
|
76
|
-
'chart.gutter.bottom': 25,
|
77
|
-
'chart.labels': null,
|
78
|
-
'chart.labels.sticks': false,
|
79
|
-
'chart.labels.x': null,
|
80
|
-
'chart.title': '',
|
81
|
-
'chart.title.background': null,
|
82
|
-
'chart.title.hpos': null,
|
83
|
-
'chart.title.vpos': null,
|
84
|
-
'chart.title.bold': true,
|
85
|
-
'chart.title.font': null,
|
86
|
-
'chart.title.x': null,
|
87
|
-
'chart.title.y': null,
|
88
|
-
'chart.title.halign': null,
|
89
|
-
'chart.title.valign': null,
|
90
|
-
'chart.colors': [
|
91
|
-
'Gradient(white:red)',
|
92
|
-
'Gradient(white:green)',
|
93
|
-
'Gradient(white:gray)',
|
94
|
-
'Gradient(white:blue)',
|
95
|
-
'Gradient(white:black)',
|
96
|
-
'Gradient(white:gray)',
|
97
|
-
'Gradient(white:pink)',
|
98
|
-
'Gradient(white:blue)',
|
99
|
-
'Gradient(white:yellow)',
|
100
|
-
'Gradient(white:green)',
|
101
|
-
'Gradient(white:red)'
|
102
|
-
],
|
103
|
-
'chart.text.size': 12,
|
104
|
-
'chart.text.boxed': true,
|
105
|
-
'chart.text.halign': 'left',
|
106
|
-
'chart.text.color': 'black',
|
107
|
-
'chart.text.font': 'Segoe UI, Arial, Verdana, sans-serif',
|
108
|
-
'chart.text.accessible': true,
|
109
|
-
'chart.text.accessible.overflow': 'visible',
|
110
|
-
'chart.text.accessible.pointerevents': false,
|
111
|
-
'chart.contextmenu': null,
|
112
|
-
'chart.shadow': false,
|
113
|
-
'chart.shadow.color': '#666',
|
114
|
-
'chart.shadow.blur': 3,
|
115
|
-
'chart.shadow.offsetx': 3,
|
116
|
-
'chart.shadow.offsety': 3,
|
117
|
-
'chart.key': null,
|
118
|
-
'chart.key.background': 'white',
|
119
|
-
'chart.key.position': 'graph',
|
120
|
-
'chart.key.halign': 'right',
|
121
|
-
'chart.key.shadow': false,
|
122
|
-
'chart.key.shadow.color': '#666',
|
123
|
-
'chart.key.shadow.blur': 3,
|
124
|
-
'chart.key.shadow.offsetx': 2,
|
125
|
-
'chart.key.shadow.offsety': 2,
|
126
|
-
'chart.key.position.gutter.boxed': false,
|
127
|
-
'chart.key.position.x': null,
|
128
|
-
'chart.key.position.y': null,
|
129
|
-
'chart.key.color.shape': 'square',
|
130
|
-
'chart.key.rounded': true,
|
131
|
-
'chart.key.linewidth': 1,
|
132
|
-
'chart.key.colors': null,
|
133
|
-
'chart.key.interactive': false,
|
134
|
-
'chart.key.interactive.highlight.chart.stroke': 'black',
|
135
|
-
'chart.key.interactive.highlight.chart.fill': 'rgba(255,255,255,0.7)',
|
136
|
-
'chart.key.interactive.highlight.label': 'rgba(255,0,0,0.2)',
|
137
|
-
'chart.key.text.color': 'black',
|
138
|
-
'chart.tooltips': null,
|
139
|
-
'chart.tooltips.effect': 'fade',
|
140
|
-
'chart.tooltips.css.class': 'RGraph_tooltip',
|
141
|
-
'chart.tooltips.event': 'onclick',
|
142
|
-
'chart.highlight.stroke': 'rgba(0,0,0,0)',
|
143
|
-
'chart.highlight.fill': 'rgba(255,255,255,0.7)',
|
144
|
-
'chart.tooltips.highlight': true,
|
145
|
-
'chart.annotatable': false,
|
146
|
-
'chart.annotate.color': 'black',
|
147
|
-
'chart.zoom.factor': 1.5,
|
148
|
-
'chart.zoom.fade.in': true,
|
149
|
-
'chart.zoom.fade.out': true,
|
150
|
-
'chart.zoom.factor': 1.5,
|
151
|
-
'chart.zoom.fade.in': true,
|
152
|
-
'chart.zoom.fade.out': true,
|
153
|
-
'chart.zoom.hdir': 'right',
|
154
|
-
'chart.zoom.vdir': 'down',
|
155
|
-
'chart.zoom.frames': 25,
|
156
|
-
'chart.zoom.delay': 16.666,
|
157
|
-
'chart.zoom.shadow': true,
|
158
|
-
'chart.zoom.background': true,
|
159
|
-
'chart.zoom.action': 'zoom',
|
160
|
-
'chart.resizable': false,
|
161
|
-
'chart.events.click': null,
|
162
|
-
'chart.events.mousemove': null,
|
163
|
-
'chart.clearto': 'rgba(0,0,0,0)'
|
164
|
-
}
|
165
|
-
|
166
|
-
// Store the data
|
167
|
-
for (var i=0; i<data.length; ++i) {
|
168
|
-
data[i] = parseFloat(data[i]);
|
169
|
-
}
|
170
|
-
this.data = data;
|
171
|
-
|
172
|
-
|
173
|
-
/**
|
174
|
-
* Create the dollar objects so that functions can be added to them
|
175
|
-
*/
|
176
|
-
for (var i=0; i<data.length; ++i) {
|
177
|
-
this['$' + i] = {};
|
178
|
-
}
|
179
|
-
|
180
|
-
|
181
|
-
/**
|
182
|
-
* Translate half a pixel for antialiasing purposes - but only if it hasn't beeen
|
183
|
-
* done already
|
184
|
-
*/
|
185
|
-
if (!this.canvas.__rgraph_aa_translated__) {
|
186
|
-
this.context.translate(0.5,0.5);
|
187
|
-
|
188
|
-
this.canvas.__rgraph_aa_translated__ = true;
|
189
|
-
}
|
190
|
-
|
191
|
-
|
192
|
-
|
193
|
-
|
194
|
-
// Short variable names
|
195
|
-
var RG = RGraph,
|
196
|
-
ca = this.canvas,
|
197
|
-
co = ca.getContext('2d'),
|
198
|
-
prop = this.properties,
|
199
|
-
pa2 = RG.path2,
|
200
|
-
win = window,
|
201
|
-
doc = document,
|
202
|
-
ma = Math
|
203
|
-
|
204
|
-
|
205
|
-
|
206
|
-
/**
|
207
|
-
* "Decorate" the object with the generic effects if the effects library has been included
|
208
|
-
*/
|
209
|
-
if (RG.Effects && typeof RG.Effects.decorate === 'function') {
|
210
|
-
RG.Effects.decorate(this);
|
211
|
-
}
|
212
|
-
|
213
|
-
|
214
|
-
|
215
|
-
|
216
|
-
/**
|
217
|
-
* A setter
|
218
|
-
*
|
219
|
-
* @param name string The name of the property to set
|
220
|
-
* @param value mixed The value of the property
|
221
|
-
*/
|
222
|
-
this.set =
|
223
|
-
this.Set = function (name)
|
224
|
-
{
|
225
|
-
var value = typeof arguments[1] === 'undefined' ? null : arguments[1];
|
226
|
-
|
227
|
-
/**
|
228
|
-
* the number of arguments is only one and it's an
|
229
|
-
* object - parse it for configuration data and return.
|
230
|
-
*/
|
231
|
-
if (arguments.length === 1 && typeof name === 'object') {
|
232
|
-
RG.parseObjectStyleConfig(this, name);
|
233
|
-
return this;
|
234
|
-
}
|
235
|
-
|
236
|
-
|
237
|
-
|
238
|
-
|
239
|
-
|
240
|
-
/**
|
241
|
-
* This should be done first - prepend the propertyy name with "chart." if necessary
|
242
|
-
*/
|
243
|
-
if (name.substr(0,6) != 'chart.') {
|
244
|
-
name = 'chart.' + name;
|
245
|
-
}
|
246
|
-
|
247
|
-
|
248
|
-
|
249
|
-
|
250
|
-
// Convert uppercase letters to dot+lower case letter
|
251
|
-
while(name.match(/([A-Z])/)) {
|
252
|
-
name = name.replace(/([A-Z])/, '.' + RegExp.$1.toLowerCase());
|
253
|
-
}
|
254
|
-
|
255
|
-
|
256
|
-
|
257
|
-
|
258
|
-
|
259
|
-
|
260
|
-
prop[name] = value;
|
261
|
-
|
262
|
-
return this;
|
263
|
-
};
|
264
|
-
|
265
|
-
|
266
|
-
|
267
|
-
|
268
|
-
/**
|
269
|
-
* A getter
|
270
|
-
*
|
271
|
-
* @param name string The name of the property to get
|
272
|
-
*/
|
273
|
-
this.get =
|
274
|
-
this.Get = function (name)
|
275
|
-
{
|
276
|
-
/**
|
277
|
-
* This should be done first - prepend the property name with "chart." if necessary
|
278
|
-
*/
|
279
|
-
if (name.substr(0,6) != 'chart.') {
|
280
|
-
name = 'chart.' + name;
|
281
|
-
}
|
282
|
-
|
283
|
-
// Convert uppercase letters to dot+lower case letter
|
284
|
-
name = name.replace(/([A-Z])/g, function (str)
|
285
|
-
{
|
286
|
-
return '.' + String(RegExp.$1).toLowerCase()
|
287
|
-
});
|
288
|
-
|
289
|
-
return prop[name.toLowerCase()];
|
290
|
-
};
|
291
|
-
|
292
|
-
|
293
|
-
|
294
|
-
|
295
|
-
/**
|
296
|
-
* The function you call to draw the bar chart
|
297
|
-
*/
|
298
|
-
this.draw =
|
299
|
-
this.Draw = function ()
|
300
|
-
{
|
301
|
-
/**
|
302
|
-
* Fire the onbeforedraw event
|
303
|
-
*/
|
304
|
-
RG.FireCustomEvent(this, 'onbeforedraw');
|
305
|
-
|
306
|
-
|
307
|
-
/**
|
308
|
-
* Parse the colors. This allows for simple gradient syntax
|
309
|
-
*/
|
310
|
-
if (!this.colorsParsed) {
|
311
|
-
this.parseColors();
|
312
|
-
|
313
|
-
// Don't want to do this again
|
314
|
-
this.colorsParsed = true;
|
315
|
-
}
|
316
|
-
|
317
|
-
|
318
|
-
/**
|
319
|
-
* This is new in May 2011 and facilitates indiviual gutter settings,
|
320
|
-
* eg chart.gutter.left
|
321
|
-
*/
|
322
|
-
this.gutterLeft = prop['chart.gutter.left'];
|
323
|
-
this.gutterRight = prop['chart.gutter.right'];
|
324
|
-
this.gutterTop = prop['chart.gutter.top'];
|
325
|
-
this.gutterBottom = prop['chart.gutter.bottom'];
|
326
|
-
|
327
|
-
// This stops the coords array from growing
|
328
|
-
this.coords = [];
|
329
|
-
|
330
|
-
/**
|
331
|
-
* Stop this growing uncntrollably
|
332
|
-
*/
|
333
|
-
this.coordsText = [];
|
334
|
-
|
335
|
-
RG.DrawTitle(this, prop['chart.title'], this.gutterTop, null, prop['chart.title.size'] ? prop['chart.title.size'] : prop['chart.text.size'] + 2);
|
336
|
-
this.DrawFunnel();
|
337
|
-
|
338
|
-
|
339
|
-
/**
|
340
|
-
* Setup the context menu if required
|
341
|
-
*/
|
342
|
-
if (prop['chart.contextmenu']) {
|
343
|
-
RG.ShowContext(this);
|
344
|
-
}
|
345
|
-
|
346
|
-
|
347
|
-
|
348
|
-
/**
|
349
|
-
* Draw the labels on the chart
|
350
|
-
*/
|
351
|
-
this.DrawLabels();
|
352
|
-
|
353
|
-
|
354
|
-
/**
|
355
|
-
* This function enables resizing
|
356
|
-
*/
|
357
|
-
if (prop['chart.resizable']) {
|
358
|
-
RG.AllowResizing(this);
|
359
|
-
}
|
360
|
-
|
361
|
-
|
362
|
-
/**
|
363
|
-
* This installs the event listeners
|
364
|
-
*/
|
365
|
-
RG.InstallEventListeners(this);
|
366
|
-
|
367
|
-
|
368
|
-
|
369
|
-
|
370
|
-
/**
|
371
|
-
* Fire the onfirstdraw event
|
372
|
-
*/
|
373
|
-
if (this.firstDraw) {
|
374
|
-
RG.fireCustomEvent(this, 'onfirstdraw');
|
375
|
-
this.firstDraw = false;
|
376
|
-
this.firstDrawFunc();
|
377
|
-
}
|
378
|
-
|
379
|
-
|
380
|
-
|
381
|
-
|
382
|
-
/**
|
383
|
-
* Fire the RGraph ondraw event
|
384
|
-
*/
|
385
|
-
RG.FireCustomEvent(this, 'ondraw');
|
386
|
-
|
387
|
-
return this;
|
388
|
-
};
|
389
|
-
|
390
|
-
|
391
|
-
|
392
|
-
/**
|
393
|
-
* Used in chaining. Runs a function there and then - not waiting for
|
394
|
-
* the events to fire (eg the onbeforedraw event)
|
395
|
-
*
|
396
|
-
* @param function func The function to execute
|
397
|
-
*/
|
398
|
-
this.exec = function (func)
|
399
|
-
{
|
400
|
-
func(this);
|
401
|
-
|
402
|
-
return this;
|
403
|
-
};
|
404
|
-
|
405
|
-
|
406
|
-
|
407
|
-
|
408
|
-
/**
|
409
|
-
* This function actually draws the chart
|
410
|
-
*/
|
411
|
-
this.drawFunnel =
|
412
|
-
this.DrawFunnel = function ()
|
413
|
-
{
|
414
|
-
var width = ca.width - this.gutterLeft - this.gutterRight;
|
415
|
-
var height = ca.height - this.gutterTop - this.gutterBottom;
|
416
|
-
var total = RG.array_max(this.data);
|
417
|
-
var accheight = this.gutterTop;
|
418
|
-
|
419
|
-
|
420
|
-
/**
|
421
|
-
* Loop through each segment to draw
|
422
|
-
*/
|
423
|
-
|
424
|
-
// Set a shadow if it's been requested
|
425
|
-
if (prop['chart.shadow']) {
|
426
|
-
co.shadowColor = prop['chart.shadow.color'];
|
427
|
-
co.shadowBlur = prop['chart.shadow.blur'];
|
428
|
-
co.shadowOffsetX = prop['chart.shadow.offsetx'];
|
429
|
-
co.shadowOffsetY = prop['chart.shadow.offsety'];
|
430
|
-
}
|
431
|
-
|
432
|
-
for (i=0,len=this.data.length; i<len; ++i) {
|
433
|
-
|
434
|
-
var firstvalue = this.data[0];
|
435
|
-
var firstwidth = (firstvalue / total) * width;
|
436
|
-
var curvalue = this.data[i];
|
437
|
-
var curwidth = (curvalue / total) * width;
|
438
|
-
var curheight = height / this.data.length;
|
439
|
-
var halfCurWidth = (curwidth / 2);
|
440
|
-
var nextvalue = this.data[i + 1];
|
441
|
-
var nextwidth = this.data[i + 1] ? (nextvalue / total) * width : null;
|
442
|
-
var halfNextWidth = (nextwidth / 2);
|
443
|
-
var center = this.gutterLeft + (firstwidth / 2);
|
444
|
-
|
445
|
-
var x1 = center - halfCurWidth;
|
446
|
-
var y1 = accheight;
|
447
|
-
var x2 = center + halfCurWidth;
|
448
|
-
var y2 = accheight;
|
449
|
-
var x3 = center + halfNextWidth;
|
450
|
-
var y3 = accheight + curheight;
|
451
|
-
var x4 = center - halfNextWidth;
|
452
|
-
var y4 = accheight + curheight;
|
453
|
-
|
454
|
-
if (nextwidth && i < this.data.length - 1) {
|
455
|
-
|
456
|
-
co.beginPath();
|
457
|
-
|
458
|
-
co.strokeStyle = prop['chart.strokestyle'];
|
459
|
-
co.fillStyle = prop['chart.colors'][i];
|
460
|
-
|
461
|
-
co.moveTo(x1, y1);
|
462
|
-
co.lineTo(x2, y2);
|
463
|
-
co.lineTo(x3, y3);
|
464
|
-
co.lineTo(x4, y4);
|
465
|
-
|
466
|
-
co.closePath();
|
467
|
-
|
468
|
-
/**
|
469
|
-
* Store the coordinates
|
470
|
-
*/
|
471
|
-
this.coords.push([x1, y1, x2, y2, x3, y3, x4, y4]);
|
472
|
-
}
|
473
|
-
|
474
|
-
|
475
|
-
// The redrawing if the shadow is on will do the stroke
|
476
|
-
if (!prop['chart.shadow']) {
|
477
|
-
co.stroke();
|
478
|
-
}
|
479
|
-
|
480
|
-
co.fill();
|
481
|
-
|
482
|
-
accheight += curheight;
|
483
|
-
}
|
484
|
-
|
485
|
-
/**
|
486
|
-
* If the shadow is enabled, redraw every segment, in order to allow for shadows going upwards
|
487
|
-
*/
|
488
|
-
if (prop['chart.shadow']) {
|
489
|
-
|
490
|
-
RG.NoShadow(this);
|
491
|
-
|
492
|
-
for (i=0; i<this.coords.length; ++i) {
|
493
|
-
|
494
|
-
co.strokeStyle = prop['chart.strokestyle'];
|
495
|
-
co.fillStyle = prop['chart.colors'][i];
|
496
|
-
|
497
|
-
co.beginPath();
|
498
|
-
co.moveTo(this.coords[i][0], this.coords[i][1]);
|
499
|
-
co.lineTo(this.coords[i][2], this.coords[i][3]);
|
500
|
-
co.lineTo(this.coords[i][4], this.coords[i][5]);
|
501
|
-
co.lineTo(this.coords[i][6], this.coords[i][7]);
|
502
|
-
co.closePath();
|
503
|
-
|
504
|
-
co.stroke();
|
505
|
-
co.fill();
|
506
|
-
}
|
507
|
-
}
|
508
|
-
|
509
|
-
/**
|
510
|
-
* Lastly, draw the key if necessary
|
511
|
-
*/
|
512
|
-
if (prop['chart.key'] && prop['chart.key'].length) {
|
513
|
-
RG.DrawKey(this, prop['chart.key'], prop['chart.colors']);
|
514
|
-
}
|
515
|
-
};
|
516
|
-
|
517
|
-
|
518
|
-
|
519
|
-
|
520
|
-
/**
|
521
|
-
* Draws the labels
|
522
|
-
*/
|
523
|
-
this.drawLabels =
|
524
|
-
this.DrawLabels = function ()
|
525
|
-
{
|
526
|
-
/**
|
527
|
-
* Draws the labels
|
528
|
-
*/
|
529
|
-
if (prop['chart.labels'] && prop['chart.labels'].length > 0) {
|
530
|
-
|
531
|
-
var font = prop['chart.text.font'];
|
532
|
-
var size = prop['chart.text.size'];
|
533
|
-
var color = prop['chart.text.color'];
|
534
|
-
var labels = prop['chart.labels'];
|
535
|
-
var halign = prop['chart.text.halign'] == 'left' ? 'left' : 'center';
|
536
|
-
var bgcolor = prop['chart.text.boxed'] ? 'white' : null;
|
537
|
-
|
538
|
-
if (typeof prop['chart.labels.x'] == 'number') {
|
539
|
-
var x = prop['chart.labels.x'];
|
540
|
-
} else {
|
541
|
-
var x = halign == 'left' ? (this.gutterLeft - 15) : ((ca.width - this.gutterLeft - this.gutterRight) / 2) + this.gutterLeft;
|
542
|
-
}
|
543
|
-
|
544
|
-
for (var j=0; j<this.coords.length; ++j) { // MUST be "j"
|
545
|
-
|
546
|
-
co.beginPath();
|
547
|
-
|
548
|
-
// Set the color back to black
|
549
|
-
co.strokeStyle = 'black';
|
550
|
-
co.fillStyle = color;
|
551
|
-
|
552
|
-
// Turn off any shadow
|
553
|
-
RG.NoShadow(this);
|
554
|
-
|
555
|
-
var label = labels[j];
|
556
|
-
|
557
|
-
RG.text2(this,{'font':font,
|
558
|
-
'size':size,
|
559
|
-
'x':x,
|
560
|
-
'y':this.coords[j][1],
|
561
|
-
'text':label,
|
562
|
-
'valign':'center',
|
563
|
-
'halign':halign,
|
564
|
-
'bounding': prop['chart.text.boxed'],
|
565
|
-
'boundingFill':bgcolor,
|
566
|
-
'tag': 'labels'
|
567
|
-
});
|
568
|
-
|
569
|
-
if (prop['chart.labels.sticks']) {
|
570
|
-
/**
|
571
|
-
* Measure the text
|
572
|
-
*/
|
573
|
-
co.font = size + 'pt ' + font;
|
574
|
-
var labelWidth = co.measureText(label).width;
|
575
|
-
|
576
|
-
/**
|
577
|
-
* Draw the horizontal indicator line
|
578
|
-
*/
|
579
|
-
co.beginPath();
|
580
|
-
co.strokeStyle = 'gray';
|
581
|
-
co.moveTo(x + labelWidth + 10, ma.round(this.coords[j][1]));
|
582
|
-
co.lineTo(this.coords[j][0] - 10, ma.round(this.coords[j][1]));
|
583
|
-
co.stroke();
|
584
|
-
}
|
585
|
-
}
|
586
|
-
|
587
|
-
|
588
|
-
|
589
|
-
/**
|
590
|
-
* This draws the last labels if defined
|
591
|
-
*/
|
592
|
-
var lastLabel = labels[j];
|
593
|
-
|
594
|
-
if (lastLabel) {
|
595
|
-
|
596
|
-
RG.text2(this,{'font':font,
|
597
|
-
'size':size,
|
598
|
-
'x':x,
|
599
|
-
'y':this.coords[j - 1][5],
|
600
|
-
'text':lastLabel,
|
601
|
-
'valign':'center',
|
602
|
-
'halign':halign,
|
603
|
-
'bounding': prop['chart.text.boxed'],
|
604
|
-
'boundingFill':bgcolor,
|
605
|
-
'tag': 'labels'
|
606
|
-
});
|
607
|
-
|
608
|
-
if (prop['chart.labels.sticks']) {
|
609
|
-
|
610
|
-
/**
|
611
|
-
* Measure the text
|
612
|
-
*/
|
613
|
-
co.font = size + 'pt ' + font;
|
614
|
-
var labelWidth = co.measureText(lastLabel).width;
|
615
|
-
|
616
|
-
/**
|
617
|
-
* Draw the horizontal indicator line
|
618
|
-
*/
|
619
|
-
co.beginPath();
|
620
|
-
co.strokeStyle = 'gray';
|
621
|
-
|
622
|
-
//co.moveTo(x + labelWidth + 10, ma.round(this.coords[j][1]));
|
623
|
-
//co.lineTo(this.coords[j][0] - 10, ma.round(this.coords[j][1]));
|
624
|
-
|
625
|
-
co.moveTo(x + labelWidth + 10, Math.round(this.coords[j - 1][7]));
|
626
|
-
co.lineTo(this.coords[j - 1][6] - 10, Math.round(this.coords[j - 1][7]));
|
627
|
-
co.stroke();
|
628
|
-
}
|
629
|
-
}
|
630
|
-
}
|
631
|
-
};
|
632
|
-
|
633
|
-
|
634
|
-
|
635
|
-
|
636
|
-
/**
|
637
|
-
* Gets the appropriate segment that has been highlighted
|
638
|
-
*/
|
639
|
-
this.getShape =
|
640
|
-
this.getSegment = function (e)
|
641
|
-
{
|
642
|
-
//var canvas = ca = e.target;
|
643
|
-
//var co = this.context;
|
644
|
-
//var prop = this.properties;
|
645
|
-
var coords = this.coords;
|
646
|
-
var mouseCoords = RG.getMouseXY(e);
|
647
|
-
var x = mouseCoords[0];
|
648
|
-
var y = mouseCoords[1];
|
649
|
-
|
650
|
-
for (i=0,len=coords.length; i<len; ++i) {
|
651
|
-
|
652
|
-
var segment = coords[i]
|
653
|
-
|
654
|
-
// Path testing
|
655
|
-
co.beginPath();
|
656
|
-
co.moveTo(segment[0], segment[1]);
|
657
|
-
co.lineTo(segment[2], segment[3]);
|
658
|
-
co.lineTo(segment[4], segment[5]);
|
659
|
-
co.lineTo(segment[6], segment[7]);
|
660
|
-
co.lineTo(segment[8], segment[9]);
|
661
|
-
|
662
|
-
if (co.isPointInPath(x, y)) {
|
663
|
-
var tooltip = RGraph.parseTooltipText(prop['chart.tooltips'], i);
|
664
|
-
return {0: this, 1: coords, 2: i, 'object': this, 'coords': segment, 'index': i, 'tooltip': tooltip};
|
665
|
-
}
|
666
|
-
}
|
667
|
-
|
668
|
-
return null;
|
669
|
-
};
|
670
|
-
|
671
|
-
|
672
|
-
|
673
|
-
|
674
|
-
/**
|
675
|
-
* Each object type has its own Highlight() function which highlights the appropriate shape
|
676
|
-
*
|
677
|
-
* @param object shape The shape to highlight
|
678
|
-
*/
|
679
|
-
this.highlight =
|
680
|
-
this.Highlight = function (shape)
|
681
|
-
{
|
682
|
-
if (prop['chart.tooltips.highlight']) {
|
683
|
-
|
684
|
-
if (typeof prop['chart.highlight.style'] === 'function') {
|
685
|
-
(prop['chart.highlight.style'])(shape);
|
686
|
-
return;
|
687
|
-
}
|
688
|
-
|
689
|
-
|
690
|
-
|
691
|
-
var coords = shape['coords'];
|
692
|
-
|
693
|
-
pa2(
|
694
|
-
co,
|
695
|
-
'b m % % l % % l % % l % % c s % f %',
|
696
|
-
coords[0], coords[1],
|
697
|
-
coords[2], coords[3],
|
698
|
-
coords[4], coords[5],
|
699
|
-
coords[6], coords[7],
|
700
|
-
prop['chart.highlight.stroke'],
|
701
|
-
prop['chart.highlight.fill']
|
702
|
-
);
|
703
|
-
}
|
704
|
-
};
|
705
|
-
|
706
|
-
|
707
|
-
|
708
|
-
|
709
|
-
/**
|
710
|
-
* The getObjectByXY() worker method. Don't call this call:
|
711
|
-
*
|
712
|
-
* RGraph.ObjectRegistry.getObjectByXY(e)
|
713
|
-
*
|
714
|
-
* @param object e The event object
|
715
|
-
*/
|
716
|
-
this.getObjectByXY = function (e)
|
717
|
-
{
|
718
|
-
var mouseXY = RGraph.getMouseXY(e);
|
719
|
-
|
720
|
-
if (
|
721
|
-
mouseXY[0] > prop['chart.gutter.left']
|
722
|
-
&& mouseXY[0] < (ca.width - prop['chart.gutter.right'])
|
723
|
-
&& mouseXY[1] > prop['chart.gutter.top']
|
724
|
-
&& mouseXY[1] < (ca.height - prop['chart.gutter.bottom'])
|
725
|
-
) {
|
726
|
-
|
727
|
-
return this;
|
728
|
-
}
|
729
|
-
};
|
730
|
-
|
731
|
-
|
732
|
-
|
733
|
-
|
734
|
-
/**
|
735
|
-
* This function positions a tooltip when it is displayed
|
736
|
-
*
|
737
|
-
* @param obj object The chart object
|
738
|
-
* @param int x The X coordinate specified for the tooltip
|
739
|
-
* @param int y The Y coordinate specified for the tooltip
|
740
|
-
* @param objec tooltip The tooltips DIV element
|
741
|
-
*/
|
742
|
-
this.positionTooltip = function (obj, x, y, tooltip, idx)
|
743
|
-
{
|
744
|
-
var coords = obj.coords[tooltip.__index__];
|
745
|
-
|
746
|
-
var x1 = coords[0];
|
747
|
-
var y1 = coords[1];
|
748
|
-
var x2 = coords[2];
|
749
|
-
var y2 = coords[3];
|
750
|
-
var x3 = coords[4];
|
751
|
-
var y3 = coords[5];
|
752
|
-
var x4 = coords[6];
|
753
|
-
var y4 = coords[7];
|
754
|
-
|
755
|
-
var coordW = x2 - x1;
|
756
|
-
var coordX = x1 + (coordW / 2);
|
757
|
-
var canvasXY = RG.getCanvasXY(ca);
|
758
|
-
var mouseXY = RG.getMouseXY(window.event);
|
759
|
-
var gutterLeft = prop['chart.gutter.left'];
|
760
|
-
var gutterTop = prop['chart.gutter.top'];
|
761
|
-
var width = tooltip.offsetWidth;
|
762
|
-
var height = tooltip.offsetHeight;
|
763
|
-
|
764
|
-
// Set the top position
|
765
|
-
tooltip.style.left = 0;
|
766
|
-
tooltip.style.top = window.event.pageY - height - 5 + 'px';
|
767
|
-
|
768
|
-
// By default any overflow is hidden
|
769
|
-
tooltip.style.overflow = '';
|
770
|
-
|
771
|
-
|
772
|
-
|
773
|
-
// Reposition the tooltip if at the edges:
|
774
|
-
|
775
|
-
// LEFT edge
|
776
|
-
if (canvasXY[0] + mouseXY[0] - (width / 2) < 0) {
|
777
|
-
tooltip.style.left = canvasXY[0] + mouseXY[0] - (width * 0.1) + 'px';
|
778
|
-
|
779
|
-
// RIGHT edge
|
780
|
-
} else if (canvasXY[0] + mouseXY[0] + (width / 2) > doc.body.offsetWidth) {
|
781
|
-
tooltip.style.left = canvasXY[0] + mouseXY[0] - (width * 0.9) + 'px';
|
782
|
-
|
783
|
-
// Default positioning - CENTERED
|
784
|
-
} else {
|
785
|
-
tooltip.style.left = canvasXY[0] + mouseXY[0] - (width / 2) + 'px';
|
786
|
-
}
|
787
|
-
};
|
788
|
-
|
789
|
-
|
790
|
-
|
791
|
-
|
792
|
-
/**
|
793
|
-
* This allows for easy specification of gradients
|
794
|
-
*/
|
795
|
-
this.parseColors = function ()
|
796
|
-
{
|
797
|
-
// Save the original colors so that they can be restored when the canvas is reset
|
798
|
-
if (this.original_colors.length === 0) {
|
799
|
-
this.original_colors['chart.colors'] = RG.array_clone(prop['chart.colors']);
|
800
|
-
this.original_colors['chart.key.colors'] = RG.array_clone(prop['chart.key.colors']);
|
801
|
-
this.original_colors['chart.highlight.fill'] = RG.array_clone(prop['chart.highlight.fill']);
|
802
|
-
this.original_colors['chart.highlight.stroke'] = RG.array_clone(prop['chart.highlight.stroke']);
|
803
|
-
this.original_colors['chart.strokestyle'] = RG.array_clone(prop['chart.strokestyle']);
|
804
|
-
}
|
805
|
-
|
806
|
-
var colors = prop['chart.colors'];
|
807
|
-
|
808
|
-
for (var i=0; i<colors.length; ++i) {
|
809
|
-
colors[i] = this.parseSingleColorForHorizontalGradient(colors[i]);
|
810
|
-
}
|
811
|
-
|
812
|
-
var keyColors = prop['chart.key.colors'];
|
813
|
-
if (keyColors) {
|
814
|
-
for (var i=0; i<keyColors.length; ++i) {
|
815
|
-
keyColors[i] = this.parseSingleColorForHorizontalGradient(keyColors[i]);
|
816
|
-
}
|
817
|
-
}
|
818
|
-
|
819
|
-
|
820
|
-
prop['chart.strokestyle'] = this.parseSingleColorForVerticalGradient(prop['chart.strokestyle']);
|
821
|
-
prop['chart.highlight.stroke'] = this.parseSingleColorForHorizontalGradient(prop['chart.highlight.stroke']);
|
822
|
-
prop['chart.highlight.fill'] = this.parseSingleColorForHorizontalGradient(prop['chart.highlight.fill']);
|
823
|
-
};
|
824
|
-
|
825
|
-
|
826
|
-
|
827
|
-
|
828
|
-
/**
|
829
|
-
* Use this function to reset the object to the post-constructor state. Eg reset colors if
|
830
|
-
* need be etc
|
831
|
-
*/
|
832
|
-
this.reset = function ()
|
833
|
-
{
|
834
|
-
};
|
835
|
-
|
836
|
-
|
837
|
-
|
838
|
-
|
839
|
-
/**
|
840
|
-
* This parses a single color value
|
841
|
-
*/
|
842
|
-
this.parseSingleColorForHorizontalGradient = function (color)
|
843
|
-
{
|
844
|
-
if (!color || typeof(color) != 'string') {
|
845
|
-
return color;
|
846
|
-
}
|
847
|
-
|
848
|
-
if (color.match(/^gradient\((.*)\)$/i)) {
|
849
|
-
|
850
|
-
var parts = RegExp.$1.split(':');
|
851
|
-
|
852
|
-
// Create the gradient
|
853
|
-
var grad = co.createLinearGradient(prop['chart.gutter.left'],0,ca.width - prop['chart.gutter.right'],0);
|
854
|
-
|
855
|
-
var diff = 1 / (parts.length - 1);
|
856
|
-
|
857
|
-
grad.addColorStop(0, RGraph.trim(parts[0]));
|
858
|
-
|
859
|
-
for (var j=1; j<parts.length; ++j) {
|
860
|
-
grad.addColorStop(j * diff, RG.trim(parts[j]));
|
861
|
-
}
|
862
|
-
}
|
863
|
-
|
864
|
-
return grad ? grad : color;
|
865
|
-
};
|
866
|
-
|
867
|
-
|
868
|
-
|
869
|
-
|
870
|
-
/**
|
871
|
-
* This parses a single color value
|
872
|
-
*/
|
873
|
-
this.parseSingleColorForVerticalGradient = function (color)
|
874
|
-
{
|
875
|
-
if (!color || typeof(color) != 'string') {
|
876
|
-
return color;
|
877
|
-
}
|
878
|
-
|
879
|
-
if (color.match(/^gradient\((.*)\)$/i)) {
|
880
|
-
|
881
|
-
var parts = RegExp.$1.split(':');
|
882
|
-
|
883
|
-
// Create the gradient
|
884
|
-
var grad = co.createLinearGradient(0, prop['chart.gutter.top'],0,ca.height - prop['chart.gutter.bottom']);
|
885
|
-
|
886
|
-
var diff = 1 / (parts.length - 1);
|
887
|
-
|
888
|
-
grad.addColorStop(0, RGraph.trim(parts[0]));
|
889
|
-
|
890
|
-
for (var j=1; j<parts.length; ++j) {
|
891
|
-
grad.addColorStop(j * diff, RG.trim(parts[j]));
|
892
|
-
}
|
893
|
-
}
|
894
|
-
|
895
|
-
return grad ? grad : color;
|
896
|
-
};
|
897
|
-
|
898
|
-
|
899
|
-
|
900
|
-
|
901
|
-
/**
|
902
|
-
* This function handles highlighting an entire data-series for the interactive
|
903
|
-
* key
|
904
|
-
*
|
905
|
-
* @param int index The index of the data series to be highlighted
|
906
|
-
*/
|
907
|
-
this.interactiveKeyHighlight = function (index)
|
908
|
-
{
|
909
|
-
var coords = this.coords[index];
|
910
|
-
|
911
|
-
if (coords && coords.length == 8) {
|
912
|
-
var pre_linewidth = co.lineWidth;
|
913
|
-
|
914
|
-
co.lineWidth = 2;
|
915
|
-
co.strokeStyle = prop['chart.key.interactive.highlight.chart.stroke'];
|
916
|
-
co.fillStyle = prop['chart.key.interactive.highlight.chart.fill'];
|
917
|
-
|
918
|
-
co.beginPath();
|
919
|
-
co.moveTo(coords[0], coords[1]);
|
920
|
-
co.lineTo(coords[2], coords[3]);
|
921
|
-
co.lineTo(coords[4], coords[5]);
|
922
|
-
co.lineTo(coords[6], coords[7]);
|
923
|
-
co.closePath();
|
924
|
-
co.fill();
|
925
|
-
co.stroke();
|
926
|
-
|
927
|
-
// Reset the linewidth
|
928
|
-
co.lineWidth = pre_linewidth;
|
929
|
-
}
|
930
|
-
};
|
931
|
-
|
932
|
-
|
933
|
-
|
934
|
-
|
935
|
-
/**
|
936
|
-
* Using a function to add events makes it easier to facilitate method chaining
|
937
|
-
*
|
938
|
-
* @param string type The type of even to add
|
939
|
-
* @param function func
|
940
|
-
*/
|
941
|
-
this.on = function (type, func)
|
942
|
-
{
|
943
|
-
if (type.substr(0,2) !== 'on') {
|
944
|
-
type = 'on' + type;
|
945
|
-
}
|
946
|
-
|
947
|
-
this[type] = func;
|
948
|
-
|
949
|
-
return this;
|
950
|
-
};
|
951
|
-
|
952
|
-
|
953
|
-
|
954
|
-
|
955
|
-
/**
|
956
|
-
* This function runs once only
|
957
|
-
* (put at the end of the file (before any effects))
|
958
|
-
*/
|
959
|
-
this.firstDrawFunc = function ()
|
960
|
-
{
|
961
|
-
};
|
962
|
-
|
963
|
-
|
964
|
-
|
965
|
-
RG.att(ca);
|
966
|
-
|
967
|
-
|
968
|
-
|
969
|
-
|
970
|
-
/**
|
971
|
-
* Always now regsiter the object
|
972
|
-
*/
|
973
|
-
RG.Register(this);
|
974
|
-
|
975
|
-
|
976
|
-
|
977
|
-
|
978
|
-
/**
|
979
|
-
* This is the 'end' of the constructor so if the first argument
|
980
|
-
* contains configuration data - handle that.
|
981
|
-
*/
|
982
|
-
if (parseConfObjectForOptions) {
|
983
|
-
RG.parseObjectStyleConfig(this, conf.options);
|
984
|
-
}
|
985
|
-
};
|
2
|
+
RGraph=window.RGraph||{isRGraph:true};RGraph.Funnel=function(conf)
|
3
|
+
{if(typeof conf==='object'&&typeof conf.data==='object'&&typeof conf.id==='string'){var id=conf.id
|
4
|
+
var canvas=document.getElementById(id);var data=conf.data;var parseConfObjectForOptions=true;}else{var id=conf;var canvas=document.getElementById(id);var data=arguments[1];}
|
5
|
+
this.id=id;this.canvas=canvas;this.context=this.canvas.getContext?this.canvas.getContext("2d",{alpha:(typeof id==='object'&&id.alpha===false)?false:true}):null;this.canvas.__object__=this;this.type='funnel';this.coords=[];this.isRGraph=true;this.uid=RGraph.CreateUID();this.canvas.uid=this.canvas.uid?this.canvas.uid:RGraph.CreateUID();this.coordsText=[];this.original_colors=[];this.firstDraw=true;if(!this.canvas){alert('[FUNNEL] No canvas support');return;}
|
6
|
+
this.properties={'chart.strokestyle':'rgba(0,0,0,0)','chart.gutter.left':25,'chart.gutter.right':25,'chart.gutter.top':25,'chart.gutter.bottom':25,'chart.labels':null,'chart.labels.sticks':false,'chart.labels.x':null,'chart.title':'','chart.title.background':null,'chart.title.hpos':null,'chart.title.vpos':null,'chart.title.bold':true,'chart.title.font':null,'chart.title.x':null,'chart.title.y':null,'chart.title.halign':null,'chart.title.valign':null,'chart.colors':['Gradient(white:red)','Gradient(white:green)','Gradient(white:gray)','Gradient(white:blue)','Gradient(white:black)','Gradient(white:gray)','Gradient(white:pink)','Gradient(white:blue)','Gradient(white:yellow)','Gradient(white:green)','Gradient(white:red)'],'chart.text.size':12,'chart.text.boxed':true,'chart.text.halign':'left','chart.text.color':'black','chart.text.font':'Segoe UI, Arial, Verdana, sans-serif','chart.text.accessible':true,'chart.text.accessible.overflow':'visible','chart.text.accessible.pointerevents':true,'chart.contextmenu':null,'chart.shadow':false,'chart.shadow.color':'#666','chart.shadow.blur':3,'chart.shadow.offsetx':3,'chart.shadow.offsety':3,'chart.key':null,'chart.key.background':'white','chart.key.position':'graph','chart.key.halign':'right','chart.key.shadow':false,'chart.key.shadow.color':'#666','chart.key.shadow.blur':3,'chart.key.shadow.offsetx':2,'chart.key.shadow.offsety':2,'chart.key.position.gutter.boxed':false,'chart.key.position.x':null,'chart.key.position.y':null,'chart.key.color.shape':'square','chart.key.rounded':true,'chart.key.linewidth':1,'chart.key.colors':null,'chart.key.interactive':false,'chart.key.interactive.highlight.chart.stroke':'black','chart.key.interactive.highlight.chart.fill':'rgba(255,255,255,0.7)','chart.key.interactive.highlight.label':'rgba(255,0,0,0.2)','chart.key.text.color':'black','chart.tooltips':null,'chart.tooltips.effect':'fade','chart.tooltips.css.class':'RGraph_tooltip','chart.tooltips.event':'onclick','chart.highlight.stroke':'rgba(0,0,0,0)','chart.highlight.fill':'rgba(255,255,255,0.7)','chart.tooltips.highlight':true,'chart.annotatable':false,'chart.annotate.color':'black','chart.zoom.factor':1.5,'chart.zoom.fade.in':true,'chart.zoom.fade.out':true,'chart.zoom.factor':1.5,'chart.zoom.fade.in':true,'chart.zoom.fade.out':true,'chart.zoom.hdir':'right','chart.zoom.vdir':'down','chart.zoom.frames':25,'chart.zoom.delay':16.666,'chart.zoom.shadow':true,'chart.zoom.background':true,'chart.zoom.action':'zoom','chart.resizable':false,'chart.events.click':null,'chart.events.mousemove':null,'chart.clearto':'rgba(0,0,0,0)'}
|
7
|
+
for(var i=0;i<data.length;++i){data[i]=parseFloat(data[i]);}
|
8
|
+
this.data=data;for(var i=0;i<data.length;++i){this['$'+i]={};}
|
9
|
+
if(!this.canvas.__rgraph_aa_translated__){this.context.translate(0.5,0.5);this.canvas.__rgraph_aa_translated__=true;}
|
10
|
+
var RG=RGraph,ca=this.canvas,co=ca.getContext('2d'),prop=this.properties,pa2=RG.path2,win=window,doc=document,ma=Math
|
11
|
+
if(RG.Effects&&typeof RG.Effects.decorate==='function'){RG.Effects.decorate(this);}
|
12
|
+
this.set=this.Set=function(name)
|
13
|
+
{var value=typeof arguments[1]==='undefined'?null:arguments[1];if(arguments.length===1&&typeof name==='object'){RG.parseObjectStyleConfig(this,name);return this;}
|
14
|
+
if(name.substr(0,6)!='chart.'){name='chart.'+name;}
|
15
|
+
while(name.match(/([A-Z])/)){name=name.replace(/([A-Z])/,'.'+RegExp.$1.toLowerCase());}
|
16
|
+
prop[name]=value;return this;};this.get=this.Get=function(name)
|
17
|
+
{if(name.substr(0,6)!='chart.'){name='chart.'+name;}
|
18
|
+
while(name.match(/([A-Z])/)){name=name.replace(/([A-Z])/,'.'+RegExp.$1.toLowerCase());}
|
19
|
+
return prop[name.toLowerCase()];};this.draw=this.Draw=function()
|
20
|
+
{RG.FireCustomEvent(this,'onbeforedraw');if(!this.colorsParsed){this.parseColors();this.colorsParsed=true;}
|
21
|
+
this.gutterLeft=prop['chart.gutter.left'];this.gutterRight=prop['chart.gutter.right'];this.gutterTop=prop['chart.gutter.top'];this.gutterBottom=prop['chart.gutter.bottom'];this.coords=[];this.coordsText=[];RG.DrawTitle(this,prop['chart.title'],this.gutterTop,null,prop['chart.title.size']?prop['chart.title.size']:prop['chart.text.size']+2);this.DrawFunnel();if(prop['chart.contextmenu']){RG.ShowContext(this);}
|
22
|
+
this.DrawLabels();if(prop['chart.resizable']){RG.AllowResizing(this);}
|
23
|
+
RG.InstallEventListeners(this);if(this.firstDraw){RG.fireCustomEvent(this,'onfirstdraw');this.firstDraw=false;this.firstDrawFunc();}
|
24
|
+
RG.FireCustomEvent(this,'ondraw');return this;};this.exec=function(func)
|
25
|
+
{func(this);return this;};this.drawFunnel=this.DrawFunnel=function()
|
26
|
+
{var width=ca.width-this.gutterLeft-this.gutterRight;var height=ca.height-this.gutterTop-this.gutterBottom;var total=RG.array_max(this.data);var accheight=this.gutterTop;if(prop['chart.shadow']){co.shadowColor=prop['chart.shadow.color'];co.shadowBlur=prop['chart.shadow.blur'];co.shadowOffsetX=prop['chart.shadow.offsetx'];co.shadowOffsetY=prop['chart.shadow.offsety'];}
|
27
|
+
for(i=0,len=this.data.length;i<len;++i){var firstvalue=this.data[0];var firstwidth=(firstvalue/total)*width;var curvalue=this.data[i];var curwidth=(curvalue/total)*width;var curheight=height/this.data.length;var halfCurWidth=(curwidth/2);var nextvalue=this.data[i+1];var nextwidth=this.data[i+1]?(nextvalue/total)*width:null;var halfNextWidth=(nextwidth/2);var center=this.gutterLeft+(firstwidth/2);var x1=center-halfCurWidth;var y1=accheight;var x2=center+halfCurWidth;var y2=accheight;var x3=center+halfNextWidth;var y3=accheight+curheight;var x4=center-halfNextWidth;var y4=accheight+curheight;if(nextwidth&&i<this.data.length-1){co.beginPath();co.strokeStyle=prop['chart.strokestyle'];co.fillStyle=prop['chart.colors'][i];co.moveTo(x1,y1);co.lineTo(x2,y2);co.lineTo(x3,y3);co.lineTo(x4,y4);co.closePath();this.coords.push([x1,y1,x2,y2,x3,y3,x4,y4]);}
|
28
|
+
if(!prop['chart.shadow']){co.stroke();}
|
29
|
+
co.fill();accheight+=curheight;}
|
30
|
+
if(prop['chart.shadow']){RG.NoShadow(this);for(i=0;i<this.coords.length;++i){co.strokeStyle=prop['chart.strokestyle'];co.fillStyle=prop['chart.colors'][i];co.beginPath();co.moveTo(this.coords[i][0],this.coords[i][1]);co.lineTo(this.coords[i][2],this.coords[i][3]);co.lineTo(this.coords[i][4],this.coords[i][5]);co.lineTo(this.coords[i][6],this.coords[i][7]);co.closePath();co.stroke();co.fill();}}
|
31
|
+
if(prop['chart.key']&&prop['chart.key'].length){RG.DrawKey(this,prop['chart.key'],prop['chart.colors']);}};this.drawLabels=this.DrawLabels=function()
|
32
|
+
{if(prop['chart.labels']&&prop['chart.labels'].length>0){var font=prop['chart.text.font'];var size=prop['chart.text.size'];var color=prop['chart.text.color'];var labels=prop['chart.labels'];var halign=prop['chart.text.halign']=='left'?'left':'center';var bgcolor=prop['chart.text.boxed']?'white':null;if(typeof prop['chart.labels.x']=='number'){var x=prop['chart.labels.x'];}else{var x=halign=='left'?(this.gutterLeft-15):((ca.width-this.gutterLeft-this.gutterRight)/2)+this.gutterLeft;}
|
33
|
+
for(var j=0;j<this.coords.length;++j){co.beginPath();co.strokeStyle='black';co.fillStyle=color;RG.NoShadow(this);var label=labels[j];RG.text2(this,{'font':font,'size':size,'x':x,'y':this.coords[j][1],'text':label,'valign':'center','halign':halign,'bounding':prop['chart.text.boxed'],'boundingFill':bgcolor,'tag':'labels'});if(prop['chart.labels.sticks']){co.font=size+'pt '+font;var labelWidth=co.measureText(label).width;co.beginPath();co.strokeStyle='gray';co.moveTo(x+labelWidth+10,ma.round(this.coords[j][1]));co.lineTo(this.coords[j][0]-10,ma.round(this.coords[j][1]));co.stroke();}}
|
34
|
+
var lastLabel=labels[j];if(lastLabel){RG.text2(this,{'font':font,'size':size,'x':x,'y':this.coords[j-1][5],'text':lastLabel,'valign':'center','halign':halign,'bounding':prop['chart.text.boxed'],'boundingFill':bgcolor,'tag':'labels'});if(prop['chart.labels.sticks']){co.font=size+'pt '+font;var labelWidth=co.measureText(lastLabel).width;co.beginPath();co.strokeStyle='gray';co.moveTo(x+labelWidth+10,Math.round(this.coords[j-1][7]));co.lineTo(this.coords[j-1][6]-10,Math.round(this.coords[j-1][7]));co.stroke();}}}};this.getShape=this.getSegment=function(e)
|
35
|
+
{var coords=this.coords;var mouseCoords=RG.getMouseXY(e);var x=mouseCoords[0];var y=mouseCoords[1];for(i=0,len=coords.length;i<len;++i){var segment=coords[i]
|
36
|
+
co.beginPath();co.moveTo(segment[0],segment[1]);co.lineTo(segment[2],segment[3]);co.lineTo(segment[4],segment[5]);co.lineTo(segment[6],segment[7]);co.lineTo(segment[8],segment[9]);if(co.isPointInPath(x,y)){var tooltip=RGraph.parseTooltipText(prop['chart.tooltips'],i);return{0:this,1:coords,2:i,'object':this,'coords':segment,'index':i,'tooltip':tooltip};}}
|
37
|
+
return null;};this.highlight=this.Highlight=function(shape)
|
38
|
+
{if(prop['chart.tooltips.highlight']){if(typeof prop['chart.highlight.style']==='function'){(prop['chart.highlight.style'])(shape);return;}
|
39
|
+
var coords=shape['coords'];pa2(co,'b m % % l % % l % % l % % c s % f %',coords[0],coords[1],coords[2],coords[3],coords[4],coords[5],coords[6],coords[7],prop['chart.highlight.stroke'],prop['chart.highlight.fill']);}};this.getObjectByXY=function(e)
|
40
|
+
{var mouseXY=RGraph.getMouseXY(e);if(mouseXY[0]>prop['chart.gutter.left']&&mouseXY[0]<(ca.width-prop['chart.gutter.right'])&&mouseXY[1]>prop['chart.gutter.top']&&mouseXY[1]<(ca.height-prop['chart.gutter.bottom'])){return this;}};this.parseColors=function()
|
41
|
+
{if(this.original_colors.length===0){this.original_colors['chart.colors']=RG.array_clone(prop['chart.colors']);this.original_colors['chart.key.colors']=RG.array_clone(prop['chart.key.colors']);this.original_colors['chart.highlight.fill']=RG.array_clone(prop['chart.highlight.fill']);this.original_colors['chart.highlight.stroke']=RG.array_clone(prop['chart.highlight.stroke']);this.original_colors['chart.strokestyle']=RG.array_clone(prop['chart.strokestyle']);}
|
42
|
+
var colors=prop['chart.colors'];for(var i=0;i<colors.length;++i){colors[i]=this.parseSingleColorForHorizontalGradient(colors[i]);}
|
43
|
+
var keyColors=prop['chart.key.colors'];if(keyColors){for(var i=0;i<keyColors.length;++i){keyColors[i]=this.parseSingleColorForHorizontalGradient(keyColors[i]);}}
|
44
|
+
prop['chart.strokestyle']=this.parseSingleColorForVerticalGradient(prop['chart.strokestyle']);prop['chart.highlight.stroke']=this.parseSingleColorForHorizontalGradient(prop['chart.highlight.stroke']);prop['chart.highlight.fill']=this.parseSingleColorForHorizontalGradient(prop['chart.highlight.fill']);};this.reset=function()
|
45
|
+
{};this.parseSingleColorForHorizontalGradient=function(color)
|
46
|
+
{if(!color||typeof(color)!='string'){return color;}
|
47
|
+
if(color.match(/^gradient\((.*)\)$/i)){var parts=RegExp.$1.split(':');var grad=co.createLinearGradient(prop['chart.gutter.left'],0,ca.width-prop['chart.gutter.right'],0);var diff=1/(parts.length-1);grad.addColorStop(0,RGraph.trim(parts[0]));for(var j=1;j<parts.length;++j){grad.addColorStop(j*diff,RG.trim(parts[j]));}}
|
48
|
+
return grad?grad:color;};this.parseSingleColorForVerticalGradient=function(color)
|
49
|
+
{if(!color||typeof(color)!='string'){return color;}
|
50
|
+
if(color.match(/^gradient\((.*)\)$/i)){var parts=RegExp.$1.split(':');var grad=co.createLinearGradient(0,prop['chart.gutter.top'],0,ca.height-prop['chart.gutter.bottom']);var diff=1/(parts.length-1);grad.addColorStop(0,RGraph.trim(parts[0]));for(var j=1;j<parts.length;++j){grad.addColorStop(j*diff,RG.trim(parts[j]));}}
|
51
|
+
return grad?grad:color;};this.interactiveKeyHighlight=function(index)
|
52
|
+
{var coords=this.coords[index];if(coords&&coords.length==8){var pre_linewidth=co.lineWidth;co.lineWidth=2;co.strokeStyle=prop['chart.key.interactive.highlight.chart.stroke'];co.fillStyle=prop['chart.key.interactive.highlight.chart.fill'];co.beginPath();co.moveTo(coords[0],coords[1]);co.lineTo(coords[2],coords[3]);co.lineTo(coords[4],coords[5]);co.lineTo(coords[6],coords[7]);co.closePath();co.fill();co.stroke();co.lineWidth=pre_linewidth;}};this.on=function(type,func)
|
53
|
+
{if(type.substr(0,2)!=='on'){type='on'+type;}
|
54
|
+
if(typeof this[type]!=='function'){this[type]=func;}else{RG.addCustomEventListener(this,type,func);}
|
55
|
+
return this;};this.firstDrawFunc=function()
|
56
|
+
{};RG.att(ca);RG.Register(this);if(parseConfObjectForOptions){RG.parseObjectStyleConfig(this,conf.options);}};
|