globals.js 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385
  1. const imgsrc = "assets/img/"
  2. const defaultWidth = 900;
  3. const defaultHeight = 600;
  4. const debugMode = false; // Turns console messages ON/OFF
  5. let audioStatus = false; // Turns game audio ON/OFF
  6. let playerName;
  7. let langString; // String that contains the selected language
  8. let lang = {};
  9. let sound = {};
  10. let levelLabel = true; // Turns explicitly showing the fractions in levels ON/OFF
  11. let currentGameState; // Name of the current selected 'game' state
  12. let self;
  13. let mapPosition; // character position in the map
  14. let mapCanMove; // When true the character can move to next position in the map
  15. let completedLevels; // Number of finished levels in the map
  16. let levelShape; // Can be 'circle' or 'square'
  17. let levelDifficulty; // A value from 1..3 or 1..5 that defines the current level difficulty
  18. /* LEVEL TYPE (the ones in the menu screen)
  19. * in squareOne/circleOne can be: 'A' (click on the floor) or 'B' (click on the amount to go/stacked figures)
  20. * in squareTwo can be: 'C' (comparing fractions) */
  21. let levelType;
  22. /* SUBLEVEL TYPE (the ones in the difficulty screen)
  23. * in squareOne levels can be: 'Plus' or 'Minus'
  24. * in circleOne levels can be: 'Plus', 'Minus' or 'Mixed'
  25. * in squareTwo levels can be: 'A', 'B' or 'C' */
  26. let sublevelType;
  27. let timer, totalTime; // Counts time spent in each game
  28. const hip = "143.107.45.11"; // Host ip
  29. // Colors available
  30. const colors = {
  31. // used in text
  32. green: "#00804d",
  33. darkRed: "#330000",
  34. blue: "#003cb3",
  35. mediumBlue: "#000080",
  36. black: "#000000",
  37. almostWhite: "#f0f5f5",
  38. // difficulty stairs
  39. diffBlue: "0x99b3ff",
  40. diffRed: "0xff6666",
  41. diffPurple: "0xb366ff",
  42. // Background color
  43. blueBckg: 0xcce5ff, // default
  44. blueBckgLevel: 0xa8c0e6, // in gameSquareOne (used for floor gap)
  45. // ok button in name State
  46. teal: 0x3d5c5c,
  47. // difficulty symbols and game color identifier
  48. darkBlue: 0x31314e,
  49. red: 0xb30000,
  50. lightBlue: 0xefeff5,
  51. // gameSquareTwo
  52. darkRed_: 0x330000,
  53. lightRed: 0xd27979,
  54. lighterRed: 0xf2d9d9,
  55. darkGreen: 0x1e2f2f,
  56. lightGreen: 0x83afaf,
  57. lighterGreen: 0xe0ebeb,
  58. };
  59. // Text styles available
  60. const textStyles = {
  61. // titles
  62. title1: { font: "32px Arial", fill: colors.green, align: "center" },
  63. title2: { font: "27px Arial", fill: colors.green, align: "center" },
  64. overtitle: { font: "20px Arial", fill: colors.darkRed, align: "center" },
  65. subtitle1: { font: "27px Arial", fill: colors.blue, align: "center" },
  66. subtitle2: { font: "27px Arial", fill: colors.black, align: "center" },
  67. // button labels
  68. buttonLabel: { font: '34px Arial', fill: colors.almostWhite, align: 'center' },
  69. difficultyLabel: { font: '25px Arial', fill: colors.almostWhite, align: 'center' },
  70. // in game labels
  71. valueLabelBlue1: { font: '26px Arial', fill: colors.mediumBlue, align: 'center' },
  72. valueLabelBlue2: { font: '20px Arial', fill: colors.mediumBlue, align: 'center' }, // numbers in gameSquareTwo
  73. valueLabelBlue3: { font: '15px Arial', fill: colors.mediumBlue, align: 'center' }, // fractions numbers in gameSquareOne
  74. };
  75. // images, spritesheets and audio files
  76. const media = {
  77. boot: function (type) {
  78. image = [
  79. // scenario
  80. ['birch', imgsrc + 'scenario/birch.png'],
  81. ['bgimage', imgsrc + 'scenario/bg.jpg'],
  82. ['bgmap', imgsrc + 'scenario/bg_map.png'],
  83. ['cloud', imgsrc + 'scenario/cloud.png'],
  84. ['floor', imgsrc + 'scenario/floor.png'],
  85. ['place_a', imgsrc + 'scenario/place_a.png'],
  86. ['place_b', imgsrc + 'scenario/place_b.png'],
  87. ['rock', imgsrc + 'scenario/rock.png'],
  88. ['road', imgsrc + 'scenario/road.png'],
  89. ['sign', imgsrc + 'scenario/sign.png'],
  90. ['tree1', imgsrc + 'scenario/tree.png'],
  91. ['tree2', imgsrc + 'scenario/tree2.png'],
  92. ['tree3', imgsrc + 'scenario/tree3.png'],
  93. ['tree4', imgsrc + 'scenario/tree4.png'],
  94. // flags
  95. ['flag_BR', imgsrc + 'flag/BRAZ.jpg'],
  96. ['flag_FR', imgsrc + 'flag/FRAN.jpg'],
  97. ['flag_IT', imgsrc + 'flag/ITAL.png'],
  98. ['flag_PE', imgsrc + 'flag/PERU.jpg'],
  99. ['flag_US', imgsrc + 'flag/UNST.jpg'],
  100. // Navigation icons on the top of the page
  101. ['back', imgsrc + 'navIcon/back.png'],
  102. ['block', imgsrc + 'navIcon/block.png'],
  103. ['help', imgsrc + 'navIcon/help.png'],
  104. ['home', imgsrc + 'navIcon/home.png'],
  105. ['world', imgsrc + 'navIcon/language.png'],
  106. ['list', imgsrc + 'navIcon/menu.png'],
  107. ['pgbar', imgsrc + 'navIcon/progressBar.png'],
  108. // mathematical operators
  109. ['equal', imgsrc + 'operator/equal.png'],
  110. ['fractionLine', imgsrc + 'operator/fractionLine.png'],
  111. //feedback options
  112. ['h_arrow', imgsrc + 'help/arrow.png'],
  113. ['h_double', imgsrc + 'help/double.png'],
  114. ['down', imgsrc + 'help/down.png'],
  115. ['h_error', imgsrc + 'help/error.png'],
  116. ['h_ok', imgsrc + 'help/ok.png'],
  117. ['pointer', imgsrc + 'help/pointer.png'],
  118. ];
  119. spritesheet = [
  120. // Game Sprites
  121. ['kid_walk', imgsrc + 'character/kid/walk.png', 78, 175, 26],
  122. // Menu icons n the top of the page
  123. ['audio', imgsrc + 'navIcon/audio_48x48.png', 48, 48, 2],
  124. // feedback options
  125. ['select', imgsrc + 'help/selectionBox.png', 310, 310, 2],
  126. ];
  127. audio = [
  128. // Sound effects
  129. ['beepSound', ['/Ifractions-web/assets/audio/beep.ogg', '/Ifractions-web/assets/audio/beep.mp3']],
  130. ['okSound', ['/Ifractions-web/assets/audio/ok.ogg', '/Ifractions-web/assets/audio/ok.mp3']],
  131. ['errorSound', ['/Ifractions-web/assets/audio/error.ogg', '/Ifractions-web/assets/audio/error.mp3']],
  132. ];
  133. return media.returnType(type);
  134. },
  135. gameSquareOne: function (type) {
  136. image = [
  137. // scenario
  138. ['farm', imgsrc + 'scenario/farm.png'],
  139. ['garage', imgsrc + 'scenario/garage.png'],
  140. ];
  141. spritesheet = [
  142. // Game sprites
  143. ['tractor', imgsrc + 'character/tractor/frame.png', 201, 144, 10]
  144. ];
  145. audio = [];
  146. return media.returnType(type);
  147. },
  148. gameSquareTwo: function (type) {
  149. image = [
  150. // scenario
  151. ['house', imgsrc + 'scenario/house.png'],
  152. ['school', imgsrc + 'scenario/school.png'],
  153. ];
  154. spritesheet = [
  155. ['kid_lost', imgsrc + 'character/kid/lost.png', 72, 170, 6],
  156. ['kid_run', imgsrc + 'character/kid/run.png', 82, 178, 12],
  157. ];
  158. audio = [];
  159. return media.returnType(type);
  160. },
  161. gameCircleOne: function (type) {
  162. image = [
  163. // scenario
  164. ['house', imgsrc + 'scenario/house.png'],
  165. ['school', imgsrc + 'scenario/school.png'],
  166. // Game Sprites
  167. ['balloon', imgsrc + 'character/balloon/airballoon_upper.png'],
  168. ['balloon_basket', imgsrc + 'character/balloon/airballoon_base.png'],
  169. ];
  170. spritesheet = [
  171. ['kid_run', imgsrc + 'character/kid/run.png', 82, 178, 12],
  172. ];
  173. audio = [];
  174. return media.returnType(type);
  175. },
  176. menu: function (type) {
  177. image = [
  178. // level Icrons
  179. ['', imgsrc + 'game/squareOne_1.png', 'Square', 'A'], // Square I
  180. ['', imgsrc + 'game/squareOne_2.png', 'Square', 'B'], // Square II
  181. ['', imgsrc + 'game/circleOne_1.png', 'Circle', 'A'], // Circle I
  182. ['', imgsrc + 'game/circleOne_2.png', 'Circle', 'B'], // Circle II
  183. ['', imgsrc + 'game/squareTwo_3.png', 'Square', 'C'] // Square III
  184. ];
  185. if (debugMode) {
  186. for (let i = 0; i < 8; i++) {
  187. image.push(['', imgsrc + 'game/squareTwo_3.png', 'Square', 'C']);
  188. }
  189. }
  190. audio = [];
  191. spritesheet = [];
  192. return media.returnType(type);
  193. },
  194. returnType: function (type) {
  195. if (type == 'image') return image;
  196. else if (type == 'spritesheet') return spritesheet;
  197. else if (type == 'audio') return audio;
  198. },
  199. };
  200. // Control navigation icons on the top of the screen
  201. let iconSettings = {
  202. // Add navigation icons on the top of the screen based on parameters
  203. func_addIcons: function (left_side, right_side, // icon side
  204. left_btn0, left_btn1, left_btn2, // first 3 icon spaces
  205. right_btn0, right_btn1, // last 2 icon spaces
  206. level, helpBtn) { // auxiliar variables
  207. let left_x = 10;
  208. let right_x = defaultWidth - 50 - 10;
  209. // 'Descriptive labels' for the navigation icons
  210. if (left_side) this.left_text = game.add.text(left_x, 53, "", textStyles.overtitle);
  211. if (right_side) {
  212. this.right_text = game.add.text(right_x + 50, 53, "", textStyles.overtitle);
  213. this.right_text.anchor.setTo(1, 0.02);
  214. }
  215. // 'Icons' on the LEFT side of the page
  216. if (left_btn0) { // Return to select difficulty screen
  217. const icon_back = game.add.sprite(left_x, 10, 'back');
  218. icon_back.inputEnabled = true;
  219. icon_back.input.useHandCursor = true;
  220. icon_back.events.onInputDown.add(this.func_callState, { state: level });
  221. icon_back.events.onInputOver.add(function () { this.left_text.text = lang.menu_back }, { left_text: this.left_text });
  222. icon_back.events.onInputOut.add(function () { this.left_text.text = "" }, { left_text: this.left_text });
  223. // Offsets value of x for next icon
  224. left_x += 50;
  225. }
  226. if (left_btn1) { // Return to main menu screen
  227. const icon_list = game.add.sprite(left_x, 10, 'list');
  228. icon_list.inputEnabled = true;
  229. icon_list.input.useHandCursor = true;
  230. icon_list.events.onInputDown.add(this.func_callState, { state: "menu" });
  231. icon_list.events.onInputOver.add(function () { this.left_text.text = lang.menu_list }, { left_text: this.left_text });
  232. icon_list.events.onInputOut.add(function () { this.left_text.text = "" }, { left_text: this.left_text });
  233. // Offsets value of x for next icon
  234. left_x += 50;
  235. }
  236. if (left_btn2) { // In some levels, shows solution to the game
  237. const icon_help = game.add.sprite(left_x, 10, 'help');
  238. icon_help.inputEnabled = true;
  239. icon_help.input.useHandCursor = true;
  240. icon_help.events.onInputDown.add(helpBtn);
  241. icon_help.events.onInputOver.add(function () { this.left_text.text = lang.menu_help }, { left_text: this.left_text });
  242. icon_help.events.onInputOut.add(function () { this.left_text.text = "" }, { left_text: this.left_text });
  243. // Offsets value of x for next icon
  244. left_x += 50;
  245. }
  246. // 'Icons' on the RIGHT side of the page
  247. if (right_btn0) { // Turns game audio on/off
  248. this.icon_audio = game.add.sprite(right_x, 10, 'audio');
  249. audioStatus ? this.icon_audio.frame = 0 : this.icon_audio.frame = 1;
  250. this.icon_audio.inputEnabled = true;
  251. this.icon_audio.input.useHandCursor = true;
  252. this.icon_audio.events.onInputDown.add(function () { if (audioStatus) { audioStatus = false; this.icon_audio.frame = 1; } else { audioStatus = true; this.icon_audio.frame = 0; } }, { icon_audio: this.icon_audio });
  253. this.icon_audio.events.onInputOver.add(function () { this.right_text.text = lang.audio }, { right_text: this.right_text });
  254. this.icon_audio.events.onInputOut.add(function () { this.right_text.text = "" }, { right_text: this.right_text });
  255. // Offsets value of x for next icon
  256. right_x -= 50;
  257. }
  258. if (right_btn1) { // Return to select language screen
  259. this.icon_world = game.add.sprite(right_x, 10, 'world');
  260. this.icon_world.inputEnabled = true;
  261. this.icon_world.input.useHandCursor = true;
  262. this.icon_world.events.onInputDown.add(this.func_callState, { state: "language" });
  263. this.icon_world.events.onInputOver.add(function () { this.right_text.text = lang.menu_world }, { right_text: this.right_text });
  264. this.icon_world.events.onInputOut.add(function () { this.right_text.text = "" }, { right_text: this.right_text });
  265. // Offsets value of x for next icon
  266. right_x -= 50;
  267. }
  268. },
  269. // refresh values of x for icons when menu screen move sideways
  270. func_refreshRightIcons_x: function (newWidth) {
  271. this.right_text.x = newWidth - 10;
  272. this.icon_audio.x = newWidth - 50 - 10;
  273. this.icon_world.x = newWidth - 50 - 50 - 10;
  274. },
  275. func_callState: function () {
  276. if (audioStatus) sound.beepSound.play();
  277. game.state.start(this.state);
  278. }
  279. };
  280. let loadLangs = function (url) {
  281. lang = {};
  282. var init = {
  283. mode: "same-origin"
  284. };
  285. fetch(url, init)
  286. .then(function (response) {
  287. return response.text();
  288. })
  289. .then(function (text) {
  290. let msg = text.split("\n");
  291. msg.forEach((temp) => {
  292. try {
  293. let msg = temp.split("=");
  294. lang[msg[0].trim()] = msg[1].trim();
  295. } catch { console.log("erro de sintaxe corrigido"); }
  296. });
  297. });
  298. }
  299. let loadAudios = function (audiosURL) {
  300. sound = {};
  301. var init = {
  302. mode: "same-origin",
  303. };
  304. audiosURL.forEach((item) => {
  305. fetch(item[1][1], init)
  306. .then(response => response.blob())
  307. .then(function (myBlob) {
  308. sound[item[0]] = new Audio(URL.createObjectURL(myBlob));
  309. })
  310. });
  311. };