diff --git a/core/src/main/assets/interfaces/icons.png b/core/src/main/assets/interfaces/icons.png index 895475356..5d9944d10 100644 Binary files a/core/src/main/assets/interfaces/icons.png and b/core/src/main/assets/interfaces/icons.png differ diff --git a/core/src/main/assets/messages/items/items.properties b/core/src/main/assets/messages/items/items.properties index 7f1efefbc..ab25e8cd1 100644 --- a/core/src/main/assets/messages/items/items.properties +++ b/core/src/main/assets/messages/items/items.properties @@ -1678,6 +1678,9 @@ items.equipableitem.unequip_cursed=You can't remove a cursed item! items.equipableitem.ac_equip=EQUIP items.equipableitem.ac_unequip=UNEQUIP +items.energycrystal.name=energy crystal +items.energycrystal.desc=A collection of small magical crystals, filled with alchemical energy.\n\nThese crystals are the most common ingredient in alchemy recipes and can be produced at an alchemy pot by scrapping consumable items. + items.gold.name=gold items.gold.desc=A pile of gold coins. Collect gold coins to spend them later in a shop. diff --git a/core/src/main/assets/messages/scenes/scenes.properties b/core/src/main/assets/messages/scenes/scenes.properties index 41c03f37f..f63870c1a 100644 --- a/core/src/main/assets/messages/scenes/scenes.properties +++ b/core/src/main/assets/messages/scenes/scenes.properties @@ -4,7 +4,7 @@ scenes.alchemyscene.title=Alchemy scenes.alchemyscene.text=Combine ingredients to create something new! scenes.alchemyscene.select=Select an item scenes.alchemyscene.cost=Energy: %d -scenes.alchemyscene.energy=Alchemical Energy: %d +scenes.alchemyscene.energy=Energy: %d scenes.amuletscene.exit=Let's call it a day scenes.amuletscene.stay=I'm not done yet diff --git a/core/src/main/assets/sprites/items.png b/core/src/main/assets/sprites/items.png index 6245d8879..e447b072b 100644 Binary files a/core/src/main/assets/sprites/items.png and b/core/src/main/assets/sprites/items.png differ diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Dungeon.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Dungeon.java index 5eeb6a99f..d2f3652ca 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Dungeon.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/Dungeon.java @@ -162,7 +162,9 @@ public class Dungeon { public static QuickSlot quickslot = new QuickSlot(); public static int depth; + public static int gold; + public static int energy; public static HashSet chapters; @@ -203,6 +205,7 @@ public class Dungeon { depth = 0; gold = 0; + energy = 0; droppedItems = new SparseArray<>(); portedItems = new SparseArray<>(); @@ -443,8 +446,9 @@ public class Dungeon { private static final String CHALLENGES = "challenges"; private static final String MOBS_TO_CHAMPION = "mobs_to_champion"; private static final String HERO = "hero"; - private static final String GOLD = "gold"; private static final String DEPTH = "depth"; + private static final String GOLD = "gold"; + private static final String ENERGY = "energy"; private static final String DROPPED = "dropped%d"; private static final String PORTED = "ported%d"; private static final String LEVEL = "level"; @@ -463,9 +467,11 @@ public class Dungeon { bundle.put( CHALLENGES, challenges ); bundle.put( MOBS_TO_CHAMPION, mobsToChampion ); bundle.put( HERO, hero ); - bundle.put( GOLD, gold ); bundle.put( DEPTH, depth ); + bundle.put( GOLD, gold ); + bundle.put( ENERGY, energy ); + for (int d : droppedItems.keyArray()) { bundle.put(Messages.format(DROPPED, d), droppedItems.get(d)); } @@ -609,9 +615,11 @@ public class Dungeon { hero = null; hero = (Hero)bundle.get( HERO ); - gold = bundle.getInt( GOLD ); depth = bundle.getInt( DEPTH ); - + + gold = bundle.getInt( GOLD ); + energy = bundle.getInt( ENERGY ); + Statistics.restoreFromBundle( bundle ); Generator.restoreFromBundle( bundle ); diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/blobs/Alchemy.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/blobs/Alchemy.java index 81e5eaa9c..a8123859f 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/blobs/Alchemy.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/blobs/Alchemy.java @@ -24,10 +24,12 @@ package com.shatteredpixel.shatteredpixeldungeon.actors.blobs; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.effects.BlobEmitter; import com.shatteredpixel.shatteredpixeldungeon.effects.Speck; +import com.shatteredpixel.shatteredpixeldungeon.items.EnergyCrystal; import com.shatteredpixel.shatteredpixeldungeon.journal.Notes; -import com.shatteredpixel.shatteredpixeldungeon.scenes.AlchemyScene; +import com.watabou.utils.PathFinder; +import com.watabou.utils.Random; -public class Alchemy extends Blob implements AlchemyScene.AlchemyProvider { +public class Alchemy extends Blob { protected int pos; @@ -39,6 +41,17 @@ public class Alchemy extends Blob implements AlchemyScene.AlchemyProvider { cell = j + i* Dungeon.level.width(); if (Dungeon.level.insideMap(cell)) { off[cell] = cur[cell]; + + //for pre-v1.1.0 saves, drops 1/4 the pot's old energy contents in crystals + if (off[cell] >= 1){ + int n; + do { + n = cell + PathFinder.NEIGHBOURS8[Random.Int( 8 )]; + } while (!Dungeon.level.passable[n] && !Dungeon.level.avoid[n]); + Dungeon.level.drop( new EnergyCrystal((int)Math.ceil(off[cell]/4f)), n ).sprite.drop( cell ); + off[cell] = 1; + } + volume += off[cell]; if (off[cell] > 0 && Dungeon.level.heroFOV[cell]){ Notes.add( Notes.Landmark.ALCHEMY ); @@ -53,18 +66,5 @@ public class Alchemy extends Blob implements AlchemyScene.AlchemyProvider { super.use( emitter ); emitter.start( Speck.factory( Speck.BUBBLE ), 0.33f, 0 ); } - - public static int alchPos; - - //1 volume is kept in reserve - - @Override - public int getEnergy() { - return Math.max(0, cur[alchPos] - 1); - } - - @Override - public void spendEnergy(int reduction) { - cur[alchPos] = Math.max(1, cur[alchPos] - reduction); - } + } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/hero/Hero.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/hero/Hero.java index 16d33faa0..061eed67e 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/hero/Hero.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/actors/hero/Hero.java @@ -832,11 +832,6 @@ public class Hero extends Char { return false; } - Alchemy alch = (Alchemy) Dungeon.level.blobs.get(Alchemy.class); - if (alch != null) { - alch.alchPos = dst; - AlchemyScene.setProvider( alch ); - } ShatteredPixelDungeon.switchScene(AlchemyScene.class); return false; diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/EnergyCrystal.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/EnergyCrystal.java new file mode 100644 index 000000000..907ad3039 --- /dev/null +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/EnergyCrystal.java @@ -0,0 +1,67 @@ +package com.shatteredpixel.shatteredpixeldungeon.items; + +import com.shatteredpixel.shatteredpixeldungeon.Assets; +import com.shatteredpixel.shatteredpixeldungeon.Dungeon; +import com.shatteredpixel.shatteredpixeldungeon.actors.hero.Hero; +import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene; +import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet; +import com.watabou.noosa.audio.Sample; +import com.watabou.utils.Random; + +import java.util.ArrayList; + +public class EnergyCrystal extends Item { + + private static final String TXT_VALUE = "%+d"; + + { + image = ItemSpriteSheet.ENERGY; + stackable = true; + } + + public EnergyCrystal() { + this( 1 ); + } + + public EnergyCrystal( int value ) { + this.quantity = value; + } + + @Override + public ArrayList actions(Hero hero ) { + return new ArrayList<>(); + } + + @Override + public boolean doPickUp( Hero hero ) { + + Dungeon.energy += quantity; + //TODO Statistics.goldCollected += quantity; + //Badges.validateGoldCollected(); + + GameScene.pickUp( this, hero.pos ); + hero.sprite.showStatus( 0x44CCFF, TXT_VALUE, quantity ); + hero.spendAndNext( TIME_TO_PICK_UP ); + + Sample.INSTANCE.play( Assets.Sounds.ITEM ); + + return true; + } + + @Override + public boolean isUpgradable() { + return false; + } + + @Override + public boolean isIdentified() { + return true; + } + + @Override + public Item random() { + quantity = Random.IntRange( 4, 6 ); + return this; + } + +} diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/Gold.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/Gold.java index 8db4c50e7..ef48d80f5 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/Gold.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/Gold.java @@ -93,18 +93,5 @@ public class Gold extends Item { quantity = Random.Int( 30 + Dungeon.depth * 10, 60 + Dungeon.depth * 20 ); return this; } - - private static final String VALUE = "value"; - - @Override - public void storeInBundle( Bundle bundle ) { - super.storeInBundle( bundle ); - bundle.put( VALUE, quantity ); - } - - @Override - public void restoreFromBundle( Bundle bundle ) { - super.restoreFromBundle(bundle); - quantity = bundle.getInt( VALUE ); - } + } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/artifacts/AlchemistsToolkit.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/artifacts/AlchemistsToolkit.java index 2ba96997b..078761033 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/artifacts/AlchemistsToolkit.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/artifacts/AlchemistsToolkit.java @@ -73,8 +73,9 @@ public class AlchemistsToolkit extends Artifact { else if (!alchemyReady) GLog.i( Messages.get(this, "not_ready") ); else if (hero.visibleEnemies() > hero.mindVisionEnemies.size()) GLog.i( Messages.get(this, "enemy_near") ); else { - - AlchemyScene.setProvider(hero.buff(kitEnergy.class)); + + //TODO notify scene we're using a toolkit here instead + //AlchemyScene.setProvider(hero.buff(kitEnergy.class)); Game.switchScene(AlchemyScene.class); } @@ -164,7 +165,7 @@ public class AlchemistsToolkit extends Artifact { alchemyReady = bundle.getBoolean(READY); } - public class kitEnergy extends ArtifactBuff implements AlchemyScene.AlchemyProvider { + public class kitEnergy extends ArtifactBuff { public void gainCharge(float levelPortion) { alchemyReady = true; @@ -197,32 +198,22 @@ public class AlchemistsToolkit extends Artifact { } else partialCharge = 0; } - - @Override - public int getEnergy() { - return charge; - } - - @Override - public void spendEnergy(int reduction) { - charge = Math.max(0, charge - reduction); - Talent.onArtifactUsed(Dungeon.hero); - } + } - + + //TODO this isn't working with new energy yet, atm it's just sucking up all energy possible public static class upgradeKit extends Recipe { @Override public boolean testIngredients(ArrayList ingredients) { - return ingredients.get(0) instanceof AlchemistsToolkit - && !AlchemyScene.providerIsToolkit(); + return ingredients.get(0) instanceof AlchemistsToolkit; } private static int lastCost; @Override public int cost(ArrayList ingredients) { - return lastCost = Math.max(1, AlchemyScene.availableEnergy()); + return lastCost = Math.max(1, Dungeon.energy); } @Override @@ -245,7 +236,7 @@ public class AlchemistsToolkit extends Artifact { sample.partialCharge = existing.partialCharge; sample.exp = existing.exp; sample.level(existing.level()); - sample.absorbEnergy(AlchemyScene.availableEnergy()); + sample.absorbEnergy(Dungeon.energy); return sample; } } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/spells/Alchemize.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/spells/Alchemize.java index e9c5d0e00..4009c3b10 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/spells/Alchemize.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/items/spells/Alchemize.java @@ -29,7 +29,8 @@ import com.shatteredpixel.shatteredpixeldungeon.scenes.AlchemyScene; import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet; import com.shatteredpixel.shatteredpixeldungeon.utils.GLog; -public class Alchemize extends Spell implements AlchemyScene.AlchemyProvider { +//TODO redesign +public class Alchemize extends Spell { { image = ItemSpriteSheet.ALCHEMIZE; @@ -43,20 +44,10 @@ public class Alchemize extends Spell implements AlchemyScene.AlchemyProvider { } detach( curUser.belongings.backpack ); updateQuickslot(); - AlchemyScene.setProvider(this); + //AlchemyScene.setProvider(this); ShatteredPixelDungeon.switchScene(AlchemyScene.class); } - @Override - public int getEnergy() { - return 0; - } - - @Override - public void spendEnergy(int reduction) { - //do nothing - } - @Override public int value() { //prices of ingredients, divided by output quantity diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/rooms/secret/SecretLaboratoryRoom.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/rooms/secret/SecretLaboratoryRoom.java index 32c6f56c8..7b12bd57f 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/rooms/secret/SecretLaboratoryRoom.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/rooms/secret/SecretLaboratoryRoom.java @@ -23,6 +23,7 @@ package com.shatteredpixel.shatteredpixeldungeon.levels.rooms.secret; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Alchemy; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob; +import com.shatteredpixel.shatteredpixeldungeon.items.EnergyCrystal; import com.shatteredpixel.shatteredpixeldungeon.items.potions.Potion; import com.shatteredpixel.shatteredpixeldungeon.items.potions.PotionOfExperience; import com.shatteredpixel.shatteredpixeldungeon.items.potions.PotionOfFrost; @@ -72,11 +73,16 @@ public class SecretLaboratoryRoom extends SecretRoom { Painter.set( level, pot, Terrain.ALCHEMY ); Blob.seed( pot.x + level.width() * pot.y, 1+Random.NormalIntRange(20, 30), Alchemy.class, level ); - + + int pos; + do { + pos = level.pointToCell(random()); + } while (level.map[pos] != Terrain.EMPTY_SP || level.heaps.get( pos ) != null); + level.drop( new EnergyCrystal().random(), pos ); + int n = Random.IntRange( 2, 3 ); HashMap, Float> chances = new HashMap<>(potionChances); for (int i=0; i < n; i++) { - int pos; do { pos = level.pointToCell(random()); } while (level.map[pos] != Terrain.EMPTY_SP || level.heaps.get( pos ) != null); diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/rooms/special/LaboratoryRoom.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/rooms/special/LaboratoryRoom.java index 1c797fa65..e06085fc7 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/rooms/special/LaboratoryRoom.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/levels/rooms/special/LaboratoryRoom.java @@ -24,6 +24,7 @@ package com.shatteredpixel.shatteredpixeldungeon.levels.rooms.special; import com.shatteredpixel.shatteredpixeldungeon.Dungeon; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Alchemy; import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob; +import com.shatteredpixel.shatteredpixeldungeon.items.EnergyCrystal; import com.shatteredpixel.shatteredpixeldungeon.items.Generator; import com.shatteredpixel.shatteredpixeldungeon.items.Item; import com.shatteredpixel.shatteredpixeldungeon.items.journal.AlchemyPage; @@ -62,11 +63,18 @@ public class LaboratoryRoom extends SpecialRoom { Painter.set( level, pot, Terrain.ALCHEMY ); int chapter = 1 + Dungeon.depth/5; - Blob.seed( pot.x + level.width() * pot.y, 1 + chapter*10 + Random.NormalIntRange(0, 10), Alchemy.class, level ); - - int n = Random.NormalIntRange( 1, 3 ); + Blob.seed( pot.x + level.width() * pot.y, 1, Alchemy.class, level ); + + int pos; + do { + pos = level.pointToCell(random()); + } while ( + level.map[pos] != Terrain.EMPTY_SP || + level.heaps.get( pos ) != null); + level.drop( new EnergyCrystal().random(), pos ); + + int n = Random.NormalIntRange( 1, 2 ); for (int i=0; i < n; i++) { - int pos; do { pos = level.pointToCell(random()); } while ( @@ -100,7 +108,6 @@ public class LaboratoryRoom extends SpecialRoom { for (int i = 0; i < pagesToDrop; i++) { AlchemyPage p = new AlchemyPage(); p.page(missingPages.remove(0)); - int pos; do { pos = level.pointToCell(random()); } while ( diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/scenes/AlchemyScene.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/scenes/AlchemyScene.java index 222b2d346..db5e25b90 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/scenes/AlchemyScene.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/scenes/AlchemyScene.java @@ -73,8 +73,11 @@ public class AlchemyScene extends PixelScene { private Emitter lowerBubbles; private SkinnedBlock water; - + + private Image energyIcon; private RenderedTextBlock energyLeft; + private IconButton energyAdd; + private RenderedTextBlock energyCost; private RedButton btnCombine; @@ -287,12 +290,24 @@ public class AlchemyScene extends PixelScene { btnGuide.setRect(0, 0, 20, 20); add(btnGuide); - energyLeft = PixelScene.renderTextBlock(Messages.get(AlchemyScene.class, "energy", availableEnergy()), 9); + energyLeft = PixelScene.renderTextBlock(Messages.get(AlchemyScene.class, "energy", Dungeon.energy), 9); energyLeft.setPos( (Camera.main.width - energyLeft.width())/2, - Camera.main.height - 5 - energyLeft.height() + Camera.main.height - 8 - energyLeft.height() ); + energyLeft.hardlight(0x44CCFF); add(energyLeft); + + energyIcon = Icons.get(Icons.ENERGY); + energyIcon.x = energyLeft.left() - energyIcon.width(); + energyIcon.y = energyLeft.top() - (energyIcon.height() - energyLeft.height())/2; + align(energyIcon); + add(energyIcon); + + //TODO does nothing currently + energyAdd = new IconButton(Icons.get(Icons.PLUS)); + energyAdd.setRect(energyLeft.right(), energyIcon.y, 16, 16); + add(energyAdd); energyCost = PixelScene.renderTextBlock(6); add(energyCost); @@ -384,9 +399,9 @@ public class AlchemyScene extends PixelScene { energyCost.visible = (cost > 0); - if (cost <= availableEnergy()) { + if (cost <= Dungeon.energy) { btnCombine.enable(true); - energyCost.resetColor(); + energyCost.hardlight(0x44CCFF); } else { btnCombine.enable(false); energyCost.hardlight(0xFF0000); @@ -408,12 +423,18 @@ public class AlchemyScene extends PixelScene { Item result = null; if (recipe != null){ - provider.spendEnergy(recipe.cost(ingredients)); - energyLeft.text(Messages.get(AlchemyScene.class, "energy", availableEnergy())); + Dungeon.energy -= recipe.cost(ingredients); + energyLeft.text(Messages.get(AlchemyScene.class, "energy", Dungeon.energy)); energyLeft.setPos( (Camera.main.width - energyLeft.width())/2, - Camera.main.height - 5 - energyLeft.height() + Camera.main.height - 8 - energyLeft.height() ); + + energyIcon.x = energyLeft.left() - energyIcon.width(); + energyIcon.y = energyLeft.top() - (energyIcon.height() - energyLeft.height())/2; + align(energyIcon); + + energyAdd.setRect(energyLeft.right(), energyIcon.y, 16, 16); result = recipe.brew(ingredients); } @@ -572,26 +593,7 @@ public class AlchemyScene extends PixelScene { slot.item( this.item = item ); } } - - private static AlchemyProvider provider; - - public static void setProvider( AlchemyProvider p ){ - provider = p; - } - - public static int availableEnergy(){ - return provider == null ? 0 : provider.getEnergy(); - } - - public static boolean providerIsToolkit(){ - return provider instanceof AlchemistsToolkit.kitEnergy; - } - - public interface AlchemyProvider { - - int getEnergy(); - - void spendEnergy(int reduction); - - } + + //TODO add code here for the toolkit's energy + } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/sprites/ItemSpriteSheet.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/sprites/ItemSpriteSheet.java index 49ebab521..4fe5c243e 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/sprites/ItemSpriteSheet.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/sprites/ItemSpriteSheet.java @@ -81,18 +81,22 @@ public class ItemSpriteSheet { private static final int UNCOLLECTIBLE = xy(1, 2); //16 slots public static final int GOLD = UNCOLLECTIBLE+0; - public static final int DEWDROP = UNCOLLECTIBLE+1; - public static final int PETAL = UNCOLLECTIBLE+2; - public static final int SANDBAG = UNCOLLECTIBLE+3; - public static final int SPIRIT_ARROW = UNCOLLECTIBLE+4; + public static final int ENERGY = UNCOLLECTIBLE+1; + + public static final int DEWDROP = UNCOLLECTIBLE+3; + public static final int PETAL = UNCOLLECTIBLE+4; + public static final int SANDBAG = UNCOLLECTIBLE+5; + public static final int SPIRIT_ARROW = UNCOLLECTIBLE+6; - public static final int GUIDE_PAGE = UNCOLLECTIBLE+6; - public static final int ALCH_PAGE = UNCOLLECTIBLE+7; + public static final int GUIDE_PAGE = UNCOLLECTIBLE+8; + public static final int ALCH_PAGE = UNCOLLECTIBLE+9; - public static final int TENGU_BOMB = UNCOLLECTIBLE+9; - public static final int TENGU_SHOCKER = UNCOLLECTIBLE+10; + public static final int TENGU_BOMB = UNCOLLECTIBLE+11; + public static final int TENGU_SHOCKER = UNCOLLECTIBLE+12; static{ assignItemRect(GOLD, 15, 13); + assignItemRect(ENERGY, 16, 16); + assignItemRect(DEWDROP, 10, 10); assignItemRect(PETAL, 8, 8); assignItemRect(SANDBAG, 10, 10); diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/CurrencyIndicator.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/CurrencyIndicator.java new file mode 100644 index 000000000..1ec0fa5c3 --- /dev/null +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/CurrencyIndicator.java @@ -0,0 +1,120 @@ +/* + * Pixel Dungeon + * Copyright (C) 2012-2015 Oleg Dolya + * + * Shattered Pixel Dungeon + * Copyright (C) 2014-2021 Evan Debenham + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see + */ + +package com.shatteredpixel.shatteredpixeldungeon.ui; + +import com.shatteredpixel.shatteredpixeldungeon.Dungeon; +import com.shatteredpixel.shatteredpixeldungeon.scenes.PixelScene; +import com.watabou.noosa.BitmapText; +import com.watabou.noosa.Game; +import com.watabou.noosa.ui.Component; + +public class CurrencyIndicator extends Component { + + private static final float TIME = 2f; + + private int lastGold = 0; + private int lastEnergy = 0; + + private BitmapText gold; + private BitmapText energy; + + private float goldTime; + private float energyTime; + + @Override + protected void createChildren() { + gold = new BitmapText( PixelScene.pixelFont); + add( gold ); + + energy = new BitmapText( PixelScene.pixelFont); + add( energy ); + + gold.visible = energy.visible = false; + } + + @Override + protected void layout() { + gold.x = x + (width - gold.width()) / 2; + gold.y = bottom() - gold.height(); + + energy.x = x + (width - energy.width()) / 2; + if (gold.visible) { + energy.y = bottom() - energy.height() - gold.height() + 2; + } else { + energy.y = bottom() - energy.height(); + } + } + + @Override + public void update() { + super.update(); + + if (gold.visible) { + + goldTime -= Game.elapsed; + if (goldTime > 0) { + gold.alpha( goldTime > TIME / 2 ? 1f : goldTime * 2 / TIME ); + } else { + gold.visible = false; + } + + } + + if (energy.visible) { + + energyTime -= Game.elapsed; + if (energyTime > 0) { + energy.alpha( energyTime > TIME / 2 ? 1f : energyTime * 2 / TIME ); + } else { + energy.visible = false; + } + + } + + if (Dungeon.gold != lastGold) { + + lastGold = Dungeon.gold; + + gold.text( Integer.toString(lastGold) ); + gold.measure(); + gold.hardlight( 0xFFFF00 ); + + gold.visible = true; + goldTime = TIME; + + layout(); + } + + if (Dungeon.energy != lastEnergy) { + lastEnergy = Dungeon.energy; + + energy.text( Integer.toString(lastEnergy) ); + energy.measure(); + energy.hardlight( 0x44CCFF ); + + energy.visible = true; + energyTime = TIME; + + layout(); + } + } +} diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/GoldIndicator.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/GoldIndicator.java deleted file mode 100644 index 9100c44a1..000000000 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/GoldIndicator.java +++ /dev/null @@ -1,83 +0,0 @@ -/* - * Pixel Dungeon - * Copyright (C) 2012-2015 Oleg Dolya - * - * Shattered Pixel Dungeon - * Copyright (C) 2014-2021 Evan Debenham - * - * This program is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see - */ - -package com.shatteredpixel.shatteredpixeldungeon.ui; - -import com.shatteredpixel.shatteredpixeldungeon.Dungeon; -import com.shatteredpixel.shatteredpixeldungeon.scenes.PixelScene; -import com.watabou.noosa.BitmapText; -import com.watabou.noosa.Game; -import com.watabou.noosa.ui.Component; - -public class GoldIndicator extends Component { - - private static final float TIME = 2f; - - private int lastValue = 0; - - private BitmapText tf; - - private float time; - - @Override - protected void createChildren() { - tf = new BitmapText( PixelScene.pixelFont); - tf.hardlight( 0xFFFF00 ); - add( tf ); - - visible = false; - } - - @Override - protected void layout() { - tf.x = x + (width - tf.width()) / 2; - tf.y = bottom() - tf.height(); - } - - @Override - public void update() { - super.update(); - - if (visible) { - - time -= Game.elapsed; - if (time > 0) { - tf.alpha( time > TIME / 2 ? 1f : time * 2 / TIME ); - } else { - visible = false; - } - - } - - if (Dungeon.gold != lastValue) { - - lastValue = Dungeon.gold; - - tf.text( Integer.toString( lastValue ) ); - tf.measure(); - - visible = true; - time = TIME; - - layout(); - } - } -} diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/Icons.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/Icons.java index 12ec82930..3ab36d811 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/Icons.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/Icons.java @@ -26,6 +26,7 @@ import com.shatteredpixel.shatteredpixeldungeon.actors.hero.HeroClass; import com.shatteredpixel.shatteredpixeldungeon.scenes.PixelScene; import com.watabou.noosa.Image; +//TODO the icons asset is getting pretty bloated, should expand the texture and reorganize public enum Icons { //button icons @@ -46,6 +47,7 @@ public enum Icons { MAGNIFY, BUFFS, BACKPACK_LRG, + PLUS, //ingame UI icons SKULL, @@ -58,8 +60,11 @@ public enum Icons { BACKPACK, SEED_POUCH, SCROLL_HOLDER, - POTION_BANDOLIER, WAND_HOLSTER, + POTION_BANDOLIER, + ENERGY, + COIN_SML, + ENERGY_SML, //hero & rankings icons DEPTH, @@ -150,6 +155,9 @@ public enum Icons { case BACKPACK_LRG: icon.frame( icon.texture.uvRect( 64, 80, 80, 96 ) ); break; + case PLUS: + icon.frame( icon.texture.uvRect( 80, 80, 91, 91 ) ); + break; case SKULL: icon.frame( icon.texture.uvRect( 0, 32, 8, 40 ) ); @@ -187,6 +195,15 @@ public enum Icons { case POTION_BANDOLIER: icon.frame( icon.texture.uvRect( 88, 32, 98, 42 ) ); break; + case ENERGY: + icon.frame( icon.texture.uvRect( 96, 80, 112, 96 ) ); + break; + case COIN_SML: + icon.frame( icon.texture.uvRect( 112, 80, 119, 87 ) ); + break; + case ENERGY_SML: + icon.frame( icon.texture.uvRect( 112, 88, 120, 95 ) ); + break; case DEPTH: icon.frame( icon.texture.uvRect( 0, 48, 13, 64 ) ); diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/QuickRecipe.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/QuickRecipe.java index 926781988..98da32fe1 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/QuickRecipe.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/QuickRecipe.java @@ -133,7 +133,7 @@ public class QuickRecipe extends Component { if (cost > 0) { arrow = new arrow(Icons.get(Icons.ARROW), cost); - arrow.hardlightText(0x00CCFF); + arrow.hardlightText(0x44CCFF); } else { arrow = new arrow(Icons.get(Icons.ARROW)); } diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/Toolbar.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/Toolbar.java index f799cfddf..169ac85ee 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/Toolbar.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/ui/Toolbar.java @@ -139,7 +139,7 @@ public class Toolbar extends Component { }); add(btnInventory = new Tool(0, 0, 24, 26) { - private GoldIndicator gold; + private CurrencyIndicator ind; @Override protected void onClick() { @@ -160,14 +160,14 @@ public class Toolbar extends Component { @Override protected void createChildren() { super.createChildren(); - gold = new GoldIndicator(); - add(gold); + ind = new CurrencyIndicator(); + add(ind); } @Override protected void layout() { super.layout(); - gold.fill(this); + ind.fill(this); } }); diff --git a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/windows/WndBag.java b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/windows/WndBag.java index cdeeb0e19..24e50c525 100644 --- a/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/windows/WndBag.java +++ b/core/src/main/java/com/shatteredpixel/shatteredpixeldungeon/windows/WndBag.java @@ -167,26 +167,64 @@ public class WndBag extends WndTabbed { } protected void placeTitle( Bag bag, int width ){ - - ItemSprite gold = new ItemSprite(ItemSpriteSheet.GOLD, null); - gold.x = width - gold.width() - 1; - gold.y = (TITLE_HEIGHT - gold.height())/2f - 1; - PixelScene.align(gold); - add(gold); - - BitmapText amt = new BitmapText( Integer.toString(Dungeon.gold), PixelScene.pixelFont ); - amt.hardlight(TITLE_COLOR); - amt.measure(); - amt.x = width - gold.width() - amt.width() - 2; - amt.y = (TITLE_HEIGHT - amt.baseLine())/2f - 1; - PixelScene.align(amt); - add(amt); + + float titleWidth; + if (Dungeon.energy == 0) { + ItemSprite gold = new ItemSprite(ItemSpriteSheet.GOLD, null); + gold.x = width - gold.width(); + gold.y = (TITLE_HEIGHT - gold.height()) / 2f; + PixelScene.align(gold); + add(gold); + + BitmapText amt = new BitmapText(Integer.toString(Dungeon.gold), PixelScene.pixelFont); + amt.hardlight(TITLE_COLOR); + amt.measure(); + amt.x = width - gold.width() - amt.width() - 1; + amt.y = (TITLE_HEIGHT - amt.baseLine()) / 2f - 1; + PixelScene.align(amt); + add(amt); + + titleWidth = amt.x; + } else { + + Image gold = Icons.get(Icons.COIN_SML); + gold.x = width - gold.width() - 0.5f; + gold.y = 0; + PixelScene.align(gold); + add(gold); + + BitmapText amt = new BitmapText(Integer.toString(Dungeon.gold), PixelScene.pixelFont); + amt.hardlight(TITLE_COLOR); + amt.measure(); + amt.x = width - gold.width() - amt.width() - 2f; + amt.y = 0; + PixelScene.align(amt); + add(amt); + + titleWidth = amt.x; + + Image energy = Icons.get(Icons.ENERGY_SML); + energy.x = width - energy.width(); + energy.y = gold.height(); + PixelScene.align(energy); + add(energy); + + amt = new BitmapText(Integer.toString(Dungeon.energy), PixelScene.pixelFont); + amt.hardlight(0x44CCFF); + amt.measure(); + amt.x = width - energy.width() - amt.width() - 1; + amt.y = energy.y; + PixelScene.align(amt); + add(amt); + + titleWidth = Math.min(titleWidth, amt.x); + } String title = selector != null ? selector.textPrompt() : null; RenderedTextBlock txtTitle = PixelScene.renderTextBlock( title != null ? Messages.titleCase(title) : Messages.titleCase( bag.name() ), 8 ); txtTitle.hardlight( TITLE_COLOR ); - txtTitle.maxWidth( (int)amt.x - 2 ); + txtTitle.maxWidth( (int)titleWidth - 2 ); txtTitle.setPos( 1, (TITLE_HEIGHT - txtTitle.height()) / 2f - 1