source: trunk/FACT++/www/viewer/index.js@ 17719

Last change on this file since 17719 was 17719, checked in by tbretz, 11 years ago
Fixed the pixel click issue on firefox... and hopefully other browsers as well.
File size: 30.7 KB
Line 
1'use strict';
2
3var editor1;
4var editor2;
5var plot;
6
7function debug(txt)
8{
9 var dbg = document.getElementById("debug");
10 dbg.appendChild(document.createTextNode(txt));
11 dbg.appendChild(document.createElement("br"));
12}
13
14function setupAccordion(accordion, container, inactive)
15{
16 function onAccordion(event, ui)
17 {
18 if (ui.oldHeader.length==0)
19 $(container).slideDown(400);
20 else
21 $(container).slideUp(400);
22 }
23
24 var config = { collapsible: true };
25
26 if (inactive)
27 {
28 config.active = false;
29 $(container).hide();
30 }
31
32 var acc = $(accordion);
33
34 acc.accordion(config);
35 acc.on("accordionbeforeactivate", onAccordion);
36}
37
38function onResize(event, ui)
39{
40 if (!ui.size)
41 return;
42
43 $(event.target.id).css({marginRight:'2px'});
44
45 var editor = event.target.id=="textcontainer1" ? editor1 : editor2;
46
47 editor.setSize("100%", ui.size.height);
48 editor.refresh();
49}
50
51function onResizeCenter(event, ui)
52{
53 var w = document.getElementById("cameracontainer").clientWidth/4;
54
55 var offy = 0;
56 var offx = 5;
57
58 var cont = document.getElementById("center").childNodes[0];
59
60 var nn;
61 if (cont)
62 {
63 nn = parseInt(cont.id[cont.id.length-1]);
64
65 document.getElementById("camera"+nn).height=parseInt(w*2);
66 document.getElementById("camera"+nn).width=parseInt(w*2);
67 }
68
69 if (nn!=1)
70 {
71 document.getElementById("camera1").height=parseInt(w)-offy;
72 document.getElementById("camera1").width=parseInt(w)-offx;
73 }
74
75 if (nn!=2)
76 {
77 document.getElementById("camera2").height=parseInt(w)-offy;
78 document.getElementById("camera2").width=parseInt(w)-offx;
79 }
80
81 if (nn!=3)
82 {
83 document.getElementById("camera3").height=parseInt(w)-offy;
84 document.getElementById("camera3").width=parseInt(w)-offx;
85 }
86
87 if (nn!=4)
88 {
89 document.getElementById("camera4").height=parseInt(w)-offy;
90 document.getElementById("camera4").width=parseInt(w)-offx;
91 }
92
93 document.getElementById("center").width=parseInt(w*2);
94
95 document.getElementById("cont1").width=parseInt(w);
96 document.getElementById("cont2").width=parseInt(w);
97 document.getElementById("cont3").width=parseInt(w);
98 document.getElementById("cont4").width=parseInt(w);
99
100 document.getElementById("cont1").height=parseInt(w);
101 document.getElementById("cont2").height=parseInt(w);
102 document.getElementById("cont3").height=parseInt(w);
103 document.getElementById("cont4").height=parseInt(w);
104
105 drawFullCam("camera1");
106 drawFullCam("camera2");
107 drawFullCam("camera3");
108 drawFullCam("camera4");
109}
110
111function createEditor(textarea)
112{
113 var editor;
114
115 var config =
116 {
117 //value: "function myScript(){return 100;}\n",
118 mode: { name: "text/typescript", globalVars: true },
119 lineNumbers: true,
120 styleActiveLine: true,
121 matchBrackets: true,
122 indentUnit: 4,
123 foldGutter: true,
124 gutters: ["CodeMirror-linenumbers", "CodeMirror-foldgutter"],
125 extraKeys: {
126 //"Ctrl-D": "duplicateLine",
127 //"Alt--": "goToBracket",
128 //"Ctrl-H": "findPrev",
129 "Ctrl-Down": "autocomplete",
130 "Tab": "indentAuto",
131 "Ctrl-Y": "deleteLine",
132 "Ctrl-.": function(cm) {
133 cm.foldCode(cm.getCursor());
134 },
135 "F11": function(cm) {
136 editor.setOption("fullScreen", !editor.getOption("fullScreen"));
137 },
138 "Ctrl-R": function(cm) {
139 editor.execCommand("replace");
140 },
141 "Esc": function(cm) {
142 if (editor.getOption("fullScreen")) editor.setOption("fullScreen", false);
143 },
144 "Enter": function(cm) {
145 editor.execCommand("indentAuto");
146 editor.execCommand("newlineAndIndent");
147 },
148 }
149
150 };
151
152 editor = CodeMirror.fromTextArea(document.getElementById(textarea), config);
153 editor.setOption("theme", "blackboard");
154
155 return editor;
156}
157
158function colorizeHTML(textarea)
159{
160 var config =
161 {
162 //value: "function myScript(){return 100;}\n",
163 mode: { name: "text/typescript", globalVars: true },
164 readOnly: true,
165 };
166
167 CodeMirror.fromTextArea(document.getElementById(textarea), config);
168}
169
170function disableControls(disabled)
171{
172 $('#event').prop('disabled', disabled);
173 $('#pixel').prop('disabled', disabled);
174 $('#cbpx').prop('disabled', disabled);
175 $('#cbpx-c').prop('disabled', disabled);
176 $('#cbpx-b').prop('disabled', disabled);
177 $('#cbpx-p').prop('disabled', disabled);
178 $('#cbpx-x').prop('disabled', disabled);
179 $('#file').prop('disabled', disabled);
180}
181
182function onReady()
183{
184 //$('input,select').keypress(function(event) { return event.keyCode != 13; });
185
186 //colorizeHTML("code0");
187 //colorizeHTML("code1");
188
189 $("#accordion").accordion({collapsible:true,active:false,heightStyle:'content'});
190 $("#accordion").find('h3').filter(':contains(Runtime)').hide();
191 if (location.href.search('debug')==-1)
192 $("#accordion").find('h3').filter(':contains(Debug)').hide();
193
194 $("#textcontainer1").resizable({handles:"s",autoHide:true,});
195 $("#textcontainer1").on("resize", onResize);
196
197 $("#textcontainer2").resizable({handles:"s",autoHide:true,});
198 $("#textcontainer2").on("resize", onResize);
199
200 $("#cameracontainer").on("resize", onResizeCenter);
201 onResizeCenter();
202
203 $("#cont1").click(onClickNew);
204 $("#cont2").click(onClickNew);
205 $("#cont3").click(onClickNew);
206 $("#cont4").click(onClickNew);
207
208 $("#camera1").click(onClick);
209 $("#camera2").click(onClick);
210 $("#camera3").click(onClick);
211 $("#camera4").click(onClick);
212
213 editor1 = createEditor("editor1");
214 editor2 = createEditor("editor2");
215
216 setupAccordion('#accordion5', '#editorcontainer1', true);
217 setupAccordion('#accordion1', '#editorcontainer2');
218
219 $('#accordion5').on("accordionactivate", function() { $('#editorcontainer1fake').hide(); editor1.refresh(); });
220 $('#accordion1').on("accordionactivate", function() { $('#editorcontainer2fake').hide(); editor2.refresh(); });
221
222 setupAccordion('#accordion2', '#cameracontainer');
223 setupAccordion('#accordion3', '#waveformcontainer');
224 setupAccordion('#accordion4', '#helpcontainer', true);
225
226 $("#selectfile1").on('change', onFile);
227 $("#selectfile2").on('change', onFile);
228
229 $(document).ajaxStart(function() { disableControls(true) }).ajaxStop(function() { disableControls(false); });
230
231
232 $.ajax({
233 type: "POST",
234 cache: false,
235 url: "index.php",
236 success: onFilelistReceived,
237 error: function(xhr) { if (xhr.status==0) alert("ERROR[0] - Request failed!"); else alert("ERROR[0] - "+xhr.statusText+" ["+xhr.status+"]"); }
238 });
239}
240
241function onFileSelect(event, ui)
242{
243 onSubmit(ui.item.value);
244}
245
246function onFilelistReceived(result)
247{
248 var dbg = document.getElementById("debug");
249
250 var pre = document.createElement("pre");
251 pre.appendChild(document.createTextNode(rc));
252 dbg.appendChild(pre);
253
254 var rc;
255 try
256 {
257 rc = JSON.parse(result);
258 }
259 catch (e)
260 {
261 alert("ERROR[0] - Decoding answer:\n"+e);
262 return;
263 }
264
265 $("#file").autocomplete({source: rc, select: onFileSelect} );
266 document.getElementById("file").value = "2014/04/17-181";
267
268 onSubmit("2014/04/17-181");
269}
270
271function setZoom(xfrom, xto, yfrom, yto)
272{
273 var xaxis = plot.getXAxes()[0];
274 var yaxis = plot.getYAxes()[0];
275
276 if (xfrom!==undefined)
277 xaxis.options.min = xfrom;
278 if (xto!==undefined)
279 xaxis.options.max = xto;
280
281 if (yfrom!==undefined)
282 yaxis.options.min = yfrom;
283 if (yto!==undefined)
284 yaxis.options.max = yto;
285
286 plot.setupGrid();
287 plot.draw();
288 plot.clearSelection();
289}
290
291function processCameraData(id, data)
292{
293 var canv = document.getElementById(id);
294
295 canv.dataAbs = [ ];
296 for (var i=0; i<1440; i++)
297 if (data[i]!==undefined && data[i]!==null)
298 canv.dataAbs[i] = data[i];
299
300 canv.min = Math.min.apply(Math, canv.dataAbs.filter(function(e){return !isNaN(e)}));
301 canv.max = Math.max.apply(Math, canv.dataAbs.filter(function(e){return !isNaN(e)}));
302
303 canv.dataRel = [ ];
304 for (var i=0; i<1440; i++)
305 if (data[i]!==undefined && data[i]!==null)
306 canv.dataRel[i] = (data[i]-canv.min)/canv.max;
307
308 var n = id[id.length-1];
309
310 if (document.getElementById("cameraminon"+n).checked)
311 document.getElementById("cameramin"+n).value = canv.min;
312 if (document.getElementById("cameramaxon"+n).checked)
313 document.getElementById("cameramax"+n).value = canv.max;
314
315 onCameraMinMax(n);
316}
317
318
319function onDataReceived(rc)
320{
321 var err = document.getElementById("error");
322 var dbg = document.getElementById("debug");
323 var con = document.getElementById("console");
324
325 var pre = document.createElement("pre");
326 pre.appendChild(document.createTextNode(rc));
327 dbg.appendChild(pre);
328
329 try
330 {
331 rc = JSON.parse(rc);
332 }
333 catch (e)
334 {
335 alert("ERROR[1] - Decoding answer:\n"+e);
336 return;
337 }
338
339 document.getElementById("event").max = rc.event.numEvents;
340 var el = document.getElementById("numevents");
341 if (el.firstChild)
342 el.removeChild(el.firstChild);
343 el.appendChild(document.createTextNode(rc.event.numEvents));
344
345 if (rc.ret)
346 {
347 while (con.lastChild)
348 con.removeChild(con.lastChild);
349 }
350
351 if (rc.err)
352 {
353 while (err.lastChild)
354 err.removeChild(err.lastChild);
355
356 err.appendChild(document.createTextNode("Javascript runtime exception: "+rc.err.file+":"+rc.err.lineNumber));
357 err.appendChild(document.createTextNode("\n"));
358 err.appendChild(document.createTextNode(rc.err.sourceLine));
359 err.appendChild(document.createTextNode("\n"));
360 err.appendChild(document.createTextNode(rc.err.trace));
361
362 var editor = rc.err.file=="main" ? editor2 : editor1;
363 editor.setCursor(rc.err.lineNumber-1, 1);
364
365 $("#accordion").find('h3').filter(':contains(Runtime)').show();
366 $("#accordion").accordion("option", "active", 0);
367 }
368
369 var canv = document.getElementById("camera1");
370
371 if (rc.debug!==undefined)
372 {
373 con.appendChild(document.createTextNode(rc.debug));
374
375 debug("return "+JSON.stringify(rc.ret));
376 debug("");
377 debug("Execution times:");
378 debug("TimeJS="+(rc.timeJs*1000).toFixed(2)+"ms");
379 }
380
381 if (rc.ret!==undefined && Array.isArray(rc.ret))
382 {
383 if (!Array.isArray(rc.ret[0]))
384 processCameraData("camera1", rc.ret);
385 else
386 processCameraData("camera1", rc.ret[0]);
387
388 if (rc.ret.length>1)
389 processCameraData("camera2", rc.ret[1]);
390
391 if (rc.ret.length>2)
392 processCameraData("camera3", rc.ret[2]);
393
394 if (rc.ret.length>3)
395 processCameraData("camera4", rc.ret[3]);
396 }
397
398 if (canv.dataAbs && rc.event)
399 document.getElementById("value").value = canv.dataAbs[rc.event.pixel];
400
401 debug("TimePhp="+(rc.timePhp*1000).toFixed(1)+"ms");
402
403 if (Array.isArray(rc.waveform))
404 {
405 var waveform = document.getElementById("waveform");
406
407 var data = [[],[],[],[]];
408
409 var min = [];
410 var max = [];
411 if (Array.isArray(rc.waveform) && rc.waveform.length==rc.event.numRoi)
412 {
413 min.push(Math.min.apply(Math, rc.waveform));
414 max.push(Math.max.apply(Math, rc.waveform));
415
416 for (var i=0; i<rc.event.numRoi; i++)
417 data[0][i] = [ i, rc.waveform[i] ];
418 }
419
420 for (var j=0; j<4; j++)
421 {
422 var ref = rc.waveform[j];
423
424 if (Array.isArray(ref) && ref.length==rc.event.numRoi)
425 {
426 min.push(Math.min.apply(Math, ref));
427 max.push(Math.max.apply(Math, ref));
428
429 for (var i=0; i<rc.event.numRoi; i++)
430 data[j][i] = [ i, ref[i] ];
431
432 }
433 }
434
435 waveform.ymin = Math.min.apply(Math, min);
436 waveform.ymax = Math.max.apply(Math, max);
437 waveform.xmin = 0;
438 waveform.xmax = rc.event.numRoi;
439
440 if (document.getElementById("waveformminon").checked)
441 document.getElementById("waveformmin").value = waveform.ymin;
442 if (document.getElementById("waveformmaxon").checked)
443 document.getElementById("waveformmax").value = waveform.ymax;
444
445 var ymin = document.getElementById("waveformminon").checked ? waveform.ymin : parseInt(document.getElementById("waveformmin").value);
446 var ymax = document.getElementById("waveformmaxon").checked ? waveform.ymax : parseInt(document.getElementById("waveformmax").value);
447
448 var opts =
449 {
450 xaxis: {
451 min: waveform.xmin-1,
452 max: waveform.xmax+1,
453 },
454 yaxis: {
455 min: ymin-5,
456 max: ymax+5,
457 },
458 series: {
459 lines: {
460 show: true
461 },
462 points: {
463 show: true,
464 symbol: 'cross',
465 }
466 },
467 selection: {
468 mode: "xy"
469 },
470 grid: {
471 hoverable: true,
472 }
473 };
474
475 plot = $.plot("#waveform", data, opts);
476
477 waveform = $('#waveform');
478 waveform.bind("plotselected", function (event, ranges)
479 {
480 setZoom(ranges.xaxis.from, ranges.xaxis.to,
481 ranges.yaxis.from, ranges.yaxis.to);
482 });
483
484 waveform.dblclick(function ()
485 {
486 var waveform = document.getElementById("waveform");
487 setZoom(waveform.xmin-1, waveform.xmax+1, waveform.ymin-5, waveform.ymax+5);
488 });
489 waveform.bind("plothover", function (event, pos, item)
490 {
491 if (!item)
492 {
493 $("#tooltip").fadeOut(100);
494 return;
495 }
496
497 var x = item.datapoint[0].toFixed(2);
498 var y = item.datapoint[1].toFixed(2);
499 //item.series.label
500
501 var tooltip = $("#tooltip");
502 tooltip.html(parseInt(x) + " / " + y);
503 tooltip.css({top: item.pageY-20, left: item.pageX+5});
504 tooltip.fadeIn(200);
505 });
506 }
507
508 //$("#accordion").accordion("refresh");
509}
510
511function onSubmit(file, pixelOnly)
512{
513 if (!file)
514 file = document.getElementById("file").value;
515
516 var dbg = document.getElementById("debug");
517 while (dbg.lastChild)
518 dbg.removeChild(dbg.lastChild);
519
520 var active = $("#accordion").accordion("option", "active");
521 if (active==0)
522 {
523 $("#accordion").accordion("option", "active", false);
524 $("#accordion").find('h3').filter(':contains(Runtime)').hide();
525 }
526
527 var event = document.getElementById("event").value;
528 var pixel = document.getElementById("pixel").value;
529 var source1 = editor1.getValue();
530 var source2 = editor2.getValue();
531
532 var uri = "file="+file+"&event="+event+"&pixel="+map[pixel];
533 uri += "&source1="+encodeURIComponent(source1);
534 if (!pixelOnly)
535 uri += "&source2="+encodeURIComponent(source2);
536
537 $.ajax({
538 type: "POST",
539 cache: false,
540 url: "index.php",
541 data: uri,
542 success: onDataReceived,
543 error: function(xhr) { if (xhr.status==0) alert("ERROR[1] - Request failed!"); else alert("ERROR[1] - "+xhr.statusText+" ["+xhr.status+"]"); }
544 });
545}
546
547function onFile(event, ui)
548{
549 var f = event.target.files[0];
550 if (!f)
551 return;
552
553 if (!f.type.match('text/plain') && !f.type.match('application/javascript'))
554 {
555 alert("ERROR - Unknown file type.");
556 return;
557 }
558
559 var id = event.target.id;
560 var editor = id[id.length-1]=='1' ? editor1 : editor2;
561
562 var reader = new FileReader();
563
564 // Closure to capture the file information.
565 reader.onload = (function(theFile) { return function(e) { editor.setValue(e.target.result); }; })(f);
566 // onloadstart
567 // onloadend
568 // onprogress
569
570 // Read in the text file
571 reader.readAsText(f);
572}
573
574function onEvent()
575{
576 onSubmit();
577}
578
579function onPixel()
580{
581 var p = parseInt(document.getElementById("pixel").value);
582
583 var cbpx = map[p];
584
585 document.getElementById("cbpx-c").value = parseInt((cbpx/360));
586 document.getElementById("cbpx-b").value = parseInt((cbpx/36)%10);
587 document.getElementById("cbpx-p").value = parseInt((cbpx/9)%4);
588 document.getElementById("cbpx-x").value = parseInt((cbpx%9));
589 document.getElementById("cbpx").value = parseInt(cbpx);
590
591 onSubmit("", true);
592}
593
594function onCBPX()
595{
596 var c = parseInt(document.getElementById("cbpx-c").value);
597 var b = parseInt(document.getElementById("cbpx-b").value);
598 var p = parseInt(document.getElementById("cbpx-p").value);
599 var x = parseInt(document.getElementById("cbpx-x").value);
600
601 var cbpx = c*360 + b*36 + p*9 + x;
602
603 document.getElementById("cbpx").value = parseInt(cbpx);
604 document.getElementById("pixel").value = map.indexOf(cbpx);
605
606 onSubmit("", true);
607}
608
609function onHW()
610{
611 var cbpx = parseInt(document.getElementById("cbpx").value);;
612
613 document.getElementById("cbpx-c").value = parseInt((cbpx/360));
614 document.getElementById("cbpx-b").value = parseInt((cbpx/36)%10);
615 document.getElementById("cbpx-p").value = parseInt((cbpx/9)%4);
616 document.getElementById("cbpx-x").value = parseInt((cbpx%9));
617
618 document.getElementById("pixel").value = map.indexOf(cbpx);
619
620 onSubmit("", true);
621}
622
623function isInside(x, y, mouse)
624{
625 var dist = Math.sqrt((mouse.x-x)*(mouse.x-x)+(mouse.y-y)*(mouse.y-y));
626 return dist<0.5;
627
628 /*
629 ctx.translate(x, y);
630 ctx.scale(1/2, 1/3);
631
632 ctx.beginPath();
633 ctx.moveTo( 1, 1);
634 ctx.lineTo( 0, 2);
635 ctx.lineTo(-1, 1);
636 ctx.lineTo(-1, -1);
637 ctx.lineTo( 0, -2);
638 ctx.lineTo( 1, -1);
639 ctx.fill();
640
641 ctx.restore();
642 */
643}
644
645function getIndex(id, mouse)
646{
647 var canv = document.getElementById(id);
648
649 var scale = 83;
650
651 var w = Math.min(canv.width/scale, canv.height/scale);
652
653 //ctx.translate(canv.width/2, canv.height/2);
654 //ctx.scale(w*2, w*2);
655 //ctx.scale(1, Math.sqrt(3)/2);
656 //ctx.translate(-0.5, 0);
657
658 mouse.x -= canv.width/2;
659 mouse.y -= canv.height/2;
660 mouse.x /= w*2;
661 mouse.y /= w*2;
662 mouse.y /= Math.sqrt(3)/2;
663 mouse.x -= -0.5;
664
665 if (isInside(0, 0, mouse))
666 return 0;
667
668 var cnt = 1;
669 for (var ring=1; ring<24; ring++)
670 {
671 for (var s=0; s<6; s++)
672 {
673 for (var i=1; i<=ring; i++)
674 {
675 var pos = new Position(s, ring, i);
676 if (pos.d() - pos.x > 395.75)
677 continue;
678
679 if (isInside(pos.x, pos.y, mouse))
680 return cnt;
681 cnt++;
682 }
683 }
684 }
685
686 if (isInside(7, -22, mouse))
687 return 1438;
688 if (isInside(7, 22, mouse))
689 return 1439;
690
691 return -1;
692}
693
694var inprogress = 0;
695function moveAnimate(n, target)
696{
697 if (inprogress==n || inprogress<0)
698 return;
699
700 inprogress = target ? -n : n;
701
702 var element = $("#camera"+n); //Allow passing in either a JQuery object or selector
703 var newParent = $(target ? target : "#cont"+n); //Allow passing in either a JQuery object or selector
704
705 var oldOffset = element.offset();
706
707 var newOffset = newParent.offset();
708
709 var w = newParent.width();
710 var h = newParent.height();
711
712 var temp = element.appendTo('body');
713 temp.css('position', 'absolute')
714 .css('left', oldOffset.left)
715 .css('top', oldOffset.top)
716 .css('zIndex', 400);
717
718 temp.animate( {'top': newOffset.top, 'left':newOffset.left, 'width':w, 'height': h},
719 'slow', function()
720 {
721 temp = temp.appendTo(newParent);
722 temp.css('position', 'default');
723 temp.css('width', 'default');
724 temp.css('height', 'default');
725 temp.css('left', '0');
726 temp.css('top', '0');
727
728 var canv = document.getElementById("camera"+n);
729
730 canv.width = w;
731 canv.height = h;
732
733 drawFullCam("camera"+n);
734
735 inprogress = 0;
736 });
737}
738
739function onClickNew(event)
740{
741 var id = event.target.id;
742 var n = parseInt(id[id.length-1]);
743
744 if (id.substr(0, 3)=="cam")
745 {
746 var cont = document.getElementById("center").childNodes[0];
747 if (cont)
748 {
749 var nn = parseInt(cont.id[cont.id.length-1]);
750 moveAnimate(nn);
751 }
752 moveAnimate(n, "#center");
753
754 }
755 else
756 moveAnimate(n);
757}
758
759function onClick(event)
760{
761 var cont = document.getElementById("center").childNodes[0];
762 if (!cont)
763 return;
764
765 if (cont.id!=event.target.id)
766 return;
767
768 // get click position relative to canvas
769 var rect = event.target.getBoundingClientRect();
770
771 var x = event.clientX - rect.left;
772 var y = event.clientY - rect.top;
773
774 var mouse = { x: x, y: y };
775
776 // convert click position to pixel index
777 var index = getIndex(event.target.id, mouse);
778 if (index<0)
779 return;
780
781 document.getElementById("pixel").value = index;
782
783 onPixel();
784}
785
786function getClickPosition(event)
787{
788 var rect = event.target.getBoundingClientRect();
789
790 var x = event.clientX - rect.left;
791 var y = event.clientY - rect.top;
792
793 return { x: x, y: y };
794}
795
796function onCameraMinMax(n)
797{
798 var canv = document.getElementById("camera"+n);
799
800 canv.zmin = document.getElementById("cameramin"+n).value;
801 canv.zmax = document.getElementById("cameramax"+n).value;
802
803 drawFullCam("camera"+n);
804}
805
806function onCameraMinMaxOn(n)
807{
808 var canv = document.getElementById("camera"+n);
809
810 var redraw;
811 if (document.getElementById("cameraminon"+n).checked)
812 {
813 document.getElementById("cameramin"+n).setAttribute("disabled", "true");
814 document.getElementById("cameramin"+n).value = canv.min;
815 redraw = true;
816 }
817 else
818 document.getElementById("cameramin"+n).removeAttribute("disabled");
819
820 if (document.getElementById("cameramaxon"+n).checked)
821 {
822 document.getElementById("cameramax"+n).setAttribute("disabled", "true");
823 document.getElementById("cameramax"+n).value = canv.max;
824 redraw = true;
825 }
826 else
827 document.getElementById("cameramax"+n).removeAttribute("disabled");
828
829 if (redraw)
830 onCameraMinMax(n);
831}
832
833function onWaveformMinMax()
834{
835 var wf = document.getElementById("waveform");
836
837 var xmin, xmax, ymin, ymax;
838
839 var redraw;
840 if (!document.getElementById("waveformminon").checked)
841 ymin = document.getElementById("waveformmin").value;
842 if (!document.getElementById("waveformmaxon").checked)
843 ymax = document.getElementById("waveformmax").value;
844
845 setZoom(xmin, xmax, ymin, ymax);
846
847}
848
849function onWaveformMinMaxOn()
850{
851 var wf = document.getElementById("waveform");
852
853 var xmin, xmax, ymin, ymax;
854
855 var redraw;
856 if (document.getElementById("waveformminon").checked)
857 {
858 document.getElementById("waveformmin").setAttribute("disabled", "true");
859 document.getElementById("waveformmin").value = wf.ymin;
860 ymin = wf.ymin-5;
861 }
862 else
863 document.getElementById("waveformmin").removeAttribute("disabled");
864
865 if (document.getElementById("waveformmaxon").checked)
866 {
867 document.getElementById("waveformmax").setAttribute("disabled", "true");
868 document.getElementById("waveformmax").value = wf.ymax;
869 ymax = wf.ymax+5;
870 }
871 else
872 document.getElementById("waveformmax").removeAttribute("disabled");
873
874 setZoom(xmin, xmax, ymin, ymax);
875}
876
877//document.addEventListener("click", getClickPosition, false);
878
879$(document).ready(onReady);
880
881// ================================== Pixel mapping =================================================
882
883var codedMap = "966676:6:A;68656364626Y?\\?;A=A<AGADAN4K4i5g5h5o506W?Z?]?_?>A@A?AJAIAFACAM4J4H4f5d5e5l5m5n516X?[?^?N?P?AA1ABAVAUAKAHAEAO4L4I4G4E4c5a5b5M6j5k5V6Y6\\6_6G?J?O?Q?S?2A4A3AYAXAWAbA_AnAkAhA3404F4D4B4`5^5_5J6K6L6S6T6W6Z6]6E?H?K?M?R?T?V?5A7A6A\\A[AZAeAdAaA^AmAjAgA24o3m3C4A4?4]5[5\\5G6H6I6P6Q6R6U6X6[6^6F?I?L?<?>?U?;@=@8Ah@9AMALA]ABCACfAcA`AoAlAiA4414n3l3<4@4>425Z5X5Y5D6E6F698N6O608E8H8K8H>K>N>?>B>=???A?<@>@@@i@k@j@PAOANAECDCCC<C9CZCWCTC=3:3734313=4;4943515o4W5U5V5A6B6C6687888m7n7C8F8I8F>I>L>=>@>C>E>@?B?D??@A@C@l@n@m@SARAQAHCGCFC?C>C;C8CYCVCSC<393633303n2:4846405n4l4T5R5S5>6?6@6384858j7k7l7o7D8G8J8G>J>M>>>A>D>4>6>C?3?5?B@2@4@o@_@0ALBKBTA0CoBIC8D7D@C=C:C[CXCUC>3;3835323o2m2k27454j3m4k4i4Q5O5P5C7<6=6g71828o8h7i7S9<8?8B8Q>T>W>@=C=F=e<h<5>7>9>4?6?8?3@5@7@`@b@a@OBNBMB3C2C1C;D:D9D_D\\DQCNCKCF3C3@3>2;282Z1W1l2j2h2k3i3g3j4h4f4N5L5M5@7A7B7d7e7f7l8m8n8P9Q9:8=8@8O>R>U>>=A=D=c<f<i<k<8>:><>7?9?;?6@8@:@c@e@d@RBQBPB6C5C4C>D=D<DbDaD^D[DPCMCJCE3B3?3=2:272Y1V1T1i2g2e2h3f3d3g4e4c4K5I5J5=7>7?7a7b7c7i8j8k8M9N9O9R9;8>8A8P>S>V>?=B=E=d<g<j<Z<\\<;>k=m=:?j>l>9@i?k?f@V@g@CBBBSBgBfB7CoCnC?DSDRDcD`D]DRCOCLCG3D3A3?2<292[1X1U1S1Q1f2d2b2e3c3a3d4b4`4H5F5G5:7;7<7^7_7`7f8g8h8J9K9L97:::=:@:C:F:I:I=L=O=7=:===n<1=[<]<_<l=n=0>k>m>o>j?l?n?W@Y@X@FBEBDBjBiBhB2D1D0DVDUDTDCE@EOELEIEXEUERE5222o1l1i1f1c1`1R1P1N1c2a2_2b3`3^3a4_4]4<5:5;5778797[7\\7]7c8d8e8G9H9I94:5:8:;:>:A:D:G:G=J=M=5=8=;=l<o<2=4=^<`<b<o=1>3>n>0?2?m?o?1@Z@\\@[@IBHBGBmBlBkB5D4D3DYDXDWDFEEEBE?ENEKEHEWETEQE4212n1k1h1e1b1_1]1O1M1K1`2^2\\2_3]3[3^4\\4Z4957585475767X7Y7Z7`8a8b8D9E9F91:2:3:6:9:<:?:B:E:H:H=K=N=6=9=<=m<0=3=d;f;a<H<J<2>b=d=1?a>c>0@`?b?]@D@^@:B9BJB^B]BnBfCeC6DJDIDZDnDmDGEDEAEPEMEJEYEVESE623202m1j1g1d1a1^1\\1[0L1J1?1]2[2Y2\\3Z3X3[4Y4W4654555172737U7V7W7]8^8_8A9B9C9e9o90:n9g:j:m:L:O:R:U:X:[:];`;c;T;W;Z;7<9<e;g;i;I<K<M<c=e=g=b>d>f>a?c?e?E@G@F@=B<B;BaB`B_BiChCgCMDLDKD1E0EoD9E7E<F9F6FaE^E[EjEgEdER0O0L0I0F0C0n0l0\\0Z0X0@1>1<1Z2X2V2Y3W3U3X4V4T4E5C5D5n6o607R7S7T7Z8[8\\8>9?9@9b9c9d9l9m9e:h:k:J:M:P:S:V:Y:[;^;a;R;U;X;6<8<:<;<h;j;l;L<N<P<f=h=j=e>g>i>d?f?h?N@Q@H@@B?B>BdBcBbBlCkCjCPDODND4E3E2E;E:E8E6E;F8F5F`E]EZEiEfEcEQ0N0K0H0E0B0m0k0j0Y0W0U0=1;191W2U2S2V3T3R3U4S4Q4B5@5A5k6l6m6O7P7Q7W8X8Y8;9<9=9_9`9a9j9k9\\:_:f:i:l:K:N:Q:T:W:Z:\\;_;b;S;V;Y;C<E<G<<<m;k;1<2<O<Q<S<i=[=P=h>X>Z>g?M@O@R@U@S@J@I@AB1B0BeBTB\\CmCAD@DQDiDhD5EdD<E4F2F0F=F:F7FbE_E\\EkEhEeES0P0M0J0G0D011o0h0g0e0V0T0`0:181Q2T2R2H2S3Q3P3R4P4K3?5=5>5c6i6j6h6M7N7L7U8V8T899:9W9]9^9\\9g9h9i9]:`:c:5;2;o:>;;;8;P;M;J;G;D;A;?<A<D<F<=<><n;o;3<5<R<T<Y=Z=Q=R=Y>[>\\>^>P@T@L@K@5B4B3B2BVBUB^C]CCDBDkDjDfDeD>E=E3F1FnElE@FCFFFIFLFOF;0>0A0205080513101i0f0d0c0b0_0I1H1D1P2O2G2F2D2O3N3M3J3H3a6b6e6f6g6I7J7K7R8S8397989V9Y9Z9[9f9^:a:d:4;1;n:=;:;7;O;L;I;F;C;@;@<B<0<4<U<V<X<`=]=\\=S=U=W=]>_>`>8B7B6BZBXBWB_CaC`CFDEDDDlDgDoEmE>FAFDFGFJFMF90<0?0003060714121a0^0]0G1C1B1N2L2E2C2B2@2L3I3`6d6E7F7G7H7O8Q8192969T9U9X96;3;0;?;<;9;Q;N;K;H;E;B;W<Y<^=_=a=T=V=X=\\B[BYBdCcCbCHDGD?FBFEFHFKFNF:0=0@0104070F1E1A1M2K2J2I2A2D7L8M8N8P809495961b:";
884var map = new Array(1440);
885
886// first: decode the pixel mapping!
887var sum = 1036080;
888for (var i=0; i<1440; i++)
889{
890 var d0 = codedMap.charCodeAt(i*2) -48;
891 var d1 = codedMap.charCodeAt(i*2+1)-48;
892
893 map[i] = d0 | (d1<<6);
894 sum -= map[i];
895}
896if (sum!=0)
897 alert("Pixel mapping table corrupted!");
898
899// ================================== Camera Display ================================================
900
901function hueToRGB(hue)
902{
903 hue /= 3;
904 hue %= 6;
905
906 if (hue<1) return parseInt(255*hue, 10);
907 if (hue<3) return parseInt(255, 10);
908 if (hue<4) return parseInt(255*(4-hue), 10);
909
910 return 0.
911}
912
913function hueToHex(flt)
914{
915 var s = hueToRGB(flt).toString(16);
916 return s.length==2 ? s : "0"+s;
917}
918
919function HLStoRGB(hue)
920{
921 if (isNaN(hue))
922 return "fff";
923
924 if (hue<0)
925 return "eef"; // 555
926
927 if (hue>1)
928 return "700"; // 666
929
930 hue *= 14;
931
932 var sr = hueToHex(20-hue);
933 var sg = hueToHex(14-hue);
934 var sb = hueToHex(26-hue);
935
936 return sr+sg+sb;
937}
938
939function drawHex(ctx, x, y, col, min, max)
940{
941 if (col===undefined || col===null)
942 return;
943
944 var lvl = (col-min)/(max-min);
945
946 ctx.fillStyle = "#"+HLStoRGB(lvl);
947
948 ctx.save();
949
950 ctx.translate(x, y);
951 ctx.scale(1/2, 1/3);
952
953 ctx.beginPath();
954 ctx.moveTo( 1, 1);
955 ctx.lineTo( 0, 2);
956 ctx.lineTo(-1, 1);
957 ctx.lineTo(-1, -1);
958 ctx.lineTo( 0, -2);
959 ctx.lineTo( 1, -1);
960 ctx.fill();
961
962 ctx.restore();
963}
964
965function Position(s, ring, i)
966{
967 switch (s)
968 {
969 case 1: this.x = ring - i*0.5; this.y = + i; break;
970 case 2: this.x = ring*0.5 - i; this.y = ring ; break;
971 case 3: this.x = -ring*0.5 - i*0.5; this.y = ring - i; break;
972 case 4: this.x = -ring + i*0.5; this.y = - i; break;
973 case 5: this.x = -ring*0.5 + i; this.y = -ring ; break;
974 case 0: this.x = ring*0.5 + i*0.5; this.y = -ring + i; break;
975 }
976 this.d = (function () { return this.x*this.x + this.y*this.y*3/4; });
977}
978
979function drawFullCam(id)
980{
981 var canv = document.getElementById(id);
982 if (!canv)
983 return;
984
985 var ctx = canv.getContext("2d");
986
987 ctx.clearRect(0, 0, canv.width, canv.height);
988
989 // ======================= Draw Graphics ======================
990
991 var data = canv.dataRel;
992 if (!data)
993 return;
994
995 var min = (canv.zmin-canv.min)/canv.max;
996 var max = (canv.zmax-canv.min)/canv.max;
997
998 var scale = 83;
999
1000 var w = Math.min(canv.width/scale, canv.height/scale);
1001
1002 ctx.save();
1003 ctx.translate(canv.width/2, canv.height/2);
1004 ctx.scale(w*2, w*2);
1005 // ctx.rotate(Math.PI/3);
1006
1007 ctx.scale(1, Math.sqrt(3)/2);
1008 ctx.translate(-0.5, 0);
1009
1010 drawHex(ctx, 0, 0, data[map[0]], min, max);
1011
1012 var cnt = 1;
1013 for (var ring=1; ring<24; ring++)
1014 {
1015 for (var s=0; s<6; s++)
1016 {
1017 for (var i=1; i<=ring; i++)
1018 {
1019 var pos = new Position(s, ring, i);
1020 if (pos.d() - pos.x > 395.75)
1021 continue;
1022
1023 drawHex(ctx, pos.x, pos.y, data[map[cnt]], min, max);
1024 cnt++;
1025 }
1026 }
1027 }
1028
1029 drawHex(ctx, 7, -22, data[map[1438]], min, max);
1030 drawHex(ctx, 7, 22, data[map[1439]], min, max);
1031
1032 ctx.restore();
1033
1034 // ======================= Draw Legend ======================
1035
1036 var lmin = parseFloat(canv.min).toFixed(1);
1037 var lmax = parseFloat(canv.max).toFixed(1);
1038
1039 var v0 = parseFloat(canv.zmin);
1040 var v1 = parseFloat(canv.zmax);
1041
1042 var diff = v1-v0;
1043
1044 var cw = canv.width;
1045 //var ch = canv.height;
1046
1047 ctx.font = "8pt Arial";
1048 ctx.textAlign = "right";
1049 ctx.textBaseline = "top";
1050
1051 for (var i=0; i<11; i++)
1052 {
1053 ctx.strokeStyle = "#"+HLStoRGB(i/10);
1054 ctx.strokeText((v0+diff*i/10).toPrecision(3), cw-5, 125-i*12);
1055 }
1056
1057 var mw = Math.max(ctx.measureText(lmin).width,
1058 ctx.measureText(lmax).width);
1059
1060 ctx.textBaseline = "top";
1061 ctx.strokeStyle = "#000";
1062
1063 //ctx.strokeText(min, 5+mw, 5+24);
1064 ctx.strokeText(lmin, 5+mw, 5+12);
1065 ctx.strokeText(lmax, 5+mw, 5);
1066}
1067
Note: See TracBrowser for help on using the repository browser.