2 * o------------------------------------------------------------------------------o
3 * | This file is part of the RGraph package - you can learn more at: |
5 * | http://www.rgraph.net |
7 * | This package is licensed under the RGraph license. For all kinds of business |
8 * | purposes there is a small one-time licensing fee to pay and for non |
9 * | commercial purposes it is free to use. You can read the full license here: |
11 * | http://www.rgraph.net/LICENSE.txt |
12 * o------------------------------------------------------------------------------o
15 if (typeof(RGraph) == 'undefined') RGraph = {isRGraph:true,type:'common'};
19 * The function which controls the annotate feature
21 * @param object obj The graph object
23 RGraph.Annotate = function (obj)
26 * This installs some event handlers
28 if (obj.Get('chart.annotatable')) {
30 var canvas = obj.canvas;
31 var context = obj.context;
34 * Capture the mouse events so we can set whther the mouse is down or not
36 canvas.onmousedown = function (e)
40 e.target.__object__.Set('chart.mousedown', true);
43 var obj = e.target.__object__;
44 var context = obj.canvas.getContext('2d');
46 // Don't want any "joining" lines or colour "bleeding"
50 var coords = RGraph.getMouseXY(e);
54 // Clear the annotation recording
55 RGraph.Registry.Set('annotate.actions', [obj.Get('chart.annotate.color')]);
57 context.strokeStyle = obj.Get('chart.annotate.color');
62 context.lineWidth = 1;
64 RGraph.Registry.Set('started.annotating', false);
67 * Fire the onannotatestart event
69 RGraph.FireCustomEvent(obj, 'onannotatestart');
76 * This cancels annotating for ALL canvases
78 window.onmouseup = function (e)
80 var tags = document.getElementsByTagName('canvas');
82 for (var i=0; i<tags.length; ++i) {
83 if (tags[i].__object__) {
84 tags[i].__object__.Set('chart.mousedown', false);
88 // Store the annotations in browser storage if it's available
89 if (RGraph.Registry.Get('annotate.actions') && RGraph.Registry.Get('annotate.actions').length > 0 && window.localStorage) {
91 var id = '__rgraph_annotations_' + e.target.id + '__';
92 var annotations = window.localStorage[id] ? window.localStorage[id] + '|' : '';
93 annotations += RGraph.Registry.Get('annotate.actions');
95 // Store the annotations information in HTML5 browser storage here
96 window.localStorage[id] = annotations;
99 // Clear the recorded annotations
100 RGraph.Registry.Set('annotate.actions', []);
103 * Fire the annotate event
105 RGraph.FireCustomEvent(e.target.__object__, 'onannotateend');
108 canvas.onmouseup = function (e)
110 //window.onmouseup(e);
113 //canvas.onmouseout = window.onmouseup;
116 * The canvas onmousemove function
118 canvas.onmousemove = function (e)
120 var e = RGraph.FixEventObject(e);
121 var obj = e.target.__object__;
122 var coords = RGraph.getMouseXY(e);
125 var gutter = obj.Get('chart.gutter');
126 var width = canvas.width;
127 var height = canvas.height;
129 obj.context.lineWidth = 1;
131 // Don't allow annotating in the gutter
133 // CHANGED 20TH DECEMBER 2010 TO ALLOW ANNOTATING IN THE GUTTER
136 canvas.style.cursor = 'crosshair';
138 if (obj.Get('chart.mousedown')) {
140 // Special case for HBars and Gantts with their extra wide left gutter
141 if ( (obj.type != 'hbar' && obj.type != 'gantt') || x > (3 * gutter)) {
144 * This is here to stop annotating in the gutter
146 if (RGraph.Registry.Get('started.annotating') == false) {
147 context.moveTo(x, y);
148 RGraph.Registry.Set('started.annotating', true)
151 context.lineTo(x, y);
153 RGraph.Registry.Set('annotate.actions', RGraph.Registry.Get('annotate.actions') + '|' + x + ',' + y);
158 * Fire the annotate event
160 RGraph.FireCustomEvent(obj, 'onannotate');
165 canvas.style.cursor = 'default';
169 RGraph.ReplayAnnotations(obj);
175 * Shows the mini palette used for annotations
177 * @param object e The event object
179 RGraph.Showpalette = function (e)
181 var isSafari = navigator.userAgent.indexOf('Safari') ? true : false;
183 e = RGraph.FixEventObject(e);
185 var canvas = e.target.parentNode.__canvas__;
186 var context = canvas.getContext('2d');
187 var obj = canvas.__object__;
188 var div = document.createElement('DIV');
189 var coords = RGraph.getMouseXY(e);
191 div.__object__ = obj; // The graph object
192 div.className = 'RGraph_palette';
193 div.style.position = 'absolute';
194 div.style.backgroundColor = 'white';
195 div.style.border = '1px solid black';
198 div.style.padding = '3px';
199 div.style.paddingBottom = 0;
200 div.style.paddingRight = 0;
201 div.style.opacity = 0;
202 div.style.boxShadow = 'rgba(96,96,96,0.5) 3px 3px 3px';
203 div.style.WebkitBoxShadow = 'rgba(96,96,96,0.5) 3px 3px 3px';
204 div.style.MozBoxShadow = 'rgba(96,96,96,0.5) 3px 3px 3px';
205 div.style.filter = 'progid:DXImageTransform.Microsoft.Shadow(color=#666666,direction=135)';
207 var common_css = 'padding: 1px; display: inline; display: inline-block; width: 15px; height: 15px; margin-right: 3px; cursor: pointer;' + (isSafari ? 'margin-bottom: 3px' : '');
208 var common_mouseover = ' onmouseover="this.style.border = \'1px black solid\'; this.style.padding = 0"';
209 var common_mouseout = ' onmouseout="this.style.border = 0; this.style.padding = \'1px\'" ';
213 var colors = ['red', 'blue', 'green', 'black', 'yellow', 'magenta', 'pink', 'cyan', 'purple', '#ddf', 'gray', '#36905c'];
215 for (i=0; i<colors.length; ++i) {
216 str = str + '<span ' + common_mouseover + common_mouseout + ' style="background-color: ' + colors[i] + '; ' + common_css + '" onclick="this.parentNode.__object__.Set(\'chart.annotate.color\', this.style.backgroundColor); this.parentNode.style.display = \'none\'"> </span>';
218 // This makes the colours go across two levels
225 document.body.appendChild(div);
228 * Now the div has been added to the document, move it up and left and set the width and height
230 div.style.width = (div.offsetWidth - (RGraph.isIE9up() ? 12 : 5)) + 'px';
231 div.style.height = (div.offsetHeight - (RGraph.isIE9up() ? 13 : 5)) + 'px';
232 div.style.left = Math.max(0, e.pageX - div.offsetWidth - 2) + 'px';
233 div.style.top = (e.pageY - div.offsetHeight - 2) + 'px';
236 * Store the palette div in the registry
238 RGraph.Registry.Set('palette', div);
240 setTimeout("RGraph.Registry.Get('palette').style.opacity = 0.2", 50);
241 setTimeout("RGraph.Registry.Get('palette').style.opacity = 0.4", 100);
242 setTimeout("RGraph.Registry.Get('palette').style.opacity = 0.6", 150);
243 setTimeout("RGraph.Registry.Get('palette').style.opacity = 0.8", 200);
244 setTimeout("RGraph.Registry.Get('palette').style.opacity = 1", 250);
246 RGraph.HideContext();
248 window.onclick = function ()
250 RGraph.HidePalette();
253 // Should this be here? Yes. This function is being used as an event handler.
260 * Clears any annotation data from global storage
262 * @param string id The ID of the canvas
264 RGraph.ClearAnnotations = function (id)
266 if (window.localStorage && window.localStorage['__rgraph_annotations_' + id + '__'] && window.localStorage['__rgraph_annotations_' + id + '__'].length) {
267 window.localStorage['__rgraph_annotations_' + id + '__'] = [];
273 * Replays stored annotations
275 * @param object obj The graph object
277 RGraph.ReplayAnnotations = function (obj)
280 if (!window.localStorage) {
284 var context = obj.context;
285 var annotations = window.localStorage['__rgraph_annotations_' + obj.id + '__'];
286 var i, len, move, coords;
289 context.lineWidth = 2;
291 if (annotations && annotations.length) {
292 annotations = annotations.split('|');
297 for (i=0, len=annotations.length; i<len; ++i) {
298 if (!annotations[i].match(/^[0-9]+,[0-9]+$/)) {
301 context.strokeStyle = annotations[i];
306 coords = annotations[i].split(',');
309 context.moveTo(coords[0], coords[1]);
312 context.lineTo(coords[0], coords[1]);