utils.js 6.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187
  1. /**
  2. * This JS file contains utils functions
  3. */
  4. class Utils {
  5. constructor(parent) {
  6. this.parent = parent;
  7. this.multipleSize = [1280, 1024, 'Mobile'];
  8. }
  9. /**
  10. * When something is written in the editor, it reset the safe mode
  11. */
  12. markDirty() {
  13. if (this.parent.monacoCreator.BlockEditorChange) return;
  14. this.setToMultipleID("safemodeToggle", "addClass", "checked");!
  15. this.setToMultipleID('safemodeToggle', 'innerHTML', 'Safe mode <i class="fa fa-check-square" aria-hidden="true"></i>');
  16. };
  17. toLocationError(errorMessage, errorEvent) {
  18. if (!errorEvent) {
  19. return null;
  20. }
  21. // Do we have any location info?
  22. if (errorEvent.hasOwnProperty('lineNumber') && errorEvent.hasOwnProperty('columnNumber'))
  23. return errorEvent;
  24. // Else try to parse the stack to retrieve location...
  25. var regEx = /\(.+:(\d+):(\d+)\)\n/g;
  26. var match = regEx.exec(errorEvent.stack);
  27. if (match) {
  28. var error = new EvalError(errorMessage);
  29. error.lineNumber = match[1];
  30. error.columnNumber = match[2];
  31. return error;
  32. }
  33. // Not an error with proper location
  34. return null;
  35. }
  36. /**
  37. * Used to show error messages
  38. * @param {String} errorMessage
  39. * @param {String} errorEvent
  40. */
  41. showError(errorMessage, errorEvent) {
  42. let errorContent = '<div class="alert alert-error"><button type="button" class="close" data-dismiss="alert">&times;</button>';
  43. const locationError = this.toLocationError(errorMessage, errorEvent);
  44. if (locationError == null) {
  45. // use a regular message
  46. errorContent += `${errorMessage}</div>`;
  47. } else {
  48. // we have location information
  49. errorContent += `<span id="gotoLocation">Line ${locationError.lineNumber} : ${locationError.columnNumber} - ${errorMessage}</span></div>`;
  50. }
  51. document.getElementById("errorZone").style.display = 'block';
  52. document.getElementById("errorZone").innerHTML = errorContent;
  53. // Close button error
  54. document.getElementById("errorZone").querySelector('.close').addEventListener('click', function () {
  55. document.getElementById("errorZone").style.display = 'none';
  56. });
  57. // Go To Location
  58. const gotoLocation = document.getElementById("gotoLocation");
  59. const jsEditor = this.parent.monacoCreator.jsEditor;
  60. if (gotoLocation) {
  61. gotoLocation.addEventListener('click', function () {
  62. const position = {
  63. lineNumber: Number(locationError.lineNumber),
  64. column: Number(locationError.columnNumber)
  65. };
  66. jsEditor.revealPositionInCenter(position, monaco.editor.ScrollType.Smooth);
  67. jsEditor.setPosition(position);
  68. });
  69. }
  70. };
  71. /**
  72. * Apply things to the differents menu sizes
  73. */
  74. setToMultipleID(id, thingToDo, param) {
  75. this.multipleSize.forEach(function (size) {
  76. if (thingToDo == "innerHTML") {
  77. document.getElementById(id + size).innerHTML = param
  78. }
  79. else if (thingToDo == "click") {
  80. if (param.length > 1) {
  81. for (var i = 0; i < param.length; i++) {
  82. document.getElementById(id + size).addEventListener("click", param[i]);
  83. }
  84. }
  85. else
  86. document.getElementById(id + size).addEventListener("click", param);
  87. }
  88. else if (thingToDo == "addClass") {
  89. document.getElementById(id + size).classList.add(param);
  90. }
  91. else if (thingToDo == "removeClass") {
  92. document.getElementById(id + size).classList.remove(param);
  93. }
  94. else if (thingToDo == "display") {
  95. document.getElementById(id + size).style.display = param;
  96. }
  97. });
  98. };
  99. /**
  100. * Function to get the current screen size
  101. */
  102. getCurrentSize() {
  103. for(var i = 0; i < this.multipleSize.length; i++) {
  104. if(document.getElementById("menuButton" + this.multipleSize[i]).offsetHeight > 0) return this.multipleSize[i];
  105. }
  106. };
  107. debounceAsync(fn, wait = 0, options = {}) {
  108. let lastCallAt
  109. let deferred
  110. let timer
  111. let pendingArgs = []
  112. return function debounced(...args) {
  113. const currentWait = getWait(wait)
  114. const currentTime = new Date().getTime()
  115. const isCold = !lastCallAt || (currentTime - lastCallAt) > currentWait
  116. lastCallAt = currentTime
  117. if (isCold && options.leading) {
  118. return options.accumulate
  119. ? Promise.resolve(fn.call(this, [args])).then(result => result[0])
  120. : Promise.resolve(fn.call(this, ...args))
  121. }
  122. if (deferred) {
  123. clearTimeout(timer)
  124. } else {
  125. deferred = defer()
  126. }
  127. pendingArgs.push(args)
  128. timer = setTimeout(flush.bind(this), currentWait)
  129. if (options.accumulate) {
  130. const argsIndex = pendingArgs.length - 1
  131. return deferred.promise.then(results => results[argsIndex])
  132. }
  133. return deferred.promise
  134. }
  135. function getWait(wait) {
  136. return (typeof wait === 'function') ? wait() : wait
  137. }
  138. function defer() {
  139. const deferred = {}
  140. deferred.promise = new Promise((resolve, reject) => {
  141. deferred.resolve = resolve
  142. deferred.reject = reject
  143. })
  144. return deferred
  145. }
  146. function flush() {
  147. const thisDeferred = deferred
  148. clearTimeout(timer)
  149. Promise.resolve(
  150. options.accumulate
  151. ? fn.call(this, pendingArgs)
  152. : fn.apply(this, pendingArgs[pendingArgs.length - 1])
  153. )
  154. .then(thisDeferred.resolve, thisDeferred.reject)
  155. pendingArgs = []
  156. deferred = null
  157. }
  158. }
  159. }