@adatechnology/game-test-room 0.8.0 → 0.10.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/README.md +2 -0
- package/dist/index.d.ts +15 -2
- package/dist/index.global.js +449 -71
- package/dist/index.global.js.map +1 -1
- package/dist/index.js +85 -5
- package/dist/index.js.map +1 -1
- package/package.json +10 -10
package/dist/index.js
CHANGED
|
@@ -322,6 +322,16 @@ var en = {
|
|
|
322
322
|
"ui.slow": "Slow motion 0.25\xD7",
|
|
323
323
|
"ui.fast": "Time \xD710",
|
|
324
324
|
"ui.tap": "Tap",
|
|
325
|
+
"ui.blast.shelter": "Shelter",
|
|
326
|
+
"ui.blast.fragmentHits": "Fragments",
|
|
327
|
+
"ui.blast.confinement": "Confinement",
|
|
328
|
+
"ui.blast.shelter.hint": "Blasts: walls and other parts between the blast and the target take their share",
|
|
329
|
+
"ui.blast.fragmentHits.hint": "Blasts: the pieces of what breaks fly on and hit what is behind",
|
|
330
|
+
"ui.blast.confinement.hint": "Blasts: pressure builds up in an enclosed room",
|
|
331
|
+
"metric.blast_shelter": "Blast reaching (%)",
|
|
332
|
+
"metric.blast_confinement": "Blast pressure (x)",
|
|
333
|
+
"metric.blast_fragments": "Fragment hits",
|
|
334
|
+
"act.blast_report": "Blast: {shelter}% reached the most sheltered target, pressure x{confinement}, {fragments} fragment hits, {n} targets",
|
|
325
335
|
"ui.quality": "Quality",
|
|
326
336
|
"ui.quality.low": "low",
|
|
327
337
|
"ui.quality.medium": "medium",
|
|
@@ -647,6 +657,16 @@ var ptBR = {
|
|
|
647
657
|
"ui.slow": "C\xE2mera lenta 0,25\xD7",
|
|
648
658
|
"ui.fast": "Tempo \xD710",
|
|
649
659
|
"ui.tap": "Torneira",
|
|
660
|
+
"ui.blast.shelter": "Abrigo",
|
|
661
|
+
"ui.blast.fragmentHits": "Estilha\xE7os",
|
|
662
|
+
"ui.blast.confinement": "Confinamento",
|
|
663
|
+
"ui.blast.shelter.hint": "Explos\xF5es: paredes e outras partes entre a explos\xE3o e o alvo ficam com a sua parte",
|
|
664
|
+
"ui.blast.fragmentHits.hint": "Explos\xF5es: os peda\xE7os do que quebra voam e acertam o que est\xE1 atr\xE1s",
|
|
665
|
+
"ui.blast.confinement.hint": "Explos\xF5es: a press\xE3o sobe num ambiente fechado",
|
|
666
|
+
"metric.blast_shelter": "Explos\xE3o que chegou (%)",
|
|
667
|
+
"metric.blast_confinement": "Press\xE3o da explos\xE3o (x)",
|
|
668
|
+
"metric.blast_fragments": "Estilha\xE7os que acertaram",
|
|
669
|
+
"act.blast_report": "Explos\xE3o: {shelter}% chegou ao alvo mais abrigado, press\xE3o x{confinement}, {fragments} estilha\xE7os acertaram, {n} alvos",
|
|
650
670
|
"ui.quality": "Qualidade",
|
|
651
671
|
"ui.quality.low": "baixa",
|
|
652
672
|
"ui.quality.medium": "m\xE9dia",
|
|
@@ -1372,6 +1392,16 @@ var segmentTouchesBox = (from, to, min, max) => {
|
|
|
1372
1392
|
|
|
1373
1393
|
// src/explosives.ts
|
|
1374
1394
|
var CONE_BLAST_RADIUS = 0.5;
|
|
1395
|
+
var summarizeBlast = (results) => {
|
|
1396
|
+
const reports = results.flatMap((r) => r.blast ? [r.blast] : []);
|
|
1397
|
+
if (reports.length === 0) return void 0;
|
|
1398
|
+
return {
|
|
1399
|
+
shelter: Math.min(...reports.map((r) => r.shelter)),
|
|
1400
|
+
confinement: reports[0].confinement,
|
|
1401
|
+
fragmentHits: reports.reduce((n, r) => n + r.fragmentHits, 0),
|
|
1402
|
+
targets: reports.length
|
|
1403
|
+
};
|
|
1404
|
+
};
|
|
1375
1405
|
var toArray = (vector) => [vector.x, vector.y, vector.z];
|
|
1376
1406
|
function createExplosives(context) {
|
|
1377
1407
|
const { THREE, scene, camera, world, renderer, arsenal, translate, format, action } = context;
|
|
@@ -1518,17 +1548,27 @@ function createExplosives(context) {
|
|
|
1518
1548
|
if (box2.isEmpty()) box2.expandByPoint(object.position);
|
|
1519
1549
|
const at = mostExposedPoint(box2, detonation);
|
|
1520
1550
|
if (!at) continue;
|
|
1521
|
-
|
|
1551
|
+
const results = world.explode(at, detonation.energy * blastEffect(detonation, at).falloff, CONE_BLAST_RADIUS, "player", context.blast());
|
|
1552
|
+
reached += results.length;
|
|
1553
|
+
told(results);
|
|
1522
1554
|
}
|
|
1523
1555
|
return reached;
|
|
1524
1556
|
};
|
|
1557
|
+
const told = (results) => {
|
|
1558
|
+
const summary = summarizeBlast(results);
|
|
1559
|
+
if (!summary) return;
|
|
1560
|
+
context.blasted(summary);
|
|
1561
|
+
action("blast_report", translate("act.blast_report", { shelter: format(summary.shelter * 100, 0), confinement: format(summary.confinement, 2), fragments: summary.fragmentHits, n: summary.targets }), { data: { ...summary } });
|
|
1562
|
+
};
|
|
1525
1563
|
const detonate = (projectile, detonation) => {
|
|
1526
1564
|
const weaponName = context.toolName(projectile.weapon);
|
|
1527
1565
|
const reach = Math.max(detonation.injuryRadius, detonation.lethalRadius);
|
|
1528
|
-
const
|
|
1566
|
+
const results = detonation.energy <= 0 || detonation.cone ? [] : world.explode(detonation.point, detonation.energy, reach, "player", context.blast());
|
|
1567
|
+
const reached = detonation.energy <= 0 ? 0 : detonation.cone ? coneBlast(detonation) : results.length;
|
|
1568
|
+
if (!detonation.cone) told(results);
|
|
1529
1569
|
if (detonation.energy > 0) {
|
|
1530
1570
|
const isPlayed = context.effects.explosion(detonation.explosive, detonation.point, { direction: detonation.direction }) !== null;
|
|
1531
|
-
renderer.explode(detonation.point, detonation.energy, reach, { visual: !isPlayed });
|
|
1571
|
+
renderer.explode(detonation.point, detonation.energy, reach, { visual: !isPlayed, report: results });
|
|
1532
1572
|
}
|
|
1533
1573
|
if (detonation.stunSeconds !== void 0) renderer.emit("flash", detonation.point, [0, 1, 0], 1, 1);
|
|
1534
1574
|
const onPlayer = blastEffect(detonation, toArray(camera.position));
|
|
@@ -1825,7 +1865,7 @@ function createLog(options = {}) {
|
|
|
1825
1865
|
}
|
|
1826
1866
|
|
|
1827
1867
|
// src/metrics.ts
|
|
1828
|
-
var ROOM_METRICS = ["fps", "frame_ms", "draw_calls", "triangles", "objects", "fragments", "particles", "decals"];
|
|
1868
|
+
var ROOM_METRICS = ["fps", "frame_ms", "draw_calls", "triangles", "objects", "fragments", "particles", "decals", "blast_shelter", "blast_confinement", "blast_fragments"];
|
|
1829
1869
|
var WINDOW_S = 0.5;
|
|
1830
1870
|
function createRoomMetrics(sources) {
|
|
1831
1871
|
const wanted = new Set(sources.ids);
|
|
@@ -1862,6 +1902,12 @@ function createRoomMetrics(sources) {
|
|
|
1862
1902
|
const render = ownsRender ? { calls, triangles } : gl.info?.render;
|
|
1863
1903
|
put("draw_calls", render?.calls);
|
|
1864
1904
|
put("triangles", render?.triangles);
|
|
1905
|
+
const blast = sources.blast?.();
|
|
1906
|
+
if (blast) {
|
|
1907
|
+
put("blast_shelter", blast.shelter * 100);
|
|
1908
|
+
put("blast_confinement", blast.confinement);
|
|
1909
|
+
put("blast_fragments", blast.fragmentHits);
|
|
1910
|
+
}
|
|
1865
1911
|
if (!["objects", "fragments", "particles", "decals"].some((id) => wanted.has(id))) return out;
|
|
1866
1912
|
const destruction = sources.destruction.stats();
|
|
1867
1913
|
const fluids = sources.fluids.stats();
|
|
@@ -2415,6 +2461,9 @@ function createPlayer(THREE, o) {
|
|
|
2415
2461
|
const blocked = (x, z) => {
|
|
2416
2462
|
if (Math.abs(x) > o.limit - PLAYER_RADIUS || Math.abs(z) > o.limit - PLAYER_RADIUS) return true;
|
|
2417
2463
|
for (const c of o.colliders) if (x > c[0] - PLAYER_RADIUS && x < c[2] + PLAYER_RADIUS && z > c[1] - PLAYER_RADIUS && z < c[3] + PLAYER_RADIUS) return true;
|
|
2464
|
+
if (o.blockers) {
|
|
2465
|
+
for (const blocked2 of o.blockers) if (blocked2(x, z, PLAYER_RADIUS)) return true;
|
|
2466
|
+
}
|
|
2418
2467
|
return false;
|
|
2419
2468
|
};
|
|
2420
2469
|
const move = (dx, dz) => {
|
|
@@ -3544,6 +3593,8 @@ function createUi(o) {
|
|
|
3544
3593
|
o.onFast(fast);
|
|
3545
3594
|
});
|
|
3546
3595
|
const tapBtn = ctl(t("ui.tap"), () => o.onTap());
|
|
3596
|
+
const blastBtns = ["shelter", "fragmentHits", "confinement"].map((key) => ({ key, b: ctl(t(`ui.blast.${key}`), () => o.onBlast(key)) }));
|
|
3597
|
+
for (const { key, b } of blastBtns) b.title = t(`ui.blast.${key}.hint`);
|
|
3547
3598
|
const qSel = mk2("select");
|
|
3548
3599
|
for (const q of ["low", "medium", "high"]) {
|
|
3549
3600
|
const op = mk2("option", void 0, t(`ui.quality.${q}`));
|
|
@@ -3748,6 +3799,7 @@ function createUi(o) {
|
|
|
3748
3799
|
}
|
|
3749
3800
|
slotsEl.forEach((b, i) => b.classList.toggle("on", i === s.slot));
|
|
3750
3801
|
tapBtn.classList.toggle("on", s.tap);
|
|
3802
|
+
for (const { key: key2, b } of blastBtns) b.classList.toggle("on", s.blast[key2]);
|
|
3751
3803
|
count.textContent = t("ui.objects", { n: s.objects });
|
|
3752
3804
|
const ak = JSON.stringify(s.animations);
|
|
3753
3805
|
if (ak !== lastAnim) {
|
|
@@ -4061,10 +4113,12 @@ function createTestRoom(options) {
|
|
|
4061
4113
|
log.setBeforeRead(flush);
|
|
4062
4114
|
let useHeld = false;
|
|
4063
4115
|
let useFirst = false;
|
|
4116
|
+
const blockers = /* @__PURE__ */ new Set();
|
|
4064
4117
|
const player = createPlayer(THREE, {
|
|
4065
4118
|
camera,
|
|
4066
4119
|
dom,
|
|
4067
4120
|
colliders: arena.colliders,
|
|
4121
|
+
blockers,
|
|
4068
4122
|
limit: arenaSize,
|
|
4069
4123
|
start: arena.playerStart,
|
|
4070
4124
|
hooks: {
|
|
@@ -4247,8 +4301,10 @@ function createTestRoom(options) {
|
|
|
4247
4301
|
film.clear();
|
|
4248
4302
|
fluids.setTap(TAP_ID, false);
|
|
4249
4303
|
};
|
|
4304
|
+
const clearListeners = /* @__PURE__ */ new Set();
|
|
4250
4305
|
const clear = () => {
|
|
4251
4306
|
clearEverything();
|
|
4307
|
+
for (const listener of [...clearListeners]) listener();
|
|
4252
4308
|
restingTops.length = 0;
|
|
4253
4309
|
pending = [];
|
|
4254
4310
|
action("clear", t("act.clear"));
|
|
@@ -4629,6 +4685,12 @@ function createTestRoom(options) {
|
|
|
4629
4685
|
bodies.push({ id: "player", box: new THREE.Box3(new THREE.Vector3(x - PLAYER_RADIUS, feet, z - PLAYER_RADIUS), new THREE.Vector3(x + PLAYER_RADIUS, y + 0.1, z + PLAYER_RADIUS)) });
|
|
4630
4686
|
return bodies;
|
|
4631
4687
|
}
|
|
4688
|
+
let blastOptions = { ...options.blast };
|
|
4689
|
+
let lastBlast;
|
|
4690
|
+
const blastOn = (key) => Boolean(blastOptions[key]);
|
|
4691
|
+
const toggleBlast = (key) => {
|
|
4692
|
+
blastOptions = { ...blastOptions, [key]: blastOn(key) ? false : true };
|
|
4693
|
+
};
|
|
4632
4694
|
const explosives = createExplosives({
|
|
4633
4695
|
THREE,
|
|
4634
4696
|
scene,
|
|
@@ -4643,6 +4705,10 @@ function createTestRoom(options) {
|
|
|
4643
4705
|
toolName,
|
|
4644
4706
|
withoutHeld,
|
|
4645
4707
|
groundAt,
|
|
4708
|
+
blast: () => blastOptions,
|
|
4709
|
+
blasted: (summary) => {
|
|
4710
|
+
lastBlast = summary;
|
|
4711
|
+
},
|
|
4646
4712
|
translate: t,
|
|
4647
4713
|
format: num,
|
|
4648
4714
|
action,
|
|
@@ -5069,7 +5135,7 @@ function createTestRoom(options) {
|
|
|
5069
5135
|
let metricsAcc = 0;
|
|
5070
5136
|
let ownsLoop = false;
|
|
5071
5137
|
const roomMetricIds = options.metrics === false ? [] : options.metrics ?? ROOM_METRICS;
|
|
5072
|
-
const roomMetrics = createRoomMetrics({ gl, destruction: renderer, fluids: fluidView, effects: vfx.world, ids: roomMetricIds });
|
|
5138
|
+
const roomMetrics = createRoomMetrics({ gl, destruction: renderer, fluids: fluidView, effects: vfx.world, ids: roomMetricIds, blast: () => lastBlast });
|
|
5073
5139
|
let qualityName = quality;
|
|
5074
5140
|
const syncContainers = (sdt) => {
|
|
5075
5141
|
for (const e of entries.values()) {
|
|
@@ -5188,6 +5254,7 @@ function createTestRoom(options) {
|
|
|
5188
5254
|
timeScale,
|
|
5189
5255
|
fast: fastForward,
|
|
5190
5256
|
tap: isTapOn(),
|
|
5257
|
+
blast: { shelter: blastOn("shelter"), fragmentHits: blastOn("fragmentHits"), confinement: blastOn("confinement") },
|
|
5191
5258
|
quality: qualityName,
|
|
5192
5259
|
objects: [...entries.values()].filter((e) => !e.arena).length
|
|
5193
5260
|
};
|
|
@@ -5436,6 +5503,14 @@ function createTestRoom(options) {
|
|
|
5436
5503
|
},
|
|
5437
5504
|
log(text, data) {
|
|
5438
5505
|
action("module_note", text, { data });
|
|
5506
|
+
},
|
|
5507
|
+
addBlocker(blocked) {
|
|
5508
|
+
blockers.add(blocked);
|
|
5509
|
+
return () => blockers.delete(blocked);
|
|
5510
|
+
},
|
|
5511
|
+
onClear(listener) {
|
|
5512
|
+
clearListeners.add(listener);
|
|
5513
|
+
return () => clearListeners.delete(listener);
|
|
5439
5514
|
}
|
|
5440
5515
|
};
|
|
5441
5516
|
const lendBench = (store) => ({
|
|
@@ -5703,6 +5778,10 @@ function createTestRoom(options) {
|
|
|
5703
5778
|
heldTilt = rad;
|
|
5704
5779
|
},
|
|
5705
5780
|
toggleTap,
|
|
5781
|
+
blast: () => ({ ...blastOptions }),
|
|
5782
|
+
setBlast: (next) => {
|
|
5783
|
+
blastOptions = { ...blastOptions, ...next };
|
|
5784
|
+
},
|
|
5706
5785
|
pause() {
|
|
5707
5786
|
paused = true;
|
|
5708
5787
|
},
|
|
@@ -5813,6 +5892,7 @@ function createTestRoom(options) {
|
|
|
5813
5892
|
setTool(loadout[index]);
|
|
5814
5893
|
},
|
|
5815
5894
|
onTap: () => toggleTap(),
|
|
5895
|
+
onBlast: (key) => toggleBlast(key),
|
|
5816
5896
|
onPlay: (objectId, clipId) => {
|
|
5817
5897
|
playAnimation(clipId, objectId);
|
|
5818
5898
|
},
|