a munch adventure
您最多选择25个主题 主题必须以字母或数字开头,可以包含连字符 (-),并且长度不得超过35个字符
 
 
 
 

184 行
5.0 KiB

  1. stories = [];
  2. function initGame(story, state) {
  3. state.info = {};
  4. state.info.time = {
  5. id: "time",
  6. name: "Time",
  7. type: "counter",
  8. value: 60*60*9,
  9. get render() {
  10. return renderTime(this.value);
  11. }
  12. }
  13. state.player.stats = {};
  14. state.timers = [];
  15. }
  16. function createStatDisplays(stats, statType) {
  17. const holder = document.querySelector("#" + statType + "-info")
  18. Object.entries(stats).forEach(([key, val]) => {
  19. if (val.type == "meter") {
  20. const field = document.createElement("div");
  21. field.id = statType + "-info-" + key;
  22. field.setAttribute("max", val.max);
  23. field.setAttribute("value", val.value);
  24. field.classList.add("stat-bar-holder");
  25. const label = document.createElement("div");
  26. label.classList.add("stat-bar-label");
  27. label.textContent = val.name;
  28. const bar = document.createElement("div");
  29. bar.classList.add("stat-bar");
  30. bar.style["background-color"] = val.color;
  31. field.appendChild(label);
  32. field.appendChild(bar);
  33. holder.appendChild(field);
  34. } else if (val.type == "counter") {
  35. const field = document.createElement("div");
  36. field.id = statType + "-info-" + key;
  37. holder.appendChild(field);
  38. }
  39. });
  40. }
  41. function initGamePostSetup(state) {
  42. createStatDisplays(state.info, "world");
  43. createStatDisplays(state.player.stats, "player");
  44. }
  45. function changeStat(stat, amount, state) {
  46. let value = state.player.stats[stat].value;
  47. value += amount;
  48. value = Math.max(value, state.player.stats[stat].min);
  49. value = Math.min(value, state.player.stats[stat].max);
  50. state.player.stats[stat].value = value;
  51. }
  52. // TODO: format string this lol
  53. function renderTime(time) {
  54. let hours = Math.floor(time / 3600) % 12;
  55. const ampm = Math.floor(time / 3600) % 24 < 12 ? "AM" : "PM";
  56. let minutes = Math.floor(time / 60) % 60;
  57. let seconds = time % 60;
  58. if (minutes <= 9)
  59. minutes = "0" + minutes;
  60. if (seconds <= 9)
  61. seconds = "0" + seconds;
  62. return hours + ":" + minutes + ":" + seconds + " " + ampm;
  63. }
  64. function updateWorldInfo(state) {
  65. Object.entries(state.info).forEach(([key, val]) => {
  66. if (val.type == "meter") {
  67. const field = document.querySelector("#world-info-" + key + " > .stat-bar");
  68. field.style.width = (val.value / val.max * 100) + "%";
  69. } else if (val.type == "counter") {
  70. const field = document.querySelector("#world-info-" + key);
  71. field.innerText = val.name + ": " + val.render;
  72. }
  73. });
  74. }
  75. function updatePlayerInfo(state) {
  76. Object.entries(state.player.stats).forEach(([key, val]) => {
  77. if (val.type == "meter") {
  78. const field = document.querySelector("#player-info-" + key + " > .stat-bar");
  79. field.style.width = (val.value / val.max * 100) + "%";
  80. } else if (val.type == "counter") {
  81. const field = document.querySelector("#player-info-" + key);
  82. field.innerText = val.name + ": " + val.value;
  83. }
  84. });
  85. }
  86. /*
  87. {
  88. id: an optional name; needed to manually kill a timer
  89. func: the function to invoke
  90. delay: how long to wait between invocations
  91. loop: false = no looping, true = loop forever
  92. room: the room associated with the timer
  93. }
  94. Returns the timeout id - but you still need to cancel it through stopTimer!
  95. */
  96. function startTimer(config, state) {
  97. const timeout = setTimeout(() => {
  98. const result = config.func(state, config);
  99. refresh();
  100. // the timer may have terminated itself!
  101. // we have to make sure it still exists
  102. if (state.timers.some(x => x.timeout == timeout)){
  103. state.timers = state.timers.filter(x => x.timeout != timeout);
  104. if (typeof(result) === "number") {
  105. config.delay = result;
  106. }
  107. // you shouldn't use a delay of 0 anyway
  108. if (result && config.loop) {
  109. startTimer(config, state);
  110. }
  111. }
  112. }, config.delay);
  113. state.timers.push({id: config.id, timeout: timeout, room: config.room, classes: config.classes || []});
  114. return timeout;
  115. }
  116. function stopTimer(id, state) {
  117. const matches = state.timers.filter(timer => timer.id == id);
  118. matches.forEach(timer => clearTimeout(timer.timeout));
  119. state.timers = state.timers.filter(timer => timer.id != id);
  120. }
  121. function stopRoomTimers(room, state) {
  122. const matches = state.timers.filter(timer => timer.room == room);
  123. matches.forEach(timer => clearTimeout(timer.timeout));
  124. state.timers = state.timers.filter(timer => timer.room != room);
  125. }
  126. function stopClassTimers(timerClass, state, inverse) {
  127. const matches = state.timers.filter(timer => timer.classes.includes(timerClass));
  128. const others = state.timers.filter(timer => !timer.classes.includes(timerClass));
  129. if (inverse) {
  130. others.forEach(timer => clearTimeout(timer.timeout));
  131. state.timers = matches;
  132. } else {
  133. matches.forEach(timer => clearTimeout(timer.timeout));
  134. state.timers = others;
  135. }
  136. }
  137. function stopAllTimers(state) {
  138. state.timers.forEach(x => clearTimeout(x.timeout));
  139. state.timers = [];
  140. }
  141. function setBackgroundColor(r, g, b) {
  142. document.querySelector(".scene").style["background-color"] = "rgb(" + r + "," + g + "," + b + ")";
  143. }