public override void Use(Entity entity, Item item) { if (SetToMin) { entity.GetComponent <HealthComponent>().InitMaxHealth = 1; return; } if (SetToMax) { var h = entity.GetComponent <HealthComponent>(); h.ModifyHealth(h.MaxHealth, item); return; } var a = Amount; if (a > 0 && Scourge.IsEnabled(Scourge.OfIllness)) { if (a == 1) { return; } a = (int)(a / 2f); } entity.GetComponent <HealthComponent>().ModifyHealth(a, entity); }
public void InitStats(bool fromInit = false) { HasFlight = false; SuperHot = false; Scourge.Clear(); GetComponent <AimComponent>().ShowLaserLine = false; GetComponent <OrbitGiverComponent>().DestroyAll(); GetComponent <FollowerComponent>().DestroyAll(); var hp = GetComponent <HealthComponent>(); if (fromInit) { hp.InitMaxHealth = 6; } hp.MaxHealthCap = 32; hp.InvincibilityTimerMax = 1f; if (CheatWindow.AutoGodMode) { Log.Info("Entering god mode for the player"); hp.Unhittable = true; } }
public override void Use(Entity entity, Item item) { base.Use(entity, item); Scourge.Enable(scourge); if (Run.Scourge == 0) { Run.AddScourge(); } }
protected override bool TryOpen(Entity entity) { var item = Scourge.GenerateItemId(); if (item != null) { Timer.Add(() => entity.GetComponent <InventoryComponent>().Pickup(Items.CreateAndAdd(item, entity.Area)), 0.3f); } return(true); }
public override void Paint(Level level) { Painter.Fill(level, this, 1, Tile.EvilFloor); var stand = new ScourgedStand(); level.Area.Add(stand); stand.Center = GetCenter() * 16 + new Vector2(8); stand.SetItem(Items.CreateAndAdd(Scourge.GenerateItemId(), level.Area), stand); }
protected override bool Interact(Entity e) { var c = e.GetComponent <HealthComponent>(); c.ModifyHealth(c.MaxHealth, this); e.GetComponent <InventoryComponent>().Pickup(Items.CreateAndAdd(Scourge.Generate(), Area)); Break(); Audio.PlaySfx("level_scourge_statue"); return(true); }
public override void Happen(Player entity) { if (amount < 0) { var sc = Run.Scourge; for (var i = 0; i < sc; i++) { Run.RemoveScourge(); } var inventory = entity.GetComponent <InventoryComponent>(); var toRemove = new List <Item>(); foreach (var i in inventory.Items) { if (i.Scourged) { i.Scourged = false; } if (i.Type == ItemType.Scourge) { toRemove.Add(i); } } Cleanse(entity.GetComponent <WeaponComponent>()); Cleanse(entity.GetComponent <ActiveWeaponComponent>()); Cleanse(entity.GetComponent <ActiveItemComponent>()); // fixme: doesnt do anything to ui inventory foreach (var i in toRemove) { inventory.Remove(i, true); } foreach (var s in Scourge.Defined) { Scourge.Disable(s); } } else { for (var i = 0; i < amount; i++) { Run.AddScourge(); } } }
public static void Place(Vector2 where, Area area) { where.Y -= 16; var goblin = new TrashGoblin(); area.Add(goblin); goblin.BottomCenter = where; goblin.X += 1; var stand = new TrashGoblinStand(); area.Add(stand); stand.Center = where + new Vector2(0, 4 + stand.Height); stand.SetItem(Items.CreateAndAdd(Scourge.GenerateItemId(), area, false), null); }
protected override bool TryPay(Entity entity) { if (base.TryPay(entity)) { var scourge = Scourge.GenerateItemId(); if (scourge != null) { Timer.Add(() => { entity.GetComponent <InventoryComponent>().Pickup(Items.CreateAndAdd(scourge, entity.Area)); }, 2f); } return(true); } return(false); }
private void RenderConsumables(bool hasMana) { var bottomY = 8 + 9 + 8 + (hasMana ? 10 : 0) + (Player.GetComponent <HealthComponent>().MaxHealth + Player.GetComponent <HeartsComponent>().Total > HeartsComponent.PerRow ? 10 : 0) + (int)(12 * (activeSlot.ActivePosition + 1)); if (Scourge.IsEnabled(Scourge.OfKeys)) { Graphics.Render(question, new Vector2(8, bottomY + 1)); return; } Graphics.Render(coin, new Vector2(Wrap(8 + coin.Center.X), bottomY + 1 + coin.Center.Y), 0, coin.Center, coinScale); PrintString($"{coins}", 18, bottomY - 1); bottomY += 12; Graphics.Render(key, new Vector2(Wrap(7 + key.Center.X), bottomY + key.Center.Y + 2), 0, key.Center, keyScale); PrintString($"{keys}", 18, bottomY - 1); bottomY += bomb.Source.Height + 2; Graphics.Render(bomb, new Vector2(Wrap(8 + bomb.Center.X), bottomY + bomb.Center.Y), 0, bomb.Center, bombScale); PrintString($"{bombs}", 18, bottomY - 1); }
static HappeningRegistry() { // Bad Add("omega_hurt", new HurtHappening(3)); Add("confused", new BuffHappening(ConfusedBuff.Id, 30)); Add("snail", new BuffHappening(SlowBuff.Id, 30)); Add("broken", new BuffHappening(BrokenArmorBuff.Id, 30)); Add("darkness", new DarknessHappening()); Add("scourge_token", new ItemGiveHappening(() => Scourge.GenerateItemId())); Add("risk", new ItemGiveHappening(() => "bk:scourge_of_risk")); Add("double_trouble", new ItemGiveHappening(() => "bk:scourge_of_blood")); Add("rage", new BkRageHappening()); Add("regular_tp", new TeleportHappening(RoomType.Regular, RoomType.Trap)); Add("reset", new FloorResetHappening()); Add("sudoku", new BombHappening()); Add("items_hurt", new MakeItemsDamageUse()); Add("scourged", new ScourgeHappening(3)); Add("reroll_items", new RerollHappening(false, true)); Add("reroll_weapon", new RerollHappening(true, false)); Add("nerf", new ModifyMaxHpHappening(-2)); Add("rob", new ModifyCoinsHappening(-10)); Add("steal", new StealWeaponHappening()); Add("bomb", new BombingHappening()); Add("slide", new SlideHappening()); // Good Add("give_random_consumable", new RandomItemHappening(ItemPool.Consumable)); Add("invincible", new BuffHappening(InvincibleBuff.Id, 30)); Add("heal", new HealHappening(2)); Add("cleanse", new ScourgeHappening(-3)); Add("chest", new ChestHappening()); Add("gift", new ModifyCoinsHappening(10)); // Neutral // Add("entrance_tp", new TeleportHappening(RoomType.Entrance)); // Add("exit_tp", new TeleportHappening(RoomType.Exit, RoomType.Boss)); }
public void RenderWindow() { ImGui.Separator(); ImGui.Text($"Time: {Math.Floor(Time / 3600f)}h {Math.Floor(Time / 60f % 60f)}m {Math.Floor(Time % 60f)}s"); ImGui.Text($"Won: {Won}"); ImGui.Text($"Loop: {Run.Loop}"); ImGui.Text($"Max Depth: {MaxDepth}"); ImGui.Text($"Game Version: {GameVersion}"); Run.CalculateScore(); ImGui.Text($"Score: {Run.Score}"); ImGui.Separator(); if (ImGui.TreeNode("Items")) { foreach (var item in Items) { ImGui.BulletText(item); } ImGui.TreePop(); } if (ImGui.TreeNode("Banned items")) { foreach (var item in Banned) { ImGui.BulletText(item); } ImGui.TreePop(); } ImGui.Separator(); ImGui.Text($"Coins Collected: {CoinsObtained}"); ImGui.Text($"Keys Collected: {KeysObtained}"); ImGui.Text($"Bombs Collected: {BombsObtained}"); ImGui.Text($"Hearts Collected: {HeartsCollected}"); ImGui.Text($"Heart Containers Collected: {MaxHealth}"); ImGui.Separator(); ImGui.Text($"Damage Taken: {DamageTaken}"); ImGui.Text($"Damage Dealt: {DamageDealt}"); ImGui.Text($"Mobs Killed: {MobsKilled}"); ImGui.Text($"Rooms Explored: {RoomsExplored} / {RoomsTotal}"); ImGui.Text($"Secret Rooms Explored: {SecretRoomsFound} / {SecretRoomsTotal}"); ImGui.Separator(); ImGui.Text($"Date Started: {Day} {Year}"); ImGui.Text($"Tiles Walked: {TilesWalked}"); ImGui.Text($"Pits Fallen: {PitsFallen}"); ImGui.Text($"Bosses Defeated: {BossesDefeated}"); ImGui.Text($"Spikes Triggered: {SpikesTriggered}"); ImGui.Text($"Paintings Broke: {GlobalSave.GetInt("paintings_destroyed")}"); ImGui.Separator(); ImGui.Text($"Luck: {Run.Luck}"); ImGui.Text($"Scourge: {Run.Scourge}"); if (ImGui.TreeNode("Scourges")) { foreach (var curse in Scourge.Defined) { var v = Scourge.IsEnabled(curse); if (ImGui.Checkbox(curse, ref v)) { if (v) { Scourge.Enable(curse); } else { Scourge.Disable(curse); } } } ImGui.TreePop(); } }
public override bool HandleEvent(Event e) { if (e is LostSupportEvent) { if (GetComponent <HealthComponent>().Unhittable) { return(true); } if (!GetComponent <BuffsComponent>().PitImmunity) { GetComponent <HealthComponent>().ModifyHealth(-1, Run.Level); } for (var i = 0; i < 4; i++) { var part = new ParticleEntity(Particles.Dust()); part.Position = Center; part.Particle.Scale = Rnd.Float(0.4f, 0.8f); Area.Add(part); } } else if (e is RoomChangedEvent c) { if (c.New == null || Run.Level == null || Camera.Instance == null) { return(base.HandleEvent(e)); } if (c.New.Tagged[Tags.MustBeKilled].Count > 0) { Audio.PlaySfx("level_door_shut"); foreach (var p in Area.Tagged[Tags.Player]) { if (p.GetComponent <RoomComponent>().Room != c.New) { AnimationUtil.Poof(p.Center); p.Center = Center; AnimationUtil.Poof(p.Center); } } } ((InGameState)Engine.Instance.State).ResetFollowing(); var pr = (PixelPerfectGameRenderer)Engine.Instance.StateRenderer; if (c.Old != null) { if (Scourge.IsEnabled(Scourge.OfLost)) { c.Old.Hide(); } if (c.Old.Type == RoomType.DarkMarket || c.Old.Type == RoomType.Hidden) { pr.EnableClip = false; c.Old.Hide(true); InBuilding = false; ((InGameState)Engine.Instance.State).UpdateRainVolume(); } } if (c.New.Type == RoomType.DarkMarket) { Achievements.Unlock("bk:dark_market"); } if (c.New.Type == RoomType.DarkMarket || c.New.Type == RoomType.Hidden) { pr.EnableClip = true; pr.ClipPosition = new Vector2(c.New.X + 16, c.New.Y + 16); pr.ClipSize = new Vector2(c.New.Width - 16, c.New.Height - 32); InBuilding = true; ((InGameState)Engine.Instance.State).UpdateRainVolume(); } else { pr.EnableClip = false; } if (c.New.Type == RoomType.Shop) { Audio.PlaySfx("level_door_bell"); } c.New.Discover(); var level = Run.Level; if (InGameState.Ready) { switch (c.New.Type) { case RoomType.Secret: case RoomType.Special: case RoomType.Shop: case RoomType.SubShop: case RoomType.Treasure: { foreach (var door in c.New.Doors) { if (door.TryGetComponent <LockComponent>(out var component) && component.Lock is GoldLock) { if (!(c.New.Type == RoomType.Shop && ((door.Rooms[0] != null && door.Rooms[0].Type == RoomType.SubShop) || (door.Rooms[1] != null && door.Rooms[1].Type == RoomType.SubShop)))) { component.Lock.SetLocked(false, this); } } } break; } case RoomType.OldMan: case RoomType.Granny: { if (c.New.Type == RoomType.OldMan) { GetComponent <StatsComponent>().SawDeal = true; } c.New.OpenHiddenDoors(); foreach (var r in Area.Tagged[Tags.Room]) { var room = (Room)r; if (room.Type == (c.New.Type == RoomType.OldMan ? RoomType.Granny : RoomType.OldMan)) { room.CloseHiddenDoors(); break; } } break; } } if (c.New.Type == RoomType.Secret) { ExplosionMaker.CheckForCracks(level, c.New, this); } } if (c.Old != null) { if (c.Old.Type == RoomType.OldMan) { var found = false; foreach (var p in c.Old.Tagged[Tags.Player]) { if (p != this && p is Player) { found = true; break; } } if (!found) { c.Old.CloseHiddenDoors(); } } else if (c.Old.Type == RoomType.Treasure && Run.Type != RunType.BossRush && !Rnd.Chance(5)) { var found = false; foreach (var p in c.Old.Tagged[Tags.Player]) { if (p != this && p is Player) { found = true; break; } } if (!found) { foreach (var door in c.Old.Doors) { var x = (int)Math.Floor(door.CenterX / 16); var y = (int)Math.Floor(door.Bottom / 16); var t = level.Get(x, y); if (level.Get(x, y).Matches(TileFlags.Passable)) { var index = level.ToIndex(x, y); level.Set(index, level.Biome is IceBiome ? Tile.WallB : Tile.WallA); level.UpdateTile(x, y); level.ReCreateBodyChunk(x, y); level.LoadPassable(); Camera.Instance.Shake(10); } } c.Old.ApplyToEachTile((x, y) => { if (Run.Level.Get(x, y).IsWall()) { return; } Timer.Add(() => { var part = new TileParticle(); part.Top = Run.Level.Tileset.WallTopADecor; part.TopTarget = Run.Level.Tileset.WallTopADecor; part.Side = Run.Level.Tileset.FloorSidesD[0]; part.Sides = Run.Level.Tileset.WallSidesA[2]; part.Tile = Tile.WallA; part.X = x * 16; part.Y = y * 16; part.Target.X = x * 16; part.Target.Y = y * 16; part.TargetZ = -8f; Area.Add(part); }, Rnd.Float(0.5f)); }); foreach (var d in c.Old.Doors) { d.Done = true; } c.Old.Done = true; } } } // Darken the lighting in evil rooms if (c.New.Type == RoomType.OldMan || c.New.Type == RoomType.Spiked) { Tween.To(0.7f, Lights.RadiusMod, x => Lights.RadiusMod = x, 0.3f); } else if (c.Old != null && (c.Old.Type == RoomType.OldMan || c.Old.Type == RoomType.Spiked)) { Tween.To(1f, Lights.RadiusMod, x => Lights.RadiusMod = x, 0.3f); } } else if (e is HealthModifiedEvent hm) { if (hm.Amount < 0) { if ((hm.From is Mob m && m.HasPrefix) || (hm.From is creature.bk.BurningKnight k && k.InFight) || hm.From is BkOrbital) { hm.Amount = Math.Min(hm.Amount, -2); } else if (hm.Type != DamageType.Custom && hm.Type != DamageType.Explosive) { hm.Amount = Math.Max(-1, hm.Amount); } } }
public override void Paint(Level level) { if (LevelSave.BiomeGenerated is IceBiome) { var clip = Painter.Clip; Painter.Clip = null; Painter.Rect(level, this, 0, Tile.WallB); Painter.Clip = clip; } var t = Tiles.Pick(Tile.Chasm, Tile.WallA, Tile.WallB, Tile.Planks); if (Rnd.Chance()) { Painter.Set(level, new Dot(Left + 1, Top + 1), t); Painter.Set(level, new Dot(Right - 1, Bottom - 1), t); } if (Rnd.Chance()) { Painter.Set(level, new Dot(Right - 1, Top + 1), t); Painter.Set(level, new Dot(Left + 1, Bottom - 1), t); } if (Rnd.Chance(10 + Run.Scourge * 5)) { var cn = GetCenter() * 16; var c = Rnd.Int(2, 4); for (var i = 0; i < c; i++) { var stand = new ScourgedStand(); level.Area.Add(stand); stand.Center = cn + new Vector2(16 + (i - c / 2f) * 32, 8); stand.SetItem(Items.CreateAndAdd(Scourge.GenerateItemId(), level.Area), stand); } return; } var center = GetCenter() * 16 + new Vector2(8); if (Rnd.Chance(5)) { var chest = new ProtoChest(); level.Area.Add(chest); chest.BottomCenter = center; return; } switch (Rnd.Int(GlobalSave.IsTrue(ShopNpc.Gobetta) ? 6 : 5)) { case 0: { for (var i = 0; i < Rnd.Int(1, 3); i++) { Items.CreateAndAdd("bk:heart", level.Area).Center = center; } break; } case 1: { for (var i = 0; i < Rnd.Int(1, 4); i++) { Items.CreateAndAdd("bk:shield", level.Area).Center = center; } break; } case 2: { var stand = new ItemStand(); level.Area.Add(stand); stand.BottomCenter = center; stand.SetItem(Items.CreateAndAdd(Items.Generate(ItemPool.Treasure), level.Area), null); break; } case 3: { var a = Rnd.Chance(); var c = Rnd.Int(1, a ? 3 : 4); for (var i = 0; i < c; i++) { var chest = a ? (Chest) new StoneChest() : new RedChest(); level.Area.Add(chest); chest.BottomCenter = center - new Vector2((c / 2f - i) * 20, 0); } break; } case 4: { for (var i = 0; i < Rnd.Int(6, 12); i++) { Items.CreateAndAdd("bk:coin", level.Area).Center = center; } break; } case 5: { Gobetta.Place(GetTileCenter() * 16 + new Vector2(8, 8), level.Area); break; } } }
public override void AddComponents() { base.AddComponents(); Width = 31; Height = 33; AddComponent(new AnimationComponent("emerald_golem")); AddComponent(new SensorBodyComponent(-Npc.Padding, -Npc.Padding, Width + Npc.Padding * 2, Height + Npc.Padding, BodyType.Static)); AddComponent(new RectBodyComponent(2, 17, 27, 16, BodyType.Static)); AddComponent(new InteractableComponent(Interact) { CanInteract = e => !broken }); GetComponent <DialogComponent>().Dialog.Voice = 15; Dialogs.RegisterCallback("eg_0", (d, c) => { if (broken) { return(null); } if (((ChoiceDialog)d).Choice == 0) { Timer.Add(() => { GetComponent <DialogComponent>().StartAndClose(Locale.Get("eg_1"), 3); }, 0.2f); var inv = c.To.GetComponent <InventoryComponent>(); var a = c.To.Area; for (var i = 0; i < Amount; i++) { inv.Pickup(Items.CreateAndAdd("bk:emerald", a)); } Timer.Add(() => { inv.Pickup(Items.CreateAndAdd(Scourge.GenerateItemId(), a)); }, 1f); Timer.Add(() => { GetComponent <AnimationComponent>().Animate(() => { Done = true; Engine.Instance.Flash = 1f; Camera.Instance.Shake(8); for (var i = 0; i < 4; i++) { var part = new ParticleEntity(Particles.Dust()); part.Position = Center + Rnd.Vector(-16, 16); part.Particle.Scale = Rnd.Float(1f, 2f); Run.Level.Area.Add(part); part.Depth = 1; } }); }, 4f); broken = true; return(null); } else if (GlobalSave.IsTrue("bk:emerald_gun")) { Timer.Add(() => { GetComponent <DialogComponent>().StartAndClose(Locale.Get("eg_1"), 3); }, 0.2f); var inv = c.To.GetComponent <InventoryComponent>(); var a = c.To.Area; inv.Pickup(Items.CreateAndAdd("bk:emerald_gun", a)); Timer.Add(() => { inv.Pickup(Items.CreateAndAdd(Scourge.GenerateItemId(), a)); }, 1f); Timer.Add(() => { GetComponent <AnimationComponent>().Animate(() => { Done = true; Engine.Instance.Flash = 1f; Camera.Instance.Shake(8); for (var i = 0; i < 4; i++) { var part = new ParticleEntity(Particles.Dust()); part.Position = Center + Rnd.Vector(-16, 16); part.Particle.Scale = Rnd.Float(1f, 2f); Run.Level.Area.Add(part); part.Depth = 1; } }); }, 4f); broken = true; return(null); } return(null); }); Subscribe <RoomChangedEvent>(); }
private void RenderHealthBar(bool pad) { var red = Player.GetComponent <HealthComponent>(); var phases = red.Phases; if (Scourge.IsEnabled(Scourge.OfRisk)) { Graphics.Render(question, new Vector2(8 + (int)((4 + ItemSlot.Source.Width) * (activeSlot.ActivePosition + 1)), 11)); if (phases > 0) { Graphics.Print($"x{phases}", Font.Small, new Vector2(8 + question.Width + 4 + (int)((4 + ItemSlot.Source.Width) * (activeSlot.ActivePosition + 1)), 12)); } return; } var hearts = Player.GetComponent <HeartsComponent>(); var totalRed = red.Health; if (lastRed > totalRed) { lastRed = totalRed; } else if (lastRed < totalRed) { lastRed = Math.Min(totalRed, lastRed + Engine.Delta * 30); } var r = (int)lastRed; var maxRed = red.MaxHealth; var hurt = red.InvincibilityTimer > 0; var shields = hearts.ShieldHalfs; var bombs = (int)hearts.Bombs; var dbombs = bombs * 2; var mbombs = (int)hearts.BombsMax; var mdbombs = mbombs * 2; var n = r; var jn = maxRed; if (jn % 2 == 1) { jn++; } var vegan = Settings.Vegan; for (var i = 0; i < maxRed; i += 2) { var region = hurt ? (vegan ? veganchangedHeartBackground : changedHeartBackground) : (vegan ? veganHeartBackground : HeartBackground); if (i == maxRed - 1) { region = hurt ? (vegan ? veganchangedHalfHeartBackground : changedHalfHeartBackground) : (vegan ? veganhalfHeartBackground : halfHeartBackground); } Graphics.Render(region, GetHeartPosition(pad, i, true)); } for (var i = jn; i < maxRed + mdbombs; i += 2) { var region = hurt ? ChangedBombBg : BombBg; Graphics.Render(region, GetHeartPosition(pad, i, true) + new Vector2(0, -1)); } for (var i = jn + mdbombs; i < maxRed + shields + mdbombs; i += 2) { var region = hurt ? changedShieldBackground : ShieldBackground; if (i == maxRed + shields - 1) { region = hurt ? changedHalfShieldBackground : halfShieldBackground; } Graphics.Render(region, GetHeartPosition(pad, i, true)); } for (var j = 0; j < n; j++) { var h = j % 2 == 0; Graphics.Render(h ? (vegan ? veganHalfHeart : HalfHeart) : (vegan ? veganHeart : Heart), GetHeartPosition(pad, j) + (h ? Vector2.Zero : new Vector2(-1, 0))); } for (var j = jn; j < maxRed + dbombs; j += 2) { Graphics.Render(Bomb, GetHeartPosition(pad, j) + new Vector2(0, -1)); } if (phases > 0) { Graphics.Print($"x{phases}", Font.Small, GetHeartPosition(pad, Math.Min(15, maxRed + shields + bombs)) + new Vector2(4, -2)); } }