private void Break(bool spawn = true) { if (!broken) { UpdateSprite(); AnimationUtil.Poof(Center); AnimationUtil.Explosion(Center); broken = true; GetComponent <AudioEmitterComponent>().EmitRandomizedPrefixed("level_explosion", 3); if (spawn) { GetComponent <DropsComponent>().SpawnDrops(); } } }
public override void Update(float dt) { base.Update(dt); if (!Attract) { return; } foreach (var p in Area.Tagged[Tags.Player]) { var dx = p.DxTo(this); var dy = p.DyTo(this); var d = MathUtils.Distance(dx, dy); if (d <= 24) { AnimationUtil.Explosion(Center); Done = true; Callback(); Camera.Instance.Shake(20); Engine.Instance.Flash = 2; var ba = GetComponent <SensorBodyComponent>(); ba.Velocity = ba.Knockback = Vector2.Zero; var bb = p.GetComponent <SensorBodyComponent>(); bb.Velocity = bb.Knockback = Vector2.Zero; return; } var a = MathUtils.Angle(dx, dy); var force = 360 * dt; if (d <= 64) { force *= 2; } p.GetComponent <RectBodyComponent>().Velocity += new Vector2((float)Math.Cos(a) * force, (float)Math.Sin(a) * force); a += (float)Math.PI; GetComponent <SensorBodyComponent>().Velocity += new Vector2((float)Math.Cos(a) * force, (float)Math.Sin(a) * force); } }
private void Break() { if (broken) { return; } broken = true; AnimationUtil.Poof(Center); AnimationUtil.Explosion(Center); UpdateSprite(); HandleEvent(new BrokenEvent { Machine = this }); }
public static void Make(Entity whoHurts, float hurtRadius = 32f, bool leave = true, Vec2 where = null, float damage = 16, float scale = 1, bool damageOwner = true) { Camera.Instance.Shake(10 * scale); Audio.SfxVolumeBuffer = 0.5f; Audio.SfxVolumeBufferResetTimer = 1f; var w = where == null ? whoHurts.Center : new Vector2(where.X, where.Y); AnimationUtil.Explosion(w, scale); for (var i = 0; i < 4; i++) { var explosion = new ParticleEntity(Particles.Animated("explosion", "smoke")); explosion.Position = w; whoHurts.Area.Add(explosion); explosion.Depth = 31; explosion.Particle.Scale = scale; explosion.Particle.AngleVelocity = 0; explosion.AddShadow(); var a = explosion.Particle.Angle - Math.PI / 2; var d = 16; explosion.Particle.Position += new Vector2((float)Math.Cos(a) * d, (float)Math.Sin(a) * d); if (i == 0) { explosion.AddComponent(new AudioEmitterComponent { DestroySounds = false }); explosion.GetComponent <AudioEmitterComponent>().EmitRandomizedPrefixed("level_explosion", 3); } } for (var i = 0; i < 6; i++) { var part = new ParticleEntity(Particles.Dust()); part.Position = w + new Vector2(Rnd.Int(-4, 4), Rnd.Int(-4, 4)); whoHurts.Area.Add(part); part.Depth = 30; part.Particle.Velocity = MathUtils.CreateVector(Rnd.AnglePI(), 80); } Engine.Instance.Split = 1f; Engine.Instance.Flash = 1f; Engine.Instance.Freeze = 1f; var damager = whoHurts; if (whoHurts is Bomb b && b.Owner != null) { damager = b.Owner; } foreach (var e in whoHurts.Area.GetEntitesInRadius(w, hurtRadius, typeof(ExplodableComponent))) { if (e == whoHurts && !damageOwner) { continue; } e.GetAnyComponent <BodyComponent>()?.KnockbackFrom(whoHurts, 4f); e.GetComponent <ExplodableComponent>().HandleExplosion(damager, whoHurts, damage); } if (Settings.Flashes) { Camera.Instance.TextureZoom -= 0.05f; Tween.To(1f, Camera.Instance.TextureZoom, x => Camera.Instance.TextureZoom = x, 0.2f); } if (leave) { whoHurts.Area.Add(new ExplosionLeftOver { Center = w }); } var xx = (int)Math.Floor(w.X / 16f); var yy = (int)Math.Floor(w.Y / 16f); var r = (int)Math.Floor(hurtRadius / 16f); var level = Run.Level; var ice = level.Biome is IceBiome; for (int x = -r; x <= r; x++) { for (int y = -r; y <= r; y++) { var xm = x * 16; var ym = y * 16; if (Math.Sqrt(xm * xm + ym * ym) <= hurtRadius) { var index = level.ToIndex(x + xx, y + yy); var l = level.Get(index, true); var ww = new Dot((x + xx) * 16 + 8, (y + yy) * 16 + 8); if (l.IsRock()) { BreakRock(level, ww, x + xx, y + yy, l); continue; } var tile = level.Get(index); if (tile == Tile.Crack) { DiscoverCrack(whoHurts, level, x + xx, y + yy); } else if (tile == Tile.Planks || (ice && tile == Tile.WallA)) { level.Break((x + xx) * 16, (y + yy) * 16); } } } } }
public override void Update(float dt) { base.Update(dt); if (Died) { if (!cleared) { cleared = true; GetComponent <DialogComponent>().Close(); foreach (var p in Area.Tagged[Tags.Projectile]) { AnimationUtil.Poof(p.Center); ((Projectile)p).Break(null); } try { var a = GetComponent <RoomComponent>().Room.Tagged[Tags.MustBeKilled].ToArray(); foreach (var p in a) { if (!(p is Boss)) { AnimationUtil.Poof(p.Center); ((Creature)p).Kill(this); } } } catch (Exception e) { Log.Error(e); } } if (deathTimer >= 3f && !Placed) { Placed = true; CreateGore(null); if (this is bk.BurningKnight) { } else { HandleEvent(new DefeatedEvent { Boss = this }); } var player = LocalPlayer.Locate(Area); var doors = new List <DoorTile>(); if (player != null) { var stats = player.GetComponent <StatsComponent>(); var e = new DealChanceCalculateEvent(); if (!stats.TookDamageInRoom) { Achievements.Unlock("bk:dodge_master"); } e.GrannyStartChance = stats.SawDeal && !stats.TookDeal ? stats.GrannyChance : 0; e.GrannyChance = e.GrannyStartChance; e.DmStartChance = stats.DMChance; e.DmChance = e.DmStartChance; player.HandleEvent(e); var gr = Rnd.Chance(e.GrannyChance * 100); var dm = Rnd.Chance(e.DmChance * 100); if (gr || (dm && e.OpenBoth)) { foreach (var r in Area.Tagged[Tags.Room]) { var room = (Room)r; if (room.Type == RoomType.Granny) { room.OpenHiddenDoors(); foreach (var d in room.Doors) { doors.Add(new DoorTile { Door = d, Tile = Tile.GrannyFloor }); } break; } } } if (dm || (gr && e.OpenBoth)) { foreach (var r in Area.Tagged[Tags.Room]) { var room = (Room)r; if (room.Type == RoomType.OldMan) { room.OpenHiddenDoors(); foreach (var d in room.Doors) { doors.Add(new DoorTile { Door = d, Tile = Tile.EvilFloor }); } break; } } } } if (doors.Count > 0) { var rm = GetComponent <RoomComponent>().Room; var level = Run.Level; var cx = rm.MapX + rm.MapW / 2f; var cy = rm.MapY + rm.MapH / 2f; var grannyDoors = new List <Door>(); var evilDoors = new List <Door>(); foreach (var d in doors) { if (d.Tile == Tile.GrannyFloor) { grannyDoors.Add(d.Door); } else { evilDoors.Add(d.Door); } } rm.PaintTunnel(grannyDoors, Tile.GrannyFloor); rm.PaintTunnel(evilDoors, Tile.EvilFloor); rm.ApplyToEachTile((x, y) => { var t = level.Get(x, y); if (t == Tile.GrannyFloor || t == Tile.EvilFloor) { level.Set(x, y, Tile.FloorA); Timer.Add(() => { var part = new TileParticle(); part.Top = t == Tile.GrannyFloor ? Tilesets.Biome.GrannyFloor[0] : Tilesets.Biome.EvilFloor[0]; part.TopTarget = Run.Level.Tileset.WallTopADecor; part.Side = Run.Level.Tileset.FloorSidesD[0]; part.Sides = Run.Level.Tileset.WallSidesA[2]; part.Tile = t; part.X = x * 16; part.Y = y * 16; part.Target.X = x * 16; part.Target.Y = y * 16; part.TargetZ = -8f; Area.Add(part); }, 1f + Rnd.Float(0.2f) + MathUtils.Distance(x - cx, y - cy) / 6f); } }, -1); level.TileUp(); level.CreateBody(); } Done = true; PlaceRewards(); if (ResetCam) { Timer.Add(() => { ((InGameState)Engine.Instance.State).ResetFollowing(); }, 0.5f); } } else { deathTimer += dt; lastExplosion -= dt; if (lastExplosion <= 0) { lastExplosion = 0.3f; AnimationUtil.Explosion(Center + new Vector2(Rnd.Float(-16, 16), Rnd.Float(-16, 16))); Camera.Instance.Shake(10); Audio.PlaySfx($"level_explosion_{Rnd.Int(1, 4)}"); } if (deathTimer > 2.5f) { Engine.Instance.FlashColor = new Color(1f, 1f, 1f, (deathTimer - 2.5f) * 2f); Engine.Instance.Flash = 0.01f; } } return; } if (!(GetComponent <StateComponent>().StateInstance is FriendlyState) && HasHealthbar && HealthBar == null) { HealthBar = new HealthBar(this); Engine.Instance.State.Ui.Add(HealthBar); AddPhases(); Engine.Instance.State.Ui.Add(new UiBanner(Locale.Get(GetId()))); } }