26f6f3c1db418f2844d6cee587d640dff09cd512
[matches/MCTX3420.git] / testing / MCTXWeb / public_html / static / mctx.gui.js
1 /**
2  * MCTX3420 2013 GUI stuff.
3  */
4
5 mctx = {};
6 //Don't use this in the final version
7 mctx.location = window.location.pathname;
8 mctx.location = mctx.location.substring(0, mctx.location.lastIndexOf('/')) + "/";
9 //mctx.location = location.protocol + "//" + location.host + "/";
10 mctx.api = location.protocol + "//" + location.host + "/" + "api/";
11 mctx.expected_api_version = 0;
12 mctx.has_control = false;
13 //mctx.debug = true;
14
15 mctx.statusCodes = {
16   STATUS_OK : 1
17 }
18
19 mctx.statusCodesDescription = {
20   "1" : "Ok",
21   "-1" : "General error",
22   "-2" : "Unauthorized",
23   "-3" : "Not running",
24   "-4" : "Already exists"
25 };
26
27 mctx.sensors = {
28   0 : {name : "Strain gauge 1"},
29   1 : {name : "Strain gauge 2"},
30   2 : {name : "Strain gauge 3"},
31   3 : {name : "Strain gauge 4"},
32   4 : {name : "Pressure sensor 1"},
33   5 : {name : "Pressure sensor 2"},
34   6 : {name : "Pressure sensor 3"}
35 };
36
37 mctx.actuators = {
38   0 : {name : "Solenoid 1"},
39   1 : {name : "Solenoid 2"},
40   2 : {name : "Solenoid 3"},
41   3 : {name : "Pressure regulator"}
42 };
43
44 mctx.strain_gauges = {};
45 mctx.strain_gauges.ids = [0, 1, 2, 3];
46 mctx.strain_gauges.time_limit = 20;
47
48 function debugLog (msg) {
49   if (typeof console === "undefined" || typeof console.log === "undefined") {
50     alert(msg);
51   } else {
52     console.log(msg);
53   }
54 }
55
56 /**
57  * Writes the current date to wherever it's called.
58  */
59 function getDate(){
60         document.write((new Date()).toDateString());
61 }
62
63 function runBeforeLoad(isLoginPage) {
64   $.ajax({
65     url : mctx.api + "identify"
66   }).done(function (data) {
67     if (mctx.debug) {
68       debugLog("Redirect disabled!");
69     } else if (data.logged_in && isLoginPage) {
70         window.location = mctx.location;
71     } else if (!data.logged_in && !isLoginPage) {
72       //Note: this only clears the nameless cookie
73       document.cookie = ""; 
74       window.location = mctx.location + "login.html";
75     } else {
76       mctx.friendlyName = data.friendly_name;
77       $("#content").css("display", "block");
78     }
79   }).fail(function (jqHXR) {
80     if (!isLoginPage) {
81       window.location = mctx.location + "login.html";
82     } else {
83       debugLog("Failed to ident server. Is API running?")
84     }
85   });
86 }
87
88 /**
89  * Populates a submenu of the navigation bar
90  * @param {string} header The header
91  * @param {object} items An object representing the submenu items
92  * @param {function} translator A function that translates an object item
93  *                              into a text and href.
94  * @returns {$.fn} Itself
95  */
96 $.fn.populateSubmenu = function(header, items, translator) {
97   var submenuHeader = $("<li/>").append($("<a/>", {text : header, href : "#"}));
98   var submenu = $("<ul/>", {"class" : "submenu"});
99   
100   for (var item in items) {
101     var info = translator(item, items);
102     submenu.append($("<li/>").append(
103           $("<a/>", {text : info.text, 
104                      href : info.href, target : "_blank"})
105     ));
106   }
107   
108   this.append(submenuHeader.append(submenu));
109   return this;
110 };
111
112 /** 
113  * Populates the navigation bar
114  */
115 $.fn.populateNavbar = function () {
116   var menu = $("<ul/>", {"class" : "menu"});
117   var sensorTranslator = function(item, items) {
118     var href = mctx.api + "sensors?start_time=0&format=tsv&id=" + item;
119     return {text : items[item].name, href : href};
120   };
121   var actuatorTranslator = function(item, items) {
122     var href = mctx.api + "actuators?start_time=0&format=tsv&id=" + item;
123     return {text : items[item].name, href : href};
124   };
125   
126   menu.populateSubmenu("Sensor data", mctx.sensors, sensorTranslator);
127   menu.populateSubmenu("Actuator data", mctx.actuators, actuatorTranslator);
128   menu.appendTo(this);
129   return this;
130 }
131
132 /**
133  * Sets the camera autoupdater
134  * @returns {$.fn}
135  */
136 $.fn.setCamera = function () {
137   var url = mctx.api + "image";  //http://beaglebone/api/image
138   var update = true;
139
140   //Stop updating if we can't retrieve an image!
141   this.error(function() {
142     update = false;
143   });
144   
145   var parent = this;
146   
147   var updater = function() {
148     if (!update) {
149       alert("Cam fail");
150       parent.attr("src", "");
151       return;
152     }
153     
154     parent.attr("src", url + "#" + (new Date()).getTime());
155     
156     setTimeout(updater, 1000);
157   };
158   
159   updater();
160   return this;
161 };
162
163 $.fn.setStrainGraphs = function () {
164   var sensor_url = mctx.api + "sensors";
165   var graphdiv = this;
166   
167   var updater = function () {
168     var time_limit = mctx.strain_gauges.time_limit;
169     var responses = new Array(mctx.strain_gauges.ids.length);
170     
171     for (var i = 0; i < mctx.strain_gauges.ids.length; i++) {
172       var parameters = {id : i, start_time: -time_limit};
173       responses[i] = $.ajax({url : sensor_url, data : parameters});
174     }
175     
176     $.when.apply(this, responses).then(function () {
177       var data = new Array(arguments.length);
178       for (var i = 0; i < arguments.length; i++) {
179         var raw_data = arguments[i][0].data;
180         var pruned_data = [];
181         var step = ~~(raw_data.length/100);
182         for (var j = 0; j < raw_data.length; j += step)
183           pruned_data.push(raw_data[j]); 
184         data[i] = pruned_data;
185       }
186       $.plot(graphdiv, data);
187       setTimeout(updater, 500);
188     }, function () {alert("It crashed");});
189   };
190   
191   updater();
192   return this;
193 };
194
195 $.fn.login = function () {
196   var username = this.find("input[name='username']").val();
197   var password = this.find("input[name='pass']").val();
198   var out = this.find("#result");
199   var redirect = function () {
200     window.location.href = mctx.location;
201   };
202   
203   out.removeAttr("class");
204   out.text("Logging in...");
205   
206   $.ajax({
207     url : mctx.api + "bind",
208     data : {user: username, pass : password}
209   }).done(function (data) {
210     if (data.status < 0) {
211       mctx.has_control = false;
212       out.attr("class", "fail");
213       out.text("Login failed: " + data.description);
214     } else {
215       //todo: error check
216       mctx.has_control = true;
217       out.attr("class", "pass");
218       out.text("Login ok!");
219       setTimeout(redirect, 800);      
220     }
221   }).fail(function (jqXHR) {
222     mctx.has_control = false;
223     out.attr("class", "fail");
224     out.text("Login request failed - connection issues.")
225   });
226 };
227
228 $.fn.logout = function () {
229   $.ajax({
230     url : mctx.api + "unbind"
231   }).always(function () {
232     //Note: this only clears the nameless cookie
233     document.cookie = ""; 
234     window.location = mctx.location + "login.html";
235   });
236 }
237
238 $.fn.setErrorLog = function () {
239   var url = mctx.api + "errorlog";
240   var outdiv = this;
241   
242   var updater = function () {
243     $.ajax({url : url}).done(function (data) {
244       outdiv.text(data);
245       outdiv.scrollTop(
246         outdiv[0].scrollHeight - outdiv.height()
247       );
248       setTimeout(updater, 1000);
249     }).fail(function (jqXHR) {
250       if (jqXHR.status === 502 || jqXHR.status === 0) {
251         outdiv.text("Failed to retrieve the error log.");
252       }
253       setTimeout(updater, 1500);
254     });
255   };
256   
257   updater();
258 };
259
260 $(document).ajaxError(function (event, jqXHR) {
261   //console.log("AJAX query failed with: " + jqXHR.status + " (" + jqXHR.statusText + ")");
262 });

UCC git Repository :: git.ucc.asn.au