littlejsengine 1.13.4 → 1.14.2
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/README.md +2 -1
- package/copyToGithub.bat +28 -0
- package/dist/littlejs.d.ts +346 -240
- package/dist/littlejs.esm.js +1370 -723
- package/dist/littlejs.esm.min.js +1 -1
- package/dist/littlejs.js +1350 -709
- package/dist/littlejs.min.js +1 -1
- package/dist/littlejs.release.js +1333 -692
- package/examples/box2d/game.js +1 -1
- package/examples/box2d/gameObjects.js +1 -1
- package/examples/breakout/game.js +30 -25
- package/examples/electron/index.html +2 -2
- package/examples/index.html +207 -96
- package/examples/platformer/gameEffects.js +19 -18
- package/examples/platformer/gameLevel.js +6 -1
- package/examples/shorts/base.html +1 -1
- package/examples/shorts/flappyGame.js +2 -1
- package/examples/shorts/helloWorld.js +1 -1
- package/examples/shorts/music.js +106 -0
- package/examples/shorts/parallax.js +71 -0
- package/examples/shorts/piano.js +7 -8
- package/examples/shorts/postProcess.js +25 -8
- package/examples/shorts/shapes.js +1 -9
- package/examples/shorts/song.mp3 +0 -0
- package/examples/shorts/uiSystem.js +15 -8
- package/examples/starter/index.html +2 -2
- package/examples/stress/index.html +8 -3
- package/examples/style.css +14 -4
- package/examples/uiSystem/game.js +11 -11
- package/package.json +1 -1
- package/plugins/box2d.js +10 -8
- package/plugins/drawUtilities.js +5 -5
- package/plugins/newgrounds.js +6 -6
- package/plugins/pluginExport.js +1 -1
- package/plugins/uiSystem.js +103 -79
- package/plugins/zzfxm.js +10 -10
- package/reference.md +90 -54
- package/src/engine.js +22 -22
- package/src/engineAudio.js +284 -109
- package/src/engineBuild.js +9 -9
- package/src/engineDebug.js +26 -26
- package/src/engineDraw.js +148 -97
- package/src/engineExport.js +22 -16
- package/src/engineInput.js +57 -67
- package/src/engineMedals.js +25 -25
- package/src/engineObject.js +25 -22
- package/src/engineParticles.js +59 -59
- package/src/engineRelease.js +1 -1
- package/src/engineSettings.js +20 -13
- package/src/engineTileLayer.js +34 -34
- package/src/engineUtilities.js +62 -55
- package/src/engineWebGL.js +447 -65
- /package/examples/shorts/{playSound.js → sound.js} +0 -0
package/plugins/box2d.js
CHANGED
|
@@ -88,14 +88,14 @@ class Box2dObject extends EngineObject
|
|
|
88
88
|
if (this.tileInfo)
|
|
89
89
|
super.render();
|
|
90
90
|
else
|
|
91
|
-
this.drawFixtures(this.color, this.lineColor, this.lineWidth
|
|
91
|
+
this.drawFixtures(this.color, this.lineColor, this.lineWidth);
|
|
92
92
|
}
|
|
93
93
|
|
|
94
94
|
/** Render debug info */
|
|
95
95
|
renderDebugInfo()
|
|
96
96
|
{
|
|
97
97
|
const isAsleep = !this.getIsAwake();
|
|
98
|
-
const isStatic = this.getBodyType()
|
|
98
|
+
const isStatic = this.getBodyType() === box2d.bodyTypeStatic;
|
|
99
99
|
const color = rgb(isAsleep?1:0, isAsleep?1:0, isStatic?1:0, .5);
|
|
100
100
|
this.drawFixtures(color);
|
|
101
101
|
}
|
|
@@ -1563,7 +1563,7 @@ class Box2dPlugin
|
|
|
1563
1563
|
queryCallback.ReportFixture = function(fixturePointer)
|
|
1564
1564
|
{
|
|
1565
1565
|
const fixture = box2d.instance.wrapPointer(fixturePointer, box2d.instance.b2Fixture);
|
|
1566
|
-
if (dynamicOnly && fixture.GetBody().GetType()
|
|
1566
|
+
if (dynamicOnly && fixture.GetBody().GetType() !== box2d.instance.b2_dynamicBody)
|
|
1567
1567
|
return true; // continue getting results
|
|
1568
1568
|
if (!fixture.TestPoint(box2d.vec2dTo(pos)))
|
|
1569
1569
|
return true; // continue getting results
|
|
@@ -1592,7 +1592,7 @@ class Box2dPlugin
|
|
|
1592
1592
|
* @param {Color} [lineColor]
|
|
1593
1593
|
* @param {number} [lineWidth]
|
|
1594
1594
|
* @param {CanvasRenderingContext2D} [context] */
|
|
1595
|
-
drawFixture(fixture, pos, angle, color=WHITE, lineColor=BLACK, lineWidth=.1, context
|
|
1595
|
+
drawFixture(fixture, pos, angle, color=WHITE, lineColor=BLACK, lineWidth=.1, context)
|
|
1596
1596
|
{
|
|
1597
1597
|
const shape = box2d.castObjectType(fixture.GetShape());
|
|
1598
1598
|
switch (shape.GetType())
|
|
@@ -1602,20 +1602,20 @@ class Box2dPlugin
|
|
|
1602
1602
|
let points = [];
|
|
1603
1603
|
for (let i=shape.GetVertexCount(); i--;)
|
|
1604
1604
|
points.push(box2d.vec2From(shape.GetVertex(i)));
|
|
1605
|
-
drawPoly(points, color, lineWidth, lineColor, pos, angle
|
|
1605
|
+
drawPoly(points, color, lineWidth, lineColor, pos, angle);
|
|
1606
1606
|
break;
|
|
1607
1607
|
}
|
|
1608
1608
|
case box2d.instance.b2Shape.e_circle:
|
|
1609
1609
|
{
|
|
1610
1610
|
const radius = shape.get_m_radius();
|
|
1611
|
-
drawCircle(pos, radius, color, lineWidth, lineColor
|
|
1611
|
+
drawCircle(pos, radius, color, lineWidth, lineColor);
|
|
1612
1612
|
break;
|
|
1613
1613
|
}
|
|
1614
1614
|
case box2d.instance.b2Shape.e_edge:
|
|
1615
1615
|
{
|
|
1616
1616
|
const v1 = box2d.vec2From(shape.get_m_vertex1());
|
|
1617
1617
|
const v2 = box2d.vec2From(shape.get_m_vertex2());
|
|
1618
|
-
drawLine(v1, v2, lineWidth, lineColor, pos, angle
|
|
1618
|
+
drawLine(v1, v2, lineWidth, lineColor, pos, angle);
|
|
1619
1619
|
break;
|
|
1620
1620
|
}
|
|
1621
1621
|
}
|
|
@@ -1694,7 +1694,9 @@ class Box2dPlugin
|
|
|
1694
1694
|
}
|
|
1695
1695
|
|
|
1696
1696
|
///////////////////////////////////////////////////////////////////////////////
|
|
1697
|
-
/** Box2d Init - Call with await
|
|
1697
|
+
/** Box2d Init - Call with await to init box2d
|
|
1698
|
+
* @example
|
|
1699
|
+
* await box2dInit();
|
|
1698
1700
|
* @return {Promise<Box2dPlugin>}
|
|
1699
1701
|
* @memberof Box2D */
|
|
1700
1702
|
async function box2dInit()
|
package/plugins/drawUtilities.js
CHANGED
|
@@ -24,7 +24,7 @@ function drawNineSliceScreen(pos, size, startTile, borderSize=32, extraSpace=2,
|
|
|
24
24
|
}
|
|
25
25
|
|
|
26
26
|
/** Draw a scalable nine-slice UI element in world space
|
|
27
|
-
* This function can apply color and additive color if
|
|
27
|
+
* This function can apply color and additive color if WebGL is enabled
|
|
28
28
|
* @param {Vector2} pos - World space position
|
|
29
29
|
* @param {Vector2} size - World space size
|
|
30
30
|
* @param {TileInfo} startTile - Starting tile for the nine-slice pattern
|
|
@@ -53,9 +53,9 @@ function drawNineSlice(pos, size, startTile, color, borderSize=1, additiveColor,
|
|
|
53
53
|
{
|
|
54
54
|
// sides
|
|
55
55
|
const horizontal = i%2;
|
|
56
|
-
const sidePos = cornerOffset.multiply(vec2(horizontal?i
|
|
56
|
+
const sidePos = cornerOffset.multiply(vec2(horizontal?i===1?1:-1:0, horizontal?0:i?-1:1));
|
|
57
57
|
const sideSize = vec2(horizontal ? borderSize : centerSize.x, horizontal ? centerSize.y : borderSize);
|
|
58
|
-
const sideTile = centerTile.offset(startTile.size.multiply(vec2(i
|
|
58
|
+
const sideTile = centerTile.offset(startTile.size.multiply(vec2(i===1?1:i===3?-1:0,i===0?-flip:i===2?flip:0)))
|
|
59
59
|
drawTile(pos.add(sidePos.rotate(rotateAngle)), sideSize, sideTile, color, angle, false, additiveColor, useWebGL, screenSpace, context);
|
|
60
60
|
}
|
|
61
61
|
for (let i=4; i--;)
|
|
@@ -84,7 +84,7 @@ function drawThreeSliceScreen(pos, size, startTile, borderSize=32, extraSpace=2,
|
|
|
84
84
|
}
|
|
85
85
|
|
|
86
86
|
/** Draw a scalable three-slice UI element in world space
|
|
87
|
-
* This function can apply color and additive color if
|
|
87
|
+
* This function can apply color and additive color if WebGL is enabled
|
|
88
88
|
* @param {Vector2} pos - World space position
|
|
89
89
|
* @param {Vector2} size - World space size
|
|
90
90
|
* @param {TileInfo} startTile - Starting tile for the three-slice pattern
|
|
@@ -116,7 +116,7 @@ function drawThreeSlice(pos, size, startTile, color, borderSize=1, additiveColor
|
|
|
116
116
|
// sides
|
|
117
117
|
const a = angle + i*PI/2;
|
|
118
118
|
const horizontal = i%2;
|
|
119
|
-
const sidePos = cornerOffset.multiply(vec2(horizontal?i
|
|
119
|
+
const sidePos = cornerOffset.multiply(vec2(horizontal?i===1?1:-1:0, horizontal?0:i?-flip:flip));
|
|
120
120
|
const sideSize = vec2(horizontal ? centerSize.y : centerSize.x, borderSize);
|
|
121
121
|
drawTile(pos.add(sidePos.rotate(rotateAngle)), sideSize, sideTile, color, a, false, additiveColor, useWebGL, screenSpace, context);
|
|
122
122
|
}
|
package/plugins/newgrounds.js
CHANGED
|
@@ -23,11 +23,11 @@ let newgrounds;
|
|
|
23
23
|
class NewgroundsMedal extends Medal
|
|
24
24
|
{
|
|
25
25
|
/** Create a newgrounds medal object and adds it to the list of medals
|
|
26
|
-
* @param {
|
|
27
|
-
* @param {
|
|
28
|
-
* @param {
|
|
29
|
-
* @param {
|
|
30
|
-
* @param {
|
|
26
|
+
* @param {number} id - The unique identifier of the medal
|
|
27
|
+
* @param {string} name - Name of the medal
|
|
28
|
+
* @param {string} [description] - Description of the medal
|
|
29
|
+
* @param {string} [icon] - Icon for the medal
|
|
30
|
+
* @param {string} [src] - Image location for the medal
|
|
31
31
|
*/
|
|
32
32
|
constructor(id, name, description, icon, src)
|
|
33
33
|
{ super(id, name, description, icon, src); }
|
|
@@ -119,7 +119,7 @@ class NewgroundsPlugin
|
|
|
119
119
|
* @param {number} id - The scoreboard id
|
|
120
120
|
* @param {string} [user] - A user's id or name
|
|
121
121
|
* @param {number} [social] - If true, only social scores will be loaded
|
|
122
|
-
* @param {number} [skip] - Number of scores to skip
|
|
122
|
+
* @param {number} [skip] - Number of scores to skip over
|
|
123
123
|
* @param {number} [limit] - Number of scores to include in the list
|
|
124
124
|
* @return {Object} - The response JSON object
|
|
125
125
|
*/
|
package/plugins/pluginExport.js
CHANGED
package/plugins/uiSystem.js
CHANGED
|
@@ -40,11 +40,11 @@ class UISystemPlugin
|
|
|
40
40
|
/** @property {Color} - Default text color for UI elements */
|
|
41
41
|
this.defaultTextColor = BLACK;
|
|
42
42
|
/** @property {Color} - Default button color for UI elements */
|
|
43
|
-
this.defaultButtonColor = hsl(0,0,.
|
|
43
|
+
this.defaultButtonColor = hsl(0,0,.7);
|
|
44
44
|
/** @property {Color} - Default hover color for UI elements */
|
|
45
|
-
this.defaultHoverColor = hsl(0,0,.
|
|
45
|
+
this.defaultHoverColor = hsl(0,0,.9);
|
|
46
46
|
/** @property {Color} - Default color for disabled UI elements */
|
|
47
|
-
this.defaultDisabledColor = hsl(0,0,.
|
|
47
|
+
this.defaultDisabledColor = hsl(0,0,.3);
|
|
48
48
|
/** @property {number} - Default line width for UI elements */
|
|
49
49
|
this.defaultLineWidth = 4;
|
|
50
50
|
/** @property {number} - Default rounded rect corner radius for UI elements */
|
|
@@ -64,16 +64,16 @@ class UISystemPlugin
|
|
|
64
64
|
|
|
65
65
|
engineAddPlugin(uiUpdate, uiRender);
|
|
66
66
|
|
|
67
|
-
function updateInvisible(o)
|
|
68
|
-
{
|
|
69
|
-
for (const c of o.children)
|
|
70
|
-
updateInvisible(c);
|
|
71
|
-
o.updateInvisible();
|
|
72
|
-
}
|
|
73
|
-
|
|
74
67
|
// setup recursive update and render
|
|
75
68
|
function uiUpdate()
|
|
76
69
|
{
|
|
70
|
+
function updateInvisibleObject(o)
|
|
71
|
+
{
|
|
72
|
+
// update invisible objects
|
|
73
|
+
for (const c of o.children)
|
|
74
|
+
updateInvisibleObject(c);
|
|
75
|
+
o.updateInvisible();
|
|
76
|
+
}
|
|
77
77
|
function updateObject(o)
|
|
78
78
|
{
|
|
79
79
|
if (o.visible)
|
|
@@ -87,7 +87,7 @@ class UISystemPlugin
|
|
|
87
87
|
o.update();
|
|
88
88
|
}
|
|
89
89
|
else
|
|
90
|
-
|
|
90
|
+
updateInvisibleObject(o);
|
|
91
91
|
}
|
|
92
92
|
uiSystem.uiObjects.forEach(o=> o.parent || updateObject(o));
|
|
93
93
|
}
|
|
@@ -113,7 +113,7 @@ class UISystemPlugin
|
|
|
113
113
|
* @param {Color} [color=uiSystem.defaultColor]
|
|
114
114
|
* @param {number} [lineWidth=uiSystem.defaultLineWidth]
|
|
115
115
|
* @param {Color} [lineColor=uiSystem.defaultLineColor]
|
|
116
|
-
* @param {number} [
|
|
116
|
+
* @param {number} [cornerRadius=uiSystem.defaultCornerRadius] */
|
|
117
117
|
drawRect(pos, size, color=uiSystem.defaultColor, lineWidth=uiSystem.defaultLineWidth, lineColor=uiSystem.defaultLineColor, cornerRadius=uiSystem.defaultCornerRadius)
|
|
118
118
|
{
|
|
119
119
|
const context = uiSystem.uiContext;
|
|
@@ -188,32 +188,40 @@ class UIObject
|
|
|
188
188
|
constructor(pos=vec2(), size=vec2())
|
|
189
189
|
{
|
|
190
190
|
/** @property {Vector2} - Local position of the object */
|
|
191
|
-
this.localPos
|
|
191
|
+
this.localPos = pos.copy();
|
|
192
192
|
/** @property {Vector2} - Screen space position of the object */
|
|
193
|
-
this.pos
|
|
193
|
+
this.pos = pos.copy();
|
|
194
194
|
/** @property {Vector2} - Screen space size of the object */
|
|
195
|
-
this.size
|
|
196
|
-
/** @property {Color} -
|
|
197
|
-
this.color
|
|
198
|
-
/** @property {
|
|
199
|
-
this.
|
|
200
|
-
/** @property {Color} -
|
|
195
|
+
this.size = size.copy();
|
|
196
|
+
/** @property {Color} - Color of the object */
|
|
197
|
+
this.color = uiSystem.defaultColor;
|
|
198
|
+
/** @property {string} - Text for this ui object */
|
|
199
|
+
this.text = undefined;
|
|
200
|
+
/** @property {Color} - Color when disabled */
|
|
201
|
+
this.disabledColor = uiSystem.defaultDisabledColor;
|
|
202
|
+
/** @property {boolean} - Is this object disabled? */
|
|
203
|
+
this.disabled = false;
|
|
204
|
+
/** @property {Color} - Color for text */
|
|
205
|
+
this.textColor = uiSystem.defaultTextColor;
|
|
206
|
+
/** @property {Color} - Color used when hovering over the object */
|
|
201
207
|
this.hoverColor = uiSystem.defaultHoverColor;
|
|
202
|
-
/** @property {Color} -
|
|
203
|
-
this.lineColor
|
|
204
|
-
/** @property {number} -
|
|
205
|
-
this.lineWidth
|
|
206
|
-
/** @property {
|
|
207
|
-
this.
|
|
208
|
-
/** @property {
|
|
209
|
-
this.
|
|
210
|
-
/** @property {
|
|
211
|
-
this.
|
|
212
|
-
/** @property {
|
|
213
|
-
this.
|
|
214
|
-
/** @property {UIObject} - this object's
|
|
215
|
-
this.
|
|
216
|
-
/** @property {
|
|
208
|
+
/** @property {Color} - Color for line drawing */
|
|
209
|
+
this.lineColor = uiSystem.defaultLineColor;
|
|
210
|
+
/** @property {number} - Width for line drawing */
|
|
211
|
+
this.lineWidth = uiSystem.defaultLineWidth;
|
|
212
|
+
/** @property {number} - Corner radius for rounded rects */
|
|
213
|
+
this.cornerRadius = uiSystem.defaultCornerRadius;
|
|
214
|
+
/** @property {string} - Font for this objecct */
|
|
215
|
+
this.font = uiSystem.defaultFont;
|
|
216
|
+
/** @property {number} - Override for text height */
|
|
217
|
+
this.textHeight = undefined;
|
|
218
|
+
/** @property {boolean} - Should this object be drawn */
|
|
219
|
+
this.visible = true;
|
|
220
|
+
/** @property {Array<UIObject>} - A list of this object's children */
|
|
221
|
+
this.children = [];
|
|
222
|
+
/** @property {UIObject} - This object's parent, position is in parent space */
|
|
223
|
+
this.parent = undefined;
|
|
224
|
+
/** @property {number} - Extra size added to make small buttons easier to touch on mobile devices */
|
|
217
225
|
this.extraTouchSize = 0;
|
|
218
226
|
/** @property {Sound} - Sound when interactive element is pressed */
|
|
219
227
|
this.soundPress = uiSystem.defaultSoundPress;
|
|
@@ -245,7 +253,7 @@ class UIObject
|
|
|
245
253
|
*/
|
|
246
254
|
removeChild(child)
|
|
247
255
|
{
|
|
248
|
-
ASSERT(child.parent
|
|
256
|
+
ASSERT(child.parent === this && this.children.includes(child));
|
|
249
257
|
this.children.splice(this.children.indexOf(child), 1);
|
|
250
258
|
child.parent = undefined;
|
|
251
259
|
}
|
|
@@ -298,7 +306,7 @@ class UIObject
|
|
|
298
306
|
this.mouseIsHeld = false;
|
|
299
307
|
}
|
|
300
308
|
|
|
301
|
-
if (this.mouseIsOver
|
|
309
|
+
if (this.mouseIsOver !== mouseWasOver)
|
|
302
310
|
this.mouseIsOver ? this.onEnter() : this.onLeave();
|
|
303
311
|
}
|
|
304
312
|
|
|
@@ -309,7 +317,7 @@ class UIObject
|
|
|
309
317
|
uiSystem.drawRect(this.pos, this.size, this.color, this.lineWidth, this.lineColor, this.cornerRadius);
|
|
310
318
|
}
|
|
311
319
|
|
|
312
|
-
/** Special update
|
|
320
|
+
/** Special update when object is not visible */
|
|
313
321
|
updateInvisible()
|
|
314
322
|
{
|
|
315
323
|
// reset input state when not visible
|
|
@@ -317,28 +325,22 @@ class UIObject
|
|
|
317
325
|
}
|
|
318
326
|
|
|
319
327
|
/** Called when the mouse enters the object */
|
|
320
|
-
onEnter()
|
|
321
|
-
{}
|
|
328
|
+
onEnter() {}
|
|
322
329
|
|
|
323
330
|
/** Called when the mouse leaves the object */
|
|
324
|
-
onLeave()
|
|
325
|
-
{}
|
|
331
|
+
onLeave() {}
|
|
326
332
|
|
|
327
333
|
/** Called when the mouse is pressed while over the object */
|
|
328
|
-
onPress()
|
|
329
|
-
{}
|
|
334
|
+
onPress() {}
|
|
330
335
|
|
|
331
336
|
/** Called when the mouse is released while over the object */
|
|
332
|
-
onRelease()
|
|
333
|
-
{}
|
|
337
|
+
onRelease() {}
|
|
334
338
|
|
|
335
339
|
/** Called when user clicks on this object */
|
|
336
|
-
onClick()
|
|
337
|
-
{}
|
|
340
|
+
onClick() {}
|
|
338
341
|
|
|
339
342
|
/** Called when the state of this object changes */
|
|
340
|
-
onChange()
|
|
341
|
-
{}
|
|
343
|
+
onChange() {}
|
|
342
344
|
};
|
|
343
345
|
|
|
344
346
|
///////////////////////////////////////////////////////////////////////////////
|
|
@@ -359,13 +361,13 @@ class UIText extends UIObject
|
|
|
359
361
|
{
|
|
360
362
|
super(pos, size);
|
|
361
363
|
|
|
362
|
-
|
|
364
|
+
// set properties
|
|
363
365
|
this.text = text;
|
|
364
|
-
/** @property {string} */
|
|
365
366
|
this.align = align;
|
|
367
|
+
this.font = font;
|
|
366
368
|
|
|
367
|
-
|
|
368
|
-
this.lineWidth = 0;
|
|
369
|
+
// make text not outlined by default
|
|
370
|
+
this.lineWidth = 0;
|
|
369
371
|
}
|
|
370
372
|
render()
|
|
371
373
|
{
|
|
@@ -392,13 +394,14 @@ class UITile extends UIObject
|
|
|
392
394
|
constructor(pos, size, tileInfo, color=WHITE, angle=0, mirror=false)
|
|
393
395
|
{
|
|
394
396
|
super(pos, size);
|
|
395
|
-
|
|
396
397
|
/** @property {TileInfo} - Tile image to use */
|
|
397
398
|
this.tileInfo = tileInfo;
|
|
398
399
|
/** @property {number} - Angle to rotate in radians */
|
|
399
400
|
this.angle = angle;
|
|
400
401
|
/** @property {boolean} - Should it be mirrored? */
|
|
401
402
|
this.mirror = mirror;
|
|
403
|
+
|
|
404
|
+
// set properties
|
|
402
405
|
this.color = color;
|
|
403
406
|
}
|
|
404
407
|
render()
|
|
@@ -424,22 +427,20 @@ class UIButton extends UIObject
|
|
|
424
427
|
{
|
|
425
428
|
super(pos, size);
|
|
426
429
|
|
|
427
|
-
|
|
430
|
+
// set properties
|
|
428
431
|
this.text = text;
|
|
429
|
-
/** @property {Color} */
|
|
430
|
-
this.disabledColor = uiSystem.defaultDisabledColor;
|
|
431
|
-
/** @property {boolean} */
|
|
432
|
-
this.disabled = false;
|
|
433
|
-
this.interactive = true;
|
|
434
432
|
this.color = color;
|
|
433
|
+
this.interactive = true;
|
|
435
434
|
}
|
|
436
435
|
render()
|
|
437
436
|
{
|
|
437
|
+
// draw the button
|
|
438
438
|
const lineColor = this.mouseIsHeld && !this.disabled ? this.color : this.lineColor;
|
|
439
439
|
const color = this.disabled ? this.disabledColor : this.mouseIsOver ? this.hoverColor : this.color;
|
|
440
440
|
uiSystem.drawRect(this.pos, this.size, color, this.lineWidth, lineColor, this.cornerRadius);
|
|
441
441
|
|
|
442
|
-
|
|
442
|
+
// draw the text
|
|
443
|
+
const textScale = .8; // scale text to fit
|
|
443
444
|
const textSize = vec2(this.size.x, this.textHeight || this.size.y*textScale);
|
|
444
445
|
uiSystem.drawText(this.text, this.pos, textSize,
|
|
445
446
|
this.textColor, 0, undefined, this.align, this.font);
|
|
@@ -457,13 +458,18 @@ class UICheckbox extends UIObject
|
|
|
457
458
|
* @param {Vector2} [pos]
|
|
458
459
|
* @param {Vector2} [size]
|
|
459
460
|
* @param {boolean} [checked]
|
|
461
|
+
* @param {string} [text]
|
|
462
|
+
* @param {Color} [color=uiSystem.defaultButtonColor]
|
|
460
463
|
*/
|
|
461
|
-
constructor(pos, size, checked=false)
|
|
464
|
+
constructor(pos, size, checked=false, text='', color=uiSystem.defaultButtonColor)
|
|
462
465
|
{
|
|
463
466
|
super(pos, size);
|
|
464
|
-
|
|
465
|
-
/** @property {boolean} */
|
|
467
|
+
/** @property {boolean} - Current percentage value of this scrollbar 0-1 */
|
|
466
468
|
this.checked = checked;
|
|
469
|
+
|
|
470
|
+
// set properties
|
|
471
|
+
this.text = text;
|
|
472
|
+
this.color = color;
|
|
467
473
|
this.interactive = true;
|
|
468
474
|
}
|
|
469
475
|
onClick()
|
|
@@ -473,14 +479,24 @@ class UICheckbox extends UIObject
|
|
|
473
479
|
}
|
|
474
480
|
render()
|
|
475
481
|
{
|
|
476
|
-
const color = this.mouseIsOver? this.hoverColor : this.color;
|
|
482
|
+
const color = this.disabled ? this.disabledColor : this.mouseIsOver ? this.hoverColor : this.color;
|
|
477
483
|
uiSystem.drawRect(this.pos, this.size, color, this.lineWidth, this.lineColor, this.cornerRadius);
|
|
478
484
|
if (this.checked)
|
|
479
485
|
{
|
|
480
|
-
|
|
481
|
-
|
|
482
|
-
|
|
486
|
+
const p = this.cornerRadius / min(this.size.x, this.size.y) * 2;
|
|
487
|
+
const length = lerp(1, 2**.5/2, p) / 2;
|
|
488
|
+
let s = this.size.scale(length);
|
|
489
|
+
uiSystem.drawLine(this.pos.add(s.multiply(vec2(-1))), this.pos.add(s.multiply(vec2(1))), this.lineWidth, this.lineColor);
|
|
490
|
+
uiSystem.drawLine(this.pos.add(s.multiply(vec2(-1,1))), this.pos.add(s.multiply(vec2(1,-1))), this.lineWidth, this.lineColor);
|
|
483
491
|
}
|
|
492
|
+
|
|
493
|
+
// draw the text to the right side of the checkbox
|
|
494
|
+
const textScale = .8; // scale text to fit
|
|
495
|
+
const gapScale = .55;
|
|
496
|
+
const textSize = vec2(this.size.x, this.textHeight || this.size.y*textScale);
|
|
497
|
+
const pos = this.pos.add(vec2(this.size.x*gapScale,0));
|
|
498
|
+
uiSystem.drawText(this.text, pos, textSize,
|
|
499
|
+
this.textColor, 0, undefined, 'left', this.font);
|
|
484
500
|
}
|
|
485
501
|
}
|
|
486
502
|
|
|
@@ -503,43 +519,51 @@ class UIScrollbar extends UIObject
|
|
|
503
519
|
{
|
|
504
520
|
super(pos, size);
|
|
505
521
|
|
|
506
|
-
/** @property {number} */
|
|
522
|
+
/** @property {number} - Current percentage value of this scrollbar 0-1 */
|
|
507
523
|
this.value = value;
|
|
508
|
-
/** @property {
|
|
509
|
-
this.text = text;
|
|
510
|
-
/** @property {Color} */
|
|
524
|
+
/** @property {Color} - Color for the handle part of the scrollbar */
|
|
511
525
|
this.handleColor = handleColor;
|
|
526
|
+
|
|
527
|
+
// set properties
|
|
528
|
+
this.text = text;
|
|
512
529
|
this.color = color;
|
|
513
530
|
this.interactive = true;
|
|
514
531
|
}
|
|
515
532
|
update()
|
|
516
533
|
{
|
|
517
534
|
super.update();
|
|
518
|
-
if (this.mouseIsHeld)
|
|
535
|
+
if (this.mouseIsHeld && this.interactive)
|
|
519
536
|
{
|
|
537
|
+
// check if value changed
|
|
520
538
|
const handleSize = vec2(this.size.y);
|
|
521
539
|
const handleWidth = this.size.x - handleSize.x;
|
|
522
540
|
const p1 = this.pos.x - handleWidth/2;
|
|
523
541
|
const p2 = this.pos.x + handleWidth/2;
|
|
524
542
|
const oldValue = this.value;
|
|
525
543
|
this.value = percent(mousePosScreen.x, p1, p2);
|
|
526
|
-
this.value
|
|
544
|
+
this.value === oldValue || this.onChange();
|
|
527
545
|
}
|
|
528
546
|
}
|
|
529
547
|
render()
|
|
530
548
|
{
|
|
531
|
-
|
|
532
|
-
const
|
|
549
|
+
// draw the scrollbar background
|
|
550
|
+
const lineColor = this.interactive && this.mouseIsHeld && !this.disabled ?
|
|
551
|
+
this.color : this.lineColor;
|
|
552
|
+
const color = this.disabled ? this.disabledColor :
|
|
553
|
+
this.interactive && this.mouseIsHeld ? this.hoverColor : this.color;
|
|
533
554
|
uiSystem.drawRect(this.pos, this.size, color, this.lineWidth, lineColor, this.cornerRadius);
|
|
534
555
|
|
|
556
|
+
// draw the scrollbar handle
|
|
535
557
|
const handleSize = vec2(this.size.y);
|
|
536
558
|
const handleWidth = this.size.x - handleSize.x;
|
|
537
559
|
const p1 = this.pos.x - handleWidth/2;
|
|
538
560
|
const p2 = this.pos.x + handleWidth/2;
|
|
539
561
|
const handlePos = vec2(lerp(p1, p2, this.value), this.pos.y);
|
|
540
|
-
const
|
|
541
|
-
|
|
562
|
+
const handleColor = this.disabled ? this.disabledColor :
|
|
563
|
+
this.interactive && this.mouseIsHeld ? this.color : this.handleColor;
|
|
564
|
+
uiSystem.drawRect(handlePos, handleSize, handleColor, this.lineWidth, this.lineColor, this.cornerRadius);
|
|
542
565
|
|
|
566
|
+
// draw the text on the scrollbar
|
|
543
567
|
const textScale = .8; // scale text to fit in scrollbar
|
|
544
568
|
const textSize = vec2(this.size.x, this.textHeight || this.size.y*textScale);
|
|
545
569
|
uiSystem.drawText(this.text, this.pos, textSize,
|
package/plugins/zzfxm.js
CHANGED
|
@@ -46,16 +46,16 @@ class ZzFXMusic extends Sound
|
|
|
46
46
|
if (!soundEnable || headlessMode) return;
|
|
47
47
|
this.randomness = 0;
|
|
48
48
|
this.sampleChannels = zzfxM(...zzfxMusic);
|
|
49
|
-
this.sampleRate =
|
|
49
|
+
this.sampleRate = audioDefaultSampleRate;
|
|
50
50
|
}
|
|
51
51
|
|
|
52
|
-
/** Play the music
|
|
53
|
-
* @param {number} [volume
|
|
54
|
-
* @param {boolean} [loop] -
|
|
52
|
+
/** Play the music that loops by default
|
|
53
|
+
* @param {number} [volume] - Volume to play the music at
|
|
54
|
+
* @param {boolean} [loop] - Should the music loop?
|
|
55
55
|
* @return {AudioBufferSourceNode} - The audio source node
|
|
56
56
|
*/
|
|
57
|
-
playMusic(volume, loop=
|
|
58
|
-
{ return super.play(undefined, volume, 1,
|
|
57
|
+
playMusic(volume=1, loop=true)
|
|
58
|
+
{ return super.play(undefined, volume, 1, 0, loop); }
|
|
59
59
|
}
|
|
60
60
|
|
|
61
61
|
///////////////////////////////////////////////////////////////////////////////
|
|
@@ -89,7 +89,7 @@ function zzfxM(instruments, patterns, sequence, BPM = 125)
|
|
|
89
89
|
let panning = 0;
|
|
90
90
|
let hasMore = 1;
|
|
91
91
|
let sampleCache = {};
|
|
92
|
-
let beatLength =
|
|
92
|
+
let beatLength = audioDefaultSampleRate / BPM * 60 >> 2;
|
|
93
93
|
|
|
94
94
|
// for each channel in order until there are no more
|
|
95
95
|
for (; hasMore; channelIndex++) {
|
|
@@ -108,15 +108,15 @@ function zzfxM(instruments, patterns, sequence, BPM = 125)
|
|
|
108
108
|
// get next offset, use the length of first channel
|
|
109
109
|
nextSampleOffset = outSampleOffset + (patterns[patternIndex][0].length - 2 - (notFirstBeat?0:1)) * beatLength;
|
|
110
110
|
// for each beat in pattern, plus one extra if end of sequence
|
|
111
|
-
isSequenceEnd = sequenceIndex
|
|
111
|
+
isSequenceEnd = sequenceIndex === sequence.length - 1;
|
|
112
112
|
for (i = 2, k = outSampleOffset; i < patternChannel.length + isSequenceEnd; notFirstBeat = ++i) {
|
|
113
113
|
|
|
114
114
|
// <channel-note>
|
|
115
115
|
note = patternChannel[i];
|
|
116
116
|
|
|
117
117
|
// stop if end, different instrument or new note
|
|
118
|
-
stop = i
|
|
119
|
-
instrument
|
|
118
|
+
stop = i === patternChannel.length + isSequenceEnd - 1 && isSequenceEnd ||
|
|
119
|
+
instrument !== (patternChannel[0] || 0) || note | 0;
|
|
120
120
|
|
|
121
121
|
// fill buffer with samples for previous beat, most cpu intensive part
|
|
122
122
|
for (j = 0; j < beatLength && notFirstBeat;
|