v0.6.2: reworked many traps and trap effects

This commit is contained in:
Evan Debenham 2017-09-26 01:35:24 -04:00
parent 35c38f2f21
commit d929e1b922
47 changed files with 816 additions and 632 deletions

View File

@ -80,6 +80,7 @@ public class ShatteredPixelDungeon extends Game {
"com.shatteredpixel.shatteredpixeldungeon.items.food.OverpricedRation" );
//v0.6.2
//rooms
com.watabou.utils.Bundle.addAlias(
com.shatteredpixel.shatteredpixeldungeon.levels.rooms.secret.RatKingRoom.class,
"com.shatteredpixel.shatteredpixeldungeon.levels.rooms.special.RatKingRoom" );
@ -90,6 +91,23 @@ public class ShatteredPixelDungeon extends Game {
com.shatteredpixel.shatteredpixeldungeon.levels.rooms.special.GardenRoom.class,
"com.shatteredpixel.shatteredpixeldungeon.levels.rooms.special.FoliageRoom" );
//traps
com.watabou.utils.Bundle.addAlias(
com.shatteredpixel.shatteredpixeldungeon.levels.traps.WornDartTrap.class,
"com.shatteredpixel.shatteredpixeldungeon.levels.traps.WornTrap" );
com.watabou.utils.Bundle.addAlias(
com.shatteredpixel.shatteredpixeldungeon.levels.traps.ShockingTrap.class,
"com.shatteredpixel.shatteredpixeldungeon.levels.traps.ParalyticTrap" );
com.watabou.utils.Bundle.addAlias(
com.shatteredpixel.shatteredpixeldungeon.levels.traps.ShockingTrap.class,
"com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap" );
com.watabou.utils.Bundle.addAlias(
com.shatteredpixel.shatteredpixeldungeon.levels.traps.GrippingTrap.class,
"com.shatteredpixel.shatteredpixeldungeon.levels.traps.SpearTrap" );
com.watabou.utils.Bundle.addAlias(
com.shatteredpixel.shatteredpixeldungeon.levels.traps.BurningTrap.class,
"com.shatteredpixel.shatteredpixeldungeon.levels.traps.FireTrap" );
com.watabou.utils.Bundle.exceptionReporter =
new com.watabou.utils.Bundle.BundleExceptionCallback() {
@Override

View File

@ -0,0 +1,117 @@
/*
* Pixel Dungeon
* Copyright (C) 2012-2015 Oleg Dolya
*
* Shattered Pixel Dungeon
* Copyright (C) 2014-2017 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 <http://www.gnu.org/licenses/>
*/
package com.shatteredpixel.shatteredpixeldungeon.actors.blobs;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Paralysis;
import com.shatteredpixel.shatteredpixeldungeon.effects.BlobEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.particles.SparkParticle;
import com.shatteredpixel.shatteredpixeldungeon.items.Heap;
import com.shatteredpixel.shatteredpixeldungeon.items.Item;
import com.shatteredpixel.shatteredpixeldungeon.items.wands.Wand;
import com.shatteredpixel.shatteredpixeldungeon.items.weapon.melee.MagesStaff;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random;
public class Electricity extends Blob {
private boolean[] water;
@Override
protected void evolve() {
water = Dungeon.level.water;
int cell;
//spread first..
for (int i = area.left-1; i <= area.right; i++) {
for (int j = area.top-1; j <= area.bottom; j++) {
cell = i + j*Dungeon.level.width();
if (cur[cell] > 0) {
spreadFromCell(cell, cur[cell]);
}
}
}
//..then decrement/shock
for (int i = area.left-1; i <= area.right; i++) {
for (int j = area.top-1; j <= area.bottom; j++) {
cell = i + j*Dungeon.level.width();
if (cur[cell] > 0) {
Char ch = Actor.findChar( cell );
if (ch != null) {
Buff.prolong( ch, Paralysis.class, 1f);
if (cur[cell] % 2 == 1) {
ch.damage(Math.round(Random.Float(2 + Dungeon.depth / 5f)), this);
}
}
Heap h = Dungeon.level.heaps.get( cell );
if (h != null){
Item toShock = h.peek();
if (toShock instanceof Wand){
((Wand) toShock).gainCharge(0.333f);
} else if (toShock instanceof MagesStaff){
((MagesStaff) toShock).gainCharge(0.333f);
}
}
off[cell] = cur[cell] - 1;
volume += off[cell];
} else {
off[cell] = 0;
}
}
}
}
private void spreadFromCell( int cell, int power ){
if (cur[cell] == 0) {
area.union(cell % Dungeon.level.width(), cell / Dungeon.level.width());
}
cur[cell] = Math.max(cur[cell], power);
for (int c : PathFinder.NEIGHBOURS4){
if (water[cell + c] && cur[cell + c] < power){
spreadFromCell(cell + c, power);
}
}
}
@Override
public void use( BlobEmitter emitter ) {
super.use( emitter );
emitter.start( SparkParticle.FACTORY, 0.05f, 0 );
}
@Override
public String tileDesc() {
return Messages.get(this, "desc");
}
}

View File

@ -25,15 +25,69 @@ import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Chill;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Frost;
import com.shatteredpixel.shatteredpixeldungeon.effects.BlobEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.CellEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.particles.SnowParticle;
import com.shatteredpixel.shatteredpixeldungeon.items.Heap;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.watabou.utils.Random;
public class Freezing {
// Returns true, if this cell is visible
public class Freezing extends Blob {
@Override
protected void evolve() {
boolean[] water = Dungeon.level.water;
int cell;
Fire fire = (Fire)Dungeon.level.blobs.get( Fire.class );
for (int i = area.left-1; i <= area.right; i++) {
for (int j = area.top-1; j <= area.bottom; j++) {
cell = i + j*Dungeon.level.width();
if (cur[cell] > 0) {
Char ch = Actor.findChar( cell );
if (ch != null) {
if (ch.buff(Frost.class) != null){
Buff.affect(ch, Frost.class, 2f);
} else {
Buff.affect(ch, Chill.class, water[cell] ? 5f : 3f);
Chill chill = ch.buff(Chill.class);
if (chill != null && chill.cooldown() >= 10f){
Buff.affect(ch, Frost.class, 5f);
}
}
}
if (fire != null) fire.clear(cell);
Heap heap = Dungeon.level.heaps.get( cell );
if (heap != null) heap.freeze();
off[cell] = cur[cell] - 1;
volume += off[cell];
} else {
off[cell] = 0;
}
}
}
}
@Override
public void use( BlobEmitter emitter ) {
super.use( emitter );
emitter.start( SnowParticle.FACTORY, 0.05f, 0 );
}
@Override
public String tileDesc() {
return Messages.get(this, "desc");
}
//legacy functionality from before this was a proper blob. Returns true if this cell is visible
public static boolean affect( int cell, Fire fire ) {
Char ch = Actor.findChar( cell );
@ -53,7 +107,7 @@ public class Freezing {
if (heap != null) {
heap.freeze();
}
if (Dungeon.level.heroFOV[cell]) {
CellEmitter.get( cell ).start( SnowParticle.FACTORY, 0.2f, 6 );
return true;

View File

@ -46,13 +46,19 @@ import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.utils.Bundle;
import com.watabou.utils.Random;
import java.util.ArrayList;
public class Burning extends Buff implements Hero.Doom {
private static final float DURATION = 8f;
private float left;
//for tracking burning of hero items
private int burnIncrement = 0;
private static final String LEFT = "left";
private static final String BURN = "burnIncrement";
{
type = buffType.NEGATIVE;
@ -62,12 +68,14 @@ public class Burning extends Buff implements Hero.Doom {
public void storeInBundle( Bundle bundle ) {
super.storeInBundle( bundle );
bundle.put( LEFT, left );
bundle.put( BURN, burnIncrement );
}
@Override
public void restoreFromBundle( Bundle bundle ) {
super.restoreFromBundle(bundle);
left = bundle.getFloat( LEFT );
burnIncrement = bundle.getInt( BURN );
}
@Override
@ -81,38 +89,42 @@ public class Burning extends Buff implements Hero.Doom {
Buff.detach( target, Chill.class);
if (target instanceof Hero) {
Hero hero = (Hero)target;
if (hero.belongings.armor != null && hero.belongings.armor.hasGlyph(Brimstone.class)){
Buff.affect(target, Brimstone.BrimstoneShield.class);
} else {
hero.damage( damage, this );
Item item = hero.belongings.randomUnequipped();
if (item instanceof Scroll
&& !(item instanceof ScrollOfUpgrade || item instanceof ScrollOfMagicalInfusion)) {
item = item.detach( hero.belongings.backpack );
GLog.w( Messages.get(this, "burnsup", Messages.capitalize(item.toString())) );
Heap.burnFX( hero.pos );
} else if (item instanceof MysteryMeat) {
item = item.detach( hero.belongings.backpack );
ChargrilledMeat steak = new ChargrilledMeat();
if (!steak.collect( hero.belongings.backpack )) {
Dungeon.level.drop( steak, hero.pos ).sprite.drop();
burnIncrement++;
//at 4+ turns, there is a (turns-3)/3 chance an item burns
if (Random.Int(3) < (burnIncrement - 3)){
burnIncrement = 0;
ArrayList<Item> burnable = new ArrayList<>();
//does not reach inside of containers
for (Item i : hero.belongings.backpack.items){
if ((i instanceof Scroll && !(i instanceof ScrollOfUpgrade || i instanceof ScrollOfMagicalInfusion))
|| i instanceof MysteryMeat){
burnable.add(i);
}
}
if (!burnable.isEmpty()){
Item toBurn = Random.element(burnable).detach(hero.belongings.backpack);
if (toBurn instanceof MysteryMeat){
ChargrilledMeat steak = new ChargrilledMeat();
if (!steak.collect( hero.belongings.backpack )) {
Dungeon.level.drop( steak, hero.pos ).sprite.drop();
}
}
Heap.burnFX( hero.pos );
GLog.w( Messages.get(this, "burnsup", Messages.capitalize(toBurn.toString())) );
}
GLog.w( Messages.get(this, "burnsup", item.toString()) );
Heap.burnFX( hero.pos );
}
}
} else {
@ -127,6 +139,9 @@ public class Burning extends Buff implements Hero.Doom {
!(item instanceof ScrollOfUpgrade || item instanceof ScrollOfMagicalInfusion)) {
target.sprite.emitter().burst( ElmoParticle.FACTORY, 6 );
((Thief)target).item = null;
} else if (item instanceof MysteryMeat) {
target.sprite.emitter().burst( ElmoParticle.FACTORY, 6 );
((Thief)target).item = new ChargrilledMeat();
}
}

View File

@ -21,21 +21,10 @@
package com.shatteredpixel.shatteredpixeldungeon.actors.buffs;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.hero.Hero;
import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.Thief;
import com.shatteredpixel.shatteredpixeldungeon.items.Item;
import com.shatteredpixel.shatteredpixeldungeon.items.food.FrozenCarpaccio;
import com.shatteredpixel.shatteredpixeldungeon.items.food.MysteryMeat;
import com.shatteredpixel.shatteredpixeldungeon.items.potions.Potion;
import com.shatteredpixel.shatteredpixeldungeon.items.potions.PotionOfMight;
import com.shatteredpixel.shatteredpixeldungeon.items.potions.PotionOfStrength;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.sprites.CharSprite;
import com.shatteredpixel.shatteredpixeldungeon.ui.BuffIndicator;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.utils.Random;
import java.text.DecimalFormat;
@ -51,40 +40,7 @@ public class Chill extends FlavourBuff {
if (target.buff(Frost.class) != null) return false;
if (super.attachTo(target)){
Burning.detach( target, Burning.class );
//chance of potion breaking is the same as speed factor.
if (Random.Float(1f) > speedFactor() && target instanceof Hero) {
Hero hero = (Hero)target;
Item item = hero.belongings.randomUnequipped();
if (item instanceof Potion
&& !(item instanceof PotionOfStrength || item instanceof PotionOfMight)) {
item = item.detach( hero.belongings.backpack );
GLog.w( Messages.get(this, "freezes", item.toString()) );
((Potion) item).shatter(hero.pos);
} else if (item instanceof MysteryMeat) {
item = item.detach( hero.belongings.backpack );
FrozenCarpaccio carpaccio = new FrozenCarpaccio();
if (!carpaccio.collect( hero.belongings.backpack )) {
Dungeon.level.drop( carpaccio, target.pos ).sprite.drop();
}
GLog.w( Messages.get(this, "freezes", item.toString()) );
}
} else if (target instanceof Thief) {
Item item = ((Thief) target).item;
if (item instanceof Potion && !(item instanceof PotionOfStrength || item instanceof PotionOfMight)) {
((Potion) ((Thief) target).item).shatter(target.pos);
((Thief) target).item = null;
}
}
Buff.detach( target, Burning.class );
return true;
} else {
return false;

View File

@ -36,6 +36,9 @@ import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.sprites.CharSprite;
import com.shatteredpixel.shatteredpixeldungeon.ui.BuffIndicator;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.utils.Random;
import java.util.ArrayList;
public class Frost extends FlavourBuff {
@ -56,24 +59,28 @@ public class Frost extends FlavourBuff {
if (target instanceof Hero) {
Hero hero = (Hero)target;
Item item = hero.belongings.randomUnequipped();
if (item instanceof Potion
&& !(item instanceof PotionOfStrength || item instanceof PotionOfMight)) {
item = item.detach( hero.belongings.backpack );
GLog.w( Messages.get(this, "freezes", item.toString()) );
((Potion) item).shatter(hero.pos);
} else if (item instanceof MysteryMeat) {
item = item.detach( hero.belongings.backpack );
FrozenCarpaccio carpaccio = new FrozenCarpaccio();
if (!carpaccio.collect( hero.belongings.backpack )) {
Dungeon.level.drop( carpaccio, target.pos ).sprite.drop();
ArrayList<Item> freezable = new ArrayList<>();
//does not reach inside of containers
for (Item i : hero.belongings.backpack.items){
if ((i instanceof Potion && !(i instanceof PotionOfStrength || i instanceof PotionOfMight))
|| i instanceof MysteryMeat){
freezable.add(i);
}
GLog.w( Messages.get(this, "freezes", item.toString()) );
}
if (!freezable.isEmpty()){
Item toFreeze = Random.element(freezable).detach( hero.belongings.backpack );
if (toFreeze instanceof Potion){
((Potion) toFreeze).shatter(hero.pos);
} else if (toFreeze instanceof MysteryMeat){
FrozenCarpaccio carpaccio = new FrozenCarpaccio();
if (!carpaccio.collect( hero.belongings.backpack )) {
Dungeon.level.drop( carpaccio, target.pos ).sprite.drop();
}
}
GLog.w( Messages.get(this, "freezes", toFreeze.toString()) );
}
} else if (target instanceof Thief) {
Item item = ((Thief) target).item;
@ -81,6 +88,8 @@ public class Frost extends FlavourBuff {
if (item instanceof Potion && !(item instanceof PotionOfStrength || item instanceof PotionOfMight)) {
((Potion) ((Thief) target).item).shatter(target.pos);
((Thief) target).item = null;
} else if (item instanceof MysteryMeat){
((Thief) target).item = new FrozenCarpaccio();;
}
}

View File

@ -26,7 +26,6 @@ import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.npcs.Ghost;
import com.shatteredpixel.shatteredpixeldungeon.items.food.MysteryMeat;
import com.shatteredpixel.shatteredpixeldungeon.items.wands.Wand;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.sprites.CharSprite;
import com.shatteredpixel.shatteredpixeldungeon.sprites.GreatCrabSprite;
@ -68,7 +67,7 @@ public class GreatCrab extends Crab {
//crab blocks all attacks originating from the hero or enemy characters or traps if it is alerted.
//All direct damage from these sources is negated, no exceptions. blob/debuff effects go through as normal.
if ((enemySeen && state != SLEEPING && paralysed == 0)
&& (src instanceof Wand || src instanceof LightningTrap.Electricity || src instanceof Char)){
&& (src instanceof Wand || src instanceof Char)){
GLog.n( Messages.get(this, "noticed") );
sprite.showStatus( CharSprite.NEUTRAL, Messages.get(this, "blocked") );
} else {

View File

@ -25,7 +25,9 @@ import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.effects.particles.SparkParticle;
import com.shatteredpixel.shatteredpixeldungeon.items.Generator;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.shatteredpixel.shatteredpixeldungeon.items.armor.glyphs.Potential;
import com.shatteredpixel.shatteredpixeldungeon.items.wands.WandOfLightning;
import com.shatteredpixel.shatteredpixeldungeon.items.weapon.enchantments.Shocking;
import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.sprites.CharSprite;
@ -93,7 +95,7 @@ public class Shaman extends Mob implements Callback {
if (Dungeon.level.water[enemy.pos] && !enemy.flying) {
dmg *= 1.5f;
}
enemy.damage( dmg, LightningTrap.LIGHTNING );
enemy.damage( dmg, this );
enemy.sprite.centerEmitter().burst( SparkParticle.FACTORY, 3 );
enemy.sprite.flash();
@ -121,6 +123,8 @@ public class Shaman extends Mob implements Callback {
}
{
resistances.add( LightningTrap.Electricity.class );
resistances.add( WandOfLightning.class );
resistances.add( Shocking.class );
resistances.add( Potential.class );
}
}

View File

@ -40,7 +40,7 @@ import com.shatteredpixel.shatteredpixeldungeon.items.weapon.enchantments.Grim;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.levels.PrisonBossLevel;
import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SpearTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.GrippingTrap;
import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
@ -171,7 +171,7 @@ public class Tengu extends Mob {
} while (!fieldOfView[trapPos] || Dungeon.level.solid[trapPos]);
if (Dungeon.level.map[trapPos] == Terrain.INACTIVE_TRAP) {
Dungeon.level.setTrap( new SpearTrap().reveal(), trapPos );
Dungeon.level.setTrap( new GrippingTrap().reveal(), trapPos );
Level.set( trapPos, Terrain.TRAP );
ScrollOfMagicMapping.discover( trapPos );
}
@ -253,7 +253,9 @@ public class Tengu extends Mob {
target = enemy.pos;
} else {
chooseEnemy();
target = enemy.pos;
if (enemy != null) {
target = enemy.pos;
}
}
spend( TICK );

View File

@ -26,7 +26,6 @@ import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.effects.Lightning;
import com.shatteredpixel.shatteredpixeldungeon.items.armor.Armor;
import com.shatteredpixel.shatteredpixeldungeon.items.armor.Armor.Glyph;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite.Glowing;
import com.watabou.noosa.Camera;
@ -45,7 +44,7 @@ public class Potential extends Glyph {
int shockDmg = Random.NormalIntRange( 2, 6 );
defender.damage( shockDmg, LightningTrap.LIGHTNING );
defender.damage( shockDmg, this );
checkOwner( defender );
if (defender == Dungeon.hero) {

View File

@ -27,9 +27,9 @@ import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Burning;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Poison;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Venom;
import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.Eye;
import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.Shaman;
import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.Warlock;
import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.Yog;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.watabou.utils.Random;
import java.util.HashSet;
@ -48,7 +48,7 @@ public class RingOfElements extends Ring {
FULL.add( ToxicGas.class );
FULL.add( Poison.class );
FULL.add( Venom.class );
FULL.add( LightningTrap.Electricity.class );
FULL.add( Shaman.class );
FULL.add( Warlock.class );
FULL.add( Eye.class );
FULL.add( Yog.BurningFist.class );

View File

@ -55,7 +55,7 @@ import com.shatteredpixel.shatteredpixeldungeon.items.scrolls.ScrollOfTeleportat
import com.shatteredpixel.shatteredpixeldungeon.items.weapon.missiles.MissileWeapon;
import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.CursingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ShockingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SummoningTrap;
import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica;
import com.shatteredpixel.shatteredpixeldungeon.messages.Languages;
@ -273,7 +273,7 @@ public class CursedWand {
//shock and recharge
case 3:
new LightningTrap().set( user.pos ).activate();
new ShockingTrap().set( user.pos ).activate();
Buff.prolong(user, Recharging.class, 20f);
ScrollOfRecharging.charge(user);
SpellSprite.show(user, SpellSprite.CHARGE);

View File

@ -122,6 +122,15 @@ public abstract class Wand extends Item {
}
}
public void gainCharge( float amt ){
partialCharge += amt;
while (partialCharge >= 1) {
curCharges = Math.min(maxCharges, curCharges+1);
partialCharge--;
updateQuickslot();
}
}
public void charge( Char owner ) {
if (charger == null) charger = new Charger();
charger.attachTo( owner );

View File

@ -29,7 +29,6 @@ import com.shatteredpixel.shatteredpixeldungeon.effects.Lightning;
import com.shatteredpixel.shatteredpixeldungeon.effects.particles.SparkParticle;
import com.shatteredpixel.shatteredpixeldungeon.items.weapon.enchantments.Shocking;
import com.shatteredpixel.shatteredpixeldungeon.items.weapon.melee.MagesStaff;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSpriteSheet;
@ -74,7 +73,7 @@ public class WandOfLightning extends DamageWand {
for (Char ch : affected){
processSoulMark(ch, chargesPerCast());
ch.damage(Math.round(damageRoll() * multipler), LightningTrap.LIGHTNING);
ch.damage(Math.round(damageRoll() * multipler), this);
if (ch == Dungeon.hero) Camera.main.shake( 2, 0.3f );
ch.sprite.centerEmitter().burst( SparkParticle.FACTORY, 3 );

View File

@ -27,7 +27,6 @@ import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.effects.Lightning;
import com.shatteredpixel.shatteredpixeldungeon.effects.particles.SparkParticle;
import com.shatteredpixel.shatteredpixeldungeon.items.weapon.Weapon;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.shatteredpixel.shatteredpixeldungeon.sprites.ItemSprite;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Random;
@ -78,7 +77,7 @@ public class Shocking extends Weapon.Enchantment {
}
affected.add(ch);
ch.damage(Dungeon.level.water[ch.pos] && !ch.flying ? 2*damage : damage, LightningTrap.LIGHTNING);
ch.damage(Dungeon.level.water[ch.pos] && !ch.flying ? 2*damage : damage, this);
ch.sprite.centerEmitter().burst(SparkParticle.FACTORY, 3);
ch.sprite.flash();

View File

@ -208,6 +208,12 @@ public class MagesStaff extends MeleeWeapon {
return this;
}
public void gainCharge( float amt ){
if (wand != null){
wand.gainCharge(amt);
}
}
public Class<?extends Wand> wandClass(){
return wand != null ? wand.getClass() : null;

View File

@ -27,23 +27,17 @@ import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.npcs.Blacksmith;
import com.shatteredpixel.shatteredpixeldungeon.levels.painters.CavesPainter;
import com.shatteredpixel.shatteredpixeldungeon.levels.painters.Painter;
import com.shatteredpixel.shatteredpixeldungeon.levels.rooms.Room;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.BurningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ConfusionTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ExplosiveTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FireTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FlashingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FlockTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FrostTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.GrippingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.GuardianTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.OozeTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ParalyticTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.PitfallTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.PoisonTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.PoisonDartTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.RockfallTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SpearTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.StormTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SummoningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.TeleportationTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.VenomTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.WarpingTrap;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
@ -102,17 +96,17 @@ public class CavesLevel extends RegularLevel {
@Override
protected Class<?>[] trapClasses() {
return new Class[]{ FireTrap.class, FrostTrap.class, PoisonTrap.class, SpearTrap.class, VenomTrap.class,
ExplosiveTrap.class, FlashingTrap.class, GrippingTrap.class, ParalyticTrap.class, LightningTrap.class, RockfallTrap.class, OozeTrap.class,
ConfusionTrap.class, FlockTrap.class, GuardianTrap.class, PitfallTrap.class, SummoningTrap.class, TeleportationTrap.class,
WarpingTrap.class};
return new Class[]{ BurningTrap.class, PoisonDartTrap.class, FrostTrap.class, StormTrap.class, VenomTrap.class,
GrippingTrap.class, ExplosiveTrap.class, RockfallTrap.class, GuardianTrap.class,
ConfusionTrap.class, SummoningTrap.class, WarpingTrap.class,
PitfallTrap.class };
}
@Override
protected float[] trapChances() {
return new float[]{ 8, 8, 8, 8, 8,
4, 4, 4, 4, 4, 4, 4,
2, 2, 2, 2, 2, 2,
4, 4, 4, 4,
2, 2, 2,
1 };
}

View File

@ -29,18 +29,15 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.painters.Painter;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.BlazingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.CursingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.DisarmingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.DisintegrationTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ExplosiveTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FlockTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FlashingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FrostTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.GrippingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.GuardianTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.OozeTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.PitfallTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.RockfallTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SpearTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.StormTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SummoningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.TeleportationTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.VenomTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.WarpingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.WeakeningTrap;
@ -91,17 +88,17 @@ public class CityLevel extends RegularLevel {
@Override
protected Class<?>[] trapClasses() {
return new Class[]{ BlazingTrap.class, FrostTrap.class, SpearTrap.class, VenomTrap.class,
ExplosiveTrap.class, GrippingTrap.class, LightningTrap.class, RockfallTrap.class, OozeTrap.class, WeakeningTrap.class,
CursingTrap.class, FlockTrap.class, GuardianTrap.class, PitfallTrap.class, SummoningTrap.class, TeleportationTrap.class,
DisarmingTrap.class, WarpingTrap.class};
return new Class[]{ FrostTrap.class, StormTrap.class, VenomTrap.class, BlazingTrap.class, DisintegrationTrap.class,
ExplosiveTrap.class, RockfallTrap.class, FlashingTrap.class, GuardianTrap.class, WeakeningTrap.class,
SummoningTrap.class, WarpingTrap.class, CursingTrap.class,
PitfallTrap.class, DisarmingTrap.class };
}
@Override
protected float[] trapChances() {
return new float[]{ 8, 8, 8, 8,
4, 4, 4, 4, 4, 4,
2, 2, 2, 2, 2, 2,
return new float[]{ 8, 8, 8, 8, 8,
4, 4, 4, 4, 4,
2, 2, 2,
1, 1 };
}

View File

@ -34,16 +34,14 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.traps.DisarmingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.DisintegrationTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.DistortionTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ExplosiveTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FlockTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FlashingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FrostTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.GrimTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.GrippingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.GuardianTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.OozeTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SpearTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.PitfallTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.RockfallTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.StormTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SummoningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.TeleportationTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.VenomTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.WarpingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.WeakeningTrap;
@ -105,17 +103,17 @@ public class HallsLevel extends RegularLevel {
@Override
protected Class<?>[] trapClasses() {
return new Class[]{ BlazingTrap.class, DisintegrationTrap.class, FrostTrap.class, SpearTrap.class, VenomTrap.class,
ExplosiveTrap.class, GrippingTrap.class, LightningTrap.class, OozeTrap.class, WeakeningTrap.class,
CursingTrap.class, FlockTrap.class, GrimTrap.class, GuardianTrap.class, SummoningTrap.class, TeleportationTrap.class,
DisarmingTrap.class, DistortionTrap.class, WarpingTrap.class};
return new Class[]{ FrostTrap.class, StormTrap.class, VenomTrap.class, BlazingTrap.class, DisintegrationTrap.class,
ExplosiveTrap.class, RockfallTrap.class, FlashingTrap.class, GuardianTrap.class, WeakeningTrap.class,
SummoningTrap.class, WarpingTrap.class, CursingTrap.class, GrimTrap.class,
PitfallTrap.class, DisarmingTrap.class, DistortionTrap.class };
}
@Override
protected float[] trapChances() {
return new float[]{ 8, 8, 8, 8, 8,
4, 4, 4, 4, 4,
2, 2, 2, 2, 2, 2,
2, 2, 2, 2,
1, 1, 1 };
}

View File

@ -35,7 +35,7 @@ import com.shatteredpixel.shatteredpixeldungeon.items.Item;
import com.shatteredpixel.shatteredpixeldungeon.items.keys.IronKey;
import com.shatteredpixel.shatteredpixeldungeon.levels.rooms.MazeRoom;
import com.shatteredpixel.shatteredpixeldungeon.levels.rooms.Room;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SpearTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.GrippingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.Trap;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.plants.Plant;
@ -223,7 +223,7 @@ public class PrisonBossLevel extends Level {
for (int i = 0; i < length(); i++){
if (map[i] == Terrain.INACTIVE_TRAP) {
Trap t = new SpearTrap().reveal();
Trap t = new GrippingTrap().reveal();
t.active = false;
setTrap(t, i);
map[i] = Terrain.INACTIVE_TRAP;

View File

@ -30,17 +30,14 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.painters.Painter;
import com.shatteredpixel.shatteredpixeldungeon.levels.painters.PrisonPainter;
import com.shatteredpixel.shatteredpixeldungeon.levels.rooms.Room;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.AlarmTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.BurningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ChillingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ConfusionTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FireTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FlashingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FlockTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.GrippingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.LightningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.OozeTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ParalyticTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.PoisonTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SpearTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.PoisonDartTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ShockingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SummoningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.TeleportationTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ToxicTrap;
@ -97,16 +94,16 @@ public class PrisonLevel extends RegularLevel {
@Override
protected Class<?>[] trapClasses() {
return new Class[]{ ChillingTrap.class, FireTrap.class, PoisonTrap.class, SpearTrap.class, ToxicTrap.class,
AlarmTrap.class, FlashingTrap.class, GrippingTrap.class, ParalyticTrap.class, LightningTrap.class, OozeTrap.class,
return new Class[]{ ChillingTrap.class, ShockingTrap.class, ToxicTrap.class, BurningTrap.class, PoisonDartTrap.class,
AlarmTrap.class, OozeTrap.class, GrippingTrap.class,
ConfusionTrap.class, FlockTrap.class, SummoningTrap.class, TeleportationTrap.class, };
}
@Override
protected float[] trapChances() {
return new float[]{ 4, 4, 4, 4,
2, 2, 2, 2, 2, 2,
1, 1, 1, 1 };
return new float[]{ 8, 8, 8, 8, 8,
4, 4, 4,
2, 2, 2, 2 };
}
@Override

View File

@ -45,10 +45,10 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.rooms.special.SpecialRoom
import com.shatteredpixel.shatteredpixeldungeon.levels.rooms.standard.EntranceRoom;
import com.shatteredpixel.shatteredpixeldungeon.levels.rooms.standard.ExitRoom;
import com.shatteredpixel.shatteredpixeldungeon.levels.rooms.standard.StandardRoom;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.BurningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ChillingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ExplosiveTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FireTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.WornTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.WornDartTrap;
import com.watabou.utils.Bundle;
import com.watabou.utils.Random;
@ -155,7 +155,7 @@ public abstract class RegularLevel extends Level {
}
protected Class<?>[] trapClasses(){
return new Class<?>[]{WornTrap.class};
return new Class<?>[]{WornDartTrap.class};
}
protected float[] trapChances() {
@ -326,7 +326,7 @@ public abstract class RegularLevel extends Level {
do {
cell = randomDropCell();
if (item instanceof Scroll) {
while (traps.get(cell) instanceof FireTrap) {
while (traps.get(cell) instanceof BurningTrap) {
cell = randomDropCell();
}

View File

@ -30,12 +30,14 @@ import com.shatteredpixel.shatteredpixeldungeon.levels.painters.Painter;
import com.shatteredpixel.shatteredpixeldungeon.levels.painters.SewerPainter;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.AlarmTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ChillingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ConfusionTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FlockTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.OozeTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ShockingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SummoningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.TeleportationTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ToxicTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.WornTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.WornDartTrap;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.tiles.DungeonTilemap;
@ -87,19 +89,19 @@ public class SewerLevel extends RegularLevel {
@Override
protected Class<?>[] trapClasses() {
return Dungeon.depth == 1 ?
new Class<?>[]{WornTrap.class} :
new Class<?>[]{ChillingTrap.class, ToxicTrap.class, WornTrap.class,
new Class<?>[]{ WornDartTrap.class } :
new Class<?>[]{ ChillingTrap.class, ShockingTrap.class, ToxicTrap.class, WornDartTrap.class,
AlarmTrap.class, OozeTrap.class,
FlockTrap.class, SummoningTrap.class, TeleportationTrap.class, };
ConfusionTrap.class, FlockTrap.class, SummoningTrap.class, TeleportationTrap.class };
}
@Override
protected float[] trapChances() {
return Dungeon.depth == 1 ?
new float[]{1} :
new float[]{4, 4, 4,
2, 2,
1, 1, 1};
new float[]{8, 8, 8, 8,
4, 4,
2, 2, 2, 2};
}
@Override

View File

@ -31,19 +31,16 @@ import com.shatteredpixel.shatteredpixeldungeon.items.weapon.missiles.MissileWea
import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain;
import com.shatteredpixel.shatteredpixeldungeon.levels.painters.Painter;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.BlazingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ConfusionTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.DisintegrationTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ExplosiveTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FlashingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FlockTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.GrimTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ParalyticTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SpearTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.GrippingTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.PoisonDartTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.SummoningTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.TeleportationTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.ToxicTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.Trap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.VenomTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.WarpingTrap;
import com.watabou.utils.Point;
import com.watabou.utils.Random;
@ -56,13 +53,10 @@ public class TrapsRoom extends SpecialRoom {
Class<? extends Trap> trapClass;
switch (Random.Int(5)){
case 0: default:
trapClass = SpearTrap.class;
break;
case 1:
case 0:
trapClass = !Dungeon.bossLevel(Dungeon.depth + 1)? null : SummoningTrap.class;
break;
case 2: case 3: case 4:
default:
trapClass = Random.oneOf(levelTraps[Dungeon.depth/5]);
break;
}
@ -153,13 +147,13 @@ public class TrapsRoom extends SpecialRoom {
@SuppressWarnings("unchecked")
private static Class<?extends Trap>[][] levelTraps = new Class[][]{
//sewers
{ToxicTrap.class, TeleportationTrap.class, FlockTrap.class},
{GrippingTrap.class, TeleportationTrap.class, FlockTrap.class},
//prison
{ConfusionTrap.class, ExplosiveTrap.class, ParalyticTrap.class},
{PoisonDartTrap.class, GrippingTrap.class, ExplosiveTrap.class},
//caves
{BlazingTrap.class, VenomTrap.class, ExplosiveTrap.class},
{PoisonDartTrap.class, FlashingTrap.class, ExplosiveTrap.class},
//city
{WarpingTrap.class, VenomTrap.class, DisintegrationTrap.class},
{WarpingTrap.class, FlashingTrap.class, DisintegrationTrap.class},
//halls, muahahahaha
{GrimTrap.class}
};

View File

@ -26,7 +26,7 @@ import com.shatteredpixel.shatteredpixeldungeon.items.Generator;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain;
import com.shatteredpixel.shatteredpixeldungeon.levels.painters.Painter;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FireTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.BurningTrap;
import com.watabou.utils.Point;
import com.watabou.utils.Random;
@ -74,7 +74,7 @@ public class BlacksmithRoom extends StandardRoom {
for(Point p : getPoints()) {
int cell = level.pointToCell(p);
if (level.map[cell] == Terrain.TRAP){
level.setTrap(new FireTrap().reveal(), cell);
level.setTrap(new BurningTrap().reveal(), cell);
}
}
}

View File

@ -24,7 +24,7 @@ package com.shatteredpixel.shatteredpixeldungeon.levels.rooms.standard;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain;
import com.shatteredpixel.shatteredpixeldungeon.levels.painters.Painter;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.FireTrap;
import com.shatteredpixel.shatteredpixeldungeon.levels.traps.BurningTrap;
import com.watabou.utils.Point;
import com.watabou.utils.Random;
@ -63,15 +63,15 @@ public class BurnedRoom extends PatchRoom {
break;
case 2:
t = Terrain.TRAP;
level.setTrap(new FireTrap().reveal(), cell);
level.setTrap(new BurningTrap().reveal(), cell);
break;
case 3:
t = Terrain.SECRET_TRAP;
level.setTrap(new FireTrap().hide(), cell);
level.setTrap(new BurningTrap().hide(), cell);
break;
case 4:
t = Terrain.INACTIVE_TRAP;
FireTrap trap = new FireTrap();
BurningTrap trap = new BurningTrap();
trap.reveal().active = false;
level.setTrap(trap, cell);
break;

View File

@ -21,13 +21,15 @@
package com.shatteredpixel.shatteredpixeldungeon.levels.traps;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Fire;
import com.shatteredpixel.shatteredpixeldungeon.effects.CellEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.particles.FlameParticle;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.watabou.utils.PathFinder;
public class FireTrap extends Trap {
public class BurningTrap extends Trap {
{
color = ORANGE;
@ -36,9 +38,13 @@ public class FireTrap extends Trap {
@Override
public void activate() {
GameScene.add( Blob.seed( pos, 2, Fire.class ) );
CellEmitter.get( pos ).burst( FlameParticle.FACTORY, 5 );
for( int i : PathFinder.NEIGHBOURS9) {
if (!Dungeon.level.solid[pos + i]) {
GameScene.add( Blob.seed( pos+i, 2, Fire.class ) );
CellEmitter.get( pos+i ).burst( FlameParticle.FACTORY, 5 );
}
}
}
}

View File

@ -23,15 +23,12 @@ package com.shatteredpixel.shatteredpixeldungeon.levels.traps;
import com.shatteredpixel.shatteredpixeldungeon.Assets;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Chill;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Freezing;
import com.shatteredpixel.shatteredpixeldungeon.effects.Splash;
import com.shatteredpixel.shatteredpixeldungeon.items.Heap;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Random;
import com.watabou.utils.PathFinder;
public class ChillingTrap extends Trap{
@ -46,17 +43,10 @@ public class ChillingTrap extends Trap{
Splash.at( pos, 0xFFB2D6FF, 5);
Sample.INSTANCE.play( Assets.SND_SHATTER );
}
Heap heap = Dungeon.level.heaps.get( pos );
if (heap != null) heap.freeze();
Char ch = Actor.findChar( pos );
if (ch != null){
Chill.prolong(ch, Chill.class, 5f + Random.Int(Dungeon.depth));
ch.damage(Random.NormalIntRange(1 , Dungeon.depth), this);
if (!ch.isAlive() && ch == Dungeon.hero){
Dungeon.fail( getClass() );
GLog.n( Messages.get(this, "ondeath") );
for( int i : PathFinder.NEIGHBOURS9) {
if (!Dungeon.level.solid[pos + i]) {
GameScene.add(Blob.seed(pos + i, 10, Freezing.class));
}
}
}

View File

@ -32,8 +32,6 @@ import com.shatteredpixel.shatteredpixeldungeon.items.Item;
import com.shatteredpixel.shatteredpixeldungeon.items.KindOfWeapon;
import com.shatteredpixel.shatteredpixeldungeon.items.KindofMisc;
import com.shatteredpixel.shatteredpixeldungeon.items.armor.Armor;
import com.shatteredpixel.shatteredpixeldungeon.items.artifacts.Artifact;
import com.shatteredpixel.shatteredpixeldungeon.items.rings.Ring;
import com.shatteredpixel.shatteredpixeldungeon.items.weapon.Weapon;
import com.shatteredpixel.shatteredpixeldungeon.items.weapon.missiles.Boomerang;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
@ -94,17 +92,13 @@ public class CursingTrap extends Trap {
}
KindofMisc misc1 = hero.belongings.misc1;
if (misc1 instanceof Artifact){
if (misc1 != null){
priorityCurse.add(misc1);
} else if (misc1 instanceof Ring){
canCurse.add(misc1);
}
KindofMisc misc2 = hero.belongings.misc2;
if (misc2 instanceof Artifact){
if (misc2 != null){
priorityCurse.add(misc2);
} else if (misc2 instanceof Ring){
canCurse.add(misc2);
}
Collections.shuffle(priorityCurse);

View File

@ -31,6 +31,7 @@ import com.shatteredpixel.shatteredpixeldungeon.effects.Beam;
import com.shatteredpixel.shatteredpixeldungeon.items.Heap;
import com.shatteredpixel.shatteredpixeldungeon.items.Item;
import com.shatteredpixel.shatteredpixeldungeon.items.bags.Bag;
import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.tiles.DungeonTilemap;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
@ -41,28 +42,41 @@ public class DisintegrationTrap extends Trap {
{
color = VIOLET;
shape = LARGE_DOT;
shape = CROSSHAIR;
}
@Override
public Trap hide() {
//this one can't be hidden
return reveal();
}
@Override
public void activate() {
if (Dungeon.level.heroFOV[ pos ]) {
ShatteredPixelDungeon.scene().add( new Beam.DeathRay( DungeonTilemap.tileCenterToWorld(pos-1),
DungeonTilemap.tileCenterToWorld(pos+1)));
ShatteredPixelDungeon.scene().add(new Beam.DeathRay(DungeonTilemap.tileCenterToWorld(pos - Dungeon.level.width()),
DungeonTilemap.tileCenterToWorld(pos + Dungeon.level.width())));
Sample.INSTANCE.play( Assets.SND_RAY );
Char target = Actor.findChar(pos);
//find the closest char that can be aimed at
if (target == null){
for (Char ch : Actor.chars()){
Ballistica bolt = new Ballistica(pos, ch.pos, Ballistica.PROJECTILE);
if (bolt.collisionPos == ch.pos &&
(target == null || Dungeon.level.distance(pos, ch.pos) < Dungeon.level.distance(pos, target.pos))){
target = ch;
}
}
}
Heap heap = Dungeon.level.heaps.get(pos);
if (heap != null) heap.explode();
Char ch = Actor.findChar(pos);
if (ch != null){
ch.damage( Math.max( ch.HT/5, Random.Int(ch.HP / 2, 2 * ch.HP / 3) ), this );
if (ch == Dungeon.hero){
Hero hero = (Hero)ch;
if (target != null) {
if (Dungeon.level.heroFOV[pos] || Dungeon.level.heroFOV[target.pos]) {
Sample.INSTANCE.play(Assets.SND_RAY);
ShatteredPixelDungeon.scene().add(new Beam.DeathRay(DungeonTilemap.tileCenterToWorld(pos), target.sprite.center()));
}
target.damage( Math.max( target.HT/5, Random.Int(target.HP / 2, 2 * target.HP / 3) ), this );
if (target == Dungeon.hero){
Hero hero = (Hero)target;
if (!hero.isAlive()){
Dungeon.fail( getClass() );
GLog.n( Messages.get(this, "ondeath") );

View File

@ -25,44 +25,56 @@ import com.shatteredpixel.shatteredpixeldungeon.Assets;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Bleeding;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Blindness;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Cripple;
import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.Mob;
import com.shatteredpixel.shatteredpixeldungeon.effects.CellEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.Speck;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Random;
public class FlashingTrap extends Trap {
{
color = YELLOW;
color = GREY;
shape = STARS;
}
@Override
public void trigger() {
if (Dungeon.level.heroFOV[pos]){
Sample.INSTANCE.play(Assets.SND_TRAP);
}
//this trap is not disarmed by being triggered
reveal();
Level.set(pos, Terrain.TRAP);
activate();
}
@Override
public void activate() {
Char ch = Actor.findChar(pos);
if (ch != null) {
int len = Random.Int(5, 10)+Dungeon.depth;
Buff.prolong( ch, Blindness.class, len );
Buff.prolong( ch, Cripple.class, len );
if (ch instanceof Mob) {
if (((Mob)ch).state == ((Mob)ch).HUNTING) ((Mob)ch).state = ((Mob)ch).WANDERING;
((Mob)ch).beckon( Dungeon.level.randomDestination() );
}
if (ch == Dungeon.hero){
Sample.INSTANCE.play( Assets.SND_BLAST );
Char c = Actor.findChar( pos );
if (c != null) {
int damage = Math.max( 0, (Dungeon.depth) - c.drRoll() );
Buff.affect( c, Bleeding.class ).set( damage );
Buff.prolong( c, Blindness.class, 10f );
Buff.prolong( c, Cripple.class, 20f );
if (c instanceof Mob) {
if (((Mob)c).state == ((Mob)c).HUNTING) ((Mob)c).state = ((Mob)c).WANDERING;
((Mob)c).beckon( Dungeon.level.randomDestination() );
}
}
if (Dungeon.level.heroFOV[pos]) {
GameScene.flash(0xFFFFFF);
CellEmitter.get(pos).burst( Speck.factory(Speck.LIGHT), 4 );
Sample.INSTANCE.play( Assets.SND_BLAST );
}
}
}

View File

@ -56,7 +56,7 @@ public class FlockTrap extends Trap {
&& Actor.findChar(i) == null
&& !(Dungeon.level.pit[i])) {
Sheep sheep = new Sheep();
sheep.lifespan = 2 + Random.Int(Dungeon.depth + 10);
sheep.lifespan = Random.NormalIntRange(3 + Dungeon.depth/4, 6 + Dungeon.depth/2 );
sheep.pos = i;
Dungeon.level.mobPress(sheep);
GameScene.add(sheep);

View File

@ -23,16 +23,13 @@ package com.shatteredpixel.shatteredpixeldungeon.levels.traps;
import com.shatteredpixel.shatteredpixeldungeon.Assets;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Chill;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Frost;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Freezing;
import com.shatteredpixel.shatteredpixeldungeon.effects.Splash;
import com.shatteredpixel.shatteredpixeldungeon.items.Heap;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.utils.BArray;
import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Random;
import com.watabou.utils.PathFinder;
public class FrostTrap extends Trap {
@ -43,22 +40,16 @@ public class FrostTrap extends Trap {
@Override
public void activate() {
if (Dungeon.level.heroFOV[ pos ]){
Splash.at( pos, 0xFFB2D6FF, 10);
Splash.at( pos, 0xFFB2D6FF, 5);
Sample.INSTANCE.play( Assets.SND_SHATTER );
}
Heap heap = Dungeon.level.heaps.get( pos );
if (heap != null) heap.freeze();
Char ch = Actor.findChar(pos);
if (ch != null){
ch.damage(Random.NormalIntRange(1 , Dungeon.depth), this);
Chill.prolong(ch, Frost.class, 10f + Random.Int(Dungeon.depth));
if (!ch.isAlive() && ch == Dungeon.hero){
Dungeon.fail( getClass() );
GLog.n( Messages.get(this, "ondeath") );
PathFinder.buildDistanceMap( pos, BArray.not( Dungeon.level.solid, null ), 2 );
for (int i = 0; i < PathFinder.distance.length; i++) {
if (PathFinder.distance[i] < Integer.MAX_VALUE) {
GameScene.add(Blob.seed(i, 20, Freezing.class));
}
}
}

View File

@ -21,20 +21,34 @@
package com.shatteredpixel.shatteredpixeldungeon.levels.traps;
import com.shatteredpixel.shatteredpixeldungeon.Assets;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Bleeding;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Cripple;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Roots;
import com.shatteredpixel.shatteredpixeldungeon.effects.Wound;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain;
import com.watabou.noosa.audio.Sample;
public class GrippingTrap extends Trap {
{
color = GREY;
shape = CROSSHAIR;
shape = DOTS;
}
@Override
public void trigger() {
if (Dungeon.level.heroFOV[pos]){
Sample.INSTANCE.play(Assets.SND_TRAP);
}
//this trap is not disarmed by being triggered
reveal();
Level.set(pos, Terrain.TRAP);
activate();
}
@Override
@ -43,10 +57,9 @@ public class GrippingTrap extends Trap {
Char c = Actor.findChar( pos );
if (c != null) {
int damage = Math.max( 0, (Dungeon.depth) - ( c.drRoll() / 2 ) );
int damage = Math.max( 0, (Dungeon.depth) - c.drRoll() );
Buff.affect( c, Bleeding.class ).set( damage );
Buff.prolong( c, Cripple.class, 15f);
Buff.prolong( c, Roots.class, 5f);
Buff.prolong( c, Cripple.class, Cripple.DURATION);
Wound.hit( c );
} else {
Wound.hit( pos );

View File

@ -1,88 +0,0 @@
/*
* Pixel Dungeon
* Copyright (C) 2012-2015 Oleg Dolya
*
* Shattered Pixel Dungeon
* Copyright (C) 2014-2017 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 <http://www.gnu.org/licenses/>
*/
package com.shatteredpixel.shatteredpixeldungeon.levels.traps;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.effects.CellEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.Lightning;
import com.shatteredpixel.shatteredpixeldungeon.effects.particles.SparkParticle;
import com.shatteredpixel.shatteredpixeldungeon.items.Heap;
import com.shatteredpixel.shatteredpixeldungeon.items.Item;
import com.shatteredpixel.shatteredpixeldungeon.items.wands.Wand;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.noosa.Camera;
import com.watabou.utils.Random;
import java.util.ArrayList;
public class LightningTrap extends Trap {
{
color = TEAL;
shape = CROSSHAIR;
}
@Override
public void activate() {
Char ch = Actor.findChar( pos );
if (ch != null) {
ch.damage( Math.max( 1, Random.Int( ch.HP / 3, 2 * ch.HP / 3 ) ), LIGHTNING );
if (ch == Dungeon.hero) {
Camera.main.shake( 2, 0.3f );
if (!ch.isAlive()) {
Dungeon.fail( getClass() );
GLog.n( Messages.get(this, "ondeath") );
}
}
ArrayList<Lightning.Arc> arcs = new ArrayList<>();
arcs.add(new Lightning.Arc(pos - Dungeon.level.width(), pos + Dungeon.level.width()));
arcs.add(new Lightning.Arc(pos - 1, pos + 1));
ch.sprite.parent.add( new Lightning( arcs, null ) );
}
Heap heap = Dungeon.level.heaps.get(pos);
if (heap != null){
//TODO: this should probably charge staffs too
Item item = heap.items.peek();
if (item instanceof Wand){
Wand wand = (Wand)item;
((Wand)item).curCharges += (int)Math.ceil((wand.maxCharges - wand.curCharges)/2f);
}
}
CellEmitter.center( pos ).burst( SparkParticle.FACTORY, Random.IntRange( 3, 4 ) );
}
//FIXME: this is bad, handle when you rework resistances, make into a category
public static final Electricity LIGHTNING = new Electricity();
public static class Electricity {
}
}

View File

@ -0,0 +1,92 @@
/*
* Pixel Dungeon
* Copyright (C) 2012-2015 Oleg Dolya
*
* Shattered Pixel Dungeon
* Copyright (C) 2014-2017 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 <http://www.gnu.org/licenses/>
*/
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.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Poison;
import com.shatteredpixel.shatteredpixeldungeon.items.weapon.missiles.Dart;
import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica;
import com.shatteredpixel.shatteredpixeldungeon.sprites.MissileSprite;
import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Callback;
import com.watabou.utils.Random;
public class PoisonDartTrap extends Trap {
{
color = GREEN;
shape = CROSSHAIR;
}
@Override
public Trap hide() {
//this one can't be hidden
return reveal();
}
@Override
public void activate() {
Char target = Actor.findChar(pos);
//find the closest char that can be aimed at
if (target == null){
for (Char ch : Actor.chars()){
Ballistica bolt = new Ballistica(pos, ch.pos, Ballistica.PROJECTILE);
if (bolt.collisionPos == ch.pos &&
(target == null || Dungeon.level.distance(pos, ch.pos) < Dungeon.level.distance(pos, target.pos))){
target = ch;
}
}
}
if (target != null) {
final Char finalTarget = target;
final PoisonDartTrap trap = this;
if (Dungeon.level.heroFOV[pos] || Dungeon.level.heroFOV[target.pos]) {
((MissileSprite) ShatteredPixelDungeon.scene().recycle(MissileSprite.class)).
reset(pos, target.sprite, new Dart(), new Callback() {
@Override
public void call() {
int dmg = Random.NormalIntRange(1, 4) - finalTarget.drRoll();
finalTarget.damage(dmg, trap);
if (finalTarget == Dungeon.hero && !finalTarget.isAlive()){
Dungeon.fail( getClass() );
}
Buff.affect( finalTarget, Poison.class )
.set( Poison.durationFactor( finalTarget ) * (4 + Dungeon.depth) );
Sample.INSTANCE.play(Assets.SND_HIT, 1, 1, Random.Float(0.8f, 1.25f));
finalTarget.sprite.bloodBurstA(finalTarget.sprite.center(), dmg);
finalTarget.sprite.flash();
}
});
} else {
finalTarget.damage(Random.NormalIntRange(1, 4) - finalTarget.drRoll(), trap);
Buff.affect( finalTarget, Poison.class )
.set( Poison.durationFactor( finalTarget ) * (4 + Dungeon.depth) );
}
}
}
}

View File

@ -29,43 +29,69 @@ import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Paralysis;
import com.shatteredpixel.shatteredpixeldungeon.effects.CellEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.Speck;
import com.shatteredpixel.shatteredpixeldungeon.levels.RegularLevel;
import com.shatteredpixel.shatteredpixeldungeon.levels.rooms.Room;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.utils.BArray;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.noosa.Camera;
import com.watabou.noosa.audio.Sample;
import com.watabou.utils.PathFinder;
import com.watabou.utils.Point;
import com.watabou.utils.Random;
import java.util.ArrayList;
public class RockfallTrap extends Trap {
{
color = GREY;
shape = DIAMOND;
}
@Override
public Trap hide() {
//this one can't be hidden
return reveal();
}
@Override
public void activate() {
boolean seen = false;
for (int i : PathFinder.NEIGHBOURS9){
if (Dungeon.level.solid[pos+i])
continue;
if (Dungeon.level.heroFOV[ pos+i ]){
CellEmitter.get( pos + i - Dungeon.level.width() ).start(Speck.factory(Speck.ROCK), 0.07f, 10);
if (!seen) {
Camera.main.shake(3, 0.7f);
Sample.INSTANCE.play(Assets.SND_ROCKS);
seen = true;
ArrayList<Integer> rockCells = new ArrayList<>();
if (Dungeon.level instanceof RegularLevel){
Room r = ((RegularLevel) Dungeon.level).room(pos);
int cell;
for (Point p : r.getPoints()){
cell = Dungeon.level.pointToCell(p);
if (!Dungeon.level.solid[cell]){
rockCells.add(cell);
}
}
//if we don't have rooms, then just do 5x5
} else {
PathFinder.buildDistanceMap( pos, BArray.not( Dungeon.level.solid, null ), 2 );
for (int i = 0; i < PathFinder.distance.length; i++) {
if (PathFinder.distance[i] < Integer.MAX_VALUE) {
rockCells.add(i);
}
}
}
boolean seen = false;
for (int cell : rockCells){
Char ch = Actor.findChar( pos+i );
if (Dungeon.level.heroFOV[ cell ]){
CellEmitter.get( cell - Dungeon.level.width() ).start(Speck.factory(Speck.ROCK), 0.07f, 10);
seen = true;
}
Char ch = Actor.findChar( cell );
if (ch != null){
int damage = Random.NormalIntRange(Dungeon.depth, Dungeon.depth*2);
int damage = Random.NormalIntRange(5+Dungeon.depth, 10+Dungeon.depth*2);
damage -= ch.drRoll();
ch.damage( Math.max(damage, 0) , this);
@ -77,6 +103,11 @@ public class RockfallTrap extends Trap {
}
}
}
if (seen){
Camera.main.shake(3, 0.7f);
Sample.INSTANCE.play(Assets.SND_ROCKS);
}
}
}

View File

@ -21,22 +21,33 @@
package com.shatteredpixel.shatteredpixeldungeon.levels.traps;
import com.shatteredpixel.shatteredpixeldungeon.Assets;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.ParalyticGas;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Electricity;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.watabou.noosa.audio.Sample;
import com.watabou.utils.PathFinder;
public class ParalyticTrap extends Trap{
public class ShockingTrap extends Trap {
{
color = YELLOW;
shape = GRILL;
shape = DOTS;
}
@Override
public void activate() {
GameScene.add( Blob.seed( pos, 80 + 5 * Dungeon.depth, ParalyticGas.class ) );
if (Dungeon.level.heroFOV[pos]){
Sample.INSTANCE.play( Assets.SND_LIGHTNING );
}
for( int i : PathFinder.NEIGHBOURS9) {
if (!Dungeon.level.solid[pos + i]) {
GameScene.add(Blob.seed(pos + i, 10, Electricity.class));
}
}
}
}

View File

@ -1,72 +0,0 @@
/*
* Pixel Dungeon
* Copyright (C) 2012-2015 Oleg Dolya
*
* Shattered Pixel Dungeon
* Copyright (C) 2014-2017 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 <http://www.gnu.org/licenses/>
*/
package com.shatteredpixel.shatteredpixeldungeon.levels.traps;
import com.shatteredpixel.shatteredpixeldungeon.Assets;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.effects.Wound;
import com.shatteredpixel.shatteredpixeldungeon.levels.Level;
import com.shatteredpixel.shatteredpixeldungeon.levels.Terrain;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Random;
public class SpearTrap extends Trap {
{
color = GREY;
shape = DOTS;
}
@Override
public void trigger() {
if (Dungeon.level.heroFOV[pos]){
Sample.INSTANCE.play(Assets.SND_TRAP);
}
//this trap is not disarmed by being triggered
reveal();
Level.set(pos, Terrain.TRAP);
activate();
}
@Override
public void activate() {
if (Dungeon.level.heroFOV[pos]){
Sample.INSTANCE.play(Assets.SND_HIT);
Wound.hit(pos);
}
Char ch = Actor.findChar( pos);
if (ch != null && !ch.flying){
int damage = Random.NormalIntRange(Dungeon.depth, Dungeon.depth*2);
damage -= ch.drRoll();
ch.damage( Math.max(damage, 0) , this);
if (!ch.isAlive() && ch == Dungeon.hero){
Dungeon.fail( getClass() );
GLog.n( Messages.get(this, "ondeath") );
}
}
}
}

View File

@ -21,31 +21,35 @@
package com.shatteredpixel.shatteredpixeldungeon.levels.traps;
import com.shatteredpixel.shatteredpixeldungeon.Assets;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Poison;
import com.shatteredpixel.shatteredpixeldungeon.effects.CellEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.particles.PoisonParticle;
public class PoisonTrap extends Trap{
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Blob;
import com.shatteredpixel.shatteredpixeldungeon.actors.blobs.Electricity;
import com.shatteredpixel.shatteredpixeldungeon.scenes.GameScene;
import com.shatteredpixel.shatteredpixeldungeon.utils.BArray;
import com.watabou.noosa.audio.Sample;
import com.watabou.utils.PathFinder;
public class StormTrap extends Trap {
{
color = VIOLET;
shape = CROSSHAIR;
color = YELLOW;
shape = STARS;
}
@Override
public void activate() {
Char ch = Actor.findChar( pos );
if (ch != null) {
Buff.affect( ch, Poison.class ).set( Poison.durationFactor( ch ) * (4 + Dungeon.depth / 2) );
if (Dungeon.level.heroFOV[pos]){
Sample.INSTANCE.play( Assets.SND_LIGHTNING );
}
PathFinder.buildDistanceMap( pos, BArray.not( Dungeon.level.solid, null ), 2 );
for (int i = 0; i < PathFinder.distance.length; i++) {
if (PathFinder.distance[i] < Integer.MAX_VALUE) {
GameScene.add(Blob.seed(i, 20, Electricity.class));
}
}
CellEmitter.center( pos ).burst( PoisonParticle.SPLASH, 3 );
}
}

View File

@ -25,18 +25,17 @@ import com.shatteredpixel.shatteredpixeldungeon.Assets;
import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
import com.shatteredpixel.shatteredpixeldungeon.actors.hero.Hero;
import com.shatteredpixel.shatteredpixeldungeon.actors.mobs.Mob;
import com.shatteredpixel.shatteredpixeldungeon.effects.CellEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.Speck;
import com.shatteredpixel.shatteredpixeldungeon.items.Heap;
import com.shatteredpixel.shatteredpixeldungeon.items.Item;
import com.shatteredpixel.shatteredpixeldungeon.items.artifacts.TimekeepersHourglass;
import com.shatteredpixel.shatteredpixeldungeon.scenes.InterlevelScene;
import com.watabou.noosa.Game;
import com.shatteredpixel.shatteredpixeldungeon.items.scrolls.ScrollOfTeleportation;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.utils.BArray;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Random;
import java.util.ArrayList;
public class WarpingTrap extends Trap {
@ -49,41 +48,50 @@ public class WarpingTrap extends Trap {
public void activate() {
CellEmitter.get(pos).start(Speck.factory(Speck.LIGHT), 0.2f, 3);
Sample.INSTANCE.play( Assets.SND_TELEPORT );
if (Dungeon.depth > 1 && !Dungeon.bossLevel()) {
//each depth has 1 more weight than the previous depth.
float[] depths = new float[Dungeon.depth-1];
for (int i = 1; i < Dungeon.depth; i++) depths[i-1] = i;
int depth = 1+Random.chances(depths);
Heap heap = Dungeon.level.heaps.get(pos);
if (heap != null) {
ArrayList<Item> dropped = Dungeon.droppedItems.get( depth );
if (dropped == null) {
Dungeon.droppedItems.put( depth, dropped = new ArrayList<Item>() );
Char ch = Actor.findChar( pos);
if (ch instanceof Hero){
ScrollOfTeleportation.teleportHero( (Hero)ch);
BArray.setFalse(Dungeon.level.visited);
BArray.setFalse(Dungeon.level.mapped);
Dungeon.observe();
} else if (ch != null){
int count = 10;
int pos;
do {
pos = Dungeon.level.randomRespawnCell();
if (count-- <= 0) {
break;
}
for (Item item : heap.items){
dropped.add(item);
} while (pos == -1);
if (pos == -1 || Dungeon.bossLevel()) {
GLog.w( Messages.get(ScrollOfTeleportation.class, "no_tele") );
} else {
ch.pos = pos;
if (ch instanceof Mob && ((Mob) ch).state == ((Mob) ch).HUNTING){
((Mob) ch).state = ((Mob) ch).WANDERING;
}
heap.destroy();
ch.sprite.place(ch.pos);
ch.sprite.visible = Dungeon.level.heroFOV[pos];
}
Char ch = Actor.findChar( pos );
if (ch == Dungeon.hero){
Buff buff = Dungeon.hero.buff(TimekeepersHourglass.timeFreeze.class);
if (buff != null) buff.detach();
InterlevelScene.mode = InterlevelScene.Mode.RETURN;
InterlevelScene.returnDepth = depth;
InterlevelScene.returnPos = -1;
Game.switchScene(InterlevelScene.class);
} else if (ch != null) {
ch.destroy();
ch.sprite.killAndErase();
Dungeon.level.mobs.remove(ch);
}
Heap heap = Dungeon.level.heaps.get(pos);
if (heap != null){
int cell = Dungeon.level.randomRespawnCell();
Item item = heap.pickUp();
if (cell != -1) {
Dungeon.level.drop( item, cell );
}
}
}

View File

@ -25,7 +25,6 @@ import com.shatteredpixel.shatteredpixeldungeon.Dungeon;
import com.shatteredpixel.shatteredpixeldungeon.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Buff;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Slow;
import com.shatteredpixel.shatteredpixeldungeon.actors.buffs.Weakness;
import com.shatteredpixel.shatteredpixeldungeon.effects.CellEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.particles.ShadowParticle;
@ -46,8 +45,6 @@ public class WeakeningTrap extends Trap{
Char ch = Actor.findChar( pos );
if (ch == Dungeon.hero){
Buff.prolong( ch, Weakness.class, Weakness.duration(ch)*2f);
} else if (ch != null) {
Buff.prolong( ch, Slow.class, Slow.duration(ch));
}
}
}

View File

@ -0,0 +1,86 @@
/*
* Pixel Dungeon
* Copyright (C) 2012-2015 Oleg Dolya
*
* Shattered Pixel Dungeon
* Copyright (C) 2014-2017 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 <http://www.gnu.org/licenses/>
*/
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.actors.Actor;
import com.shatteredpixel.shatteredpixeldungeon.actors.Char;
import com.shatteredpixel.shatteredpixeldungeon.items.weapon.missiles.Dart;
import com.shatteredpixel.shatteredpixeldungeon.mechanics.Ballistica;
import com.shatteredpixel.shatteredpixeldungeon.sprites.MissileSprite;
import com.watabou.noosa.audio.Sample;
import com.watabou.utils.Callback;
import com.watabou.utils.Random;
public class WornDartTrap extends Trap {
{
color = GREY;
shape = CROSSHAIR;
}
@Override
public Trap hide() {
//this one can't be hidden
return reveal();
}
@Override
public void activate() {
Char target = Actor.findChar(pos);
//find the closest char that can be aimed at
if (target == null){
for (Char ch : Actor.chars()){
Ballistica bolt = new Ballistica(pos, ch.pos, Ballistica.PROJECTILE);
if (bolt.collisionPos == ch.pos &&
(target == null || Dungeon.level.distance(pos, ch.pos) < Dungeon.level.distance(pos, target.pos))){
target = ch;
}
}
}
if (target != null) {
final Char finalTarget = target;
final WornDartTrap trap = this;
if (Dungeon.level.heroFOV[pos] || Dungeon.level.heroFOV[target.pos]) {
((MissileSprite) ShatteredPixelDungeon.scene().recycle(MissileSprite.class)).
reset(pos, target.sprite, new Dart(), new Callback() {
@Override
public void call() {
int dmg = Random.NormalIntRange(1, 4) - finalTarget.drRoll();
finalTarget.damage(dmg, trap);
if (finalTarget == Dungeon.hero && !finalTarget.isAlive()){
Dungeon.fail( getClass() );
}
Sample.INSTANCE.play(Assets.SND_HIT, 1, 1, Random.Float(0.8f, 1.25f));
finalTarget.sprite.bloodBurstA(finalTarget.sprite.center(), dmg);
finalTarget.sprite.flash();
}
});
} else {
finalTarget.damage(Random.NormalIntRange(1, 4) - finalTarget.drRoll(), trap);
}
}
}
}

View File

@ -1,47 +0,0 @@
/*
* Pixel Dungeon
* Copyright (C) 2012-2015 Oleg Dolya
*
* Shattered Pixel Dungeon
* Copyright (C) 2014-2017 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 <http://www.gnu.org/licenses/>
*/
package com.shatteredpixel.shatteredpixeldungeon.levels.traps;
import com.shatteredpixel.shatteredpixeldungeon.effects.CellEmitter;
import com.shatteredpixel.shatteredpixeldungeon.effects.Speck;
import com.shatteredpixel.shatteredpixeldungeon.messages.Messages;
import com.shatteredpixel.shatteredpixeldungeon.utils.GLog;
public class WornTrap extends Trap {
{
color = BLACK;
shape = DOTS;
}
@Override
public Trap hide() {
//this one can't be hidden
return reveal();
}
@Override
public void activate() {
CellEmitter.get(pos).burst(Speck.factory(Speck.STEAM), 6);
GLog.i( Messages.get(this, "nothing") );
}
}

View File

@ -36,42 +36,19 @@ public class MissileSprite extends ItemSprite implements Tweener.Listener {
private Callback callback;
public void reset( int from, int to, Item item, Callback listener ) {
revive();
int image;
if (item == null) view(image = 0, null);
else view(image = item.image(), item.glowing());
setup( DungeonTilemap.tileToWorld( from ),
DungeonTilemap.tileToWorld( to ),
image,
listener);
reset( DungeonTilemap.tileToWorld( from ), DungeonTilemap.tileToWorld( to ), item, listener);
}
public void reset( Visual from, Visual to, Item item, Callback listener ) {
revive();
int image;
if (item == null) view(image = 0, null);
else view(image = item.image(), item.glowing());
setup( from.center(this),
to.center(this),
image,
listener);
reset(from.center(this), to.center(this), item, listener );
}
public void reset( Visual from, int to, Item item, Callback listener ) {
revive();
int image;
if (item == null) view(image = 0, null);
else view(image = item.image(), item.glowing());
setup( from.center(this),
DungeonTilemap.tileToWorld( to ),
image,
listener);
reset(from.center(this), DungeonTilemap.tileToWorld( to ), item, listener );
}
public void reset( int from, Visual to, Item item, Callback listener ) {
reset(DungeonTilemap.tileToWorld( from ), to.center(this), item, listener );
}
public void reset( PointF from, PointF to, Item item, Callback listener) {

View File

@ -1,10 +1,15 @@
###blobs
actors.blobs.confusiongas.desc=A cloud of confusion gas is swirling here.
actors.blobs.electricity.desc=A field of electricity is sparking brightly here.
actors.blobs.electricity.rankings_desc=Electrocuted
actors.blobs.fire.desc=A fire is raging here.
actors.blobs.foliage.desc=Shafts of light pierce the gloom of the underground garden.
actors.blobs.freezing.desc=The air is unnaturally frigid here.
actors.blobs.goowarn.desc=Specks of dark energy are swarming here!
actors.blobs.paralyticgas.desc=A cloud of paralytic gas is swirling here.

View File

@ -33,9 +33,11 @@ levels.traps.alarmtrap.desc=This trap seems to be tied to a loud alarm mechanism
levels.traps.blazingtrap.name=Blazing trap
levels.traps.blazingtrap.desc=Stepping on this trap will ignite a powerful chemical mixture, setting a wide area ablaze.
levels.traps.burningtrap.name=Burning trap
levels.traps.burningtrap.desc=Stepping on this trap will ignite a chemical mixture, setting the surrounding area aflame.
levels.traps.chillingtrap.name=Chilling trap
levels.traps.chillingtrap.ondeath=You succumb to the chilling trap...
levels.traps.chillingtrap.desc=When activated, chemicals in this trap will trigger a snap-frost at its location.
levels.traps.chillingtrap.desc=When activated, chemicals in this trap will rapidly freeze the air around its location.
levels.traps.confusiontrap.name=Confusion gas trap
levels.traps.confusiontrap.desc=Triggering this trap will set a cloud of confusion gas loose within the immediate area.
@ -52,7 +54,7 @@ levels.traps.disintegrationtrap.name=Disintegration trap
levels.traps.disintegrationtrap.one=The trap disintegrates your %s!
levels.traps.disintegrationtrap.some=The trap disintegrates some of your %s!
levels.traps.disintegrationtrap.ondeath=You were killed by the disintegration trap...
levels.traps.disintegrationtrap.desc=When triggered, this trap will lance the target with beams of disintegration, dealing significant damage and destroying items.
levels.traps.disintegrationtrap.desc=When triggered, this trap will lance the nearest target with beams of disintegration, dealing significant damage and destroying items.\n\nThankfully the trigger mechanism isn't hidden.
levels.traps.distortiontrap.name=Distortion trap
levels.traps.distortiontrap.desc=Built from strange magic of unknown origin, this trap will shift and morph the world around you.
@ -60,25 +62,21 @@ levels.traps.distortiontrap.desc=Built from strange magic of unknown origin, thi
levels.traps.explosivetrap.name=Explosive trap
levels.traps.explosivetrap.desc=This trap contains some powdered explosive and a trigger mechanism. Activating it will cause an explosion in the immediate area.
levels.traps.firetrap.name=Fire trap
levels.traps.firetrap.desc=Stepping on this trap will ignite a chemical mixture, setting the immediate area aflame.
levels.traps.flashingtrap.name=Flashing trap
levels.traps.flashingtrap.desc=On activation, this trap will ignite a potent flashing powder stored within, temporarily blinding and crippling its victim.
levels.traps.flashingtrap.desc=On activation, this trap will ignite a potent flashing powder stored within, temporarily blinding, crippling, and injuring its victim.\n\nThe trap must have a large store of powder, as it can activate many times without breaking.
levels.traps.flocktrap.name=Flock trap
levels.traps.flocktrap.desc=Perhaps a joke from some amateur mage, triggering this trap will create a flock of magical sheep.
levels.traps.frosttrap.name=Frost trap
levels.traps.frosttrap.ondeath=You succumb to the freezing trap...
levels.traps.frosttrap.desc=When activated, chemicals in this trap will trigger a powerful snap-frost at its location.
levels.traps.frosttrap.desc=When activated, chemicals in this trap will rapidly freeze the air in a wide range around its location.
levels.traps.grimtrap.name=Grim trap
levels.traps.grimtrap.ondeath=You were killed by the blast of a grim trap...
levels.traps.grimtrap.desc=Extremely powerful destructive magic is stored within this trap, enough to instantly kill all but the healthiest of heroes. Triggering it will send a ranged blast of lethal magic towards the nearest character.
levels.traps.grimtrap.desc=Extremely powerful destructive magic is stored within this trap, enough to instantly kill all but the healthiest of heroes. Triggering it will send a ranged blast of lethal magic towards the nearest character.\n\nThankfully the trigger mechanism isn't hidden.
levels.traps.grippingtrap.name=Gripping trap
levels.traps.grippingtrap.desc=Triggering this trap will send barbed claws along the ground, damaging the victims feet and rooting them in place.
levels.traps.grippingtrap.desc=This trap latches onto the feet of whoever trigger it, damaging them and slowing their movement.\n\nDue to its simple nature, this trap can activate many times without breaking.
levels.traps.guardiantrap.name=Guardian trap
levels.traps.guardiantrap.alarm=The trap emits a piercing sound that echoes throughout the dungeon!
@ -86,35 +84,30 @@ levels.traps.guardiantrap.desc=This trap is tied to a strange magical mechanism,
levels.traps.guardiantrap$guardian.name=summoned guardian
levels.traps.guardiantrap$guardian.desc=This blue apparition seems to be a summoned echo of one of the dungeon's stone guardians.\n\nWhile the statue itself is almost incorporeal, the _%s,_ it's wielding, looks real.
levels.traps.lightningtrap.name=Lightning trap
levels.traps.lightningtrap.ondeath=You were killed by a discharge of a lightning trap...
levels.traps.lightningtrap.desc=A mechanism with a large amount of energy stored into it. Triggering the trap will discharge that energy into whatever activates it.
levels.traps.oozetrap.name=Ooze trap
levels.traps.oozetrap.desc=This trap will splash out caustic ooze when activated, which will burn until it is washed away.
levels.traps.paralytictrap.name=Paralytic gas trap
levels.traps.paralytictrap.desc=Triggering this trap will set a cloud of paralytic gas loose within the surrounding area.
levels.traps.pitfalltrap.name=Pitfall trap
levels.traps.pitfalltrap.desc=This pressure plate rests atop a fairly weak floor, and will likely collapse into a pit if it is pressed.
levels.traps.poisontrap.name=Poison trap
levels.traps.poisontrap.desc=A small dart-blower must be hidden nearby, activating this trap will cause it to shoot a poisoned dart at you.
levels.traps.poisondarttrap.name=Poison dart trap
levels.traps.poisondarttrap.desc=A small dart-blower must be hidden nearby, activating this trap will cause it to shoot a poisoned dart at the nearest target.\n\nThankfully the trigger mechanism isn't hidden.
levels.traps.rockfalltrap.name=Rockfall trap
levels.traps.rockfalltrap.ondeath=You were crushed by the rockfall trap...
levels.traps.rockfalltrap.desc=This trap is connected to a series of loose rocks above, triggering it will cause them to come crashing down.
levels.traps.rockfalltrap.desc=This trap is connected to a series of loose rocks above, triggering it will cause them to come crashing down over the entire room!\n\nThankfully the trigger mechanism isn't hidden.
levels.traps.speartrap.name=Spear trap
levels.traps.speartrap.ondeath=You were skewered by the spear trap...
levels.traps.speartrap.desc=The classic spear trap, primitive but effective. Due to their simple nature, these traps can activate many times without breaking.
levels.traps.shockingtrap.name=Shocking trap
levels.traps.shockingtrap.desc=A mechanism with a large amount of energy stored into it. Triggering this trap will discharge that energy into a field around it.
levels.traps.stormtrap.name=Storm trap
levels.traps.stormtrap.desc=A mechanism with a massive amount of energy stored into it. Triggering this trap will discharge that energy into a large electrical storm.
levels.traps.summoningtrap.name=Summoning trap
levels.traps.summoningtrap.desc=Triggering this trap will summon a number of this area's monsters to this location.
levels.traps.teleportationtrap.name=Teleportation trap
levels.traps.teleportationtrap.desc=Whatever triggers this trap will be warped to some other location on this floor.
levels.traps.teleportationtrap.desc=Whatever triggers this trap will be teleported to some other location on this floor.
levels.traps.toxictrap.name=Toxic gas trap
levels.traps.toxictrap.desc=Triggering this trap will set a cloud of toxic gas loose within the surrounding area.
@ -125,14 +118,13 @@ levels.traps.venomtrap.name=Venom gas trap
levels.traps.venomtrap.desc=Triggering this trap will set a cloud of deadly venom gas loose within the immediate area.
levels.traps.warpingtrap.name=Warping trap
levels.traps.warpingtrap.desc=Whatever triggers this trap will be warped to some other location in the dungeon.
levels.traps.warpingtrap.desc=Whatever triggers this trap will be warped to some other location on this floor.
levels.traps.weakeningtrap.name=Weakening trap
levels.traps.weakeningtrap.desc=Dark magic in this trap sucks the energy out of anything that comes into contact with it.
levels.traps.worntrap.name=Worn out trap
levels.traps.worntrap.nothing=Nothing happens...
levels.traps.worntrap.desc=Due to age and possibly poor workmanship, it looks like this trap has worn to the point where it won't do anything when triggered.
levels.traps.worndarttrap.name=Worn dart trap
levels.traps.worndarttrap.desc=A small dart-blower must be hidden nearby, activating this trap will cause it to shoot at the nearest target.\n\nDue to it's age it's not very harmful though, it isn't even hidden...