otsdaq_prepmodernization  v2_04_01
NimPlus_app.js
1 //NimPlus_app JS
2 //Created by Ben Hawks (bhawks at fnal.gov)
3 /*
4 TODO
5 
6  - (Later) Have the ability to load previous versions of config?
7 
8  --- Save Procedure ---
9  set subsetBasePath value
10  -> getSubsetRecords
11  -> getFieldsOfRecords
12  -> setFieldValuesForRecords
13  -> popUpSaveModifiedTablesForm
14  -> activateGroup
15  -> getFieldValuesForRecords
16 
17 
18 
19 */
20 
21 
22 
23 var _TABLE_BOOL_TYPE_TRUE_COLOR = "rgb(201, 255, 201)";
24 var _TABLE_BOOL_TYPE_FALSE_COLOR = "rgb(255, 178, 178)";
25 var _nimUids = null;
26 var timeout = null; //voltField timeout value, used to wait till user done entering a value
27 var stepTimeout = null;
28 var trigTimeout = null; //triggerSyncWordCalc timeout val, used to wait till user done entering a value
29 var modifiedList = []; //List of values that are modified, used to keep track of what values need to be updated
30 var invalidInput = false; //Track if any textbox input is invalid, used to prevent saving if there is
31 var syncArray = [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0] //empty array for 40Mhz Sync Word, 24 bits
32 var accelMaskArray = [0,0,0,0,0,0,0,0] //empty array for Accel Clock Sync Word, 8 bits, only 1 true max
33 var tMuxAArray = [[0,0,0,0,0,0,0,0,0]]; //empty array for Trigger Mux Bank A
34 var tMuxBArray= [[0,0,0,0,0,0,0,0,0]]; //empty array for Trigger Mux Bank B
35 var logicArray = [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0] //empty array for coincidence logic word
36 var _subsetBasePath = "FENIMPlusInterfaceConfiguration";
37 var _modifiedTables = [];
38 var writeFEInterfaceStatus = false;
39 var FEInterfaceStatusValue = "";
40 var ogBoardState = "";
41 var fieldList = [["NimStatus","Status"],
42 ["NimPlusIP","InterfaceIPAddress"],
43 ["NimPlusPort","InterfacePort"],
44 ["otsHostIP","HostIPAddress"],
45 ["otsHostPort","HostPort"],
46 ["ChAInEn","LogicInputChannelA"],
47 ["ChBInEn","LogicInputChannelB"],
48 ["ChCInEn","LogicInputChannelC"],
49 ["ChDInEn","LogicInputChannelD"],
50 ["useExtClk","UseExternalClock"],
51 ["OutputSourceOutput1","TriggerInputChannel1"],
52 ["OutputSourceOutput2","TriggerInputChannel2"],
53 ["ChAInInv","InvertPolarityInputChannelA"],
54 ["ChBInInv","InvertPolarityInputChannelB"],
55 ["ChCInInv","InvertPolarityInputChannelC"],
56 ["ChDInInv","InvertPolarityInputChannelD"],
57 ["ChADacEl1","DACValueChannelA"],
58 ["ChBDacEl1","DACValueChannelB"],
59 ["ChCDacEl1","DACValueChannelC"],
60 ["ChDDacEl1","DACValueChannelD"],
61 ["ChAOutMux","OutputMuxSelectChannelA"],
62 ["ChBOutMux","OutputMuxSelectChannelB"],
63 ["ChCOutMux","OutputMuxSelectChannelC"],
64 ["ChDOutMux","OutputMuxSelectChannelD"],
65 ["ChAOutInv","InvertPolarityOutputChannelA"],
66 ["ChBOutInv","InvertPolarityOutputChannelB"],
67 ["ChCOutInv","InvertPolarityOutputChannelC"],
68 ["ChDOutInv","InvertPolarityOutputChannelD"],
69 ["Sync1","ClockMaskSetup"],
70 ["AccSync1","40MHzClockDelay"],
71 ["EnableSync0","EnableClockMaskTriggerOutputChannel0"],
72 ["EnableSync1","EnableClockMaskTriggerOutputChannel1"],
73 ["EnableSync2","EnableClockMaskTriggerOutputChannel2"],
74 ["VetoCount","TimeVetoTriggerOutputChannel0"],
75 ["Veto1Count","TimeVetoTriggerOutputChannel1"],
76 ["Veto2Count","TimeVetoTriggerOutputChannel2"],
77 ["VetoSourceOutput0","VetoSourceTriggerOutputChannel0"],
78 ["VetoSourceOutput1","VetoSourceTriggerOutputChannel1"],
79 ["VetoSourceOutput2","VetoSourceTriggerOutputChannel2"],
80 ["PsCount","PrescaleTriggerOutputChannel0"],
81 ["PsCount1","PrescaleTriggerOutputChannel1"],
82 ["PsCount2","PrescaleTriggerOutputChannel2"],
83 ["SL0","CoincidenceLogicWord"],
84 ["bkpEnableA","EnableBackPressureNwFmcPta1"],
85 ["bkpEnableB","EnableBackPressureNwFmcPta2"],
86 ["SGPulseCnt","SignalGeneratorPulseCount"],
87 ["SGHighPer","SignalGeneratorHighPeriod"],
88 ["SGLowPer","SignalGeneratorLowPeriod"],
89 ["sigGenEn","SignalGeneratorEnable"],
90 ["sigGenInv","SignalGeneratorInvertPolarity"],
91 ["ChADelayEl","DelayInputChannelA"],
92 ["ChAWidthEl","WidthInputChannelA"],
93 ["ChBDelayEl","DelayInputChannelB"],
94 ["ChBWidthEl","WidthInputChannelB"],
95 ["ChCDelayEl","DelayInputChannelC"],
96 ["ChCWidthEl","WidthInputChannelC"],
97 ["ChDDelayEl","DelayInputChannelD"],
98 ["ChDWidthEl","WidthInputChannelD"],
99 ["ChSNDelayEl","DelayTriggerOutputChannel0"],
100 ["ChSNWidthEl","WidthTriggerOutputChannel0"],
101 ["ChSCMS1DelayEl","DelayTriggerOutputChannel1"],
102 ["ChSCMS1WidthEl","WidthTriggerOutputChannel1"],
103 ["ChSCMS2DelayEl","DelayTriggerOutputChannel2"],
104 ["ChSCMS2WidthEl","WidthTriggerOutputChannel2"],
105 ["triggerDelaySecs","SecondsDelayBeforeStartingTriggers"],
106 ["ExtClkSel","ExternalClockSource"],
107 ["bkpOutSel0","BackpressureTriggerOutputChannel0"],
108 ["bkpOutSel1","BackpressureTriggerOutputChannel1"],
109 ["bkpOutSel2","BackpressureTriggerOutputChannel2"],
110 ["TMuxB1","TriggerMuxSelectionsBankB"],
111 ["TMuxA1","TriggerMuxSelectionsBankA"],
112 ["triggerFilename","TriggerCountAtRunStopFilename"],
113 ["BurstEn","EnableBurstData"],
114 ["BurstLogicDelay","BurstDataLogicSampleDelay"],
115 ["BurstMuxSel","BurstDataMuxSelect"],
116 ["BurstGateInputCh","BurstDataGateInputChannel"]
117 
118 ]
119 
120 //----------------------------------------- Save Functions -----------------------------------------
121 
122 
123 // Save Page Function
124 function savePageValues(e) {
125  if(modifiedList.length > 0){
126  if (invalidInput == false) {
127 
128 
129 
130 // ConfigurationAPI.getSubsetRecords(
131 // _subsetBasePath /*subsetBasePath*/ ,
132 // "", //"FEInterfacePluginName=FEOtsUDPTemplateInterface"/*filterList*/,
133 // getNimFieldsForSave /*responseHandler*/ ,
134 // _modifiedTables /*modifiedTables*/ )
135  if(writeFEInterfaceStatus == false){ //Dont need to set FEInterface status
136  console.log("Don't need to write to FEInterfaceconfiguration, skipping that write.");
137  ConfigurationAPI.getFieldsOfRecords(
138  _subsetBasePath, selUID,//["NimPlus0"]
139  "",/*_editableFieldList*/
140  -1,//maxDepth
141  setNimFieldValuesForSave,//responseHandler
142  //_modifiedTables//modifiedTables
143  )
144  }
145  else{
146  console.log("Need to write to FEInterfaceconfiguration...");
147  ConfigurationAPI.getFieldsOfRecords( //Need to set FEInterface status
148  "FEInterfaceConfiguration", selUID,//["NimPlus0"]
149  "",/*_editableFieldList*/
150  -1,//maxDepth
151  setFEInterfaceStatusForSave,//responseHandler
152  //_modifiedTables//modifiedTables
153  )
154  }
155 
156 
157 
158  } else {
159  document.getElementById("saveEl").innerHTML = "Warning! Unable to save, some fields contain invalid values";
160  console.log("Warning! Textbox on page has invalid value, aborting save...")
161  console.log("Please check the following fields for possible invalid values (some might beSigNorm/ correct)");
162  Debug.log("NimPlus Configuration Changes NOT Saved, Invalid value(s) in fields", Debug.HIGH_PRIORITY);
163  console.log(modifiedList);
164  }
165  }
166  else{
167  Debug.log("Error! No Changes to Save!", Debug.WARN_PRIORITY);
168  }
169 }
170 
171 
172 /* //Unused Function, still useful as reference
173 function getNimFieldsForSave(nimUids) {
174  if (nimUids.length == 0) {
175  Debug.log("No NIMPlus UID's found", Debug.HIGH_PRIORITY);
176  return;
177  }
178  _nimUids = nimUids;
179  console.log("getNimUIDs' Input: \n")
180  console.log(nimUids);
181  console.log("\n");
182  Debug.log("getNimUIDs ", Debug.INFO_PRIORITY);
183 
184  ConfigurationAPI.getFieldsOfRecords(
185  _subsetBasePath, nimUids,//["NimPlus0"]
186  "",//_editableFieldList
187  -1,//maxDepth
188  setNimFieldValuesForSave,//responseHandler
189  _modifiedTables//modifiedTables
190  );
191 }
192 */
193  function setFEInterfaceStatusForSave(recFields){
194  console.log("setFEInterfaceStatusForSave hit");
195  var valsToWrite = [];
196  var objToWrite = [];
197  //Debug.log("recFields found = " + recFields.length);
198 
199  console.log("setFEInterfaceStatusForSave input: \n");
200  console.log(recFields);
201  console.log("\n");
202  for (let a of recFields) {
203  if(a.fieldColumnName == "Status" && a.fieldRelativePath == "") {
204  objToWrite.push(a); //objects to update
205  valsToWrite.push(FEInterfaceStatusValue); //values for the corresponding objects
206  }
207  else{
208  //console.log("Status field not there?!?!")
209  }
210  }
211  ogBoardState = FEInterfaceStatusValue;
212  console.log(objToWrite);
213  console.log(valsToWrite);
214 
215  ConfigurationAPI.setFieldValuesForRecords(
216  "FEInterfaceConfiguration",//subsetBasePath
217  selUID,//recordArr
218  objToWrite,//fieldObjArr
219  valsToWrite,//valueArr
220  FEInterfaceToNIMPlusConfigWrite,//responseHandler
221  _modifiedTables//modifiedTables
222  )
223 
224 }
225 
226  function FEInterfaceToNIMPlusConfigWrite(newModifiedTables){
227  _modifiedTables.push(newModifiedTables[0])
228  console.log("FEInterfaceToNimplus handoff hit");
229  console.log(newModifiedTables[0]);
230  console.log(_modifiedTables);
231  ConfigurationAPI.getFieldsOfRecords(
232  _subsetBasePath, selUID,//["NimPlus0"]
233  "",/*_editableFieldList*/
234  -1,//maxDepth
235  setNimFieldValuesForSave,//responseHandler
236  _modifiedTables//modifiedTables
237  )
238 
239 }
240 function setNimFieldValuesForSave(recFields) {
241  var valsToWrite = [];
242  var objToWrite = [];
243  //Debug.log("recFields found = " + recFields.length);
244 
245  console.log("setNimFields input: \n");
246  console.log(recFields);
247  console.log("\n");
248 
249 
250 //Compare Modified list and list of returned fields, populate a 2 arrays with the objects and data to write
251 //to the table of the elements of the page that have been modified since last save
252  for (let i of modifiedList) {
253  for (let a of recFields) {
254  if(a.fieldColumnName == i[0]) {
255  objToWrite.push(a); //objects to update
256  valsToWrite.push(i[1]); //values for the corresponding objects
257  console.log("Object found");
258  }
259  else{
260  //console.log("\nno match for " + a.fieldColumnName);
261  }
262  }
263  }
264  console.log(objToWrite);
265  console.log(valsToWrite);
266 
267  ConfigurationAPI.setFieldValuesForRecords(
268  _subsetBasePath,//subsetBasePath
269  selUID,//recordArr
270  objToWrite,//fieldObjArr
271  valsToWrite,//valueArr
272  saveNimTableDialog,//responseHandler
273  _modifiedTables//modifiedTables
274  )
275 
276 };
277 
278 function saveNimTableDialog(newModifiedTables){
279  modifiedList = [];
280  console.log(newModifiedTables);
281  console.log(_modifiedTables);
282  _modifiedTables = newModifiedTables.splice(0);
283  console.log(_modifiedTables);
284  ConfigurationAPI.saveModifiedTables(
285  _modifiedTables,
286  activateNimTables
287  )
288 };
289 function activateNimTables(SavedTable,SavedGroup,SavedAlias){
290  for(let i of SavedGroup) {
291  ConfigurationAPI.activateGroup(i.groupName, i.groupKey, false)
292  }
293 
294  //#43c130 = green color, alerts user that changes are saved
295  $("body").css("background-color", "#43c130");
296  //Table Updates Here
297  Debug.log("NimPlus Configuration Changes Saved to UID " + selUID[0], Debug.INFO_PRIORITY);
298  console.log("Page Values Saved");
299  console.log(modifiedList);
300  _modifiedTables = [];
301  writeFEInterfaceStatus = false;
302  document.getElementById("saveEl").innerHTML = "Save Successful!";
303 
304 };
305 
306 
307 //------------------------------------Error Check etc. Functions------------------------------------
308 
309 
310 
311 //Calculate the 40 Mhz Sync Mask
312 function syncMaskCalc(val,a) {
313  syncArray[a]=val;
314  var n = 0;
315  var l = syncArray.length;
316  for (var i = 0; i < l; i++) {
317  n |= ((syncArray[i]?1:0) << i)
318  //n = (n << 1) + (syncArray[i]?1:0);
319  };
320  console.log(n)
321  $("#triggerSyncWord").val(n);
322  return n;
323 }
324 
325 //Calculate the Accelerator Clock Sync Mask
326 function accelMaskCalc(val,a) {
327  n = (val?1:0) << a // Should only have 1 bit true ever, so dont save values like the 40Mhz mask
328  console.log(n);
329  return n;
330 }
331 
332 //Calculate the Coincidence Logic Word
333 function LogicWordCalc(val,a) {
334  logicArray[a]=val;
335  var n = 0;
336  var l = logicArray.length;
337  for (var i = 0; i < l; i++) {
338  n = (n << 1) + (logicArray[i]?1:0);
339  }
340  console.log(n)
341  return n;
342 }
343 
344 //Calculate the Trigger Mux Word for Bank A
345 function TMuxAWordCalc(val,a) {
346  tMuxAArray[0][a]=val;
347  return JSON.stringify(tMuxAArray);
348 }
349 
350 //Calculate the Trigger Mux Word for Bank B
351 function TMuxBWordCalc(val,a) {
352  tMuxBArray[0][a]=val;
353  return JSON.stringify(tMuxBArray);
354 }
355 
356 
357 //Return an element by it's ID string
358 function elByID(id) {
359  e = document.getElementById(id);
360  return e;
361 }
362 //Return an element's value by it's ID String
363 function valByID(id) {
364  e = document.getElementById(id);
365  return e.value;
366 }
367 
368 //Set invalid input flag to false to allow saving
369 function validInput(e) {
370  invalidInput = false;
371 }
372 
373 //Set invalid input flag to true to disallow saving
374 function invalidValue(e) {
375  invalidInput = true;
376 }
377 
378 //Delay&Width Error Checking
379 function dwValidCheck(firstVal, secondValElId, msgElId) {
380  firstVal = parseInt(firstVal);
381  var secondVal = parseInt(document.getElementById(secondValElId).value);
382  if ((firstVal + secondVal) > 64) {
383  //console.log((firstVal + secondVal));
384  document.getElementById(msgElId).innerHTML = "Invald Delay/Width Combination! Sum of Delay and Width should be <=64!";
385  $("#" + msgElId).css("background-color", "red");
386  invalidInput = true;
387  } else {
388  document.getElementById(msgElId).innerHTML = "";
389  $("#" + msgElId).css("background-color", "#eee");
390  invalidInput = false;
391  }
392 
393 }
394 
395 //Add a value to the list to save into the selected row (UID) of the NIMPlus table
396  function addModifiedList(tableVal, tableDat) {
397  //#fcd125 = yellow color, notifies user that there are unsaved changes on the page
398  $("body").css("background-color", "#fcd125")
399  document.getElementById("saveEl").innerHTML = "Unsaved Changes are Present";
400 
401  var modifiedListNames = modifiedList.map(function(value,index) { return value[0]; });
402  existsAt = null;
403  existsAt = $.inArray(tableVal, modifiedListNames);
404  //document.getElementById("saveEl").innerHTML = "";
405  if (existsAt < 0) {
406  console.log(existsAt);
407  console.log($.inArray(tableVal, modifiedList[0]));
408  console.log(tableVal);
409  console.log(modifiedList[0]);
410  console.log([tableVal, tableDat]);
411  modifiedList.push([tableVal, tableDat]);
412  console.log(modifiedList);
413 // console.log(modifiedList);
414  } else {
415  modifiedList[existsAt] = [tableVal,tableDat];
416  //console.log(" element already exists in modified list, not updating list...")
417  }
418 
419 }
420  function FEInterfaceSetStatus(state){
421  console.log("ogBoardState = " + ogBoardState);
422  console.log("desired board state = " + state);
423 
424  FEInterfaceStatusValue = state;
425  if(state == ogBoardState)
426  writeFEInterfaceStatus = false;
427  else
428  writeFEInterfaceStatus = true;
429 
430  console.log("writeFEInterfaceStatus = " + writeFEInterfaceStatus)
431 
432 }
433 
434 //Dac Control Functions to link all 3 inputs together
435 //Dac ranges from 0-3.3 volts with 4096 (0-4095) steps of resolution, input must be step value
436 
437 //Update the volt field and steps when the slider is changed
438 function voltSlider(myValue, VoltElId, StepsElId) {
439  voltVal = (((10000 * ((myValue * (33 / 40950)))) + (((8 - (10000 * ((myValue * (33 / 40950)))) % 8)))) / 10000) - 0.0008;
440  document.getElementById(StepsElId).value = myValue;
441  document.getElementById(VoltElId).value = voltVal.toFixed(4);
442  invalidInput = false;
443 }
444 
445 //A litte ugly, but it works
446 //Update the volt slider and steps when the field is changed
447 function voltField(VoltElId, SlideElId, StepElId) {
448  clearTimeout(timeout);
449  timeout = setTimeout(function () {
450  myValue = VoltElId.value;
451  newValue = (((10000 * myValue) + (((8 - (10000 * myValue) % 8)))) / 10000) - 0.0008;
452  document.getElementById(SlideElId).value = Math.round((40950000 * newValue / 33000));
453  document.getElementById(StepElId).value = Math.round((40950000 * newValue / 33000));
454  VoltElId.value = newValue.toFixed(4);
455  console.log(newValue)
456  console.log(newValue.toFixed(4));
457  invalidInput = false;
458  }, 900);
459 
460 
461 }
462 function voltSteps(myValue, VoltElId, SlideElId) {
463  voltVal = (((10000 * ((myValue * (33 / 40950)))) + (((8 - (10000 * ((myValue * (33 / 40950)))) % 8)))) / 10000) - 0.0008;
464  document.getElementById(SlideElId).value = (myValue);
465  document.getElementById(VoltElId).value = voltVal.toFixed(4) //(myValue * 33 / 40950);
466  invalidInput = false;
467 }
468 
469 function triggerSyncWordCalc(val){
470  clearTimeout(trigTimeout);
471  setTimeout(function () {
472  for(bitCnt=0; bitCnt<=23; bitCnt++){
473  elByID("Sync"+(bitCnt+1).toString()).checked=((val>>(bitCnt)) % 2 != 0); //intentionally reversing bit order
474  syncArray[bitCnt]=((val>>(bitCnt)) % 2 != 0); //intentionally reversing bit order
475  /*
476  elByID("Sync"+(bitCnt+1).toString()).checked=((val>>(23-bitCnt)) % 2 != 0); //intentionally reversing bit order
477  syncArray[bitCnt]=((val>>(23-bitCnt)) % 2 != 0); //intentionally reversing bit order
478  */
479  }
480  },900)
481 }
482 
483 // ------------------------------ JQuery UI Stuff ------------------------------
484 
485 $(document).ready(function () {
486  // Set Background color
487  //#6b86ff = Light Blue, indicates page is unchanged/ @ default state
488  $("body").css("background-color", "#6b86ff")
489 
490  // CSS for Inner (hidden) divs
491  //Hide the divs by default
492 
493  //InChEnCtl
494  $("#InChEnCtl").hide();
495 
496  //DacCtl
497  $("#DacCtl").hide();
498 
499  //DWConfig
500  $("#DWConfigCtl").hide();
501 
502  //InMuxCtl
503  $("#InMuxCtl").hide();
504 
505  //OutMuxCtl
506  $("#OutMuxCtl").hide();
507  /*
508  //ResetCtl
509  $("#ResetCtl").hide();
510 
511  //EnableCtl
512  $("#EnableCtl").hide();
513  */
514  //SyncCtl
515  $("#SyncCtl").hide();
516 
517  //VetoCtl
518  $("#VetoCtl").hide();
519 
520  //PsCtl
521  $("#PsCtl").hide();
522 
523  //SelLogCtl
524  $("#SelLogCtl").hide();
525 
526  //BkpCtl
527  $("#BkpCtl").hide();
528 
529  //SigGenCtl
530  $("#SigGenCtl").hide();
531 
532  //ConnCtl
533  $("#ConnCtl").hide();
534 
535  //BurstCtl
536  $("#BurstCtl").hide();
537 
538  //Setup button actions to hide/show the divs
539 
540  $("#InChEnCtlBtn").click(function () {
541  $("#InChEnCtl").toggle(400);
542  });
543 
544  $("#DacCtlBtn").click(function () {
545  $("#DacCtl").toggle(400);
546  });
547 
548  $("#DWConfigBtn").click(function () {
549  $("#DWConfigCtl").toggle(400);
550  });
551 
552  $("#InMuxCtlBtn").click(function () {
553  $("#InMuxCtl").toggle(400);
554  });
555 
556  $("#OutMuxCtlBtn").click(function () {
557  $("#OutMuxCtl").toggle(400);
558  });
559  /*
560  $("#ResetCtlBtn").click(function(){
561  $("#ResetCtl").toggle(400);
562  });
563 
564  $("#EnableCtlBtn").click(function(){
565  $("#EnableCtl").toggle(400);
566  });
567  */
568  $("#SyncCtlBtn").click(function () {
569  $("#SyncCtl").toggle(400);
570  });
571 
572  $("#VetoCtlBtn").click(function () {
573  $("#VetoCtl").toggle(400);
574  });
575 
576  $("#PsCtlBtn").click(function () {
577  $("#PsCtl").toggle(400);
578  });
579 
580  $("#SelLogCtlBtn").click(function () {
581  $("#SelLogCtl").toggle(400);
582  });
583 
584  $("#BkpCtlBtn").click(function () {
585  $("#BkpCtl").toggle(400);
586  });
587 
588  $("#SigGenCtlBtn").click(function () {
589  $("#SigGenCtl").toggle(400);
590  });
591 
592  $("#ConnCtlBtn").click(function () {
593  $("#ConnCtl").toggle(400);
594  });
595 
596  $("#BurstCtlBtn").click(function () {
597  $("#BurstCtl").toggle(400);
598  });
599 
600  //Setup IP Address Mask for input
601  $('.ip_address').mask('0ZZ.0ZZ.0ZZ.0ZZ', {translation: {'Z': {pattern: /[0-9]/, optional: true}}});
602 
603  //Setup Hex/Dec mask for triggerSyncWord input
604  $('#triggerSyncWord').mask('ZZHHHHHHL', {'translation': {
605  Z: {pattern: /[0x]/, optional: true},
606  H: {pattern: /[A-Fa-f0-9]/},
607  L: {pattern: /[0-9]/}
608  }
609  });
610 
611  //Setup trigger sync word as a spinner
612  var spinner = $( "#triggerSyncWord" ).spinner({
613  min: 0,
614  max: 1777215
615  });
616  $("#triggerSyncWord").on("spinstop", function(){
617  triggerSyncWordCalc(this.value);
618  addModifiedList('AcceleratorClockMask',this.value);
619  });
620  console.log(spinner);
621  console.log("jquery ui setup done!")
622 
623  //Grab values to populate fields
624  ConfigurationAPI.getSubsetRecords(
625  _subsetBasePath /*subsetBasePath*/ ,
626  "", //"FEInterfacePluginName=FEOtsUDPTemplateInterface"/*filterList*/,
627  getNimUidsForList /*responseHandler*/ ,
628  _modifiedTables /*modifiedTables*/ )
629 
630 
631 });
632 
633 // ---------------------------------------------- Field Population ------------------------------------------------------
634 
635 var selUID;
636 var bitCnt;
637 
638 function getNimUidsForList(nimUids) {
639  if (nimUids.length == 0) {
640  Debug.log("No NIMPlus UID's found", Debug.HIGH_PRIORITY);
641  return;
642  }
643  else{
644  _nimUids = nimUids;
645  console.log("getNimUIDs' Input: \n")
646  console.log(nimUids);
647  console.log("\n");
648  //Debug.log("getNimUIDs ", Debug.INFO_PRIORITY);
649  console.log(nimUids)
650  console.log("first index: " + nimUids[0])
651  $.each(nimUids, function(val, text) {
652  $('#nimUIDSelect').append( $('<option></option>').val(text).html(text) )
653  $('#nimUIDToCopySelect').append( $('<option></option>').val(text).html(text) )
654  console.log(val)
655  console.log(text)
656  });
657  selUID = [nimUids[0]];
658  console.log(selUID);
659  ConfigurationAPI.getFieldsOfRecords(
660  _subsetBasePath, selUID,//["NimPlus0"]
661  "",/*_editableFieldList*/
662  -1,//maxDepth
663  getNimFieldsForPage,//responseHandler
664  _modifiedTables//modifiedTablesto
665  );
666  }
667 }
668 
669 function getNimFieldsForPage(recFields){
670  console.log("recFields: \n");
671  console.log(recFields);
672  ConfigurationAPI.getFieldValuesForRecords(
673  _subsetBasePath, selUID,
674  recFields,
675  getNimValuesForPage,
676  _modifiedTables)
677 }
678 
679 function getNimValuesForPage(recFields) {
680  //Debug.log("recFields found = " + recFields.length);
681 
682  console.log("getNimValuesForPage input: \n");
683  console.log(recFields);
684  console.log("\n");
685 
686  for (let i of fieldList) {
687  for (let a of recFields) {
688  // console.log(i)
689  //console.log(a.fieldPath)
690  //console.log(a.fieldPath.includes(i[1]));
691  if(a.fieldPath.includes(i[1])) { //found value
692  try{
693  if(elByID(i[0]).type == "checkbox" && !a.fieldPath.includes("CoincidenceLogicWord") && !a.fieldPath.includes("TriggerClockMask") && !a.fieldPath.includes("AcceleratorClockMask"))
694  {
695  if(a.fieldValue == "Yes" || a.fieldValue == "True" || a.fieldValue == "On"){
696  elByID(i[0]).checked = true;
697  console.log("checkbox element " + i[0] + " set to checked = true")
698  }
699  else{
700  elByID(i[0]).checked = false;
701  console.log("checkbox element " + i[0] + " set to checked = false")
702  }
703  }
704  else if(a.fieldPath.includes("CoincidenceLogicWord")){
705  for(bitCnt=0; bitCnt<=15; bitCnt++){
706  elByID("SL"+bitCnt.toString()).checked=((a.fieldValue>>(bitCnt)) % 2 != 0);
707  logicArray[bitCnt]=((a.fieldValue>>(15-bitCnt)) % 2 != 0); //intentionally reversing bit order
708  }
709 
710  console.log("Coincidence Logic Word set");
711  }
712  else if(a.fieldPath.includes("TriggerClockMask")){
713  for(bitCnt=0; bitCnt<=23; bitCnt++){
714 // elByID("Sync"+(bitCnt+1).toString()).checked=((a.fieldValue>>(23-bitCnt)) % 2 != 0); //intentionally reversing bit order
715 // syncArray[bitCnt]=((a.fieldValue>>(23-bitCnt)) % 2 != 0); //intentionally reversing bit order
716 // }
717  elByID("Sync"+(bitCnt+1).toString()).checked=((a.fieldValue>>(bitCnt)) % 2 != 0);
718  syncArray[bitCnt]=((a.fieldValue>>(bitCnt)) % 2 != 0);
719  }
720  elByID("triggerSyncWord").value = a.fieldValue;
721  console.log("Trigger Clock Mask set")
722  }
723  else if(a.fieldPath.includes("AcceleratorClockMask")){
724  for(bitCnt=0; bitCnt<=7; bitCnt++){
725  elByID("AccSync"+(bitCnt+1).toString()).checked=((a.fieldValue>>(bitCnt)) % 2 != 0);
726  accelMaskArray[bitCnt]=((a.fieldValue>>(bitCnt)) % 2 != 0);
727  }
728  console.log("Accelerator Clock Mask set")
729  }
730  else if(a.fieldPath.includes("Status")){
731  if(a.fieldValue == "Yes" || a.fieldValue == "True" || a.fieldValue == "On"){
732  ogBoardState = "On";
733  elByID(i[0]).value = "On";
734  console.log("NimPlus Status " + i[0] + " set to On/Enabled")
735  }
736  else{
737  ogBoardState = "Off";
738  elByID(i[0]).value = "Off";
739  console.log("NimPlus Status " + i[0] + " set to Off/Disabled")
740  }
741  }
742  else if(a.fieldPath.includes("TriggerMuxSelectionsBankA")){
743  loadMuxArr = JSON.parse(a.fieldValue);
744  for(k=0; k<=8; k++){
745  elByID("TMuxA"+(k+1).toString()).value=loadMuxArr[0][k];
746  tMuxAArray[0][k]=loadMuxArr[0][k];
747  }
748  console.log("Loaded TMux Bank A with values: " + loadMuxArr );
749  }
750  else if(a.fieldPath.includes("TriggerMuxSelectionsBankB")){
751  loadMuxArr = JSON.parse(a.fieldValue);
752  for(k=0; k<=8; k++){
753  elByID("TMuxB"+(k+1).toString()).value=loadMuxArr[0][k];
754  tMuxBArray[0][k]=loadMuxArr[0][k];
755  }
756 
757  console.log("Loaded TMux Bank B with values: " + loadMuxArr);
758  }
759  else if(elByID(i[0]).id=="ChADacEl1"){
760  voltSteps(a.fieldValue, "ChADacEl2", "ChADacEl0")
761  elByID(i[0]).value = a.fieldValue
762  console.log("Set CH A Dac")
763  }
764  else if(elByID(i[0]).id=="ChBDacEl1"){
765  voltSteps(a.fieldValue, "ChBDacEl2", "ChBDacEl0")
766  elByID(i[0]).value = a.fieldValue
767  console.log("Set CH B Dac")
768  }
769  else if(elByID(i[0]).id=="ChCDacEl1"){
770  voltSteps(a.fieldValue, "ChCDacEl2", "ChCDacEl0")
771  elByID(i[0]).value = a.fieldValue
772  console.log("Set CH C Dac")
773  }
774  else if(elByID(i[0]).id=="ChDDacEl1"){
775  voltSteps(a.fieldValue, "ChDDacEl2", "ChDDacEl0")
776  elByID(i[0]).value = a.fieldValue
777  console.log("Set CH D Dac")
778  }
779  else{
780  elByID(i[0]).value = a.fieldValue;
781  console.log("set element " + i[0] + " to value " + a.fieldValue + " from " + a.fieldPath)
782  }
783  }
784  catch(e){
785  console.log("\n!!!_-_-_WARNING_-_-_!!!\n");
786  console.log("Exception occured while trying to set an element supposedly named " + i[0] + " to the value of " + a.fieldValue + " from the field " + a.fieldPath);
787  console.log("Incoming exception data...\n");
788  console.log(e);
789  console.log("\n!!!_-_-_END WARNING_-_-_!!!\n");
790  }
791 
792  }
793  else if(a.fieldPath.includes("EnableExpertWebappFeatures")){ //Show/Hide expert features
794  if(a.fieldValue == "Yes"){
795  $("#SigGenBox").show() //Signal Generator
796  $("#BkpBox").show() //Backpressure Vetos
797  $("#SyncBox").show() //40Mhz Sync
798  $("#BurstBox").show() //40Mhz Sync
799  }
800  else{
801  $("#SigGenBox").hide() //Signal Generator
802  $("#BkpBox").hide() //Backpressure Vetos
803  $("#SyncBox").hide() //40Mhz Sync
804  $("#BurstBox").hide() //40Mhz Sync
805  }
806  }
807  else{/*
808  console.log("\nno match for " + a.fieldColumnName);
809  console.log(a.fieldColumnName);
810  console.log(i[1]);
811  console.log(a.fieldColumnName == i[1]);
812  */
813  }
814  }
815  }
816 
817 
818 
819 };
820 
821 //Update form data when UID is swiched
822 function getNimValuesOnUIDSelect(selValue) {
823 
824  selUID = [selValue];
825  console.log(selUID);
826  ConfigurationAPI.getFieldsOfRecords(
827  _subsetBasePath, selUID,//["NimPlus0"]
828  "",/*_editableFieldList*/
829  -1,//maxDepth
830  getNimFieldsForPage,//responseHandler
831  _modifiedTables//modifiedTables
832  );
833 
834 };
835 
836 
837 //----------------------------------------------"Add New Nimplus" stuff ---------------------------------------------------------------------
838 
839 //--------------------------- Modal Setup ------------------------------ Unstable/Disabled for release
840 /*
841 window.onload = function() {
842 var modal = elByID('newNimPlusPopup');
843 var openBtn = elByID('addNewNIMPlus');
844 var xBtn = document.getElementsByClassName("close")[0];
845 var cancelBtn = elByID('cancelNewNIMPlusAdd');
846 
847 
848 //Open Modal
849 openBtn.onclick = function() {
850  modal.style.display = "block";
851  elByID("newNIMUIDErr").innerHTML = ""
852  elByID("newNIMUID").value = ""
853 }
854 //Close Modal
855 xBtn.onclick = function() {
856  modal.style.display = "none";
857 }
858 cancelBtn.onclick = function() {
859  modal.style.display = "none";
860 }
861 }
862 
863 
864 var gottenFields = [];
865 var copyUID;
866 var alphaNumRegEx = /^[a-z0-9]+$/i
867 var _recFields = [];
868 function checkNewNIMPlusUID(){
869  if(alphaNumRegEx.test(valByID("newNIMUID"))){
870  elByID("newNIMUIDErr").innerHTML = ""
871  selUID = [valByID("newNIMUID")]
872  copyUID = [valByID("nimUIDToCopySelect")]
873  //create new UID stuff
874  ConfigurationAPI.addSubsetRecords( //NimPlusConfiguration
875  "FENIMPlusInterfaceConfiguration",
876  selUID, //new NIMUID
877  loadNewNIMPlusConfigTable,
878  _modifiedTables);
879 
880  ConfigurationAPI.addSubsetRecords( //NimPlusOptionalConfiguration
881  "FENIMPlusInterfaceOptionalConfiguration",
882  selUID, //new NIMUID
883  loadNewNIMPlusOptionalConfigTable,
884  _modifiedTables);
885 
886  ConfigurationAPI.addSubsetRecords( //FEInterfaces
887  "FEInterfaceConfiguration",
888  selUID, //new NIMUID
889  loadNewNIMPlusFEInterfaceTable,
890  _modifiedTables);
891 
892  }
893  else{
894  elByID("newNIMUIDErr").innerHTML = "New NIMPlus UID MUST be Alphanumeric (A-Z, 0-9) Characters only!"
895  console.log("Bad New UID")
896  }
897 
898 }
899 
900 
901 
902 //Inital Response handlers
903 function loadNewNIMPlusConfigTable(newModifiedTables){
904  //assume only one table modified
905  if(newModifiedTables.length)
906  _modifiedTables.push(newModifiedTables[0]);
907  //console.log("New row in NimPlusConfiguration created")
908 }
909 function loadNewNIMPlusOptionalConfigTable(newModifiedTables){
910  if(newModifiedTables.length)
911  _modifiedTables .push(newModifiedTables[0]);
912  ConfigurationAPI.getFieldsOfRecords(
913  _subsetBasePath, copyUID,
914  "",
915  -1,//maxDepth
916  getNimFieldValuesForNewNIMPlus,
917  _modifiedTables)
918 }
919 function loadNewNIMPlusFEInterfaceTable(newModifiedTables){
920  if(newModifiedTables.length)
921  _modifiedTables.push(newModifiedTables[0]);
922 }
923 
924 
925 
926 
927 //Copying table for NimPlus Config Vals
928 function getNimFieldValuesForNewNIMPlus(recFields) {
929  gottenFields = recFields.slice(0);
930  ConfigurationAPI.getFieldValuesForRecords(
931  _subsetBasePath, copyUID,
932  recFields,
933  setNimOptionalLinkForNewNIMPlus,
934  _modifiedTables)
935 }
936 
937 
938 function setNimOptionalLinkForNewNIMPlus(recFields) {
939  var valsToWrite = [];
940  var objToWrite = [];
941  _recFields = recFields.splice(0);
942  //...forge some objects
943  var linkObj = {}
944  linkObj.fieldTableName = "FENIMPlusInterfaceConfiguration"
945  linkObj.fieldUID = selUID[0]
946  linkObj.fieldColumnName = "LinkToOptionalParameters"
947  linkObj.fieldRelativePath = ""
948  linkObj.fieldColumnType = "ChildLink-optionalParameters"
949  linkObj.fieldColumnDataType = "VARCHAR2"
950  linkObj.fieldColumnDataChoicesArr = []
951  linkObj.fieldColumnDefaultValue = ""
952  var linkUIDObj = {};
953  linkUIDObj.fieldTableName = "FENIMPlusInterfaceConfiguration"
954  linkUIDObj.fieldUID = selUID[0]
955  linkUIDObj.fieldColumnName = "LinkToOptionalParametersUID"
956  linkUIDObj.fieldRelativePath = ""
957  linkUIDObj.fieldColumnType = "ChildLinkUID-optionalParameters"
958  linkUIDObj.fieldColumnDataType = "VARCHAR2"
959  linkUIDObj.fieldColumnDataChoicesArr = [0]
960  linkUIDObj.fieldColumnDefaultValue = ""
961  objToWrite = [linkObj,linkUIDObj]
962  valsToWrite = ["FENIMPlusInterfaceOptionalConfiguration",selUID[0]]
963 
964 
965  ConfigurationAPI.setFieldValuesForRecords(
966  _subsetBasePath,//subsetBasePath
967  selUID,//recordArr
968  objToWrite,//fieldObjArr
969  valsToWrite,//valueArr
970  setNimFieldValuesForNewNIMPlus,//responseHandler
971  _modifiedTables)//modifiedTables
972 
973 }
974 
975 function setNimFieldValuesForNewNIMPlus(newModifiedTables) {
976  var valsToWrite = [];
977  var objToWrite = [];
978  for (let j of _modifiedTables){
979  if (j.tableName ==_subsetBasePath){
980  _modifiedTables[_modifiedTables.indexOf(j)] = newModifiedTables[0];
981  }
982  }
983  //Debug.log("recFields found = " + recFields.length);
984 
985  console.log("setNimFields input: \n");
986  console.log(_recFields);
987  console.log("\n");
988  console.log(gottenFields);
989 
990 
991  for (let i of gottenFields) {
992  objToWrite.push(i);
993  }
994  for (let a of _recFields) {
995  valsToWrite.push(a.fieldValue);
996 
997  }
998 
999  console.log(objToWrite);
1000  console.log(valsToWrite);
1001 
1002  ConfigurationAPI.setFieldValuesForRecords(
1003  _subsetBasePath,//subsetBasePath
1004  selUID,//recordArr
1005  objToWrite,//fieldObjArr
1006  valsToWrite,//valueArr
1007  saveNimTableDialog,//responseHandler
1008  _modifiedTables)//modifiedTables
1009 }
1010 */