rgraph-rails 1.0.7 → 1.0.8

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.
Files changed (61) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +3 -3
  3. data/lib/rgraph-rails/version.rb +1 -1
  4. data/license.txt +4 -16
  5. data/vendor/assets/javascripts/RGraph.bar.js +3734 -241
  6. data/vendor/assets/javascripts/RGraph.bipolar.js +2005 -115
  7. data/vendor/assets/javascripts/RGraph.common.annotate.js +395 -35
  8. data/vendor/assets/javascripts/RGraph.common.context.js +595 -30
  9. data/vendor/assets/javascripts/RGraph.common.core.js +5282 -405
  10. data/vendor/assets/javascripts/RGraph.common.csv.js +276 -19
  11. data/vendor/assets/javascripts/RGraph.common.deprecated.js +450 -35
  12. data/vendor/assets/javascripts/RGraph.common.dynamic.js +1395 -86
  13. data/vendor/assets/javascripts/RGraph.common.effects.js +1545 -90
  14. data/vendor/assets/javascripts/RGraph.common.key.js +753 -54
  15. data/vendor/assets/javascripts/RGraph.common.resizing.js +563 -37
  16. data/vendor/assets/javascripts/RGraph.common.sheets.js +352 -29
  17. data/vendor/assets/javascripts/RGraph.common.tooltips.js +450 -32
  18. data/vendor/assets/javascripts/RGraph.common.zoom.js +219 -14
  19. data/vendor/assets/javascripts/RGraph.drawing.background.js +570 -35
  20. data/vendor/assets/javascripts/RGraph.drawing.circle.js +544 -35
  21. data/vendor/assets/javascripts/RGraph.drawing.image.js +755 -52
  22. data/vendor/assets/javascripts/RGraph.drawing.marker1.js +645 -41
  23. data/vendor/assets/javascripts/RGraph.drawing.marker2.js +633 -37
  24. data/vendor/assets/javascripts/RGraph.drawing.marker3.js +514 -36
  25. data/vendor/assets/javascripts/RGraph.drawing.poly.js +559 -39
  26. data/vendor/assets/javascripts/RGraph.drawing.rect.js +548 -35
  27. data/vendor/assets/javascripts/RGraph.drawing.text.js +664 -36
  28. data/vendor/assets/javascripts/RGraph.drawing.xaxis.js +812 -50
  29. data/vendor/assets/javascripts/RGraph.drawing.yaxis.js +856 -51
  30. data/vendor/assets/javascripts/RGraph.fuel.js +964 -58
  31. data/vendor/assets/javascripts/RGraph.funnel.js +984 -55
  32. data/vendor/assets/javascripts/RGraph.gantt.js +1354 -77
  33. data/vendor/assets/javascripts/RGraph.gauge.js +1421 -87
  34. data/vendor/assets/javascripts/RGraph.hbar.js +2562 -146
  35. data/vendor/assets/javascripts/RGraph.hprogress.js +1401 -80
  36. data/vendor/assets/javascripts/RGraph.line.js +4226 -244
  37. data/vendor/assets/javascripts/RGraph.meter.js +1280 -74
  38. data/vendor/assets/javascripts/RGraph.modaldialog.js +301 -19
  39. data/vendor/assets/javascripts/RGraph.odo.js +1264 -71
  40. data/vendor/assets/javascripts/RGraph.pie.js +2288 -137
  41. data/vendor/assets/javascripts/RGraph.radar.js +1847 -110
  42. data/vendor/assets/javascripts/RGraph.rose.js +1977 -108
  43. data/vendor/assets/javascripts/RGraph.rscatter.js +1432 -80
  44. data/vendor/assets/javascripts/RGraph.scatter.js +3036 -168
  45. data/vendor/assets/javascripts/RGraph.semicircularprogress.js +1120 -60
  46. data/vendor/assets/javascripts/RGraph.svg.bar.js +1067 -0
  47. data/vendor/assets/javascripts/RGraph.svg.common.ajax.js +247 -0
  48. data/vendor/assets/javascripts/RGraph.svg.common.core.js +3363 -0
  49. data/vendor/assets/javascripts/RGraph.svg.common.csv.js +277 -0
  50. data/vendor/assets/javascripts/RGraph.svg.common.fx.js +1304 -0
  51. data/vendor/assets/javascripts/RGraph.svg.common.sheets.js +353 -0
  52. data/vendor/assets/javascripts/RGraph.svg.common.tooltips.js +233 -0
  53. data/vendor/assets/javascripts/RGraph.svg.hbar.js +1141 -0
  54. data/vendor/assets/javascripts/RGraph.svg.line.js +1486 -0
  55. data/vendor/assets/javascripts/RGraph.svg.pie.js +781 -0
  56. data/vendor/assets/javascripts/RGraph.svg.radar.js +1326 -0
  57. data/vendor/assets/javascripts/RGraph.svg.semicircularprogress.js +817 -0
  58. data/vendor/assets/javascripts/RGraph.thermometer.js +1135 -62
  59. data/vendor/assets/javascripts/RGraph.vprogress.js +1470 -83
  60. data/vendor/assets/javascripts/RGraph.waterfall.js +1347 -80
  61. metadata +15 -3
@@ -0,0 +1,781 @@
1
+ // version: 2017-01-02
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 licensed under the Open Source MIT license. That means that it's |
9
+ * | totally free to use! |
10
+ * o--------------------------------------------------------------------------------o
11
+ */
12
+
13
+ RGraph = window.RGraph || {isRGraph: true};
14
+ RGraph.SVG = RGraph.SVG || {};
15
+
16
+ // Module pattern
17
+ (function (win, doc, undefined)
18
+ {
19
+ var RG = RGraph,
20
+ ua = navigator.userAgent,
21
+ ma = Math,
22
+ win = window,
23
+ doc = document;
24
+
25
+
26
+
27
+ RG.SVG.Pie = function (conf)
28
+ {
29
+ this.id = conf.id;
30
+ this.uid = RG.SVG.createUID();
31
+ this.container = document.getElementById(this.id);
32
+ this.svg = RG.SVG.createSVG({container: this.container});
33
+ this.isRGraph = true;
34
+ this.width = Number(this.svg.getAttribute('width'));
35
+ this.height = Number(this.svg.getAttribute('height'));
36
+ this.data = conf.data;
37
+ this.type = 'pie';
38
+ this.angles = [];
39
+ this.colorsParsed = false;
40
+ this.originalColors = {};
41
+ this.gradientCounter = 1;
42
+ this.nodes = [];
43
+ this.shadowNodes = [];
44
+
45
+ // Add this object to the ObjectRegistry
46
+ RG.SVG.OR.add(this);
47
+
48
+ // Set the DIV container to be inline-block
49
+ this.container.style.display = 'inline-block';
50
+
51
+ this.properties =
52
+ {
53
+ centerx: null,
54
+ centery: null,
55
+ radius: null,
56
+
57
+ gutterLeft: 35,
58
+ gutterRight: 35,
59
+ gutterTop: 35,
60
+ gutterBottom: 35,
61
+
62
+ colors: [
63
+ '#f66', '#6f6', '#66f', '#ff6', '#6ff', '#ccc',
64
+ 'pink', 'orange', 'cyan', 'maroon', 'olive', 'teal'
65
+ ],
66
+ strokestyle: 'rgba(0,0,0,0)',
67
+
68
+ margin: 3,
69
+
70
+ textColor: 'black',
71
+ textFont: 'sans-serif',
72
+ textSize: 12,
73
+ textBold: false,
74
+ textItalic: false,
75
+ labels: [],
76
+
77
+ linewidth: 1,
78
+
79
+ tooltips: null,
80
+ tooltipsOverride: null,
81
+ tooltipsEffect: 'fade',
82
+ tooltipsCssClass: 'RGraph_tooltip',
83
+ tooltipsEvent: 'click',
84
+
85
+ highlightStroke: 'rgba(0,0,0,0)',
86
+ highlightFill: 'rgba(255,255,255,0.7)',
87
+ highlightLinewidth: 1,
88
+
89
+ title: '',
90
+ titleSize: 16,
91
+ titleX: null,
92
+ titleY: null,
93
+ titleHalign: 'center',
94
+ titleValign: 'bottom',
95
+ titleColor: 'black',
96
+ titleFont: null,
97
+ titleBold: false,
98
+ titleItalic: false,
99
+
100
+ titleSubtitle: '',
101
+ titleSubtitleSize: 10,
102
+ titleSubtitleX: null,
103
+ titleSubtitleY: null,
104
+ titleSubtitleHalign: 'center',
105
+ titleSubtitleValign: 'top',
106
+ titleSubtitleColor: '#aaa',
107
+ titleSubtitleFont: null,
108
+ titleSubtitleBold: false,
109
+ titleSubtitleItalic: false,
110
+
111
+ shadow: false,
112
+ shadowOffsetx: 2,
113
+ shadowOffsety: 2,
114
+ shadowBlur: 2,
115
+ shadowOpacity: 0.25,
116
+
117
+ exploded: 0,
118
+ roundRobinMultiplier: 1,
119
+
120
+ attribution: true,
121
+ attributionX: null,
122
+ attributionY: null,
123
+ attributionHref: 'http://www.rgraph.net/svg/index.html',
124
+ attributionHalign: 'right',
125
+ attributionValign: 'bottom',
126
+ attributionSize: 8,
127
+ attributionColor: 'gray',
128
+ attributionFont: 'sans-serif',
129
+ attributionItalic: false,
130
+ attributionBold: false
131
+ };
132
+
133
+
134
+
135
+
136
+
137
+ /**
138
+ * "Decorate" the object with the generic effects if the effects library has been included
139
+ */
140
+ if (RG.SVG.FX && typeof RG.SVG.FX.decorate === 'function') {
141
+ RG.SVG.FX.decorate(this);
142
+ }
143
+
144
+
145
+
146
+
147
+ var prop = this.properties;
148
+
149
+
150
+
151
+
152
+ //
153
+ // A setter that the constructor uses (at the end)
154
+ // to set all of the properties
155
+ //
156
+ // @param string name The name of the property to set
157
+ // @param string value The value to set the property to
158
+ //
159
+ this.set = function (name, value)
160
+ {
161
+ if (arguments.length === 1 && typeof name === 'object') {
162
+ for (i in arguments[0]) {
163
+ if (typeof i === 'string') {
164
+ this.set(i, arguments[0][i]);
165
+ }
166
+ }
167
+ } else {
168
+ this.properties[name] = value;
169
+ }
170
+
171
+ return this;
172
+ };
173
+
174
+
175
+
176
+
177
+
178
+
179
+
180
+
181
+ //
182
+ // The draw method draws the Bar chart
183
+ //
184
+ this.draw = function ()
185
+ {
186
+ // Fire the beforedraw event
187
+ RG.SVG.fireCustomEvent(this, 'onbeforedraw');
188
+
189
+
190
+
191
+
192
+ // Create the defs tag if necessary
193
+ RG.SVG.createDefs(this);
194
+
195
+
196
+
197
+
198
+ this.graphWidth = this.width - prop.gutterLeft - prop.gutterRight;
199
+ this.graphHeight = this.height - prop.gutterTop - prop.gutterBottom;
200
+
201
+
202
+
203
+ // Work out the center point
204
+ this.centerx = (this.graphWidth / 2) + prop.gutterLeft;
205
+ this.centery = (this.graphHeight / 2) + prop.gutterTop;
206
+ this.radius = ma.min(this.graphWidth, this.graphHeight) / 2;
207
+
208
+
209
+
210
+ // Allow the user to override the calculated centerx/y/radius
211
+ this.centerx = typeof prop.centerx === 'number' ? prop.centerx : this.centerx;
212
+ this.centery = typeof prop.centery === 'number' ? prop.centery : this.centery;
213
+ this.radius = typeof prop.radius === 'number' ? prop.radius : this.radius;
214
+
215
+ //
216
+ // Allow the centerx/centery/radius to be a plus/minus
217
+ //
218
+ if (typeof prop.radius === 'string' && prop.radius.match(/^\+|-\d+$/) ) this.radius += parseFloat(prop.radius);
219
+ if (typeof prop.centerx === 'string' && prop.centerx.match(/^\+|-\d+$/) ) this.centery += parseFloat(prop.centerx);
220
+ if (typeof prop.centery === 'string' && prop.centery.match(/^\+|-\d+$/) ) this.centerx += parseFloat(prop.centery);
221
+
222
+
223
+ /**
224
+ * Parse the colors. This allows for simple gradient syntax
225
+ *
226
+ * ** must be after the cx/cy/r has been calcuated **
227
+ */
228
+ if (!this.colorsParsed) {
229
+ this.parseColors();
230
+
231
+ // Don't want to do this again
232
+ this.colorsParsed = true;
233
+ }
234
+
235
+
236
+ // Go through the data and work out the maximum value
237
+ this.max = RG.SVG.arrayMax(this.data);
238
+ this.total = RG.SVG.arraySum(this.data);
239
+
240
+ // Set the explosion to be an array if it's a number
241
+ if (typeof prop.exploded === 'number' && prop.exploded > 0) {
242
+ var val = prop.exploded;
243
+
244
+ prop.exploded = [];
245
+
246
+ for (var i=0; i<this.data.length; ++i) {
247
+ prop.exploded[i] = val;
248
+ }
249
+ }
250
+
251
+
252
+
253
+ // Draw the segments
254
+ this.drawSegments({shadow: true});
255
+
256
+
257
+
258
+ // Draw the title and subtitle
259
+ RG.SVG.drawTitle(this);
260
+
261
+
262
+
263
+ // Draw the labels
264
+ this.drawLabels();
265
+
266
+
267
+ // Add the attribution link. If you're adding this elsewhere on your page/site
268
+ // and you don't want it displayed then there are options available to not
269
+ // show it.
270
+ RG.SVG.attribution(this);
271
+
272
+
273
+ // Add the event listener that clears the highlight if
274
+ // there is any. Must be MOUSEDOWN (ie before the click event)
275
+ var obj = this;
276
+ document.body.addEventListener('mousedown', function (e)
277
+ {
278
+ RG.SVG.removeHighlight(obj);
279
+ }, false);
280
+
281
+
282
+
283
+ // Fire the draw event
284
+ RG.SVG.fireCustomEvent(this, 'ondraw');
285
+
286
+
287
+
288
+ return this;
289
+ };
290
+
291
+
292
+
293
+
294
+
295
+
296
+
297
+
298
+ //
299
+ // Draws the segments
300
+ //
301
+ // @param bool Whether or not this is a redraw. If this is a redraw
302
+ // shadows are omitted
303
+ //
304
+ this.drawSegments = function (opt)
305
+ {
306
+ var start = 0,
307
+ end = 0,
308
+ angle = 0,
309
+ sum = RG.SVG.arraySum(this.data),
310
+ segment = 0;
311
+
312
+
313
+
314
+
315
+ // Work out the start and end angles for the data
316
+ for (var i=0,len=this.data.length; i<len; ++i) {
317
+
318
+ var value = this.data[i] * prop.roundRobinMultiplier;
319
+
320
+ start = angle;
321
+ segment = ((value / sum) * RG.SVG.TRIG.TWOPI);
322
+ end = start + segment;
323
+
324
+ var explosion = RG.SVG.TRIG.getRadiusEndPoint({
325
+ angle: start + (segment / 2),
326
+ r: prop.exploded[i]
327
+ });
328
+
329
+ var explosionX = explosion[1],
330
+ explosionY = explosion[0];
331
+
332
+
333
+ this.angles[i] = {
334
+ start: start,
335
+ end: end,
336
+ angle: end - start,
337
+ halfway: ((end - start) / 2) + start,
338
+ cx: this.centerx + (parseFloat(explosionX) || 0),
339
+ cy: this.centery - (parseFloat(explosionY) || 0),
340
+ radius: this.radius
341
+ };
342
+
343
+ // Increase the angle at which we start drawing the next segment at
344
+ angle += (end - start);
345
+ }
346
+
347
+
348
+
349
+ if (opt.shadow) {
350
+ RG.SVG.setShadow({
351
+ object: this,
352
+ offsetx: prop.shadowOffsetx,
353
+ offsety: prop.shadowOffsety,
354
+ blur: prop.shadowBlur,
355
+ opacity: prop.shadowOpacity,
356
+ id: 'dropShadow'
357
+ });
358
+ }
359
+
360
+
361
+ //
362
+ // This loop goes thru the angles that were
363
+ // generated above and adds them to the
364
+ // scene
365
+ //
366
+ for (var i=0; i<this.angles.length; ++i) {
367
+
368
+ var path = RG.SVG.TRIG.getArcPath({
369
+ cx: this.angles[i].cx,
370
+ cy: this.angles[i].cy,
371
+ r: this.radius,
372
+ start: this.angles[i].start,
373
+ end: this.angles[i].end
374
+ });
375
+
376
+
377
+ var arc = RG.SVG.create({
378
+ svg: this.svg,
379
+ type: 'path',
380
+ attr: {
381
+ d: path + " L {1} {2} Z".format(
382
+ this.angles[i].cx,
383
+ this.angles[i].cy
384
+ ),
385
+ fill: prop.colors[i],
386
+ stroke: prop.strokestyle,
387
+ 'stroke-width': prop.linewidth,
388
+ 'data-tooltip': (!RG.SVG.isNull(prop.tooltips) && prop.tooltips.length) ? prop.tooltips[i] : '',
389
+ 'data-index': i,
390
+ 'data-value': value,
391
+ 'data-start-angle': this.angles[i].start,
392
+ 'data-end-angle': this.angles[i].end,
393
+ 'data-radius': this.radius,
394
+ filter: (prop.shadow && opt.shadow) ? 'url(#dropShadow)' : ''
395
+ }
396
+ });
397
+
398
+ // Store a reference to the node
399
+ if (prop.shadow && opt.shadow) {
400
+ this.shadowNodes[i] = arc;
401
+ } else {
402
+ this.nodes[i] = arc;
403
+ }
404
+
405
+ if (prop.tooltips && prop.tooltips[i] && (!opt.shadow || !prop.shadow)) {
406
+
407
+ // Make the tooltipsEvent default to click
408
+ if (prop.tooltipsEvent !== 'mousemove') {
409
+ prop.tooltipsEvent = 'click';
410
+ }
411
+
412
+ (function (index, obj)
413
+ {
414
+ arc.addEventListener(prop.tooltipsEvent, function (e)
415
+ {
416
+ // Show the tooltip
417
+ RG.SVG.tooltip({
418
+ object: obj,
419
+ index: index,
420
+ sequentialIndex: index,
421
+ text: prop.tooltips[index],
422
+ event: e
423
+ });
424
+
425
+ // Highlight the rect that has been clicked on
426
+ obj.highlight(e.target);
427
+
428
+ var highlight = RG.SVG.REG.get('highlight');
429
+
430
+ if (prop.tooltipsEvent === 'mousemove') {
431
+ highlight.style.cursor = 'pointer';
432
+ }
433
+
434
+ }, false);
435
+
436
+ // Install the event listener that changes the
437
+ // cursor if necessary
438
+ if (prop.tooltipsEvent === 'click') {
439
+ arc.addEventListener('mousemove', function (e)
440
+ {
441
+ e.target.style.cursor = 'pointer';
442
+ }, false);
443
+ }
444
+
445
+ }(i, this));
446
+ }
447
+ }
448
+
449
+ //
450
+ // Redraw the segments if necessary so that they're on
451
+ // top of any shadow
452
+ //
453
+ if (prop.shadow && opt.shadow) {
454
+ this.redrawSegments();
455
+ }
456
+ };
457
+
458
+
459
+
460
+
461
+
462
+
463
+
464
+
465
+ //
466
+ // Redraw the Bars o that the bars appear above any shadow
467
+ //
468
+ this.redrawSegments = function ()
469
+ {
470
+ this.drawSegments({shadow: false});
471
+ };
472
+
473
+
474
+
475
+
476
+
477
+
478
+
479
+
480
+ //
481
+ // Draw the labels
482
+ //
483
+ this.drawLabels = function ()
484
+ {
485
+ var angles = this.angles,
486
+ prop = this.properties,
487
+ labels = prop.labels;
488
+
489
+ for (var i=0; i<angles.length; ++i) {
490
+
491
+ var endpoint = RG.SVG.TRIG.getRadiusEndPoint({
492
+ angle: angles[i].halfway - RG.SVG.TRIG.HALFPI,
493
+ r: angles[i].radius + 15
494
+ });
495
+
496
+ var x = endpoint[0] + angles[i].cx,
497
+ y = endpoint[1] + angles[i].cy,
498
+ valign,
499
+ halign;
500
+
501
+ // Figure out the valign and halign based on the quadrant
502
+ // the the center of the sgement is in.
503
+ if (angles[i].halfway > 0 && angles[i].halfway < RG.SVG.TRIG.HALFPI) {
504
+ halign = 'left';
505
+ valign = 'bottom';
506
+ } else if (angles[i].halfway > RG.SVG.TRIG.HALFPI && angles[i].halfway < RG.SVG.TRIG.PI) {
507
+ halign = 'left';
508
+ valign = 'top';
509
+ } else if (angles[i].halfway > RG.SVG.TRIG.PI && angles[i].halfway < (RG.SVG.TRIG.HALFPI + RG.SVG.TRIG.PI)) {
510
+ halign = 'right';
511
+ valign = 'top';
512
+ } else if (angles[i].halfway > (RG.SVG.TRIG.HALFPI + RG.SVG.TRIG.PI) && angles[i].halfway < RG.SVG.TRIG.TWOPI) {
513
+ halign = 'right';
514
+ valign = 'top';
515
+ }
516
+
517
+ RG.SVG.text({
518
+ object: this,
519
+ text: typeof labels[i] === 'string' ? labels[i] : '',
520
+ font: prop.textFont,
521
+ size: prop.textSize,
522
+ x: x,
523
+ y: y,
524
+ valign: valign,
525
+ halign: halign,
526
+ bold: prop.textBold,
527
+ italic: prop.textItalic,
528
+ color: prop.textColor
529
+ });
530
+ }
531
+ };
532
+
533
+
534
+
535
+
536
+
537
+
538
+
539
+
540
+ /**
541
+ * This function can be used to highlight a segment on the chart
542
+ *
543
+ * @param object segment The segment to highlight
544
+ */
545
+ this.highlight = function (segment)
546
+ {
547
+ var highlight = RG.SVG.create({
548
+ svg: this.svg,
549
+ type: 'path',
550
+ attr: {
551
+ d: segment.getAttribute('d'),
552
+ fill: prop.highlightFill,
553
+ stroke: prop.highlightStroke,
554
+ 'stroke-width': prop.highlightLinewidth
555
+ }
556
+ });
557
+
558
+ if (prop.tooltipsEvent === 'mousemove') {
559
+ highlight.addEventListener('mouseout', function (e)
560
+ {
561
+ highlight.parentNode.removeChild(highlight);
562
+ RG.SVG.hideTooltip();
563
+
564
+ RG.SVG.REG.set('highlight', null);
565
+ }, false);
566
+ }
567
+
568
+
569
+ // Store the highlight rect in the registry so
570
+ // it can be cleared later
571
+ RG.SVG.REG.set('highlight', highlight);
572
+ };
573
+
574
+
575
+
576
+
577
+
578
+
579
+
580
+
581
+ /**
582
+ * This allows for easy specification of gradients
583
+ */
584
+ this.parseColors = function ()
585
+ {
586
+ // Save the original colors so that they can be restored when the canvas is reset
587
+ if (!Object.keys(this.originalColors).length) {
588
+ this.originalColors = {
589
+ colors: RG.SVG.arrayClone(prop.colors),
590
+ highlightFill: RG.SVG.arrayClone(prop.highlightFill)
591
+ }
592
+ }
593
+
594
+
595
+ // colors
596
+ var colors = prop.colors;
597
+
598
+ if (colors) {
599
+ for (var i=0; i<colors.length; ++i) {
600
+ colors[i] = RG.SVG.parseColorRadial({
601
+ object: this,
602
+ color: colors[i]
603
+ });
604
+ }
605
+ }
606
+
607
+ // Highlight fill
608
+ prop.highlightFill = RG.SVG.parseColorRadial({
609
+ object: this,
610
+ color: prop.highlightFill
611
+ });
612
+ };
613
+
614
+
615
+
616
+
617
+
618
+
619
+
620
+
621
+ //
622
+ // A roundRobin effect for the Pie chart
623
+ //
624
+ // @param object Options for the effect
625
+ // @param function An optional callback function to call when
626
+ // the effect is complete
627
+ //
628
+ this.roundRobin = function ()
629
+ {
630
+ var obj = this,
631
+ opt = arguments[0] || {},
632
+ data = RG.SVG.arrayClone(this.data),
633
+ prop = this.properties,
634
+ frame = 1,
635
+ frames = opt.frames || 30,
636
+ callback = typeof opt.callback === 'function' ? opt.callback : function () {},
637
+ dataSum = RG.SVG.arraySum(this.data),
638
+ textColor = prop.textColor;
639
+
640
+ // Set the text color to transparent
641
+ this.properties.textColor = 'rgba(0,0,0,0)';
642
+
643
+
644
+ // Draw the chart first
645
+ obj.draw();
646
+
647
+ // Now get the resulting angles
648
+ angles = RG.SVG.arrayClone(obj.angles);
649
+
650
+
651
+ function iterator ()
652
+ {
653
+ prop.roundRobinMultiplier = 1 / frames * frame++;
654
+
655
+ for (var i=0; i<obj.angles.length; ++i) {
656
+
657
+ var value = obj.data[i];
658
+
659
+
660
+
661
+ // NB This was an absolute git to work out for some reason.
662
+
663
+
664
+
665
+ obj.angles[i].start = angles[i].start * prop.roundRobinMultiplier;
666
+ obj.angles[i].end = angles[i].end * prop.roundRobinMultiplier;
667
+
668
+ //var segment = (((value * prop.roundRobinMultiplier) / dataSum) * RG.SVG.TRIG.TWOPI);
669
+ var segment = ((obj.angles[i].end - obj.angles[i].start) / 2);
670
+ var explodedX = ma.cos(obj.angles[i].start + segment - RG.SVG.TRIG.HALFPI) * (prop.exploded[i] || 0);
671
+ var explodedY = ma.sin(obj.angles[i].start + segment - RG.SVG.TRIG.HALFPI) * (prop.exploded[i] || 0);
672
+
673
+
674
+
675
+ var path = RG.SVG.TRIG.getArcPath({
676
+ cx: obj.centerx + explodedX,
677
+ cy: obj.centery + explodedY,
678
+ r: obj.radius,// * prop.roundRobinMultiplier,
679
+ start: obj.angles[i].start,
680
+ end: obj.angles[i].end
681
+ });
682
+
683
+ path = path + " L {1} {2} Z".format(
684
+ obj.centerx + explodedX,
685
+ obj.centery + explodedY
686
+ );
687
+
688
+ if (obj.shadowNodes && obj.shadowNodes[i]) {
689
+ obj.shadowNodes[i].setAttribute('d', path);
690
+ }
691
+ obj.nodes[i].setAttribute('d', path);
692
+ }
693
+
694
+
695
+ if (frame <= frames) {
696
+ RG.SVG.FX.update(iterator);
697
+ } else {
698
+ prop.textColor = textColor;
699
+
700
+ RG.SVG.redraw(obj.svg);
701
+
702
+ callback(obj);
703
+ }
704
+ }
705
+
706
+ iterator();
707
+
708
+ return this;
709
+ };
710
+
711
+
712
+
713
+
714
+
715
+
716
+
717
+
718
+ /**
719
+ * Using a function to add events makes it easier to facilitate method
720
+ * chaining
721
+ *
722
+ * @param string type The type of even to add
723
+ * @param function func
724
+ */
725
+ this.on = function (type, func)
726
+ {
727
+ if (type.substr(0,2) !== 'on') {
728
+ type = 'on' + type;
729
+ }
730
+
731
+ RG.SVG.addCustomEventListener(this, type, func);
732
+
733
+ return this;
734
+ };
735
+
736
+
737
+
738
+
739
+
740
+
741
+
742
+
743
+ //
744
+ // Used in chaining. Runs a function there and then - not waiting for
745
+ // the events to fire (eg the onbeforedraw event)
746
+ //
747
+ // @param function func The function to execute
748
+ //
749
+ this.exec = function (func)
750
+ {
751
+ func(this);
752
+
753
+ return this;
754
+ };
755
+
756
+
757
+
758
+
759
+
760
+
761
+
762
+
763
+ //
764
+ // Set the options that the user has provided
765
+ //
766
+ for (i in conf.options) {
767
+ if (typeof i === 'string') {
768
+ this.set(i, conf.options[i]);
769
+ }
770
+ }
771
+ };
772
+
773
+
774
+
775
+ return this;
776
+
777
+
778
+
779
+
780
+ // End module pattern
781
+ })(window, document);