From 5b05e453da3c294bacc506481222e8bc9a7d5d6b Mon Sep 17 00:00:00 2001 From: Evan Debenham Date: Thu, 5 May 2022 17:18:49 -0400 Subject: [PATCH] v1.3.0: added new badges, and made a few more tweaks to existing ones --- core/src/main/assets/interfaces/badges.png | Bin 4755 -> 5648 bytes .../main/assets/messages/misc/misc.properties | 42 ++- .../shatteredpixeldungeon/Badges.java | 332 ++++++++++++------ .../shatteredpixeldungeon/Dungeon.java | 1 + .../shatteredpixeldungeon/Rankings.java | 2 + .../shatteredpixeldungeon/Statistics.java | 7 + .../actors/blobs/SacrificialFire.java | 2 + .../actors/mobs/DM100.java | 2 + .../actors/mobs/DM300.java | 12 + .../actors/mobs/DwarfKing.java | 11 + .../actors/mobs/Eye.java | 2 + .../actors/mobs/Goo.java | 11 +- .../actors/mobs/Pylon.java | 10 +- .../actors/mobs/Shaman.java | 2 + .../actors/mobs/Tengu.java | 24 +- .../actors/mobs/Warlock.java | 2 + .../actors/mobs/YogDzewa.java | 9 + .../actors/mobs/YogFist.java | 3 + .../effects/BadgeBanner.java | 4 +- .../items/armor/glyphs/Viscosity.java | 2 +- .../items/artifacts/ChaliceOfBlood.java | 2 + .../items/bombs/ArcaneBomb.java | 2 + .../scrolls/exotic/ScrollOfPsionicBlast.java | 2 + .../items/wands/CursedWand.java | 3 + .../items/wands/WandOfCorrosion.java | 6 + .../items/wands/WandOfLightning.java | 8 + .../items/wands/WandOfTransfusion.java | 2 + .../items/wands/WandOfWarding.java | 2 + .../items/weapon/missiles/ForceCube.java | 1 + .../levels/CavesBossLevel.java | 14 +- .../levels/rooms/special/SentryRoom.java | 4 +- .../levels/traps/GrimTrap.java | 2 + .../levels/traps/PoisonDartTrap.java | 9 +- .../shatteredpixeldungeon/ui/BadgesGrid.java | 2 +- .../windows/WndBadge.java | 14 +- 35 files changed, 424 insertions(+), 129 deletions(-) diff --git a/core/src/main/assets/interfaces/badges.png b/core/src/main/assets/interfaces/badges.png index dedb4fd886f551714258e390858ebfc5c0219533..c3b02bf005f7e6e18bc0835e499ee68f1e2a25f4 100644 GIT binary patch delta 5381 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 delta 4468 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 removedBadges = new HashSet<>(); static{ - //no recently removed badges + //v1.3.0 (These were removed and re-added internally as new unlock reqs were added) + removedBadges.add("YASD"); + removedBadges.add("DEATH_FROM_GLYPH"); } private static final HashMap renamedBadges = new HashMap<>(); @@ -559,7 +577,7 @@ public class Badges { local.add( badge ); displayBadge( badge ); - validateYASD(); + validateDeathFromAll(); } public static void validateDeathFromPoison() { @@ -567,7 +585,7 @@ public class Badges { local.add( badge ); displayBadge( badge ); - validateYASD(); + validateDeathFromAll(); } public static void validateDeathFromGas() { @@ -575,7 +593,7 @@ public class Badges { local.add( badge ); displayBadge( badge ); - validateYASD(); + validateDeathFromAll(); } public static void validateDeathFromHunger() { @@ -583,39 +601,86 @@ public class Badges { local.add( badge ); displayBadge( badge ); - validateYASD(); + validateDeathFromAll(); } - - public static void validateDeathFromGlyph() { - Badge badge = Badge.DEATH_FROM_GLYPH; - local.add( badge ); - displayBadge( badge ); - validateYASD(); - } - public static void validateDeathFromFalling() { Badge badge = Badge.DEATH_FROM_FALLING; local.add( badge ); displayBadge( badge ); - validateYASD(); + validateDeathFromAll(); + } + + public static void validateDeathFromEnemyMagic() { + Badge badge = Badge.DEATH_FROM_ENEMY_MAGIC; + local.add( badge ); + displayBadge( badge ); + + validateDeathFromAll(); } - private static void validateYASD() { + public static void validateDeathFromFriendlyMagic() { + Badge badge = Badge.DEATH_FROM_FRIENDLY_MAGIC; + local.add( badge ); + displayBadge( badge ); + + validateDeathFromAll(); + } + + public static void validateDeathFromSacrifice() { + Badge badge = Badge.DEATH_FROM_SACRIFICE; + local.add( badge ); + displayBadge( badge ); + + validateDeathFromAll(); + } + + public static void validateDeathFromGrimTrap() { + Badge badge = Badge.DEATH_FROM_GRIM_TRAP; + local.add( badge ); + displayBadge( badge ); + + validateDeathFromAll(); + } + + private static void validateDeathFromAll() { if (isUnlocked( Badge.DEATH_FROM_FIRE ) && isUnlocked( Badge.DEATH_FROM_POISON ) && isUnlocked( Badge.DEATH_FROM_GAS ) && isUnlocked( Badge.DEATH_FROM_HUNGER) && - isUnlocked( Badge.DEATH_FROM_GLYPH) && - isUnlocked( Badge.DEATH_FROM_FALLING)) { + isUnlocked( Badge.DEATH_FROM_FALLING) && + isUnlocked( Badge.DEATH_FROM_ENEMY_MAGIC) && + isUnlocked( Badge.DEATH_FROM_FRIENDLY_MAGIC) && + isUnlocked( Badge.DEATH_FROM_SACRIFICE) && + isUnlocked( Badge.DEATH_FROM_GRIM_TRAP)) { - Badge badge = Badge.YASD; + Badge badge = Badge.DEATH_FROM_ALL; if (!isUnlocked( badge )) { displayBadge( badge ); } } } + + private static LinkedHashMap firstBossClassBadges = new LinkedHashMap<>(); + static { + firstBossClassBadges.put(HeroClass.WARRIOR, Badge.BOSS_SLAIN_1_WARRIOR); + firstBossClassBadges.put(HeroClass.MAGE, Badge.BOSS_SLAIN_1_MAGE); + firstBossClassBadges.put(HeroClass.ROGUE, Badge.BOSS_SLAIN_1_ROGUE); + firstBossClassBadges.put(HeroClass.HUNTRESS, Badge.BOSS_SLAIN_1_HUNTRESS); + } + + private static LinkedHashMap thirdBossSubclassBadges = new LinkedHashMap<>(); + static { + thirdBossSubclassBadges.put(HeroSubClass.BERSERKER, Badge.BOSS_SLAIN_3_BERSERKER); + thirdBossSubclassBadges.put(HeroSubClass.GLADIATOR, Badge.BOSS_SLAIN_3_GLADIATOR); + thirdBossSubclassBadges.put(HeroSubClass.BATTLEMAGE, Badge.BOSS_SLAIN_3_BATTLEMAGE); + thirdBossSubclassBadges.put(HeroSubClass.WARLOCK, Badge.BOSS_SLAIN_3_WARLOCK); + thirdBossSubclassBadges.put(HeroSubClass.ASSASSIN, Badge.BOSS_SLAIN_3_ASSASSIN); + thirdBossSubclassBadges.put(HeroSubClass.FREERUNNER, Badge.BOSS_SLAIN_3_FREERUNNER); + thirdBossSubclassBadges.put(HeroSubClass.SNIPER, Badge.BOSS_SLAIN_3_SNIPER); + thirdBossSubclassBadges.put(HeroSubClass.WARDEN, Badge.BOSS_SLAIN_3_WARDEN); + } public static void validateBossSlain() { Badge badge = null; @@ -639,75 +704,40 @@ public class Badges { displayBadge( badge ); if (badge == Badge.BOSS_SLAIN_1) { - switch (Dungeon.hero.heroClass) { - case WARRIOR: - badge = Badge.BOSS_SLAIN_1_WARRIOR; - break; - case MAGE: - badge = Badge.BOSS_SLAIN_1_MAGE; - break; - case ROGUE: - badge = Badge.BOSS_SLAIN_1_ROGUE; - break; - case HUNTRESS: - badge = Badge.BOSS_SLAIN_1_HUNTRESS; - break; - } + badge = firstBossClassBadges.get(Dungeon.hero.heroClass); + if (badge == null) return; local.add( badge ); unlock(badge); - - if (isUnlocked( Badge.BOSS_SLAIN_1_WARRIOR ) && - isUnlocked( Badge.BOSS_SLAIN_1_MAGE ) && - isUnlocked( Badge.BOSS_SLAIN_1_ROGUE ) && - isUnlocked( Badge.BOSS_SLAIN_1_HUNTRESS)) { + + boolean allUnlocked = true; + for (Badge b : firstBossClassBadges.values()){ + if (!isUnlocked(b)){ + allUnlocked = false; + break; + } + } + if (allUnlocked) { badge = Badge.BOSS_SLAIN_1_ALL_CLASSES; if (!isUnlocked( badge )) { displayBadge( badge ); } } - } else - if (badge == Badge.BOSS_SLAIN_3) { - switch (Dungeon.hero.subClass) { - case GLADIATOR: - badge = Badge.BOSS_SLAIN_3_GLADIATOR; - break; - case BERSERKER: - badge = Badge.BOSS_SLAIN_3_BERSERKER; - break; - case WARLOCK: - badge = Badge.BOSS_SLAIN_3_WARLOCK; - break; - case BATTLEMAGE: - badge = Badge.BOSS_SLAIN_3_BATTLEMAGE; - break; - case FREERUNNER: - badge = Badge.BOSS_SLAIN_3_FREERUNNER; - break; - case ASSASSIN: - badge = Badge.BOSS_SLAIN_3_ASSASSIN; - break; - case SNIPER: - badge = Badge.BOSS_SLAIN_3_SNIPER; - break; - case WARDEN: - badge = Badge.BOSS_SLAIN_3_WARDEN; - break; - default: - return; - } + } else if (badge == Badge.BOSS_SLAIN_3) { + + badge = thirdBossSubclassBadges.get(Dungeon.hero.subClass); + if (badge == null) return; local.add( badge ); unlock(badge); - - if (isUnlocked( Badge.BOSS_SLAIN_3_GLADIATOR ) && - isUnlocked( Badge.BOSS_SLAIN_3_BERSERKER ) && - isUnlocked( Badge.BOSS_SLAIN_3_WARLOCK ) && - isUnlocked( Badge.BOSS_SLAIN_3_BATTLEMAGE ) && - isUnlocked( Badge.BOSS_SLAIN_3_FREERUNNER ) && - isUnlocked( Badge.BOSS_SLAIN_3_ASSASSIN ) && - isUnlocked( Badge.BOSS_SLAIN_3_SNIPER ) && - isUnlocked( Badge.BOSS_SLAIN_3_WARDEN )) { - + + boolean allUnlocked = true; + for (Badge b : thirdBossSubclassBadges.values()){ + if (!isUnlocked(b)){ + allUnlocked = false; + break; + } + } + if (allUnlocked) { badge = Badge.BOSS_SLAIN_3_ALL_SUBCLASSES; if (!isUnlocked( badge )) { displayBadge( badge ); @@ -716,6 +746,32 @@ public class Badges { } } } + + public static void validateBossChallengeCompleted(){ + Badge badge = null; + switch (Dungeon.depth) { + case 5: + badge = Badge.BOSS_CHALLENGE_1; + break; + case 10: + badge = Badge.BOSS_CHALLENGE_2; + break; + case 15: + badge = Badge.BOSS_CHALLENGE_3; + break; + case 20: + badge = Badge.BOSS_CHALLENGE_4; + break; + case 25: + badge = Badge.BOSS_CHALLENGE_5; + break; + } + + if (badge != null) { + local.add(badge); + displayBadge(badge); + } + } public static void validateMastery() { @@ -827,15 +883,42 @@ public class Badges { if (Rankings.INSTANCE.totalNumber >= 50 || Rankings.INSTANCE.wonNumber >= 5) { badge = Badge.GAMES_PLAYED_3; } - if (Rankings.INSTANCE.totalNumber >= 100 || Rankings.INSTANCE.wonNumber >= 10) { + if (Rankings.INSTANCE.totalNumber >= 200 || Rankings.INSTANCE.wonNumber >= 10) { badge = Badge.GAMES_PLAYED_4; } - if (Rankings.INSTANCE.totalNumber >= 250 || Rankings.INSTANCE.wonNumber >= 25) { + if (Rankings.INSTANCE.totalNumber >= 1000 || Rankings.INSTANCE.wonNumber >= 25) { badge = Badge.GAMES_PLAYED_5; } displayBadge( badge ); } + + //TODO this is calibrated for scoring changes I plan to make + public static void validateHighScore( int score ){ + Badge badge = null; + if (score >= 5000) { + badge = Badge.HIGH_SCORE_1; + local.add( badge ); + } + if (score >= 25_000) { + badge = Badge.HIGH_SCORE_2; + local.add( badge ); + } + if (score >= 100_000) { + badge = Badge.HIGH_SCORE_3; + local.add( badge ); + } + if (score >= 250_000) { + badge = Badge.HIGH_SCORE_4; + local.add( badge ); + } + if (score >= 1_000_000) { + badge = Badge.HIGH_SCORE_5; + local.add( badge ); + } + + displayBadge( badge ); + } //necessary in order to display the happy end badge in the surface scene public static void silentValidateHappyEnd() { @@ -929,6 +1012,7 @@ public class Badges { } + //only show the highest unlocked and the lowest locked private static final Badge[][] tierBadgeReplacements = new Badge[][]{ {Badge.MONSTERS_SLAIN_1, Badge.MONSTERS_SLAIN_2, Badge.MONSTERS_SLAIN_3, Badge.MONSTERS_SLAIN_4, Badge.MONSTERS_SLAIN_5}, {Badge.GOLD_COLLECTED_1, Badge.GOLD_COLLECTED_2, Badge.GOLD_COLLECTED_3, Badge.GOLD_COLLECTED_4, Badge.GOLD_COLLECTED_5}, @@ -938,17 +1022,31 @@ public class Badges { {Badge.FOOD_EATEN_1, Badge.FOOD_EATEN_2, Badge.FOOD_EATEN_3, Badge.FOOD_EATEN_4, Badge.FOOD_EATEN_5}, {Badge.ITEMS_CRAFTED_1, Badge.ITEMS_CRAFTED_2, Badge.ITEMS_CRAFTED_3, Badge.ITEMS_CRAFTED_4, Badge.ITEMS_CRAFTED_5}, {Badge.BOSS_SLAIN_1, Badge.BOSS_SLAIN_2, Badge.BOSS_SLAIN_3, Badge.BOSS_SLAIN_4}, + {Badge.HIGH_SCORE_1, Badge.HIGH_SCORE_2, Badge.HIGH_SCORE_3, Badge.HIGH_SCORE_4, Badge.HIGH_SCORE_5}, {Badge.GAMES_PLAYED_1, Badge.GAMES_PLAYED_2, Badge.GAMES_PLAYED_3, Badge.GAMES_PLAYED_4, Badge.GAMES_PLAYED_5}, {Badge.CHAMPION_1, Badge.CHAMPION_2, Badge.CHAMPION_3} }; - private static final Badge[][] metaBadgeReplacements = new Badge[][]{ - {Badge.DEATH_FROM_FIRE, Badge.YASD}, - {Badge.DEATH_FROM_GAS, Badge.YASD}, - {Badge.DEATH_FROM_HUNGER, Badge.YASD}, - {Badge.DEATH_FROM_POISON, Badge.YASD}, - {Badge.DEATH_FROM_GLYPH, Badge.YASD}, - {Badge.DEATH_FROM_FALLING, Badge.YASD }, + //don't show the later badge if the earlier one isn't unlocked + private static final Badge[][] prerequisiteBadges = new Badge[][]{ + {Badge.BOSS_SLAIN_1, Badge.BOSS_CHALLENGE_1}, + {Badge.BOSS_SLAIN_2, Badge.BOSS_CHALLENGE_2}, + {Badge.BOSS_SLAIN_3, Badge.BOSS_CHALLENGE_3}, + {Badge.BOSS_SLAIN_4, Badge.BOSS_CHALLENGE_4}, + {Badge.VICTORY, Badge.BOSS_CHALLENGE_5}, + }; + + //If the summary badge is unlocked, don't show the component badges + private static final Badge[][] summaryBadgeReplacements = new Badge[][]{ + {Badge.DEATH_FROM_FIRE, Badge.DEATH_FROM_ALL}, + {Badge.DEATH_FROM_GAS, Badge.DEATH_FROM_ALL}, + {Badge.DEATH_FROM_HUNGER, Badge.DEATH_FROM_ALL}, + {Badge.DEATH_FROM_POISON, Badge.DEATH_FROM_ALL}, + {Badge.DEATH_FROM_FALLING, Badge.DEATH_FROM_ALL}, + {Badge.DEATH_FROM_ENEMY_MAGIC, Badge.DEATH_FROM_ALL}, + {Badge.DEATH_FROM_FRIENDLY_MAGIC, Badge.DEATH_FROM_ALL}, + {Badge.DEATH_FROM_SACRIFICE, Badge.DEATH_FROM_ALL}, + {Badge.DEATH_FROM_GRIM_TRAP, Badge.DEATH_FROM_ALL}, {Badge.ALL_WEAPONS_IDENTIFIED, Badge.ALL_ITEMS_IDENTIFIED}, {Badge.ALL_ARMOR_IDENTIFIED, Badge.ALL_ITEMS_IDENTIFIED}, @@ -965,7 +1063,7 @@ public class Badges { leaveBest( badges, tierReplace ); } - for (Badge[] metaReplace : metaBadgeReplacements){ + for (Badge[] metaReplace : summaryBadgeReplacements){ leaveBest( badges, metaReplace ); } @@ -983,7 +1081,11 @@ public class Badges { } } - public static List filterHigherIncrementalBadges(List badges ) { + public static List filterBadgesWithoutPrerequisites(List badges ) { + + for (Badge[] prereqReplace : prerequisiteBadges){ + leaveWorst( badges, prereqReplace ); + } for (Badge[] tierReplace : tierBadgeReplacements){ leaveWorst( badges, tierReplace ); @@ -1011,7 +1113,7 @@ public class Badges { addLower( badges, tierReplace ); } - for (Badge[] metaReplace : metaBadgeReplacements){ + for (Badge[] metaReplace : summaryBadgeReplacements){ addLower( badges, metaReplace ); } @@ -1028,4 +1130,34 @@ public class Badges { } } } + + //used for badges with completion progress that would otherwise be hard to track + public static String showCompletionProgress( Badge badge ){ + if (isUnlocked(badge)) return null; + + String result = "\n"; + + if (badge == Badge.BOSS_SLAIN_1_ALL_CLASSES){ + for (HeroClass cls : HeroClass.values()){ + result += "\n"; + if (isUnlocked(firstBossClassBadges.get(cls))) result += "_" + Messages.titleCase(cls.title()) + "_"; + else result += Messages.titleCase(cls.title()); + } + + return result; + + } else if (badge == Badge.BOSS_SLAIN_3_ALL_SUBCLASSES){ + + for (HeroSubClass cls : HeroSubClass.values()){ + if (cls == HeroSubClass.NONE) continue; + result += "\n"; + if (isUnlocked(thirdBossSubclassBadges.get(cls))) result += "_" + Messages.titleCase(cls.title()) + "_"; + else result += Messages.titleCase(cls.title()) ; + } + + return result; + } + + return null; + } } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Dungeon.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Dungeon.java index ac52acea5..b545e06f8 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Dungeon.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Dungeon.java @@ -324,6 +324,7 @@ public class Dungeon { level.create(); Statistics.qualifiedForNoKilling = !bossLevel(); + Statistics.qualifiedForBossChallengeBadge = bossLevel(); return level; } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Rankings.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Rankings.java index 2391d7cb9..0f96d26b2 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Rankings.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Rankings.java @@ -75,6 +75,8 @@ public enum Rankings { rec.herolevel = Dungeon.hero.lvl; rec.depth = Dungeon.depth; rec.score = score( win ); + + Badges.validateHighScore( rec.score ); INSTANCE.saveGameData(rec); diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Statistics.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Statistics.java index 0a33e985f..b0f7dd1ab 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Statistics.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Statistics.java @@ -44,6 +44,7 @@ public class Statistics { public static boolean qualifiedForNoKilling = false; public static boolean completedWithNoKilling = false; + public static boolean qualifiedForBossChallengeBadge = false; public static boolean amuletObtained = false; @@ -66,6 +67,7 @@ public class Statistics { duration = 0; qualifiedForNoKilling = false; + qualifiedForBossChallengeBadge = false; amuletObtained = false; @@ -88,6 +90,7 @@ public class Statistics { private static final String DURATION = "duration"; private static final String NO_KILLING_QUALIFIED = "qualifiedForNoKilling"; + private static final String BOSS_CHALLENGE_QUALIFIED= "qualifiedForBossChallengeBadge"; private static final String AMULET = "amuletObtained"; @@ -109,6 +112,8 @@ public class Statistics { bundle.put( DURATION, duration ); bundle.put(NO_KILLING_QUALIFIED, qualifiedForNoKilling); + + bundle.put(BOSS_CHALLENGE_QUALIFIED, qualifiedForBossChallengeBadge); bundle.put( AMULET, amuletObtained ); } @@ -131,6 +136,8 @@ public class Statistics { duration = bundle.getFloat( DURATION ); qualifiedForNoKilling = bundle.getBoolean( NO_KILLING_QUALIFIED ); + + qualifiedForBossChallengeBadge = bundle.getBoolean( BOSS_CHALLENGE_QUALIFIED ); amuletObtained = bundle.getBoolean( AMULET ); } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/blobs/SacrificialFire.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/blobs/SacrificialFire.java index 2ec1e16dc..52cce78eb 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/blobs/SacrificialFire.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/blobs/SacrificialFire.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.actors.blobs; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; @@ -157,6 +158,7 @@ public class SacrificialFire extends Blob { exp *= Random.IntRange( 2, 3 ); } else if (ch instanceof Hero) { exp = 1_000_000; //always enough to activate the reward, if you can somehow get it + Badges.validateDeathFromSacrifice(); } if (exp > 0) { diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/DM100.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/DM100.java index 7b583164f..b8dc3e8c7 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/DM100.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/DM100.java @@ -21,6 +21,7 @@ package com.shatteredpixel.shatteredpixeldungeon.actors.mobs; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.effects.particles.SparkParticle; @@ -102,6 +103,7 @@ public class DM100 extends Mob implements Callback { Camera.main.shake( 2, 0.3f ); if (!enemy.isAlive()) { + Badges.validateDeathFromEnemyMagic(); Dungeon.fail( getClass() ); GLog.n( Messages.get(this, "zap_kill") ); } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/DM300.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/DM300.java index 940ade973..ea6274812 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/DM300.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/DM300.java @@ -25,6 +25,7 @@ import com.shatteredpixel.shatteredpixeldungeon.Assets; import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Challenges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; +import com.shatteredpixel.shatteredpixeldungeon.Statistics; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob; @@ -298,6 +299,14 @@ public class DM300 extends Mob { return super.act(); } + @Override + public boolean attack(Char enemy, float dmgMulti, float dmgBonus, float accMulti) { + if (enemy == Dungeon.hero && supercharged){ + Statistics.qualifiedForBossChallengeBadge = false; + } + return super.attack(enemy, dmgMulti, dmgBonus, accMulti); + } + @Override protected Char chooseEnemy() { Char enemy = super.chooseEnemy(); @@ -533,6 +542,9 @@ public class DM300 extends Mob { } Badges.validateBossSlain(); + if (Statistics.qualifiedForBossChallengeBadge){ + Badges.validateBossChallengeCompleted(); + } LloydsBeacon beacon = Dungeon.hero.belongings.getItem(LloydsBeacon.class); if (beacon != null) { diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/DwarfKing.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/DwarfKing.java index 3248d1a43..e247b40fd 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/DwarfKing.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/DwarfKing.java @@ -26,6 +26,7 @@ import com.shatteredpixel.shatteredpixeldungeon.Assets; import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Challenges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; +import com.shatteredpixel.shatteredpixeldungeon.Statistics; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Barrier; @@ -47,6 +48,8 @@ import com.shatteredpixel.shatteredpixeldungeon.items.armor.glyphs.Viscosity; import com.shatteredpixel.shatteredpixeldungeon.items.artifacts.DriedRose; import com.shatteredpixel.shatteredpixeldungeon.items.artifacts.LloydsBeacon; import com.shatteredpixel.shatteredpixeldungeon.items.scrolls.ScrollOfTeleportation; +import com.shatteredpixel.shatteredpixeldungeon.items.wands.Wand; +import com.shatteredpixel.shatteredpixeldungeon.items.wands.WandOfLightning; import com.shatteredpixel.shatteredpixeldungeon.levels.CityBossLevel; import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica; import com.shatteredpixel.shatteredpixeldungeon.messages.Messages; @@ -435,6 +438,11 @@ public class DwarfKing extends Mob { @Override public void damage(int dmg, Object src) { + //lightning and corrosion have their own custom logic + if (src == Dungeon.hero || (src instanceof Wand && !(src instanceof WandOfLightning))){ + Statistics.qualifiedForBossChallengeBadge = false; + } + if (isInvulnerable(src.getClass())){ super.damage(dmg, src); return; @@ -513,6 +521,9 @@ public class DwarfKing extends Mob { } Badges.validateBossSlain(); + if (Statistics.qualifiedForBossChallengeBadge){ + Badges.validateBossChallengeCompleted(); + } Dungeon.level.unseal(); diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Eye.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Eye.java index d15c25745..7957acdd5 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Eye.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Eye.java @@ -21,6 +21,7 @@ package com.shatteredpixel.shatteredpixeldungeon.actors.mobs; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; @@ -184,6 +185,7 @@ public class Eye extends Mob { } if (!ch.isAlive() && ch == Dungeon.hero) { + Badges.validateDeathFromEnemyMagic(); Dungeon.fail( getClass() ); GLog.n( Messages.get(this, "deathgaze_kill") ); } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Goo.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Goo.java index d3b61e92a..3853881be 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Goo.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Goo.java @@ -24,6 +24,7 @@ package com.shatteredpixel.shatteredpixeldungeon.actors.mobs; import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Challenges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; +import com.shatteredpixel.shatteredpixeldungeon.Statistics; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; @@ -67,6 +68,7 @@ public class Goo extends Mob { int max = (HP*2 <= HT) ? 12 : 8; if (pumpedUp > 0) { pumpedUp = 0; + Statistics.qualifiedForBossChallengeBadge = false; return Random.NormalIntRange( min*3, max*3 ); } else { return Random.NormalIntRange( min, max ); @@ -96,6 +98,7 @@ public class Goo extends Mob { if (Dungeon.level.water[pos] && HP < HT) { HP += healInc; + Statistics.qualifiedForBossChallengeBadge = false; LockedFloor lock = Dungeon.hero.buff(LockedFloor.class); if (lock != null) lock.removeTime(healInc*2); @@ -211,7 +214,10 @@ public class Goo extends Mob { @Override public boolean attack( Char enemy, float dmgMulti, float dmgBonus, float accMulti ) { boolean result = super.attack( enemy, dmgMulti, dmgBonus, accMulti ); - pumpedUp = 0; + if (pumpedUp > 0) { + pumpedUp = 0; + Statistics.qualifiedForBossChallengeBadge = false; + } return result; } @@ -263,6 +269,9 @@ public class Goo extends Mob { } Badges.validateBossSlain(); + if (Statistics.qualifiedForBossChallengeBadge){ + Badges.validateBossChallengeCompleted(); + } yell( Messages.get(this, "defeated") ); } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Pylon.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Pylon.java index 5e4195207..81a75dff0 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Pylon.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Pylon.java @@ -24,6 +24,7 @@ package com.shatteredpixel.shatteredpixeldungeon.actors.mobs; import com.shatteredpixel.shatteredpixeldungeon.Assets; import com.shatteredpixel.shatteredpixeldungeon.Challenges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; +import com.shatteredpixel.shatteredpixeldungeon.Statistics; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Electricity; @@ -124,9 +125,12 @@ public class Pylon extends Mob { ch.sprite.flash(); ch.damage(Random.NormalIntRange(10, 20), new Electricity()); - if (ch == Dungeon.hero && !ch.isAlive()){ - Dungeon.fail(DM300.class); - GLog.n( Messages.get(Electricity.class, "ondeath") ); + if (ch == Dungeon.hero) { + Statistics.qualifiedForBossChallengeBadge = false; + if (!ch.isAlive()) { + Dungeon.fail(DM300.class); + GLog.n(Messages.get(Electricity.class, "ondeath")); + } } } } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Shaman.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Shaman.java index 8ff73a476..ad667bce6 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Shaman.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Shaman.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.actors.mobs; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; @@ -119,6 +120,7 @@ public abstract class Shaman extends Mob { enemy.damage( dmg, new EarthenBolt() ); if (!enemy.isAlive() && enemy == Dungeon.hero) { + Badges.validateDeathFromEnemyMagic(); Dungeon.fail( getClass() ); GLog.n( Messages.get(this, "bolt_kill") ); } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Tengu.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Tengu.java index 8eb29b59d..fb0645518 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Tengu.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Tengu.java @@ -25,6 +25,7 @@ import com.shatteredpixel.shatteredpixeldungeon.Assets; import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Challenges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; +import com.shatteredpixel.shatteredpixeldungeon.Statistics; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob; @@ -209,6 +210,9 @@ public class Tengu extends Mob { super.die( cause ); Badges.validateBossSlain(); + if (Statistics.qualifiedForBossChallengeBadge){ + Badges.validateBossChallengeCompleted(); + } LloydsBeacon beacon = Dungeon.hero.belongings.getItem(LloydsBeacon.class); if (beacon != null) { @@ -612,8 +616,12 @@ public class Tengu extends Mob { ch.damage(dmg, Bomb.class); } - if (ch == Dungeon.hero && !ch.isAlive()) { - Dungeon.fail(Tengu.class); + if (ch == Dungeon.hero){ + Statistics.qualifiedForBossChallengeBadge = false; + + if (!ch.isAlive()) { + Dungeon.fail(Tengu.class); + } } } @@ -840,6 +848,9 @@ public class Tengu extends Mob { if (ch != null && !ch.isImmune(Fire.class) && !(ch instanceof Tengu)) { Buff.affect( ch, Burning.class ).reignite( ch ); } + if (ch == Dungeon.hero){ + Statistics.qualifiedForBossChallengeBadge = false; + } if (Dungeon.level.flamable[cell]){ Dungeon.level.destroy( cell ); @@ -1021,9 +1032,12 @@ public class Tengu extends Mob { if (ch != null && !(ch instanceof Tengu)){ ch.damage(2 + Dungeon.depth, new Electricity()); - if (ch == Dungeon.hero && !ch.isAlive()) { - Dungeon.fail(Tengu.class); - GLog.n( Messages.get(Electricity.class, "ondeath") ); + if (ch == Dungeon.hero){ + Statistics.qualifiedForBossChallengeBadge = false; + if (!ch.isAlive()) { + Dungeon.fail(Tengu.class); + GLog.n(Messages.get(Electricity.class, "ondeath")); + } } } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Warlock.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Warlock.java index 88d28dd36..ee007f85e 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Warlock.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/Warlock.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.actors.mobs; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; @@ -112,6 +113,7 @@ public class Warlock extends Mob implements Callback { enemy.damage( dmg, new DarkBolt() ); if (enemy == Dungeon.hero && !enemy.isAlive()) { + Badges.validateDeathFromEnemyMagic(); Dungeon.fail( getClass() ); GLog.n( Messages.get(this, "bolt_kill") ); } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/YogDzewa.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/YogDzewa.java index dfc3431e5..58b6de823 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/YogDzewa.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/YogDzewa.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.actors.mobs; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Challenges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.Statistics; @@ -225,6 +226,7 @@ public class YogDzewa extends Mob { CellEmitter.center(pos).burst(PurpleParticle.BURST, Random.IntRange(1, 2)); } if (!ch.isAlive() && ch == Dungeon.hero) { + Badges.validateDeathFromEnemyMagic(); Dungeon.fail(getClass()); GLog.n(Messages.get(Char.class, "kill", name())); } @@ -463,6 +465,13 @@ public class YogDzewa extends Mob { updateVisibility(Dungeon.level); GameScene.bossSlain(); + + if (Dungeon.isChallenged(Challenges.STRONGER_BOSSES) && Statistics.spawnersAlive == 4){ + Badges.validateBossChallengeCompleted(); + } else { + Statistics.qualifiedForBossChallengeBadge = false; + } + Dungeon.level.unseal(); super.die( cause ); diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/YogFist.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/YogFist.java index 4289153f5..8ab276aa0 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/YogFist.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/mobs/YogFist.java @@ -21,6 +21,7 @@ package com.shatteredpixel.shatteredpixeldungeon.actors.mobs; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; @@ -473,6 +474,7 @@ public abstract class YogFist extends Mob { Buff.prolong( enemy, Blindness.class, Blindness.DURATION/2f ); if (!enemy.isAlive() && enemy == Dungeon.hero) { + Badges.validateDeathFromEnemyMagic(); Dungeon.fail( getClass() ); GLog.n( Messages.get(Char.class, "kill", name()) ); } @@ -540,6 +542,7 @@ public abstract class YogFist extends Mob { } if (!enemy.isAlive() && enemy == Dungeon.hero) { + Badges.validateDeathFromEnemyMagic(); Dungeon.fail( getClass() ); GLog.n( Messages.get(Char.class, "kill", name()) ); } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/effects/BadgeBanner.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/effects/BadgeBanner.java index cc4de0533..aa28c90b7 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/effects/BadgeBanner.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/effects/BadgeBanner.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.effects; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.watabou.gltextures.SmartTexture; import com.watabou.gltextures.TextureCache; import com.watabou.noosa.Game; @@ -134,8 +135,7 @@ public class BadgeBanner extends Image { //we also hardcode any special cases static { - //combo master - highlightPositions.put(66, new Point(3, 7)); + highlightPositions.put(Badges.Badge.MASTERY_COMBO.image, new Point(3, 7)); } //adds a shine to an appropriate pixel on a badge diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/armor/glyphs/Viscosity.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/armor/glyphs/Viscosity.java index 1d1af91ad..1efab6f44 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/armor/glyphs/Viscosity.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/armor/glyphs/Viscosity.java @@ -146,7 +146,7 @@ public class Viscosity extends Glyph { target.damage( damageThisTick, this ); if (target == Dungeon.hero && !target.isAlive()) { - Badges.validateDeathFromGlyph(); + Badges.validateDeathFromFriendlyMagic(); Dungeon.fail( getClass() ); GLog.n( Messages.get(this, "ondeath") ); diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/artifacts/ChaliceOfBlood.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/artifacts/ChaliceOfBlood.java index 0351015eb..466cc16e2 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/artifacts/ChaliceOfBlood.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/artifacts/ChaliceOfBlood.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.items.artifacts; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.hero.Hero; import com.shatteredpixel.shatteredpixeldungeon.effects.particles.ShadowParticle; @@ -116,6 +117,7 @@ public class ChaliceOfBlood extends Artifact { hero.damage(damage, this); if (!hero.isAlive()) { + Badges.validateDeathFromFriendlyMagic(); Dungeon.fail( getClass() ); GLog.n( Messages.get(this, "ondeath") ); } else { diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/bombs/ArcaneBomb.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/bombs/ArcaneBomb.java index 9ecd9c53c..c4c81c8c1 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/bombs/ArcaneBomb.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/bombs/ArcaneBomb.java @@ -21,6 +21,7 @@ package com.shatteredpixel.shatteredpixeldungeon.items.bombs; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; @@ -84,6 +85,7 @@ public class ArcaneBomb extends Bomb { float multiplier = 1f - (.16667f*Dungeon.level.distance(cell, ch.pos)); ch.damage(Math.round(damage*multiplier), this); if (ch == Dungeon.hero && !ch.isAlive()){ + Badges.validateDeathFromFriendlyMagic(); Dungeon.fail(Bomb.class); } } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/scrolls/exotic/ScrollOfPsionicBlast.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/scrolls/exotic/ScrollOfPsionicBlast.java index 959b24bd8..7eefc6f07 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/scrolls/exotic/ScrollOfPsionicBlast.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/scrolls/exotic/ScrollOfPsionicBlast.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.items.scrolls.exotic; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Blindness; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; @@ -64,6 +65,7 @@ public class ScrollOfPsionicBlast extends ExoticScroll { Dungeon.observe(); readAnimation(); } else { + Badges.validateDeathFromFriendlyMagic(); Dungeon.fail( getClass() ); GLog.n( Messages.get(this, "ondeath") ); } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/CursedWand.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/CursedWand.java index abf60e242..f720d01d6 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/CursedWand.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/CursedWand.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.items.wands; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Challenges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.ShatteredPixelDungeon; @@ -223,9 +224,11 @@ public class CursedWand { Sample.INSTANCE.play(Assets.Sounds.CURSED); if (!toDamage.isAlive()) { if (origin != null) { + Badges.validateDeathFromFriendlyMagic(); Dungeon.fail( origin.getClass() ); GLog.n( Messages.get( CursedWand.class, "ondeath", origin.name() ) ); } else { + Badges.validateDeathFromFriendlyMagic(); Dungeon.fail( toHeal.getClass() ); } } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfCorrosion.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfCorrosion.java index f641df33c..a3ea4bd83 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfCorrosion.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfCorrosion.java @@ -23,12 +23,14 @@ package com.shatteredpixel.shatteredpixeldungeon.items.wands; import com.shatteredpixel.shatteredpixeldungeon.Assets; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; +import com.shatteredpixel.shatteredpixeldungeon.Statistics; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.CorrosiveGas; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Ooze; +import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.DwarfKing; import com.shatteredpixel.shatteredpixeldungeon.effects.CellEmitter; import com.shatteredpixel.shatteredpixeldungeon.effects.MagicMissile; import com.shatteredpixel.shatteredpixeldungeon.effects.Speck; @@ -64,6 +66,10 @@ public class WandOfCorrosion extends Wand { Char ch = Actor.findChar(bolt.collisionPos + i); if (ch != null) { wandProc(ch, chargesPerCast()); + + if (i == 0 && ch instanceof DwarfKing){ + Statistics.qualifiedForBossChallengeBadge = false; + } } } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfLightning.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfLightning.java index 333d333a9..1c2796cdb 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfLightning.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfLightning.java @@ -22,9 +22,12 @@ package com.shatteredpixel.shatteredpixeldungeon.items.wands; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; +import com.shatteredpixel.shatteredpixeldungeon.Statistics; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; +import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.DwarfKing; import com.shatteredpixel.shatteredpixeldungeon.effects.CellEmitter; import com.shatteredpixel.shatteredpixeldungeon.effects.Lightning; import com.shatteredpixel.shatteredpixeldungeon.effects.particles.SparkParticle; @@ -87,6 +90,7 @@ public class WandOfLightning extends DamageWand { } if (!curUser.isAlive()) { + Badges.validateDeathFromFriendlyMagic(); Dungeon.fail( getClass() ); GLog.n(Messages.get(this, "ondeath")); } @@ -133,6 +137,10 @@ public class WandOfLightning extends DamageWand { Char ch = Actor.findChar( cell ); if (ch != null) { + if (ch instanceof DwarfKing){ + Statistics.qualifiedForBossChallengeBadge = false; + } + affected.add( ch ); arcs.add( new Lightning.Arc(curUser.sprite.center(), ch.sprite.center())); arc(ch); diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfTransfusion.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfTransfusion.java index 394c68a1e..4e18a536f 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfTransfusion.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfTransfusion.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.items.wands; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; @@ -131,6 +132,7 @@ public class WandOfTransfusion extends Wand { curUser.damage(damage, this); if (!curUser.isAlive()){ + Badges.validateDeathFromFriendlyMagic(); Dungeon.fail( getClass() ); GLog.n( Messages.get(this, "ondeath") ); } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfWarding.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfWarding.java index 105cd7163..fe6db7d10 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfWarding.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/wands/WandOfWarding.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.items.wands; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; @@ -328,6 +329,7 @@ public class WandOfWarding extends Wand { } if (!enemy.isAlive() && enemy == Dungeon.hero) { + Badges.validateDeathFromFriendlyMagic(); Dungeon.fail( getClass() ); } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/weapon/missiles/ForceCube.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/weapon/missiles/ForceCube.java index 8ae5ee111..2d742c78b 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/weapon/missiles/ForceCube.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/weapon/missiles/ForceCube.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.items.weapon.missiles; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/CavesBossLevel.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/CavesBossLevel.java index d313a1dae..01229a0c7 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/CavesBossLevel.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/CavesBossLevel.java @@ -25,6 +25,7 @@ import com.shatteredpixel.shatteredpixeldungeon.Assets; import com.shatteredpixel.shatteredpixeldungeon.Bones; import com.shatteredpixel.shatteredpixeldungeon.Challenges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; +import com.shatteredpixel.shatteredpixeldungeon.Statistics; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob; @@ -44,6 +45,7 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.painters.Painter; import com.shatteredpixel.shatteredpixeldungeon.messages.Messages; import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene; import com.shatteredpixel.shatteredpixeldungeon.sprites.CharSprite; +import com.shatteredpixel.shatteredpixeldungeon.sprites.PylonSprite; import com.shatteredpixel.shatteredpixeldungeon.tiles.CustomTilemap; import com.shatteredpixel.shatteredpixeldungeon.tiles.DungeonTilemap; import com.shatteredpixel.shatteredpixeldungeon.utils.GLog; @@ -794,9 +796,15 @@ public class CavesBossLevel extends Level { ch.damage( Random.NormalIntRange(6, 12), Electricity.class); ch.sprite.flash(); - if (ch == Dungeon.hero && !ch.isAlive()) { - Dungeon.fail(DM300.class); - GLog.n( Messages.get(Electricity.class, "ondeath") ); + if (ch == Dungeon.hero){ + if (energySourceSprite != null && energySourceSprite instanceof PylonSprite){ + //took damage while DM-300 was supercharged + Statistics.qualifiedForBossChallengeBadge = false; + } + if ( !ch.isAlive()) { + Dungeon.fail(DM300.class); + GLog.n(Messages.get(Electricity.class, "ondeath")); + } } } } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/rooms/special/SentryRoom.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/rooms/special/SentryRoom.java index 7b9975ec2..5a837a727 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/rooms/special/SentryRoom.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/rooms/special/SentryRoom.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.levels.rooms.special; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Challenges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; @@ -275,8 +276,9 @@ public class SentryRoom extends SpecialRoom { public void onZapComplete(){ Dungeon.hero.damage(Random.NormalIntRange(2+Dungeon.depth/2, 4+Dungeon.depth), new Eye.DeathGaze()); if (!Dungeon.hero.isAlive()){ - GLog.n( Messages.capitalize(Messages.get(Char.class, "kill", name())) ); + Badges.validateDeathFromEnemyMagic(); Dungeon.fail( getClass() ); + GLog.n( Messages.capitalize(Messages.get(Char.class, "kill", name())) ); } } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/traps/GrimTrap.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/traps/GrimTrap.java index 06f8e7b9c..e381b7c57 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/traps/GrimTrap.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/traps/GrimTrap.java @@ -22,6 +22,7 @@ package com.shatteredpixel.shatteredpixeldungeon.levels.traps; import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Badges; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; @@ -99,6 +100,7 @@ public class GrimTrap extends Trap { if (finalTarget == Dungeon.hero) { Sample.INSTANCE.play(Assets.Sounds.CURSED); if (!finalTarget.isAlive()) { + Badges.validateDeathFromGrimTrap(); Dungeon.fail( GrimTrap.class ); GLog.n( Messages.get(GrimTrap.class, "ondeath") ); } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/traps/PoisonDartTrap.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/traps/PoisonDartTrap.java index 7891e4f58..381da71bc 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/traps/PoisonDartTrap.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/traps/PoisonDartTrap.java @@ -24,6 +24,7 @@ package com.shatteredpixel.shatteredpixeldungeon.levels.traps; import com.shatteredpixel.shatteredpixeldungeon.Assets; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.ShatteredPixelDungeon; +import com.shatteredpixel.shatteredpixeldungeon.Statistics; import com.shatteredpixel.shatteredpixeldungeon.actors.Actor; import com.shatteredpixel.shatteredpixeldungeon.actors.Char; import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff; @@ -94,8 +95,12 @@ public class PoisonDartTrap extends Trap { public void call() { int dmg = Random.NormalIntRange(4, 8) - finalTarget.drRoll(); finalTarget.damage(dmg, trap); - if (finalTarget == Dungeon.hero && !finalTarget.isAlive()){ - Dungeon.fail( trap.getClass() ); + if (finalTarget == Dungeon.hero){ + //for the poison dart traps in the Tengu fight + Statistics.qualifiedForBossChallengeBadge = false; + if (!finalTarget.isAlive()) { + Dungeon.fail(trap.getClass()); + } } Buff.affect( finalTarget, Poison.class ).set( poisonAmount() ); Sample.INSTANCE.play(Assets.Sounds.HIT, 1, 1, Random.Float(0.8f, 1.25f)); diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/BadgesGrid.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/BadgesGrid.java index 8e45d2ca7..73a8aaa47 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/BadgesGrid.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/BadgesGrid.java @@ -61,7 +61,7 @@ public class BadgesGrid extends Component { lockedBadges.add(badge); } } - Badges.filterHigherIncrementalBadges(lockedBadges); + Badges.filterBadgesWithoutPrerequisites(lockedBadges); for (Badges.Badge badge : lockedBadges) { BadgeButton button = new BadgeButton( badge, false ); diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/windows/WndBadge.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/windows/WndBadge.java index 6ea0bd734..6645cfb3c 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/windows/WndBadge.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/windows/WndBadge.java @@ -49,10 +49,20 @@ public class WndBadge extends Window { if (!unlocked) title.hardlight( 0x888822 ); add(title); - RenderedTextBlock info = PixelScene.renderTextBlock( badge.desc(), 6 ); + String desc = badge.desc(); + String unlock = Badges.showCompletionProgress(badge); + + if (unlock != null){ + desc += unlock; + } + + RenderedTextBlock info = PixelScene.renderTextBlock( desc, 6 ); info.maxWidth(MAX_WIDTH - MARGIN * 2); info.align(RenderedTextBlock.CENTER_ALIGN); - if (!unlocked) info.hardlight( 0x888888 ); + if (!unlocked) { + info.hardlight( 0x888888 ); + info.setHightlighting( true, 0x888822 ); + } add(info); float w = Math.max( icon.width(), Math.max(title.width(), info.width()) ) + MARGIN * 2;