littlejsengine 1.19.3 → 1.21.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/FAQ.md +841 -820
- package/README.md +29 -25
- package/dist/littlejs.d.ts +2857 -955
- package/dist/littlejs.esm.js +33428 -20995
- package/dist/littlejs.esm.min.js +4 -3
- package/dist/littlejs.js +33386 -20996
- package/dist/littlejs.min.js +2 -2
- package/dist/littlejs.release.js +27841 -20422
- package/package.json +10 -5
- package/plugins/audioEffects.js +28 -24
- package/plugins/box2d.js +2516 -2073
- package/plugins/drawUtilities.js +206 -31
- package/plugins/gltf.js +786 -0
- package/plugins/jsconfig.json +19 -0
- package/plugins/lightSystem.js +719 -332
- package/plugins/math3d.js +148 -27
- package/plugins/medalSystem.js +326 -280
- package/plugins/newgrounds.js +400 -199
- package/plugins/pathFinder.js +208 -175
- package/plugins/pluginExport.js +25 -0
- package/plugins/postProcess.js +96 -24
- package/plugins/render3d.js +2067 -1632
- package/plugins/render3dDebug.js +110 -0
- package/plugins/render3dEditor.js +1812 -0
- package/plugins/render3dExtras.js +1948 -0
- package/plugins/render3dLevel.js +189 -0
- package/plugins/render3dVoxels.js +514 -0
- package/plugins/sceneSystem.js +58 -0
- package/plugins/textureSheet.js +496 -458
- package/plugins/threejs.js +183 -163
- package/plugins/tweakables.js +411 -0
- package/plugins/tweenSystem.js +265 -145
- package/plugins/uiSystem.js +2024 -1687
- package/plugins/zzfxm.js +159 -159
- package/src/engine.js +378 -97
- package/src/engineAudio.js +231 -127
- package/src/engineBuild.mjs +292 -256
- package/src/engineDebug.js +967 -743
- package/src/engineDraw.js +391 -198
- package/src/engineEditor.js +2452 -0
- package/src/engineExport.js +18 -0
- package/src/engineInput.js +1466 -1293
- package/src/engineLogo.js +19 -0
- package/src/engineMath.js +1274 -1252
- package/src/engineObject.js +197 -82
- package/src/engineParticles.js +583 -532
- package/src/engineRelease.js +79 -45
- package/src/engineSettings.js +115 -29
- package/src/engineTileLayer.js +995 -741
- package/src/engineUtilities.js +19 -13
- package/src/engineWebGL.js +239 -82
- package/src/jsconfig.json +17 -13
- package/plugins/box2d.wasm.js +0 -630
- package/plugins/box2d.wasm.wasm +0 -0
package/plugins/medalSystem.js
CHANGED
|
@@ -1,280 +1,326 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* LittleJS Medal System
|
|
3
|
-
* - Achievement/trophy system for games
|
|
4
|
-
* - Medal class with name, description, icon, and unlock tracking
|
|
5
|
-
* - Automatic saving to local storage
|
|
6
|
-
* - Visual display queue with slide-in notifications
|
|
7
|
-
* - Newgrounds
|
|
8
|
-
* -
|
|
9
|
-
* @namespace Medals
|
|
10
|
-
*/
|
|
11
|
-
|
|
12
|
-
'use strict';
|
|
13
|
-
|
|
14
|
-
let debugMedals = false;
|
|
15
|
-
|
|
16
|
-
///////////////////////////////////////////////////////////////////////////////
|
|
17
|
-
// Medals settings
|
|
18
|
-
|
|
19
|
-
/** How long to show medals for in seconds
|
|
20
|
-
* @type {number}
|
|
21
|
-
* @default
|
|
22
|
-
* @memberof Settings */
|
|
23
|
-
let medalDisplayTime = 5;
|
|
24
|
-
|
|
25
|
-
/** How quickly to slide on/off medals in seconds
|
|
26
|
-
* @type {number}
|
|
27
|
-
* @default
|
|
28
|
-
* @memberof Settings */
|
|
29
|
-
let medalDisplaySlideTime = .5;
|
|
30
|
-
|
|
31
|
-
/** Size of medal display
|
|
32
|
-
* @type {Vector2}
|
|
33
|
-
* @default Vector2(640,80)
|
|
34
|
-
* @memberof Settings */
|
|
35
|
-
let medalDisplaySize = vec2(640, 80);
|
|
36
|
-
|
|
37
|
-
/** Set to stop medals from being unlockable (like if cheats are enabled)
|
|
38
|
-
* @type {boolean}
|
|
39
|
-
* @default
|
|
40
|
-
* @memberof Settings */
|
|
41
|
-
let medalsPreventUnlock = false;
|
|
42
|
-
|
|
43
|
-
/** List of all medals
|
|
44
|
-
* @type {Object}
|
|
45
|
-
* @memberof Medals */
|
|
46
|
-
const medals = {};
|
|
47
|
-
|
|
48
|
-
// Engine internal variables not exposed to documentation
|
|
49
|
-
let medalsDisplayQueue = [], medalsSaveName, medalsDisplayTimeLast;
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
* -
|
|
56
|
-
*
|
|
57
|
-
*
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
//
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
{
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
}
|
|
243
|
-
|
|
244
|
-
/**
|
|
245
|
-
* @
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
//
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
*
|
|
280
|
-
|
|
1
|
+
/**
|
|
2
|
+
* LittleJS Medal System
|
|
3
|
+
* - Achievement/trophy system for games
|
|
4
|
+
* - Medal class with name, description, icon, and unlock tracking
|
|
5
|
+
* - Automatic saving to local storage, unless a service like Newgrounds holds the medal (see Medal.isLocal)
|
|
6
|
+
* - Visual display queue with slide-in notifications
|
|
7
|
+
* - The Newgrounds plugin extends it with NewgroundsMedal, held on the server while logged in
|
|
8
|
+
* - Setting debugMedals = true in the game code before medalsInit skips the load and the save, and in the debug build logs the Newgrounds traffic; it is not exported, so only a script tag build can set it
|
|
9
|
+
* @namespace Medals
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
'use strict';
|
|
13
|
+
|
|
14
|
+
let debugMedals = false; // see the header
|
|
15
|
+
|
|
16
|
+
///////////////////////////////////////////////////////////////////////////////
|
|
17
|
+
// Medals settings
|
|
18
|
+
|
|
19
|
+
/** How long to show medals for in seconds
|
|
20
|
+
* @type {number}
|
|
21
|
+
* @default
|
|
22
|
+
* @memberof Settings */
|
|
23
|
+
let medalDisplayTime = 5;
|
|
24
|
+
|
|
25
|
+
/** How quickly to slide on/off medals in seconds
|
|
26
|
+
* @type {number}
|
|
27
|
+
* @default
|
|
28
|
+
* @memberof Settings */
|
|
29
|
+
let medalDisplaySlideTime = .5;
|
|
30
|
+
|
|
31
|
+
/** Size of medal display
|
|
32
|
+
* @type {Vector2}
|
|
33
|
+
* @default Vector2(640,80)
|
|
34
|
+
* @memberof Settings */
|
|
35
|
+
let medalDisplaySize = vec2(640, 80);
|
|
36
|
+
|
|
37
|
+
/** Set to stop medals from being unlockable (like if cheats are enabled)
|
|
38
|
+
* @type {boolean}
|
|
39
|
+
* @default
|
|
40
|
+
* @memberof Settings */
|
|
41
|
+
let medalsPreventUnlock = false;
|
|
42
|
+
|
|
43
|
+
/** List of all medals
|
|
44
|
+
* @type {Object<number, Medal>}
|
|
45
|
+
* @memberof Medals */
|
|
46
|
+
const medals = {};
|
|
47
|
+
|
|
48
|
+
// Engine internal variables not exposed to documentation
|
|
49
|
+
let medalsDisplayQueue = [], medalsSaveName, medalsDisplayTimeLast, medalsRenderAdded;
|
|
50
|
+
let medalsLoadWaiting = false; // medalsInit came before any medal, each one made reads its own unlock
|
|
51
|
+
|
|
52
|
+
///////////////////////////////////////////////////////////////////////////////
|
|
53
|
+
|
|
54
|
+
/** Initialize medals with a save name used for storage
|
|
55
|
+
* - Call this after creating all medals
|
|
56
|
+
* - Loads which medals are unlocked from the save, and writes the catalog back
|
|
57
|
+
* - A medal a service like Newgrounds holds is left as it is, see Medal.isLocal
|
|
58
|
+
* @param {string} saveName - The localStorage key the medals are kept under, a different one from the game's own
|
|
59
|
+
* readSaveData and writeSaveData, or each would overwrite the other
|
|
60
|
+
* @memberof Medals */
|
|
61
|
+
function medalsInit(saveName)
|
|
62
|
+
{
|
|
63
|
+
medalsSaveName = saveName;
|
|
64
|
+
medalsLoad();
|
|
65
|
+
|
|
66
|
+
// add the medal display once, however often this is called
|
|
67
|
+
if (!medalsRenderAdded)
|
|
68
|
+
engineAddPlugin(undefined, medalsRender);
|
|
69
|
+
medalsRenderAdded = true;
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
// check which local medals are unlocked in the save, and write the catalog back
|
|
73
|
+
function medalsLoad()
|
|
74
|
+
{
|
|
75
|
+
// with no medals made yet, the save is left as it is for them, a game that calls medalsInit first keeps its unlocks;
|
|
76
|
+
// it keeps waiting from then on, so loading again (a dropped Newgrounds session) does not drop medals still to come
|
|
77
|
+
medalsLoadWaiting ||= !Object.keys(medals).length;
|
|
78
|
+
if (debugMedals || !medalsSaveName) return;
|
|
79
|
+
const saved = readSaveData(medalsSaveName);
|
|
80
|
+
ASSERT(Object.keys(saved).every(key=> isNumber(+key)),
|
|
81
|
+
'the medals save name holds other data, give medalsInit a name of its own');
|
|
82
|
+
medalsForEach(medal=> {
|
|
83
|
+
if (medal.isLocal())
|
|
84
|
+
medal.unlocked = !!saved[medal.id]?.unlocked;
|
|
85
|
+
});
|
|
86
|
+
medalsSave();
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
// show the first medal in the queue, sliding it on and off
|
|
90
|
+
function medalsRender()
|
|
91
|
+
{
|
|
92
|
+
if (!medalsDisplayQueue.length) return;
|
|
93
|
+
|
|
94
|
+
// update first medal in queue
|
|
95
|
+
const medal = medalsDisplayQueue[0];
|
|
96
|
+
const elapsed = timeReal - medalsDisplayTimeLast;
|
|
97
|
+
if (!medalsDisplayTimeLast)
|
|
98
|
+
medalsDisplayTimeLast = timeReal;
|
|
99
|
+
else if (elapsed > medalDisplayTime)
|
|
100
|
+
{
|
|
101
|
+
medalsDisplayTimeLast = 0;
|
|
102
|
+
medalsDisplayQueue.shift();
|
|
103
|
+
}
|
|
104
|
+
else
|
|
105
|
+
{
|
|
106
|
+
// slide on/off medals, the slides share the display time when it is short
|
|
107
|
+
const slideTime = min(medalDisplaySlideTime, medalDisplayTime/2);
|
|
108
|
+
const slideOffTime = medalDisplayTime - slideTime;
|
|
109
|
+
const hidePercent =
|
|
110
|
+
elapsed < slideTime ? 1 - elapsed / slideTime :
|
|
111
|
+
elapsed > slideOffTime ? (elapsed - slideOffTime) / slideTime : 0;
|
|
112
|
+
medal.render(hidePercent);
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
/**
|
|
117
|
+
* @callback MedalCallbackFunction - Function that processes a medal
|
|
118
|
+
* @param {Medal} medal
|
|
119
|
+
* @memberof Medals
|
|
120
|
+
*/
|
|
121
|
+
|
|
122
|
+
/** Calls a function for each medal
|
|
123
|
+
* @param {MedalCallbackFunction} callback
|
|
124
|
+
* @memberof Medals */
|
|
125
|
+
function medalsForEach(callback)
|
|
126
|
+
{ Object.values(medals).forEach(medal=> callback(medal)); }
|
|
127
|
+
|
|
128
|
+
/** Reset all medals to locked and persist the cleared catalog
|
|
129
|
+
* - A medal a service like Newgrounds holds is left alone, the service has it
|
|
130
|
+
* @memberof Medals */
|
|
131
|
+
function medalsReset()
|
|
132
|
+
{
|
|
133
|
+
medalsForEach(medal=> medal.isLocal() && (medal.unlocked = false));
|
|
134
|
+
if (medalsLoadWaiting && medalsSaveName && !debugMedals)
|
|
135
|
+
{
|
|
136
|
+
// the saved unlocks of medals not made yet are cleared too, they are read when those medals are made
|
|
137
|
+
const saved = readSaveData(medalsSaveName);
|
|
138
|
+
for (const id in saved)
|
|
139
|
+
if (!medals[id] && saved[id] && typeof saved[id] === 'object')
|
|
140
|
+
saved[id].unlocked = false;
|
|
141
|
+
writeSaveData(medalsSaveName, saved);
|
|
142
|
+
}
|
|
143
|
+
medalsSave();
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
// write the local medals to the save, keeping the entries of medals a service holds
|
|
147
|
+
function medalsSave()
|
|
148
|
+
{
|
|
149
|
+
if (debugMedals || !medalsSaveName) return;
|
|
150
|
+
// while medalsInit waits for medals made later, their saved entries are kept for them
|
|
151
|
+
const saved = readSaveData(medalsSaveName);
|
|
152
|
+
const data = medalsLoadWaiting ? {...saved} : {};
|
|
153
|
+
for (const key in saved) // what is not a medal is the game's own, saved under the same name, and stays
|
|
154
|
+
isNumber(+key) || (data[key] = saved[key]);
|
|
155
|
+
medalsForEach(medal=> {
|
|
156
|
+
if (!medal.isLocal())
|
|
157
|
+
{
|
|
158
|
+
// a service holds this medal, its entry stays as it was for when it is local again
|
|
159
|
+
if (saved[medal.id]) data[medal.id] = saved[medal.id];
|
|
160
|
+
return;
|
|
161
|
+
}
|
|
162
|
+
const entry = {
|
|
163
|
+
name: medal.name,
|
|
164
|
+
description: medal.description,
|
|
165
|
+
icon: medal.icon,
|
|
166
|
+
unlocked: medal.unlocked,
|
|
167
|
+
};
|
|
168
|
+
if (medal.image) entry.src = medal.image.src;
|
|
169
|
+
data[medal.id] = entry;
|
|
170
|
+
});
|
|
171
|
+
writeSaveData(medalsSaveName, data);
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
///////////////////////////////////////////////////////////////////////////////
|
|
175
|
+
|
|
176
|
+
/**
|
|
177
|
+
* Medal - Tracks an unlockable medal
|
|
178
|
+
* @memberof Medals
|
|
179
|
+
* @example
|
|
180
|
+
* // create a medal
|
|
181
|
+
* const medal_example = new Medal(0, 'Example Medal', 'More info about the medal goes here.', '🎖️');
|
|
182
|
+
*
|
|
183
|
+
* // initialize medals
|
|
184
|
+
* medalsInit('Example Game');
|
|
185
|
+
*
|
|
186
|
+
* // unlock the medal
|
|
187
|
+
* medal_example.unlock();
|
|
188
|
+
*/
|
|
189
|
+
class Medal
|
|
190
|
+
{
|
|
191
|
+
/** Create a medal and add it to the list of medals
|
|
192
|
+
* @param {number} id - The unique identifier of the medal
|
|
193
|
+
* @param {string} name - Name of the medal
|
|
194
|
+
* @param {string} [description] - Description of the medal
|
|
195
|
+
* @param {string} [icon] - Icon for the medal
|
|
196
|
+
* @param {string} [src] - Image location for the medal
|
|
197
|
+
*/
|
|
198
|
+
constructor(id, name, description='', icon='🏆', src)
|
|
199
|
+
{
|
|
200
|
+
ASSERT(isNumber(id) && id >= 0 && !medals[id], 'medal id must be a unique number of 0 or more');
|
|
201
|
+
|
|
202
|
+
/** @property {number} - The unique identifier of the medal */
|
|
203
|
+
this.id = id;
|
|
204
|
+
|
|
205
|
+
/** @property {string} - Name of the medal */
|
|
206
|
+
this.name = name;
|
|
207
|
+
|
|
208
|
+
/** @property {string} - Description of the medal */
|
|
209
|
+
this.description = description;
|
|
210
|
+
|
|
211
|
+
/** @property {string} - Icon for the medal */
|
|
212
|
+
this.icon = icon;
|
|
213
|
+
|
|
214
|
+
/** @property {boolean} - Is the medal unlocked? */
|
|
215
|
+
this.unlocked = false;
|
|
216
|
+
|
|
217
|
+
/** @property {HTMLImageElement|undefined} - Source image for the medal icon, if any
|
|
218
|
+
* @type {HTMLImageElement|undefined} */
|
|
219
|
+
this.image = undefined;
|
|
220
|
+
if (src)
|
|
221
|
+
(this.image = new Image).src = src;
|
|
222
|
+
|
|
223
|
+
// add this to list of medals, unlocked if the save says so when medalsInit came before any medal
|
|
224
|
+
medals[id] = this;
|
|
225
|
+
if (medalsLoadWaiting && !debugMedals && this.isLocal())
|
|
226
|
+
this.unlocked = !!readSaveData(medalsSaveName)[id]?.unlocked;
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
/** Unlocks a medal if not already unlocked
|
|
230
|
+
* - The promise is optional, for when a game wants to know the outcome
|
|
231
|
+
* @return {Promise<boolean>} - Whether the medal is unlocked, right away unless a service like Newgrounds has to confirm */
|
|
232
|
+
unlock()
|
|
233
|
+
{
|
|
234
|
+
if (!medalsPreventUnlock && !this.unlocked)
|
|
235
|
+
{
|
|
236
|
+
ASSERT(medalsSaveName, 'save name must be set');
|
|
237
|
+
this.unlocked = true;
|
|
238
|
+
medalsSave();
|
|
239
|
+
medalsDisplayQueue.push(this);
|
|
240
|
+
}
|
|
241
|
+
return Promise.resolve(this.unlocked);
|
|
242
|
+
}
|
|
243
|
+
|
|
244
|
+
/** Whether the local save holds this medal, it is neither loaded nor written while a service like Newgrounds holds it
|
|
245
|
+
* @return {boolean} */
|
|
246
|
+
isLocal() { return true; }
|
|
247
|
+
|
|
248
|
+
/** Render a medal
|
|
249
|
+
* @param {number} [hidePercent] - How much to slide the medal off screen
|
|
250
|
+
*/
|
|
251
|
+
render(hidePercent=0)
|
|
252
|
+
{
|
|
253
|
+
const context = mainContext;
|
|
254
|
+
const width = min(medalDisplaySize.x, mainCanvasSize.x);
|
|
255
|
+
const height = medalDisplaySize.y;
|
|
256
|
+
const x = mainCanvasSize.x - width;
|
|
257
|
+
const y = -height*hidePercent;
|
|
258
|
+
const backgroundColor = hsl(0,0,.9);
|
|
259
|
+
|
|
260
|
+
// draw containing rect and clip to that region
|
|
261
|
+
context.save();
|
|
262
|
+
context.beginPath();
|
|
263
|
+
context.fillStyle = backgroundColor.toString();
|
|
264
|
+
context.strokeStyle = BLACK.toString();
|
|
265
|
+
const lineWidth = context.lineWidth = 3;
|
|
266
|
+
context.rect(x + lineWidth/2, y + lineWidth/2, width - lineWidth, height - lineWidth); // the whole border shows
|
|
267
|
+
context.fill();
|
|
268
|
+
context.stroke();
|
|
269
|
+
context.clip();
|
|
270
|
+
|
|
271
|
+
// draw the icon
|
|
272
|
+
const gap = vec2(.1, .05).scale(height);
|
|
273
|
+
const iconSize = height - 2*gap.x;
|
|
274
|
+
this.renderIcon(vec2(x + gap.x + iconSize/2, y + height/2), iconSize);
|
|
275
|
+
|
|
276
|
+
// draw the name
|
|
277
|
+
const nameSize = height*.5;
|
|
278
|
+
const descriptionSize = height*.3;
|
|
279
|
+
const pos = vec2(x + iconSize + 2*gap.x, y + gap.y*2 + nameSize/2);
|
|
280
|
+
const textWidth = width - iconSize - 3*gap.x;
|
|
281
|
+
drawTextScreen(this.name, pos, nameSize, BLACK, 0, undefined, 'left', undefined, undefined, textWidth);
|
|
282
|
+
|
|
283
|
+
// draw the description
|
|
284
|
+
pos.y = y + height - gap.y*2 - descriptionSize/2;
|
|
285
|
+
drawTextScreen(this.description, pos, descriptionSize, BLACK, 0, undefined, 'left', undefined, undefined, textWidth);
|
|
286
|
+
context.restore();
|
|
287
|
+
}
|
|
288
|
+
|
|
289
|
+
/** Render the icon for a medal
|
|
290
|
+
* @param {Vector2} pos - Screen space position
|
|
291
|
+
* @param {number} size - Screen space size
|
|
292
|
+
*/
|
|
293
|
+
renderIcon(pos, size)
|
|
294
|
+
{
|
|
295
|
+
// draw the image once it has loaded, or the icon; a broken image would throw
|
|
296
|
+
const image = this.image;
|
|
297
|
+
if (image && image.complete && image.naturalWidth)
|
|
298
|
+
mainContext.drawImage(image, pos.x-size/2, pos.y-size/2, size, size);
|
|
299
|
+
else
|
|
300
|
+
drawTextScreen(this.icon, pos, size*.7, BLACK);
|
|
301
|
+
}
|
|
302
|
+
|
|
303
|
+
}
|
|
304
|
+
|
|
305
|
+
///////////////////////////////////////////////////////////////////////////////
|
|
306
|
+
// Medals setting setters
|
|
307
|
+
|
|
308
|
+
/** Set how long to show medals for in seconds
|
|
309
|
+
* @param {number} time
|
|
310
|
+
* @memberof Settings */
|
|
311
|
+
function setMedalDisplayTime(time) { medalDisplayTime = time; }
|
|
312
|
+
|
|
313
|
+
/** Set how quickly to slide on/off medals in seconds
|
|
314
|
+
* @param {number} time
|
|
315
|
+
* @memberof Settings */
|
|
316
|
+
function setMedalDisplaySlideTime(time) { medalDisplaySlideTime = time; }
|
|
317
|
+
|
|
318
|
+
/** Set size of medal display
|
|
319
|
+
* @param {Vector2} size
|
|
320
|
+
* @memberof Settings */
|
|
321
|
+
function setMedalDisplaySize(size) { medalDisplaySize = size.copy(); }
|
|
322
|
+
|
|
323
|
+
/** Set to stop medals from being unlockable
|
|
324
|
+
* @param {boolean} preventUnlock
|
|
325
|
+
* @memberof Settings */
|
|
326
|
+
function setMedalsPreventUnlock(preventUnlock) { medalsPreventUnlock = preventUnlock; }
|