quake2ts 0.0.506 → 0.0.510

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.
@@ -2384,6 +2384,10 @@ function pickupPowerup(client, item, time) {
2384
2384
  powerupId = PowerupId.DoubleDamage;
2385
2385
  icon = "p_double";
2386
2386
  break;
2387
+ case "item_invisibility":
2388
+ powerupId = PowerupId.Invisibility;
2389
+ icon = "p_invisibility";
2390
+ break;
2387
2391
  }
2388
2392
  if (powerupId) {
2389
2393
  const expiresAt = inventory.powerups.get(powerupId);
@@ -2399,6 +2403,9 @@ function pickupPowerup(client, item, time) {
2399
2403
  client.enviro_time = newExpiresAt / 1e3;
2400
2404
  } else if (powerupId === PowerupId.Rebreather) {
2401
2405
  client.breather_time = newExpiresAt / 1e3;
2406
+ } else if (powerupId === PowerupId.Invisibility) {
2407
+ client.invisible_time = newExpiresAt / 1e3;
2408
+ client.invisibility_fade_time = newExpiresAt / 1e3 - 3;
2402
2409
  }
2403
2410
  setPickup(inventory, icon, time);
2404
2411
  return true;
@@ -3153,6 +3160,20 @@ function visible(self, other, trace, options) {
3153
3160
  if ((other.flags & FL_NOVISIBLE) !== 0) {
3154
3161
  return false;
3155
3162
  }
3163
+ if (other.client && options?.timeSeconds !== void 0) {
3164
+ if (other.client.invisible_time && other.client.invisible_time > options.timeSeconds) {
3165
+ if (other.client.invisibility_fade_time && options.timeSeconds < other.client.invisibility_fade_time) {
3166
+ return false;
3167
+ }
3168
+ if (options.random) {
3169
+ if (other.alpha !== void 0) {
3170
+ if (options.random() > other.alpha) {
3171
+ return false;
3172
+ }
3173
+ }
3174
+ }
3175
+ }
3176
+ }
3156
3177
  const start = { x: self.origin.x, y: self.origin.y, z: self.origin.z + self.viewheight };
3157
3178
  const end = { x: other.origin.x, y: other.origin.y, z: other.origin.z + other.viewheight };
3158
3179
  const mask = options?.throughGlass ? 1 /* Opaque */ : 1 /* Opaque */ | 2 /* Window */;
@@ -3357,13 +3378,13 @@ function foundTarget(self, level, context, options) {
3357
3378
  self.monsterinfo.pausetime = 0;
3358
3379
  self.monsterinfo.run?.(self, context);
3359
3380
  }
3360
- function classifyClientVisibility(self, other, level, trace) {
3381
+ function classifyClientVisibility(self, other, level, trace, random5) {
3361
3382
  const distance4 = rangeTo(self, other);
3362
3383
  const range = classifyRange(distance4);
3363
3384
  if (range === "far" /* Far */) return false;
3364
3385
  if (other.light_level <= 5) return false;
3365
3386
  if ((self.monsterinfo.aiflags & 1048576 /* ThirdEye */) === 0) {
3366
- if (!visible(self, other, trace, { throughGlass: false })) return false;
3387
+ if (!visible(self, other, trace, { throughGlass: false, timeSeconds: level.timeSeconds, random: random5 })) return false;
3367
3388
  }
3368
3389
  if (range === "near" /* Near */) {
3369
3390
  return level.timeSeconds <= other.show_hostile || infront(self, other);
@@ -3388,15 +3409,15 @@ function AI_GetSightClient(self, context, trace) {
3388
3409
  if ((self.monsterinfo.aiflags & 1048576 /* ThirdEye */) !== 0) {
3389
3410
  return ent;
3390
3411
  }
3391
- if (visible(self, ent, trace, { throughGlass: false })) {
3412
+ if (visible(self, ent, trace, { throughGlass: false, timeSeconds: context.timeSeconds, random: () => context.rng.frandom() })) {
3392
3413
  return ent;
3393
3414
  }
3394
3415
  }
3395
3416
  return null;
3396
3417
  }
3397
- function updateSoundChase(self, client, level, hearability, trace) {
3418
+ function updateSoundChase(self, client, level, hearability, trace, context) {
3398
3419
  if ((self.spawnflags & SPAWNFLAG_MONSTER_AMBUSH) !== 0) {
3399
- if (!visible(self, client, trace)) return false;
3420
+ if (!visible(self, client, trace, { timeSeconds: level.timeSeconds, random: () => context.rng.frandom() })) return false;
3400
3421
  } else if (hearability.canHear && !hearability.canHear(self, client)) {
3401
3422
  return false;
3402
3423
  }
@@ -3456,12 +3477,12 @@ function findTarget(self, level, context, trace, hearability = {}) {
3456
3477
  return false;
3457
3478
  }
3458
3479
  if (!heardit) {
3459
- if (!classifyClientVisibility(self, candidate, level, trace)) {
3480
+ if (!classifyClientVisibility(self, candidate, level, trace, () => context.rng.frandom())) {
3460
3481
  return false;
3461
3482
  }
3462
3483
  self.monsterinfo.aiflags &= ~4 /* SoundTarget */;
3463
3484
  self.enemy = candidate;
3464
- } else if (!updateSoundChase(self, candidate, level, hearability, trace)) {
3485
+ } else if (!updateSoundChase(self, candidate, level, hearability, trace, context)) {
3465
3486
  return false;
3466
3487
  }
3467
3488
  foundTarget(self, level, context);
@@ -3483,8 +3504,8 @@ function findCover(self, context) {
3483
3504
  for (const spot of spots) {
3484
3505
  if (spot.owner) continue;
3485
3506
  if (spot.targetname) continue;
3486
- if (!visible(self, spot, context.trace, { throughGlass: false })) continue;
3487
- if (visible(spot, self.enemy, context.trace, { throughGlass: false })) continue;
3507
+ if (!visible(self, spot, context.trace, { throughGlass: false, timeSeconds: context.timeSeconds, random: () => context.rng.frandom() })) continue;
3508
+ if (visible(spot, self.enemy, context.trace, { throughGlass: false, timeSeconds: context.timeSeconds, random: () => context.rng.frandom() })) continue;
3488
3509
  self.goalentity = spot;
3489
3510
  self.movetarget = spot;
3490
3511
  setIdealYawTowards(self, spot);
@@ -3646,13 +3667,13 @@ function ai_run(self, dist, context) {
3646
3667
  setIdealYawTowards2(self, self.enemy ?? self.goalentity);
3647
3668
  }
3648
3669
  changeYaw(self, MONSTER_TICK);
3649
- if (self.enemy && self.enemy.inUse && visible(self, self.enemy, context.trace, { throughGlass: false })) {
3670
+ if (self.enemy && self.enemy.inUse && visible(self, self.enemy, context.trace, { throughGlass: false, timeSeconds: context.timeSeconds, random: () => context.rng.frandom() })) {
3650
3671
  self.monsterinfo.blind_fire_target = addVec3(self.enemy.origin, scaleVec3(self.enemy.velocity, -0.1));
3651
3672
  }
3652
3673
  if (ai_checkattack(self, dist, context)) {
3653
3674
  return;
3654
3675
  }
3655
- const enemy_vis = self.enemy && visible(self, self.enemy, context.trace, { throughGlass: false });
3676
+ const enemy_vis = self.enemy && visible(self, self.enemy, context.trace, { throughGlass: false, timeSeconds: context.timeSeconds, random: () => context.rng.frandom() });
3656
3677
  if (!enemy_vis && self.monsterinfo.attack_state === 1 /* Sliding */) {
3657
3678
  self.monsterinfo.attack_state = 0 /* Straight */;
3658
3679
  }
@@ -10682,6 +10703,12 @@ var POWERUP_ITEMS = {
10682
10703
  id: "item_enviro",
10683
10704
  name: "Enviro Suit",
10684
10705
  timer: 30
10706
+ },
10707
+ "item_invisibility": {
10708
+ type: "powerup",
10709
+ id: "item_invisibility",
10710
+ name: "Invisibility",
10711
+ timer: 30
10685
10712
  }
10686
10713
  };
10687
10714
  var POWER_ARMOR_ITEMS = {
@@ -15029,7 +15056,7 @@ function SP_monster_flipper(self, context) {
15029
15056
  self.model = "models/monsters/flipper/tris.md2";
15030
15057
  self.mins = { x: -16, y: -16, z: 0 };
15031
15058
  self.maxs = { x: 16, y: 16, z: 32 };
15032
- self.movetype = 6 /* Fly */;
15059
+ self.movetype = 5 /* Step */;
15033
15060
  self.flags |= 2 /* Swim */;
15034
15061
  self.solid = 2 /* BoundingBox */;
15035
15062
  self.health = 50 * context.health_multiplier;