package th; import java.util.Vector; class Items { public static Kind key = new Kind(); public static Kind scalpel = new Kind(); public static Kind stick = new Kind(); public static Kind pencil = new Kind(); public static Kind pocket_knife = new Kind(); public static Kind spork = new Kind(); public static Kind glass = new Kind(); public static Kind meter_stick = new Kind(); public static Kind ethernet_cable = new Kind(); public static Kind screwdriver = new Kind(); public static Kind knife = new Kind(); public static Kind baseball_bat = new Kind(); public static Kind rock = new Kind(); public static Kind lightsaber = new Kind(); public static Kind textbook = new Kind(); public static Kind novel = new Kind(); public static Kind ball = new Kind(); public static Kind frying_pan = new Kind(); public static Kind whistle = new Kind(); public static Kind coffee = new Kind(); public static Kind filth = new Kind(); public static Kind dragon_fang = new Kind(); public static Kind magnifying_glass = new Kind(); public static Kind oompa_corpse = new Kind(); public static Kind gum = new Kind(); public static Kind vest = new Kind(); public static Kind top_hat = new Kind(); public static Kind fox_socks = new Kind(); public static Kind fox_box = new Kind(); public static Kind overalls = new Kind(); public static Kind wonka_whistle = new Kind(); // Quest artifacts public static Kind zaurus = new Kind(); public static Kind nerf_sword = new Kind(); public static Kind pen = new Kind(); public static Kind flask = new Kind(); public static Kind pikachu_egg = new Kind(); public static Kind cage = new Kind(); public static Kind sack = new Kind(); public static Kind mirror = new Kind(); public static Kind cookie = new Kind(); public static Kind mcookie = new Kind(); public static Kind soda = new Kind(); public static Kind carrot = new Kind(); public static Kind peanut = new Kind(); public static Kind chocolate = new Kind(); public static Kind red_shirt = new Kind(); public static Kind spock_ears = new Kind(); public static Kind furry_costume = new Kind(); public static Kind chainmail = new Kind(); // Creature corpses public static Kind gnome_corpse = new Kind(); public static Kind dwarf_corpse = new Kind(); public static Kind zergling_corpse = new Kind(); public static Kind giant_hamster_corpse = new Kind(); public static Kind human_corpse = new Kind(); public static Kind squirrel_corpse = new Kind(); public static Kind hamster_corpse = new Kind(); public static Kind cat_corpse = new Kind(); public static Kind pikachu_corpse = new Kind(); public static Kind fox_corpse = new Kind(); public static Kind spider_corpse = new Kind(); public static Kind parrot_corpse = new Kind(); public static Kind tribble_corpse = new Kind(); public static Kind mind_flayer_corpse = new Kind(); public static Kind crocodile_corpse = new Kind(); public static Kind dog_corpse = new Kind(); public static Kind conical_hat = new Kind(); public static Kind tattered_rags = new Kind(); public static Kind cloak = new Kind(); public static Kind t_shirt = new Kind(); public static Kind jacket = new Kind(); public static Kind mask = new Kind(); public static Kind metal_slab = new Kind(); public static Kind lab_coat = new Kind(); public static Kind steroid_pill = new Kind(); public static Kind pick_axe = new Kind(); public static Kind fur_scrap = new Kind(); public static Kind toad_corpse = new Kind(); public static Kind whip = new Kind(); public static Kind wand = new Kind(); public static Kind camera = new Kind(); public static Kind bulletproof_vest = new Kind(); public static Kind briefcase = new Kind(); public static Kind scythe = new Kind(); public static Kind[] all_items = { stick, scalpel, pencil, pocket_knife, spork, glass, meter_stick, ethernet_cable, screwdriver, knife, baseball_bat, rock, lightsaber, textbook, novel, ball, frying_pan, flask, cookie, mcookie, soda, squirrel_corpse, carrot, peanut, chocolate, gnome_corpse, human_corpse, hamster_corpse, cat_corpse, pikachu_corpse, tribble_corpse, spider_corpse, crocodile_corpse, conical_hat, tattered_rags, cloak, t_shirt, jacket, metal_slab, mask, lab_coat, sack, zergling_corpse, mind_flayer_corpse, steroid_pill, pick_axe, fur_scrap, wand, parrot_corpse, coffee, magnifying_glass, giant_hamster_corpse, fox_corpse, overalls, top_hat, vest, dragon_fang, filth, pikachu_egg, toad_corpse, whip, cage, whistle, gum, camera, bulletproof_vest, spock_ears, red_shirt, chainmail, furry_costume, mirror }; public static Kind[] one_of_everything = { stick, scalpel, pencil, pocket_knife, spork, glass, meter_stick, ethernet_cable, screwdriver, knife, baseball_bat, rock, lightsaber, textbook, novel, ball, frying_pan, flask, cookie, mcookie, soda, carrot, peanut, chocolate, gnome_corpse, human_corpse, hamster_corpse, cat_corpse, pikachu_corpse, tribble_corpse, spider_corpse, crocodile_corpse, conical_hat, tattered_rags, cloak, t_shirt, jacket, metal_slab, lab_coat, mask, sack, zergling_corpse, mind_flayer_corpse, steroid_pill, pick_axe, fur_scrap, wand, parrot_corpse, coffee, magnifying_glass, giant_hamster_corpse, fox_corpse, overalls, top_hat, vest, dragon_fang, filth, pikachu_egg, toad_corpse, whip, cage, whistle, gum, camera, bulletproof_vest, spock_ears, red_shirt, chainmail, furry_costume, mirror, squirrel_corpse, zaurus, pen, nerf_sword, wonka_whistle, fox_box, key, scythe }; public static Kind[] corpses = { hamster_corpse, gnome_corpse, human_corpse, cat_corpse, pikachu_corpse, tribble_corpse, spider_corpse, crocodile_corpse, zergling_corpse, mind_flayer_corpse, dwarf_corpse, parrot_corpse, giant_hamster_corpse, fox_corpse, toad_corpse, squirrel_corpse }; public static Kind[] deadly_weapons = { knife, baseball_bat, lightsaber, pick_axe, metal_slab }; public Items () { try { // stick stick.name = "Stick"; stick.damage = 1; scythe.name = "Aetherial Scythe"; scythe.damage = 30; scythe.special = Utl.gclass("scytheSpecial"); scythe.to_hit = 80; coffee.name = "Coffee"; coffee.heal = 7; coffee.veg_level = Itm.VEGETARIAN; coffee.tasty = "You prefer yours black."; coffee.special = Utl.gclass("coffeeSpecial"); whistle.name = "Ultrasonic Whistle"; whistle.special = Utl.gclass("whistleSpecial"); wonka_whistle.name = "Brass Whistle"; wonka_whistle.special = Utl.gclass("wonka_whistleSpecial"); wonka_whistle.pc_only = true; briefcase.name = "Briefcase"; briefcase.damage = 9; briefcase.special = Utl.gclass("documentSpecial"); briefcase.pc_only = true; filth.name = "Pile of Filth"; filth.tainted_chance = 100; filth.heal = 100; mask.name = "Gas Mask"; mask.armor = 1; mask.special = Utl.gclass("maskSpecial"); ball.name = "Sports Ball"; ball.damage = 1; key.name = "Key"; key.damage = 1; key.special = Utl.gclass("keySpecial"); key.pc_only = true; magnifying_glass.name = "Lens"; magnifying_glass.damage = 3; magnifying_glass.special = Utl.gclass("magnifying_glassSpecial"); mirror.name = "Magic Mirror"; mirror.special = Utl.gclass("mirrorSpecial"); scalpel.name = "Scalpel"; scalpel.damage = 4; scalpel.special = Utl.gclass("bladeSpecial"); pencil.name = "Pencil"; pencil.damage = 1; spork.name = "Plastic Spork"; spork.damage = 1; spork.special = Utl.gclass("bladeSpecial"); pocket_knife.name = "Pocket Knife"; pocket_knife.damage = 5; pocket_knife.special = Utl.gclass("bladeSpecial"); meter_stick.name = "Meter stick"; meter_stick.damage = 4; pick_axe.name = "Pick-axe"; pick_axe.damage = 12; pick_axe.deadly_weapon = true; ethernet_cable.name = "Networking cable"; ethernet_cable.damage = 2; screwdriver.name = "Screwdriver"; screwdriver.damage = 3; baseball_bat.name = "Baseball bat"; baseball_bat.damage = 9; knife.name = "Knife"; knife.damage = 10; knife.to_hit = 10; knife.deadly_weapon = true; knife.special = Utl.gclass("bladeSpecial"); novel.name = "Novel"; novel.damage = 3; novel.special = Utl.gclass("novelSpecial"); novel.use = Kind.MISC; textbook.name = "Textbook"; textbook.damage = 5; textbook.special = Utl.gclass("textbookSpecial"); textbook.use = Kind.MISC; steroid_pill.name = "Steroid Pill"; steroid_pill.heal = 5; steroid_pill.special = Utl.gclass("steroidSpecial"); lightsaber.name = "Glowing Sword"; lightsaber.damage = 20; lightsaber.deadly_weapon = true; lightsaber.to_hit = 15; whip.name = "Bullwhip"; whip.damage = 10; whip.to_hit = 25; dragon_fang.name = "Dragon Fang"; dragon_fang.damage = 12; dragon_fang.deadly_weapon = true; dragon_fang.to_hit = 50; dragon_fang.special = Utl.gclass("dragon_fangSpecial"); // The pen is mightier than the glowing sword... pen.name = "Pen of the Propagandists"; pen.damage = 25; pen.pc_only = true; pen.deadly_weapon = true; pen.special = Utl.gclass("penSpecial"); pen.to_hit = 10; zaurus.name = "Zaurus of Perspicacity"; zaurus.special = Utl.gclass("zaurusSpecial"); zaurus.pc_only = true; nerf_sword.name = "Dread Sword of Nerfing"; nerf_sword.damage = 15; nerf_sword.pc_only = true; nerf_sword.deadly_weapon = true; nerf_sword.special = Utl.gclass("nerfSpecial"); nerf_sword.to_hit = 10; frying_pan.name = "Frying Pan"; frying_pan.damage = 10; frying_pan.armor = 4; rock.name = "Rock"; rock.damage = 5; soda.name = "Soda"; soda.heal = 5; soda.veg_level = Itm.VEGAN; soda.tasty = "This sugared water is very tasty."; chocolate.name = "Chunk of chocolate"; chocolate.heal = 15; chocolate.veg_level = Itm.VEGAN; // It's dark chocolate. No milk. chocolate.tasty = "It tastes wonderful!"; fox_corpse.name = "Talking Fox corpse"; fox_corpse.heal = 10; fox_corpse.tasty = "It tastes like surrealists."; oompa_corpse.name = "Oompa-Loompa corpse"; oompa_corpse.heal = 20; oompa_corpse.tasty = "Mmm, prime-quality and chocolate fed!"; glass.name = "Shard of Glass"; glass.damage = 5; peanut.name = "Peanut"; peanut.heal = 2; peanut.veg_level = Itm.VEGAN; peanut.tasty = "Eh, it's unsalted."; carrot.name = "Carrot"; carrot.heal = 3; carrot.veg_level = Itm.VEGAN; carrot.tasty = "You feel very hoppy to have such food."; carrot.tainted_chance = 3; hamster_corpse.name = "Hamster corpse"; hamster_corpse.heal = 2; hamster_corpse.tainted_chance = 5; hamster_corpse.tasty = "It tastes like wood shavings."; squirrel_corpse.name = "Squirrel corpse"; squirrel_corpse.heal = 10; squirrel_corpse.tainted_chance = 0; squirrel_corpse.tasty = "It is very meaty, and tastes good also!"; giant_hamster_corpse.name = "Giant hamster corpse"; giant_hamster_corpse.heal = 50; giant_hamster_corpse.tainted_chance = 50; giant_hamster_corpse.tasty = "The giant hamster is an ample meal."; mind_flayer_corpse.name = "Mind flayer corpse"; mind_flayer_corpse.heal = 12; mind_flayer_corpse.tainted_chance = 20; mind_flayer_corpse.tasty = "This is real brain food."; gnome_corpse.name = "Gnome corpse"; gnome_corpse.heal = 6; gnome_corpse.tainted_chance = 10; gnome_corpse.tasty = "Gnome, the other white meat!"; dwarf_corpse.name = "Dwarf corpse"; dwarf_corpse.heal = 10; dwarf_corpse.tainted_chance = 10; dwarf_corpse.tasty = "Wow, the beard is the most flavorful part!"; pikachu_corpse.name = "Pikachu corpse"; pikachu_corpse.heal = 12; pikachu_corpse.tainted_chance = 50; pikachu_corpse.tasty = "The pikachu corpse smells slightly of ozone, and tastes tangy."; parrot_corpse.name = "Parrot corpse"; parrot_corpse.heal = 8; parrot_corpse.tainted_chance = 5; parrot_corpse.tasty = "It's not just pinin' for the fjords."; human_corpse.name = "Human corpse"; human_corpse.heal = 10; human_corpse.tainted_chance = 10; human_corpse.tasty = "Ewww..."; cat_corpse.name = "Cat corpse"; cat_corpse.heal = 5; cat_corpse.tainted_chance = 5; cat_corpse.tasty = "Hmm, tastes like rabbit."; dog_corpse.name = "Dog corpse"; dog_corpse.heal = 8; dog_corpse.tainted_chance = 5; dog_corpse.tasty = "You find the dog very tasty."; zergling_corpse.name = "Zergling corpse"; zergling_corpse.heal = 8; zergling_corpse.tainted_chance = 5; zergling_corpse.tasty = "Mmm, that's tasty parody!"; crocodile_corpse.name = "Crocodile corpse"; crocodile_corpse.heal = 12; crocodile_corpse.tainted_chance = 25; crocodile_corpse.tasty = "Mmm, savory!"; spider_corpse.name = "Spider corpse"; spider_corpse.heal = 50; spider_corpse.tainted_chance = 100; spider_corpse.tasty = "This is a bug."; toad_corpse.name = "Giant toad corpse"; toad_corpse.heal = 50; toad_corpse.tainted_chance = 100; toad_corpse.tasty = "This is a bug."; tribble_corpse.name = "Tribble corpse"; tribble_corpse.heal = 1; tribble_corpse.tainted_chance = 5; tribble_corpse.tasty = "Eww, there was a hair in this corpse!"; cookie.name = "Cookie"; cookie.heal = 8; cookie.veg_level = Itm.VEGETARIAN; cookie.tasty = "It tastes very good."; mcookie.name = "Chromatic Cookie"; mcookie.heal = 1000; mcookie.using_does_not_destroy = false; mcookie.veg_level = Itm.VEGAN; mcookie.tasty = "You are lifted to the heights of culinary wonder."; mcookie.special = Utl.gclass("mcookieSpecial"); mcookie.tainted_chance = 8; mcookie.damage = 1; mcookie.use = Kind.DEFENSE; conical_hat.name = "Conical hat"; conical_hat.armor = 2; conical_hat.special = Utl.gclass("conical_hatSpecial"); conical_hat.use = Kind.ESCAPE; tattered_rags.name = "Tattered clothing"; tattered_rags.armor = 1; chainmail.name = "Chainmail Bikini"; chainmail.armor = 3; furry_costume.name = "Costume"; furry_costume.armor = 5; furry_costume.special = Utl.gclass("furry_costumeSpecial"); overalls.name = "Pair of Overalls"; overalls.armor = 5; top_hat.name = "Top Hat"; top_hat.armor = 2; vest.name = "Black Vest"; vest.armor = 2; fur_scrap.name = "Scrap of Fur"; fur_scrap.special = Utl.gclass("fur_scrapSpecial"); fur_scrap.use = Kind.OFFENSE; wand.name = "Rubber Wand"; wand.damage = 7; wand.special = Utl.gclass("wandSpecial"); wand.use = Kind.OFFENSE; cloak.name = "Cloak"; cloak.armor = 3; jacket.name = "Fasionable Jacket"; jacket.armor = 2; t_shirt.name = "T-Shirt"; t_shirt.armor = 2; red_shirt.name = "Red Star-Trek Uniform"; red_shirt.armor = -10; // tehe spock_ears.name = "Vulcan Ears"; spock_ears.armor = 1; spock_ears.special = Utl.gclass("spock_earsSpecial"); metal_slab.armor = 4; metal_slab.name = "Slab of Metal"; metal_slab.damage = 9; flask.name = "Flask of Chemicals"; flask.special = Utl.gclass("flaskSpecial"); flask.damage = 1; flask.veg_level = Itm.VEGAN; flask.heal = 1; flask.tainted_chance = 8; flask.tasty = "It tastes funny..."; flask.use = Kind.DEFENSE; gum.name = "Blue Gum"; gum.special = Utl.gclass("gumSpecial"); gum.heal = 1; gum.veg_level = Itm.VEGAN; gum.damage = 2; gum.tainted_chance = 10; pikachu_egg.name = "Striped Yellow Egg"; pikachu_egg.heal = 20; pikachu_egg.veg_level = Itm.VEGETARIAN; pikachu_egg.tasty = "It has a bit of a zing to it."; pikachu_egg.tainted_chance = 3; pikachu_egg.special = Utl.gclass("pikachu_eggSpecial"); lab_coat.name = "Lab Coat"; lab_coat.armor = 4; lab_coat.special = Utl.gclass("lab_coatSpecial"); bulletproof_vest.name = "Bulletproof Vest"; bulletproof_vest.armor = 8; bulletproof_vest.special = Utl.gclass("bulletproof_vestSpecial"); sack.name = "Sack"; sack.special = Utl.gclass("sackSpecial"); cage.name = "Animal Cage"; cage.special = Utl.gclass("cageSpecial"); fox_box.name = "Small Cage"; fox_box.special = Utl.gclass("fox_boxSpecial"); fox_socks.name = "Fox Socks"; fox_socks.armor = 1; camera.name = "Camera"; camera.damage = 5; camera.special = Utl.gclass("cameraSpecial"); camera.use = Kind.MISC; } catch (Exception e) { Ifc.msg("Exception: " + e.getMessage()); } } } class pikachu_eggSpecial extends Special { public static String[] COLORS = { "chartreuse", "celadon", "lime-colored", "asparagus-colored", "yellow", "orpiment", "ochre", "cadmium-yellow" }; public boolean monUse (Mon user) { return false; // They should still eat it. } public boolean use (Itm self, Mon user, Node here) { Ifc.you("crack open the egg."); Itm what = Ifc.choice_itm("Dip what in the yoke?", user.inventory); if (what == null) { Ifc.you("carefully put the egg back together."); return false; } if (what.kind == Items.wand) { Ifc.your("wand glows a resplendant yellow"); ((wandSpecial)what.special).super_charge = true; } else if (what.kind == Items.dragon_fang) { Ifc.your("dragon frag glows with a " + Utl.rn(COLORS) + " aura."); what.blessed = true; } else if (what.kind == Items.flask) { Ifc.you("see the chemicals in the flask sparkle"); ((flaskSpecial)what.special).super_charge = true; } else if (Utl.contains(Items.corpses, what.kind)) { Ifc.you("watch as the arcane energies of the egg surge through the "+what.kind.name+"..."); if (what.living_form == null) { Ifc.msg("But nothing else happens. It's beyond all mortal aid.\n"); if (what.kind == Items.parrot_corpse) Ifc.msg("This is an ex-parrot!"); user.inventory.remove(self); Ifc.you("discard the empty shell."); return true; } if (!self.tainted && Utl.rn()) { Ifc.you("see the " + what.living_form.species.name + " rise form the dead as your minion!"); what.living_form.hp = 1; what.living_form.dead = false; // No more undead pikachu what.living_form.ai = what.living_form.PET; here.add(what.living_form); user.inventory.remove(what); } else if (!self.tainted) { Ifc.you("see the " + what.living_form.species.name + " rise form the dead!"); what.living_form.hp = 1; what.living_form.dead = false; here.add(what.living_form); user.inventory.remove(what); } else { Ifc.you("see something go horribly, horribly wrong!"); Ifc.msg("The corpse spasms and evaporates into a cloud of pungent smoke!\n"); Ifc.msg("Oh no, you inhale some of the acrid gas!\n"); user.last_damage = "a burning "+what.kind.name+(what.name != null? " named "+what.name : ""); user.hp = Utl.rn(3); Ifc.you("feel very sick."); user.inventory.remove(what); } } else { Ifc.your(what.kind.name+" absorbs some " +Utl.rn(COLORS)+" yolk." ); what.tainted = self.tainted; } user.inventory.remove(self); Ifc.you("discard the empty shell."); return true; } } class keySpecial extends Special { public int type = 0; public boolean monUse (Mon user) { return false; } public boolean use (Itm self, Mon user, Node here) { Ifc.msg("The key is labeled #"+type); return true; } } class flaskSpecial extends Special { public String[] types = { "Acid", "Poison", "Sticky Stuff", "Toxic Waste", "Tasty Juice" }; public int type = 0; public int uses = 0; boolean super_charge = false; public flaskSpecial () { uses = Utl.d(10); type = Utl.rn(types.length); } public boolean monUse (Mon user) { return true; } public boolean use (Itm self, Mon user, Node here) { if (user == g.player) { if (g.player.in > 11) Ifc.you("have a flask of " + types[type] + ".", user); else if (g.player.in < 5) Ifc.you("have a flask of funny liquid.", user); else { if (Utl.rn(g.player.in) < 2 || self.tainted) Ifc.you("think this is " + Utl.rn(types) + ".", user); else Ifc.you("think this is " + types[type] + ".", user); } return true; } Mon who; who = user.get_target(); if (who == null) return true; used_as_weapon(self, user, here, who, Utl.rn()); return true; } public void used_as_weapon (Itm self, Mon wielder, Node location, Mon target, boolean hit) { --uses; Ifc.you("throw|s| liquid from a flask!", wielder); if (uses == 0) { Ifc.you("run|s| out of " + types[type] + ".", wielder); wielder.inventory.remove(self); wielder.wielded = null; } if (!hit) return; switch (type) { case 0: if (target.resist_chemical) Ifc.you("|is| unaffected!", target); else { target.hp -= Utl.d(8) + (super_charge? 10 : 0); target.last_damage = "vitriol throwing"; } break; case 1: //if (target.dx > Utl.rn(20)) // Ifc.you("dodge|s| a splash of poison!", target); //else { Ifc.you("|is| weakened by poison!", target); target.st -= Utl.d(2); target.hp -= Utl.d(2,6) + (super_charge? 10 : 0); target.last_damage = (super_charge? "very ": "" ) +"poisonous liquid"; //} break; case 2: //if (target.dx > Utl.rn(20)) // Ifc.you("dodge|s| a splash of sticky liquid!", target); // else { Ifc.you("|is| covered by sticky junk!", target); target.dx -= Utl.d(2); g.update.addElement(target); // } break; case 3: // if (target.dx > Utl.rn(10)) // Ifc.you("dodge|s| a splash of chromatic liquid!", target); //else { // if (target.species.resist_polymorph) { Ifc.you("look|s| a bit like a "+Utl.rn(Species.all_creatures).name +", then returns to normal.", target); break; } if (target.resist_polymorph) { Ifc.you("|is| protected by "+Ifc.his(target)+" full-body costume.", target); break; } Ifc.you("undergo|es| a strange transformation!", target); Spe tmp = Utl.rn(Species.all_creatures); if (target == g.player) ++g.polymorphed; Ifc.you("turn|s| into a " + tmp.name + "!", target); target.species = tmp; target.reroll_stats(); // } break; case 4: Ifc.you("do|es|n't seem to be affected.", target); break; } } public boolean eat (Itm self, Mon eater, Node here) { // Mons killing themselves by drinking acid is stupid if ((!(type == 2 || type == 4) || (type == 3 && eater.hp < eater.mhp / 3)) && eater != g.player) return false; Ifc.you("drink|s| from the flask.", eater); --uses; if (uses == 0) { Ifc.you("run|s| out of " + types[type] + ".", eater); eater.inventory.remove(self); eater.wielded = null; } switch (type) { case 0: Ifc.your("throat burns terribly!", eater); eater.hp = Utl.rn(2) - (self.tainted? 3 : 0); eater.last_damage = "using acid"; break; case 1: // 3 Ifc.you("feel|s| very ill.", eater); eater.hp = Utl.rn(4) - (self.tainted? 2 : 0); eater.last_damage = "drinking poison"; eater.st = Utl.d(3); eater.dx = Utl.d(3); break; case 2: Ifc.you("drink|s| viscous liquid.", eater); if (eater == g.player) ++g.food; if (self.tainted) { Ifc.you("feel|s| quite ill.", eater); eater.st /= 2; eater.dx /= 2; g.update.addElement(eater); break; } eater.st = eater.mst; eater.dx = eater.mdx; eater.in = eater.min; g.update.addElement(eater); Ifc.you("feel|s| restored.", eater); break; case 3: Ifc.you("drink|s| some chromatic liquid.", eater); if (eater.species.resist_polymorph) { Ifc.you("feel|s| like a new "+eater.species.name+"!", eater); eater.reroll_stats(); break; } if (eater == g.player) ++g.polymorphed; if (self.tainted && !super_charge) { eater.species = Species.amorphous_blob; Ifc.you("undergo|es| a hideous transformation!", eater); } else if (super_charge && !self.tainted && eater == g.player) { String tmp = Ifc.gstring("Become what sort of creature?"); eater.species = Ifc.get_spe(tmp); Ifc.you("think "+tmp+"-like thoughts and hope."); if (eater.species == Species.amorphous_blob) { Ifc.msg("Oh no, it didn't work!"); } else { ++g.controlled_polymorph; } } else { eater.species = Utl.rn(Species.all_creatures); } eater.reroll_stats(); Ifc.you("turn|s| into a " + eater.species.name + "!", eater); break; case 4: Ifc.you("find|s| it quite tasty.", eater); if (eater == g.player) ++g.food; eater.hp += Utl.d(2,10) + 5; if (eater.hp > eater.mhp) { eater.st = eater.mst; Ifc.you("feel|s| really good.", eater); eater.mhp += (eater.hp - eater.mhp)/3; eater.hp = eater.mhp; } break; } Ifc.you("decide|s| not to drink it all.", eater); return false; } } class gumSpecial extends Special { boolean super_charge = false; public boolean monUse (Mon user) { return false; } public boolean use (Itm self, Mon user, Node here) { Ifc.you("note that it smells of berries."); return true; } public void used_as_weapon (Itm self, Mon wielder, Node location, Mon target, boolean hit) { Ifc.you("attempt|s| to feed blue gum to "+Ifc.the_mon(target)+"!", wielder); if (!hit) return; if (Utl.rn(wielder.dx) < Utl.rn(target.dx)) return; eat(self, target, null); self.wielded = false; wielder.wielded = null; wielder.inventory.remove(self); } public boolean eat (Itm self, Mon eater, Node here) { // Mons killing themselves by this is stupid if (eater != g.player && !eater.rabid) return false; Ifc.you("swallow|s| the gum.", eater); if (eater.species.resist_polymorph) { Ifc.you("doesn't seem to be affected.", eater); } else if (eater.resist_polymorph && here == null) { Ifc.you("see|s| the gum land harmlessly inside "+Ifc.his(eater)+" costume.", eater); }else { Ifc.you("swell|s| up like a giant blueberry.", eater); if (Utl.rn()) { eater.species = Species.blueberry; eater.reroll_stats(); eater.stunner = "being inflated with blueberry juice"; eater.stunned = Utl.d(6); } else { Ifc.you("burst|s| and die|s|.", eater); eater.stunner = "being inflated with blueberry juice"; eater.hp = -1000; eater.stunned = Utl.d(6); eater.last_damage = "exploding"; eater.die(null); } } // not resist polyworphy if (here != null) eater.inventory.remove(self); return false; } } class penSpecial extends Special { private String[] no_effect = { "Elbereth", "Xyzzy", "ELBERETH", "XYZZY", "PLUGH", "Plugh" }; private void write(String tmp) { for (String nr : no_effect) if (tmp.compareTo(nr) == 0) Ifc.msg("Nice try."); if (tmp.compareTo("Pikachu, I choose you!") == 0) { Ifc.msg("Sent in some pikachu!"); for (int i = 0; i < 5; ++i) g.here.add(Species.pikachu.make()); } } public boolean monUse (Mon user) { return false; } public boolean use ( Itm self, Mon user) { if (user.alignment != 0) { Ifc.you("|is| ignored by the pen.",user); return true; } ++g.illiterate; Ifc.you("write on the wall with the pen.", user); String tmp = Ifc.gstring("Write what?"); Ifc.you("write \""+tmp+"\" on the wall.", user); write(tmp); return true; } public void used_as_weapon (Itm self, Mon wielder, Node location, Mon target, boolean hit) { if (wielder.alignment != 0) return; if (hit && !target.species.boss && Utl.rn(3)== 0 && target.in < wielder.in + Utl.rn(-wielder.in/2)) { Ifc.you("feel|s| drawn to "+Ifc.the_mon(wielder)+"!", target); if (wielder == g.player) { target.ai = target.PET; if (target.species.smart) Ifc.you("swear|s| loyalty to your cause!", target); } else { Ifc.you("|is| paralyzed by indecision!", target); target.stunned = Utl.d(3); target.stunner = "a moral conflict"; } } } } class nerfSpecial extends Special { public boolean use ( Itm self, Mon user) { Ifc.msg("Nothing happens when you use the Nerf Sword."); return false; } public void used_as_weapon (Itm self, Mon user, Node location, Mon target, boolean hit) { if (!hit) return; if (user.alignment >= 0) return; // no special unless jock switch (Utl.rn(10)) { case 0: case 1: case 2: case 3: Ifc.your("foam-rubber blade shoots "+Ifc.the_mon(target) +" with noxious polymers!", user); if (!target.resist_chemical) { target.dx -= 1; g.update.addElement(target); } target.damage(10, user); target.last_damage = "dangerous toys"; break; case 4: case 5: case 6: Ifc.your("foam-rubber blade nerfs "+Ifc.the_mon(target) +"!", user); target.dx -= Utl.d(6); target.st -= Utl.d(6); target.in -= Utl.d(6); g.update.addElement(target); break; case 7: case 8: if (target.wielded != null) { Ifc.your("foam-rubber blade nerfs the "+target.species.name+"'s weapon!", user); target.wielded.kind.damage /= 2; Ifc.msg("A distant voice says: \"Nerfed the "+ target.wielded.kind.name+"!\""); } else { Ifc.your("foam-rubber blade bisects "+Ifc.the_mon(target)+"!", user); target.hp = 0; target.last_damage = "very dangerous toys"; } case 9: Ifc.your("foam-rubber blade nerfs "+target.species.name+"s!", user); Ifc.msg("A distant voice says: \"Nerfed the "+ target.species.name+"!\""); target.species.st -= Utl.rn(1); target.species.dx -= Utl.rn(1); target.species.in -= Utl.rn(1); target.species.hp -= Utl.rn(5); break; } } } class scytheSpecial extends Special { public boolean use ( Itm self, Mon user) { Ifc.you("hear singing gnomes.", user); //Ifc.msg("You open a rift in space!"); // Teleport to dying return false; } public void used_as_weapon (Itm self, Mon user, Node location, Mon target, boolean hit) { if (!hit) return; Ifc.you("reap|s| "+Ifc.the_mon(target)+"'s aetherial energy!", user); target.hp = -42; target.last_damage = "The Scythe of Death"; } } class textbookSpecial extends Special { public int topic = 0; private int uses = 0; public String[] topics = { "Adventuring For Dummies", "Linear Algebra", "The Art of Computer Programming", "Differential Equations", "Algebra", "Elementary Calculus", "The Book of Foo", "Java in a Nutshell", "Introductory Biology", "Essentials of Medicinal Chemistry", "Advanced Inorganic Chemistry", "Prealgebra", "English Orthography", "Elements of Style", "Gomer's World Of Outhouses", "My First Book of Tasty Animals", "Baby's First Book", "Physics for Scientists and Engineers", "The CRC Handbook of Chemistry and Physics" }; public int[] difficulty = { 5, 11, 11, 12, 8, 9, 5, 30, 8, 11, 11, 7, 8, 8, 3, 2, 1, 10, 15 }; public textbookSpecial () { topic = Utl.rn(topics.length); uses = Utl.d(3); } public boolean monUse (Mon user) { return (user.species.smart? true : false); } public boolean wield (Itm self, Mon wielder, Node location) { if (wielder.alignment < 0 && (topic == 2 || topic == 6 )) { Ifc.you("|is| zapped by the powerfully nerd-aligned tome!"); wielder.hp -= Utl.d(8); wielder.last_damage = "really bad paper cuts"; } return true; } public void used_as_weapon (Itm self, Mon wielder, Node location, Mon target, boolean hit) { if (!hit) return; if (topic == 18) { Ifc.you("smash|es| the massive tome into " + Ifc.the_mon(target) + "!", wielder); target.damage(Utl.d(8), wielder); } if ((topic == 2 || topic == 7) && target.species.alignment < 0) { Ifc.your("flesh is burned by the powerfully nerd-aligned tome!", target); target.hp -= Utl.d(8); target.last_damage = topics[topic]; } int index = target.in - difficulty[topic]; if (index < -3 && target.species.smart) { // Only "intelligent" creatures can be stupified by textbooks Ifc.you("|is| rendered helpless and stupified by the awesome power of " + topics[topic] + "!", target); target.stunned = Utl.d(difficulty[topic]/2 + 1); target.stunner = "morbid dread of " + topics[topic]; } else if (index < 3 && Utl.rn()) { Ifc.you("recoil|s| in fear of " + topics[topic] + "!", target); if (target == g.player) { target.stunned = 1; target.stunner = "being terrified of " + topics[topic]; } else target.ai = target.FLEEING; } } public boolean use (Itm self, Mon user, Node here) { // reading the title counts as reading. if (user == g.player) ++g.illiterate; int inscore = (user.in + Utl.rn(2)) - difficulty[topic]; Ifc.you("examine|s| the textbook titled \"" + topics[topic] + "\"...", user); ++uses; if (user == g.player && g.player.in > 4 && !Ifc.yn("Do you want to read it?")) return false; if (user.species.alignment < 0 && (topic == 2 || topic == 7)) { switch (Utl.rn(4)) { case 0: user.hp = 0; // Instakill! // fall thru case 1: case 2: user.last_damage = "a computer science text"; Ifc.you("|is| blasted by the powerfully nerd-aligned tome!", user); user.hp -= Utl.rn(20); break; case 3: Ifc.you("feel|s| powerfully captivated by the contents.", user); Ifc.you("abandon|s| "+Ifc.his(user)+" former course and embrace|s| the Geek Way!", user); user.species = Species.nerd; user.reroll_stats(); return true; } } if (inscore < -5) { Ifc.your("brain is utterly overwhelmed by the contents!", user); if (topic == 7) Ifc.you("understand|s| everything momentarily, and then die|s|!", user); else Ifc.you("collapse|s| into a catatonic state.", user); user.last_damage = "being stupified by " + topics[topic]; user.hp = 0; // Instadeath... } else if (inscore < 0 || self.tainted) { Ifc.you("can't understand the cryptic verbage.", user); if (Utl.rn()) { Ifc.you("|is| stunned by the book's power.", user); user.stunned = Utl.d(difficulty[topic]); user.stunner = "a textbook titled " + topics[topic]; } // No further effects. } else if (inscore < 7) { Ifc.you("understand|s| the book, and feel|s| smarter!", user); ++user.in; ++user.min; if (topic == 7) { Ifc.you("comprehend|s| the bizzare nature of the universe.", user); ++user.in; ++user.min; user.hp = user.mhp * 2; } } else { Ifc.you("can't really get any benefit from something this low level.", user); } if (Utl.rn(uses) != 0) { Ifc.you("see|s| the textbook disintegrate from use.", user); user.drop(self); here.items.remove(self); } return true; } } class dragon_fangSpecial extends Special { private int topic = 0; private int uses = 0; public dragon_fangSpecial () { ; } public boolean monUse (Mon user) { return false; } public void used_as_weapon (Itm self, Mon wielder, Node location, Mon target, boolean hit) { if (!hit) return; if (self.blessed) { target.stunned = Utl.rn(1); if (target.stunned != 0) Ifc.you("|is| stunned by the fang's power!", target); target.stunner = "a dragon's fang"; } } } class cameraSpecial extends Special { int memory; Vector pictures; public cameraSpecial () { memory = Utl.d(3,12); pictures = new Vector(); } private void show_pics() { Ifc.msg("You view the pictures."); for (int i = 0; i < pictures.size(); ++i) Ifc.msg("\t- "+(String)pictures.elementAt(i)); } public boolean monUse (Mon user) { return user.species.smart && Utl.rn() && memory > 2; } public void used_as_weapon (Itm self, Mon wielder, Node location, Mon target, boolean hit) { if (!hit) return; if (Utl.rn(5) == 0) { target.stunned = Utl.d(3); Ifc.you("trigger|s| the camera's flash!", wielder); Ifc.you("|is| temporarily blinded!", target); target.stunner = "a camera's flash"; } } public boolean use (Itm self, Mon user, Node here) { if (user == g.player && !Ifc.yn("Would you like to take a picture?")) { show_pics(); return true; } if (memory == 0) { Ifc.your(" camera is out of memory.", user); return true; } Mon subject; if (user == g.player) subject = Ifc.choice_mon("Take a picture of whom?", here.mons); else subject = (Mon)Utl.rn(here.mons); if (subject == null) return false; --memory; String photo = subject.photograph(user); pictures.add(photo); Ifc.you("photograph|s| the "+subject.species.name+".", user); Ifc.you("get|s| "+photo, user); return true; } } class documentSpecial extends Special { public documentSpecial () { ; } public boolean monUse (Mon user) { return false; } public void used_as_weapon (Itm self, Mon wielder, Node location, Mon target, boolean hit) { if (!hit) return; if (Utl.rn(4) == 0 && target.species.smart) { target.stunned = Utl.rn(2); Ifc.you("take|s| a document from the briefcase and shows it to " + Ifc.the_mon(target) + "!", wielder); Ifc.you("|is| dumbfounded by the doubletalk of the document!", target); target.stunner = "obsfucated legal verbage"; target.in -= Utl.rn(2); } } } class conical_hatSpecial extends Special { public boolean monUse (Mon user) { return true; // In the future, should tell it to use it // when escaping. } public boolean use (Itm self, Mon user, Node here) { Node where; Itm what; Mon who; int success = user.in + Utl.rn(-5); if (success < 7 || self.tainted) { Ifc.you("experiance|s| a transporter malfunction!", user); switch (Utl.rn(4)) { case 0: if (user.species.resist_polymorph) { Ifc.you("look|s| strange for a moment.", user); break; } user.species = Utl.rn(Species.all_creatures); Ifc.you("turn|s| into a " + user.species.name + "!", user); user.reroll_stats(); if (g.player == user) ++g.polymorphed; user.hp -= Utl.rn(10); if (user.hp <= 0) Ifc.your("new biochemistry is not workable.", user); user.last_damage = "polymorphing into a " + user.species.name; break; case 1: user.hp = 0; Ifc.you("|is| embedded in the wall!", user); user.last_damage = "playing with a hat"; break; case 2: if (user.inventory.isEmpty()) Ifc.you("|is| a bit queezy.", user); else { what = (Itm)Utl.rn(user.inventory); user.drop(what); here.items.remove(what); Ifc.your(what.kind.name + " slips from " + Ifc.his(user) + " grasp and vanishes!", user); } break; default: Ifc.you("seem|s| to have attracted some attention from the management.", user); here.add(Species.debugger.make()); here.add(Species.debugger.make()); here.add(Species.garbage_collector.make()); break; } } else if (success < 12 || !self.worn) { Ifc.you("note|s| that nothing happens when " + Ifc.he(user) + " operates the hat.", user); } else { Ifc.you("disappear|s| in a flash of light!", user); here.mons.remove(user); if (user == g.player) ++g.teleported; where = Utl.rn_node(true, 0);//(Node)Utl.rn(g.nodes); where.add(user); if (user == g.player) g.here = where; Ifc.you("suddenly appear|s| in a flash of light!", user); } return true; } } class novelSpecial extends Special { public boolean monUse (Mon user) { return (user.species.smart? true : false); } public boolean use (Itm self, Mon user, Node here) { if (user == g.player) ++g.illiterate; if (user.in < 6) Ifc.you("|is| confused by the big words.", user); else if (user.in < 10) Ifc.you("read|s| a little bit of the turgid prose.", user); else Ifc.you("wonder|s| aloud how this drivel got published.", user); return true; } } class fur_scrapSpecial extends Special { public boolean monUse (Mon user) { for (int i = 0; i < user.inventory.size(); ++i) { Itm tmp = (Itm)user.inventory.elementAt(i); if (tmp.kind == Items.wand && ((wandSpecial)tmp.special).charges < 3) return true; } return false; } public boolean use (Itm self, Mon user, Node here) { if (user == g.player) { Itm what = Ifc.choice_itm("Rub what with the fur?", user.inventory); if (what == null) return false; if (what.kind == Items.wand) { Ifc.msg("The hairs bristle with electricity."); ++((wandSpecial)what.special).charges; } else { Ifc.you("suspect that wouldn't do anything."); return false; } } else { for (int i = 0; i < user.inventory.size(); ++i) { Itm tmp = (Itm)user.inventory.elementAt(i); if (tmp.kind == Items.wand && ((wandSpecial)tmp.special).charges < 3) { ++((wandSpecial)tmp.special).charges; Ifc.you("rub|s| the wand with the fur.", user); Ifc.your("wand crackles with electricity.", user); break; } } } if (Utl.rn(5) == 0 || self.tainted) { Ifc.your("fur scrap is worn out.", user); user.drop(self); here.items.remove(self); } return true; } } class wandSpecial extends Special { public boolean super_charge = false; public static String[] CHARGE_ADJECTIVE = { "bright", "dazzling", "brilliant", "blazing", "stupendious", "magnificent" }; public static String[] FRIED_MSG = { "|is| burned to a crisp!", "|is| reduced to ashes!", "explode|s| into a cloud of smoke!", "|is| utterly annihilated!", "burn|s| to ashes!", "eat|s| blazing electric death!" }; public int charges = 0; public wandSpecial () { charges = Utl.d(4); } public boolean monUse(Mon user) { return Utl.rn(); } public boolean use (Itm self, Mon user, Node here) { Mon who; if (charges == 0) { Ifc.your("wand is totally discharged.", user); return false; } if (Utl.rn(charges)-3 > 0) { Ifc.your("overcharged wand malfunctions and shocks "+Ifc.the_mon(user)+"!", user); user.last_damage = "an unfortunate wand-related accident"; user.hp -= Utl.d(charges-3, (50-user.in)/(super_charge? 4 : 1)); return true; } if (here.mons.size() < 1) Ifc.you("don't see anything to aim at."); if (user == g.player) { who = Ifc.choice_mon("Zap it at whom?", here.mons); if (who == null) return false; if (who.ai == who.PET) { Ifc.you("wouldn't want to hurt your "+who.species.name+"!"); return false; } if (who == g.player) { Ifc.you("would feel rather daft zapping yourself."); return false; } who.ai = (who.hp > who.mhp/2? who.ATTACKING : who.FLEEING); // If it survives... } else { who = user.get_wand_target(); if (who == null) return false; } Ifc.you("|is| struck by a " +(charges < 5? CHARGE_ADJECTIVE[charges] : "lightning-like")+" electric arc!", who); who.last_damage = "a bolt of blazing electric death, administered by a "+user.species.name; if (user == g.player) ++g.used_wand; who.hp -= Utl.d(charges--,30+(super_charge? 10 : 0)); if (super_charge && Utl.rn()) { Ifc.you("|is| paralyzed by shock!", who); who.stunner = "an electric shock"; who.stunned = charges + 1; } if (who.hp <= -(Utl.rn(25)+10) && who.species != Species.nemesis) { Ifc.you(Utl.rn(FRIED_MSG), who); if (who != g.player) here.mons.remove(who); } return true; } } class zaurusSpecial extends Special { public boolean monUse (Mon user) { return false; } public void used_as_weapon (Itm self, Mon user, Node location, Mon target, boolean hit) { if (user.alignment <= 0) return; } public boolean use (Itm self, Mon user, Node here) { if (user.species.alignment < 0) { Ifc.you("|is| blasted by the PDA's power!", user); user.hp -= Utl.d(2,20); user.last_damage = "playing with a dangerous gadget"; return true; } Mon tmp; Node where; if (user.in +Utl.rn(6) < 12) { Ifc.you("really mess up badly."); Ifc.your("Zaurus yells for help!"); tmp = Species.programmer.make(); tmp.ai = tmp.ATTACKING; here.add(tmp); Ifc.you("see a programmer appear!"); Ifc.msg("\"What are you doing with MY Zaurus?\""); return true; } switch (Ifc.choice("What would you like to do?", "View Map|Scan for Life-forms|Engage in Introspection|Teleport Other")) { case 0: Map.show(g.here, 79, 23, true, 0); Ifc.pk(); break; case 1: where = Ifc.gnsew("Aim it in which direction?", here); if (where.mons.size() == 0) { Ifc.you("detect no lifeforms there."); break; } tmp = Ifc.choice_mon("Scan which creature?", where.mons); if (tmp == null) return false; Ifc.msg("Status of " + Ifc.the_mon(tmp) + ":"); Ifc.msg(tmp.detailed_describe()); Ifc.pk(); break; case 2: System.out.printf("Stats of %s the %s level %d/%d %s:\n", g.player.name, Tunnels.GENDERS[g.player.gender], g.player.level, g.player.xp, g.player.species.name ); System.out.printf("You are %s aligned. (%d)\n", (g.player.species.alignment < 0? "jock" : (g.player.species.alignment > 0? "nerd" : "neutrally")), g.player.species.alignment); System.out.printf("ST: %d/%d IN: %d/%d DX: %d/%d HP: %d/%d Rg: 1/%d Ar: %d\n", g.player.st, g.player.mst, g.player.in, g.player.min, g.player.dx, g.player.mdx, g.player.hp, g.player.mhp, g.player.species.regeneration, g.player.armor); System.out.printf("Sins: Murder: %d/%d, Canibalism: %d, Attack peacefuls: %d\n", g.player.murders, g.allow_murder, g.player.canibal, g.player.peacefuls); if (g.player.resist_chemical) Ifc.msg("You are chemical resistant."); Ifc.pk(); break; case 3: if (Utl.rn(60) > user.in) { Ifc.you("can't get it to work for some reason."); break; } if (here.mons.size() < 2) Ifc.you("See no-one to teleport."); else { tmp = Ifc.choice_mon("Aim at whom?", here.mons); if (tmp == null) return false; Ifc.your("Zaurus fires a beam of energy at " + Ifc.the_mon(tmp) + "!", user); here.mons.remove(tmp); Ifc.you("vanish|es| in a poof of binary!", tmp); } break; } return true; } } class steroidSpecial extends Special { public boolean monUse (Mon user) { return (user.species.alignment < 0? true : false); } public boolean use (Itm self, Mon eater, Node here) { if (eater.species.level == null) { eater.st = eater.mst; Ifc.you("feel strange.", eater); } else { int bonus = Utl.d(1,4) + 1; eater.mst = (eater.mst+bonus > eater.species.level.mst? eater.species.level.mst : eater.mst + bonus); eater.st = (eater.st+bonus > eater.mst? eater.mst : eater.st+bonus); // ternary ? for the win Ifc.you("feel|s| tough.", eater); } if (Utl.rn(6) == 0) { Ifc.you("experiance|s| a negative side-effect.", eater); eater.mhp -= Utl.rn(10); eater.hp = (eater.hp > eater.mhp? eater.mhp : eater.hp); eater.last_damage = "steroid abuse"; } eater.inventory.remove(self); return true; } } class whistleSpecial extends Special { public boolean monUse (Mon user) { return false; } public boolean use (Itm self, Mon user, Node here) { Mon current; Ifc.you("blow|s| the whistle.", user); if (self.tainted) Ifc.msg("What an unpleasant buzzing squawk!"); for (int i = 0; i < here.mons.size(); ++i) { current = (Mon)here.mons.elementAt(i); if (current == user) continue; if (current.ai == Mon.PET) continue; if (Utl.rn(current.in) + (current.species.smart? 3 : 0 ) < 4+(user.in > 10? 1 : -1)) { if (current == user) { Ifc.you("find|s| the sound very captivating.", user); continue; } current.ai = current.PET; Ifc.you("|is| captivated by the aetherial sound!", current); } else if ((current.in > 10 && !current.species.peaceful && current.in != current.PET) || self.tainted) { Ifc.you("anger|s| " + Ifc.the_mon(current) + " with the sound!", user); current.ai = current.ATTACKING; } else { Ifc.you("seem|s| irritated by the noise.", current); } } return true; } } class wonka_whistleSpecial extends Special { boolean first_use = true; boolean freed_oompas = false; public boolean monUse (Mon user) { return false; } public boolean use (Itm self, Mon user, Node here) { Mon current; Ifc.you("blow|s| the brass whistle.", user); if (first_use) { first_use = false; Mon tmp = Species.oompa.make(); tmp.name = "Doompel Empa"; tmp.ai = tmp.PET; here.add(tmp); Ifc.msg("You see an oompa-loompa enter the room, apparently summoned by the whistle."); Ifc.msg("He says: \"Thank you, "+Ifc.sir(g.player)+", for defeating the Dark One\"."); freed_oompas = Ifc.yn("\"Will you now earn our eternal gratitude by setting us free?\"", true); if (!freed_oompas) { Ifc.msg("The oompa-loompa looks at you, his new master, sadly."); } else { Ifc.msg("\tWe oompa loompas must now defeat our deluded breathren who are still"); Ifc.msg("\tunder the influence of the slavers, but we are eternally in your debt.\""); Ifc.msg("\"Should you ever need our aid on your righeous and very"); Ifc.msg("noble quest, blow the whistle and we shall come.\""); Species.oompa.alignment = g.player.species.alignment; tmp.alignment = g.player.alignment; Species.oompa.peaceful = true; tmp.ai = tmp.WANDERING; Ifc.msg("\"There is another thing, friend " + g.player.species.name + ". Wonka trusted "); Ifc.msg("me with some secrets, and I wish to share them with you. If you blow that whistle"); Ifc.msg("in the oompa-loompa catacombs to the north, you will find the secret lab.\""); Ifc.pk(); for (int i = 0; i < g.monsters.size(); ++i) { tmp = (Mon)g.monsters.elementAt(i); if (tmp.species == Species.oompa) { tmp.alignment = g.player.alignment; tmp.ai = tmp.WANDERING; } } g.special_merits.add("+100 You were the savior of the Oompa-Loompas."); g.bonus += 100; } } if (here.name == "Ancient Oompa-Loompa Catacombs" && freed_oompas) { Ifc.msg("There is a rumbling sound!"); here.do_special(0, self, user); Ifc.pk(); } else { if (freed_oompas) { int f = Utl.d(6); for (int i = 0; i < f; ++i) here.add(Species.oompa.make()); } else { Mon tmp = Species.oompa.make(); tmp.ai = tmp.PET; tmp.name = "Slave"; here.add(tmp); } } return true; } } class sackSpecial extends Special { private Vector contents; private int capacity; public boolean monUse (Mon user) { return false; } public sackSpecial() { capacity = 9; contents = new Vector(); while (Utl.rn() && contents.size() <= capacity) contents.add(((Kind)Utl.rn(Items.all_items)).make()); } public boolean use (Itm self, Mon user, Node here) { int mode = Ifc.choice("Do what with the sack?", "Take something out|Put something in|Look in"); Itm what = null; if (mode == 0) { if (user.inventory.size() >= user.st) { Ifc.you("are unable to remove anything while carrying so much stuff."); return false; } if (contents.isEmpty()) { Ifc.you("see that the sack is empty."); return false; } what = Ifc.choice_itm("Take out what?", contents); if (what == null) return false; contents.remove(what); user.inventory.add(what); Ifc.you("take out the " + what.kind.name + "."); } else if (mode == 1) { if (contents.size() == capacity) { Ifc.you("can't fit any more stuff into the sack."); return true; } what = Ifc.choice_itm("Put what in?", user.inventory); if (what == null) return false; if (what.wielded) { what.wielded = false; user.wielded = null; Ifc.you("no longer wield the " + what.kind.name + "."); } if (what.worn && what.special != null && !what.special.unwear(what, user, here)) return true; what.worn = false; contents.add(what); user.inventory.remove(what); if (self == what) { Ifc.you("see the sack disappear in a poof of logic."); if (Utl.rn()) { Ifc.you("attract some company."); here.add(Species.garbage_collector.make()); Ifc.you("note that the garbage collecter is slightly confused."); Ifc.you("hear it mutter a complaint about circular references."); } } else Ifc.you("put in the " + what.kind.name + "."); } else { Ifc.show_items("Contents of the sack:",contents); } return true; } } class fox_boxSpecial extends Special { Mon fox; public fox_boxSpecial () { fox = Species.fox.make(); fox.hp = 1; fox.inventory.clear(); Itm tmp; if (Utl.rn()) { fox.name = "Millie"; tmp = Items.overalls.make(); tmp.worn = true; fox.inventory.add(tmp); fox.gender = 2; } else { fox.name = "Ozy"; tmp = Items.top_hat.make(); tmp.worn = true; fox.inventory.add(tmp); tmp = Items.vest.make(); tmp.worn = true; fox.inventory.add(tmp); fox.gender = 1; } } public boolean monUse() { return false; } public boolean use (Itm self, Mon user, Node here) { if (fox == null) { Ifc.msg("The tiny cage is empty and in unusably poor condition."); return false; } if (fox.hp > 0) { Ifc.msg("You open the cage and discover that it contains a Talking Fox."); Ifc.msg("Sadly, "+Ifc.he(fox)+" has been badly mistreated and appears to be only barely"); Ifc.msg("clinging to life. You doubt "+Ifc.he(fox)+" will live much longer."); } else { Ifc.msg("You find a dead fox."); fox = null; here.add(Items.fox_corpse.make()); return true; } switch (Ifc.choice("What do you want to do?", "1. Leave the fox in the box." + "|2. Remove the fox from the box." + "|3. Put the fox out of "+Ifc.his(fox)+" misery." + "|4. Treat the fox's injuries.")+1) { case 1: fox.hp = 0; Ifc.msg("You leave the fox to die."); break; case 2: fox.hp = (user.dx < Utl.rn(3,6)? -1 : 1); if (fox.hp > 0) { Ifc.msg("You carefully remove the fox from the box."); g.bonus += 50; Ifc.msg(Ifc.color(Ifc.YELLOW)+"Gain 50 Points for your good deed."+Ifc.color()); g.special_merits.add("+50 For helping a fox in a box."); } else { Ifc.msg("You slip up and mistakenly finish off the poor creature. Opps."); } break; case 4: if (user.in + user.dx < Utl.rn(2,24)) { Ifc.msg("If you wanted to become a doctor, the fox would probably"); Ifc.msg("have advised you to not quit your day job. However, "+Ifc.he(fox)); Ifc.msg("can't do that now, because your incompentant work has finished "+Ifc.him(fox)); Ifc.msg("off in a rather messy and painful way. Opps."); g.bonus -= 100; g.special_merits.add("-100 For your inept attempt at veterinary medicine."); Ifc.you(Ifc.color(Ifc.RED)+"Lose 100 Points for your medical ineptitude."+Ifc.color()); fox.hp = 0; } else { Ifc.msg("You manage to help the fox, and have earned "+Ifc.his(fox)+" eternal gratitude."); Ifc.msg(Ifc.color(Ifc.YELLOW)+"You good deed has also earned you 200 bonus points."+Ifc.color()); g.bonus += 200; g.special_merits.add("+200 For your elite veterinary medical skillz"); fox.ai = fox.PET; fox.hp = fox.mhp/2; here.add(fox); fox = null; } break; case 3: if (user.wielded != null) { if (user.wielded.kind == Items.pencil) { Ifc.msg("Finishing off the fox with a pencil would not exactly be merciful."); } else if (user.wielded.kind == Items.stick) { Ifc.msg("You don't think killing the fox with a stick would be euthanasia."); } else if (user.wielded.kind == Items.screwdriver) { Ifc.msg("You now know why Dr. Kevorkian did not use screwdrivers. That was messy."); fox.hp = 0; g.bonus -= 100; g.special_merits.add("-100 For hurting helpless fuzzy animals."); Ifc.you(Ifc.color(Ifc.RED)+"Lose 100 Points for your cruel ineptitude."+Ifc.color()); } else if (user.wielded.kind == Items.novel) { Ifc.msg("You're wielding a novel. What are you going to do, bore it to death?"); } else if (user.wielded.kind == Items.ball) { Ifc.msg("You can't think of any way to euthanize a fox with the ball you are wielding."); } else { Ifc.you("swiftly kill the fox with your "+user.wielded.kind.name +", ending "+Ifc.his(fox)+" suffering."); Ifc.you("wish you could have done more, but are glad to know that at least"); Ifc.msg("the poor creature is no longer in pain."); g.bonus += 100; fox.hp = 0; g.special_merits.add("+100 For administering deserved euthanisia."); Ifc.you(Ifc.color(Ifc.YELLOW)+"Gain 100 Points for your good dead."+Ifc.color()); } } else { if (user.st > 10) { Ifc.msg("You quickly snap the fox's neck, ending "+Ifc.his(fox)+" suffering."); fox.hp = 0; g.bonus += 100; g.special_merits.add("+100 For administering deserved euthanisia."); Ifc.you("wish you could have done more, but are glad to know that at least"); Ifc.msg("the poor creature is no longer in pain."); Ifc.you(Ifc.color(Ifc.YELLOW)+"Gain 100 Points for your good dead."+Ifc.color()); } else { Ifc.msg("You aren't strong enough to kill the fox painlessly with your bare hands."); } } break; } return true; } } class cageSpecial extends Special { public Vector contents; public int capacity, used_space; public boolean monUse (Mon user) { return false; } public cageSpecial() { capacity = Spe.LARGE; used_space = 0; contents = new Vector(); } public boolean use (Itm self, Mon user, Node here) { int mode = Ifc.choice("Do what with the cage?", "Remove a creature|Put in a creature|Look inside"); Mon what = null; if (mode == 0) { if (contents.isEmpty()) { Ifc.you("see that the cage is empty."); return false; } what = Ifc.choice_mon("Let out who?", contents); if (what == null) return false; contents.remove(what); here.add(what); used_space -= what.species.size; Ifc.you("let out the " + what.species.name + "."); } else if (mode == 1) { what = Ifc.choice_mon("Put what who?", here.mons); if (what == null) return false; if (used_space + what.species.size > capacity) { Ifc.you("can't fit this creature into the cage."); if (what.species.size > capacity) Ifc.msg("It's simply too large."); else Ifc.msg("Perhaps it might fit if it had less company in there."); return true; } if (what == user) { Ifc.msg("And how do you plan to get out, genius?"); return false; } if (what.ai != what.PET && what.dx > user.dx+Utl.rn(-5)) { Ifc.you("evade|s| "+Ifc.his(user)+" grasp!", what); return true; } else if (what.ai != what.PET) { Ifc.you("capture the " + what.species.name+"!"); } contents.add(what); what.here = null; used_space += what.species.size; here.mons.remove(what); Ifc.you("put in the " + what.species.name + "."); } else { Ifc.show_mons("Contents of the animal cage:",contents); if (used_space == capacity) Ifc.msg("It looks rather crowded in there."); } return true; } } class lab_coatSpecial extends Special { public boolean monUse (Mon user) { return false; } public boolean wear (Itm self, Mon wearer, Node location) { if (wearer.resist_chemical) { if (wearer == g.player) Ifc.you("cannot wear another lab coat!", wearer); return false; } wearer.resist_chemical = true; if (wearer.species.alignment <= 0) Ifc.you("look|s| geeky.", wearer); else Ifc.you("look|s| sharp.", wearer); return true; } public boolean unwear (Itm self, Mon unwearer, Node location) { unwearer.resist_chemical = unwearer.species.resist_chemical; return true; } public boolean use (Itm self, Mon user, Node here) { Ifc.you("examine the lab coat. There isn't a monogram."); return false; } } class maskSpecial extends Special { public boolean monUse (Mon user) { return false; } public boolean wear (Itm self, Mon wearer, Node location) { if (wearer.resist_gas) { if (wearer == g.player) Ifc.you("cannot wear another gas mask", wearer); return false; } wearer.resist_gas = true; return true; } public boolean unwear (Itm self, Mon unwearer, Node location) { unwearer.resist_gas = unwearer.species.resist_gas; return true; } public boolean use (Itm self, Mon user, Node here) { Ifc.you("examine gas mask. It looks sound."); return false; } } class mirrorSpecial extends Special { public boolean monUse (Mon user) { return false; } public boolean use (Itm self, Mon user, Node here) { Mon who = Ifc.choice_mon("Aim the mirror at whom?", here.mons); if (who == null) return false; Ifc.you("gaze|s| into the mirror...", who); Ifc.msg(Ifc.color(Ifc.CYAN)+" -<% The Most Awesome "+who.species.name +"-kind in the Land: %>-"+Ifc.color()); int count = 0, equals = 0, superiors = 0; Spe which_kind = who.species; Mon[] critters = new Mon[5]; for (Object x: g.monsters) { Mon which = (Mon)x; if (which.species != which_kind) continue; maybe_add(critters, which); ++count; if (which.level == who.level) ++equals; if (which.level > who.level) ++superiors; } for (Mon x: critters) { if (x == null) continue; Ifc.msg(" * "+Ifc.the_mon(x)); Ifc.msg(" Level: "+x.level+" Kills: "+x.vanquished+" Gender: "+ x.GENDER[x.gender]); Ifc.msg(" Location: "+(x.here.unique?"The " : "A ")+x.here.name); if (x.wielded != null) Ifc.msg(" "+Ifc.his(x)+" weapon: A "+x.wielded.kind.name); Ifc.msg(" "+x.describe()); Ifc.msg(""); } if (count == 1) Ifc.you("|is| unique among all beings.",who); else if (superiors == 0 && equals == 0) Ifc.you("|is| the most awesome of all "+who.species.name,who); else if (superiors == 0) Ifc.you("|is| indeed awesome, but "+(equals == 1? "another is" : "others are")+" yet awesome.",who); else Ifc.you("|is| not that impressive, relly.", who); return true; } private void maybe_add(Mon[] critters, Mon who) { if (who.ai == who.SLEEPING) return; int lowest_idx = 0, lowest = 9999; for (int i = 0; i < critters.length; ++i) { if (critters[i] == null) { critters[i] = who; return; } else if (critters[i].level < lowest) { lowest = critters[i].level; lowest_idx = i; } } if (who.level > lowest) critters[lowest_idx] = who; } } class furry_costumeSpecial extends Special { String kind = null; public furry_costumeSpecial() { kind = Utl.rn(Species.one_of_everything).name; } public boolean monUse (Mon user) { return false; } public boolean wear (Itm self, Mon wearer, Node location) { if (wearer.armor > 3) { if (wearer == g.player) Ifc.you("can't manage to get it on.", wearer); return false; } wearer.resist_polymorph = true; return true; } public boolean unwear (Itm self, Mon unwearer, Node location) { unwearer.resist_polymorph = unwearer.species.resist_polymorph; return true; } public boolean use (Itm self, Mon user, Node here) { Ifc.msg("This is a costume of a "+kind); return false; } } class bulletproof_vestSpecial extends Special { public boolean wear (Itm self, Mon wearer, Node location) { if (wearer.resist_bullets) { if (wearer == g.player) Ifc.you("cannot wear another bulletproof vest!", wearer); return false; } wearer.resist_bullets = true; if (wearer.species.alignment >= 0) Ifc.you("look|s| paranoid.", wearer); else Ifc.you("look|s| tough.", wearer); return true; } public boolean unwear (Itm self, Mon unwearer, Node location) { unwearer.resist_bullets = false; return true; } } class spock_earsSpecial extends Special { int original_alignment = 0; public boolean wear (Itm self, Mon wearer, Node location) { if (wearer.alignment > 0) { if (wearer == g.player) Ifc.you("look geeky enough as it is!", wearer); return false; } original_alignment = wearer.alignment; wearer.alignment = 10; if (wearer.species.alignment == 0) Ifc.you("look|s| like a trekie.", wearer); else Ifc.you("look|s| like a nerd.", wearer); return true; } public boolean unwear (Itm self, Mon unwearer, Node location) { Ifc.you("remove|s| the pointed ears.", unwearer); unwearer.alignment = original_alignment; return true; } } class magnifying_glassSpecial extends Special { public boolean monUse (Mon user) { return false; } public boolean use (Itm self, Mon user, Node here) { Itm what = Ifc.choice_itm("Examine what?", user.inventory); if (what == null) return false; if (user.in < 8) Ifc.you("don't see anything interesting."); else if (user.in < 14) { if (Utl.rn()) if (what.tainted) Ifc.you("suspect that it might be defective."); else Ifc.you("think it is in good order."); else if (Utl.rn()) if (!what.tainted) Ifc.you("suspect that it might be defective."); else Ifc.you("think it is in good order."); } else { if (what.tainted) Ifc.you("suspect that it might be defective."); else Ifc.you("think it is in good order."); } return true; } } // Various kinds of blade allow you to tell if food is tainted or not. class bladeSpecial extends Special { public boolean monUse (Mon user) { return false; } public boolean use (Itm self, Mon user, Node here) { Itm what = Ifc.choice_itm("What do you want to cut?", user.inventory); if (what == null) return false; if (what.kind.heal == 0) { Ifc.you("shouldn't bother cutting that."); return false; } if (Utl.rn(-3) + user.dx + (self.kind.name == "scalpel"? 3 : 0) < 8 || what.kind == Items.soda) { Ifc.you("clumisly drop the " + what.kind.name + ", destroying it."); user.drop(what); here.items.remove(what); } else { Ifc.you("carefully "+(what.kind == Items.mcookie || what.kind == Items.cookie? "probe" : "dissect")+" the " + what.kind.name +" with your "+self.kind.name+". " + (what.tainted? "It's rotten! Yuck!" : (user.hp < user.mhp / 2? "It looks fresh and tasty." : "It appears to be edible.")) ); } if (what.tainted) return true; if (what.kind == Items.gnome_corpse) { Ifc.you("convince yourself that gnomes are essentially a species of chicken."); } else if (what.kind == Items.hamster_corpse) { Ifc.you("rationalize that a hamster is basically a small cow."); } else if (what.kind == Items.human_corpse) { Ifc.you("must be really hungry."); } else if (what.kind == Items.pikachu_corpse) { if (Utl.rn()) Ifc.you("wonder if Pikachu are considered kosher."); else Ifc.you("think Pikachu are a type of lamb."); } return true; } } class mcookieSpecial extends Special { public boolean monUse (Mon user) { return true; } public boolean eat (Itm self, Mon eater, Node here) { if (self.tainted) { Ifc.your("mouth burns! The cookie was poisoned!", eater); eater.hp = Utl.rn(5); eater.last_damage = "eating a poisoned magic cookie"; return true; } Ifc.you("find|s| the taste awe-inspiring!", eater); if (Utl.rn()) { Ifc.you("|is| stronger!", eater); eater.st = eater.mst = eater.mst + Utl.d(3); } if (Utl.rn()) { Ifc.you("|is| smarter!", eater); eater.in = eater.min = eater.min + Utl.d(3); } if (Utl.rn()) { Ifc.you("|is| more agile!", eater); eater.dx = eater.mdx = eater.mdx + Utl.d(3); g.update.addElement(eater); } Ifc.you("feel|s| healthier!", eater); eater.hp = eater.mhp = eater.mhp + Utl.d(20); return true; } public void used_as_weapon(Itm self, Mon wielder, Node location, Mon target, boolean hit) { if (hit) use (self, target,location); } public boolean use (Itm self, Mon user, Node here) { Node where; Itm what; Ifc.you("gaze|s| into the cookie...", user); if (user.in + Utl.rn(3) < 10) { Ifc.you("|is| very hungry.", user); user.hp -= Utl.rn(10); } else { switch (Utl.rn(16)) { case 9: case 8: case 7: case 6: where = Utl.rn(here); if (where.mons.isEmpty()) Ifc.you("gain|s| an insight from the cookie. {The room to the " + Utl.nsew(where) + " is empty.}", user); else Ifc.you("gain|s| an insight from the cookie. {The room to the " + Utl.nsew(where) + " contains a " + ((Mon)Utl.rn(where.mons)).species.name + ".}", user); break; case 5: Ifc.you("|is| weakened by the cookie's power!", user); --user.mhp; --user.hp; break; case 4: Ifc.you("find|s| new strength!", user); ++user.mhp; ++user.hp; break; case 3: case 2: case 1: Ifc.you("vanish|es| in a puff of chocolate smoke!", user); if (user == g.player) ++g.teleported; here.mons.remove(user); where = Utl.rn_node(true, 0);//(Node)Utl.rn(g.nodes); where.add(user); if (user == g.player) g.here = where; Ifc.you("suddenly appear|s| out of cookie-space!", user); if (self.tainted && Utl.rn() && !user.species.resist_polymorph) { Ifc.you("|is| horrified to discover that "+Ifc.he(user)+" |is| partially turned into chocolate!", user); user.hp = 0; user.here.add(Items.chocolate.make()); user.here.add(Items.chocolate.make()); user.last_damage = "being turned to chocolate by a defective magic cookie"; return true; } else if (self.tainted) { Ifc.you("smell|s| a whiff of old chocolate.", user); } break; default: Ifc.you("see|s| a glowing map projected from the cookie!", user); if (user == g.player) { Map.show(g.here, 40, 10, true, 0); Ifc.pk(); } } } user.last_damage = "contemplating a quasi-magical cookie"; user.hp -= (10 - user.in); // Yes, at high intelligence, cookie heals. if (user.hp > user.mhp) user.hp = user.mhp; return true; } } class coffeeSpecial extends Special { public boolean eat (Itm self, Mon eater, Node here) { if (eater.species.level == null) { eater.dx = eater.mdx; Ifc.you("feel|s| awake and ready to go.", eater); } else { int bonus = Utl.d(1,4) + 1; eater.mdx = (eater.mdx+bonus > eater.species.level.mdx? eater.species.level.mdx : eater.mdx + bonus); eater.dx = (eater.dx+bonus > eater.mdx? eater.mdx : eater.dx+bonus); // ternary ? for the win Ifc.you("feel|s| jittery.", eater); } return true; } }