tims@zeus.UUCP (Tim Stoehr) (11/26/86)
#!/bin/sh-----cut here-----cut here-----cut here-----cut here-----
# shar: Shell Archiver
# Run the following text with /bin/sh to create:
# object.c # object.h # pack.c # play.c # use.c
echo shar: extracting object.c
cat - << \SHAR_EOF > object.c
/*
* object.c
*
* This source herein may be modified and/or distributed by anybody who
* so desires, with the following restrictions:
* 1.) This notice shall not be removed.
* 2.) Credit shall not be taken for the creation of this source.
* 3.) This code is not to be traded, sold, or used for personal
* gain or profit.
*
*/
#include <curses.h>
#include "object.h"
#include "monster.h"
#include "room.h"
object level_objects;
unsigned short dungeon[DROWS][DCOLS];
short foods = 0;
short party_counter;
object *free_list = (object *) 0;
char *fruit = "slime-mold ";
fighter rogue = {
0, 0, /* armor, weapon */
0, 0, /* rings */
INIT_HP, /* Hp current */
INIT_HP, /* Hp max */
16, 16, /* Str */
{0}, /* pack */
0, /* gold */
1, 0, /* exp, exp_points */
0, 0, /* row, col */
'@', /* char */
1250 /* moves */
};
struct identify id_potions[POTIONS] = {
{100, "blue \0 ", "of increase strength ", 0},
{250, "red \0 ", "of restore strength ", 0},
{100, "green \0 ", "of healing ", 0},
{200, "grey \0 ", "of extra healing ", 0},
{10, "brown \0 ", "of poison ", 0},
{300, "clear \0 ", "of raise level ", 0},
{10, "pink \0 ", "of blindness ", 0},
{25, "white \0 ", "of hallucination ", 0},
{100, "purple \0 ", "of detect monster ", 0},
{100, "black \0 ", "of detect things ", 0},
{10, "yellow \0 ", "of confusion ", 0},
{80, "plaid \0 ", "of levitation ", 0},
{150, "burgundy \0 ", "of haste self ", 0},
{145, "beige \0 ", "of see invisible ", 0}
};
struct identify id_scrolls[SCROLLS] = {
{505, " ", "of protect armor ", 0},
{200, " ", "of hold monster ", 0},
{235, " ", "of enchant weapon ", 0},
{235, " ", "of enchant armor ", 0},
{175, " ", "of identify ", 0},
{190, " ", "of teleportation ", 0},
{25, " ", "of sleep ", 0},
{610, " ", "of scare monster ", 0},
{210, " ", "of remove curse ", 0},
{100, " ", "of create monster ",0},
{25, " ", "of aggravate monster ",0},
{180, " ", "of magic mapping ",0}
};
struct identify id_weapons[WEAPONS] = {
{150, "short bow ", "", 0},
{8, "darts ", "", 0},
{15, "arrows ", "", 0},
{27, "daggers ", "", 0},
{35, "shurikens ", "", 0},
{360, "mace ", "", 0},
{470, "long sword ", "", 0},
{580, "two-handed sword ", "", 0}
};
struct identify id_armors[ARMORS] = {
{300, "leather armor ", "", (UNIDENTIFIED)},
{300, "ring mail ", "", (UNIDENTIFIED)},
{400, "scale mail ", "", (UNIDENTIFIED)},
{500, "chain mail ", "", (UNIDENTIFIED)},
{600, "banded mail ", "", (UNIDENTIFIED)},
{600, "splint mail ", "", (UNIDENTIFIED)},
{700, "plate mail ", "", (UNIDENTIFIED)}
};
struct identify id_wands[WANDS] = {
{25, " ", "of teleport away ",0},
{50, " ", "of slow monster ", 0},
{45, " ", "of confuse monster ",0},
{8, " ", "of invisibility ",0},
{55, " ", "of polymorph ",0},
{2, " ", "of haste monster ",0},
{25, " ", "of sleep ",0},
{20, " ", "of magic missile ",0},
{20, " ", "of cancellation ",0},
{0, " ", "of do nothing ",0}
};
struct identify id_rings[RINGS] = {
{250, " ", "of stealth ",0},
{100, " ", "of teleportation ", 0},
{255, " ", "of regeneration ",0},
{295, " ", "of slow digestion ",0},
{200, " ", "of add strength ",0},
{250, " ", "of sustain strength ",0},
{250, " ", "of dexterity ",0},
{25, " ", "of adornment ",0},
{300, " ", "of see invisible ",0},
{290, " ", "of maintain armor ",0},
{270, " ", "of searching ",0},
};
extern short current_level, max_level;
extern short party_room;
extern char *error_file;
extern boolean is_wood[];
put_objects()
{
short i, n;
object *obj, *get_rand_object();
if (current_level < max_level) {
return;
}
n = coin_toss() ? get_rand(2, 4) : get_rand(3, 5);
while (rand_percent(33)) {
n++;
}
if (current_level == party_counter) {
make_party();
party_counter = next_party();
}
for (i = 0; i < n; i++) {
obj = get_rand_object();
put_object_rand_location(obj);
}
put_gold();
}
put_gold()
{
short i, j;
short row,col;
unsigned short is_maze, is_room;
for (i = 0; i < MAXROOMS; i++) {
is_maze = (rooms[i].is_room & R_MAZE);
is_room = (rooms[i].is_room & R_ROOM);
if (!(is_room || is_maze)) {
continue;
}
if (is_maze || rand_percent(GOLD_PERCENT)) {
for (j = 0; j < 50; j++) {
row = get_rand(rooms[i].top_row+1,
rooms[i].bottom_row-1);
col = get_rand(rooms[i].left_col+1,
rooms[i].right_col-1);
if ((dungeon[row][col] == FLOOR) ||
(dungeon[row][col] == TUNNEL)) {
put_gold_at(row, col, is_maze);
break;
}
}
}
}
}
put_gold_at(row, col, is_maze)
short row, col;
boolean is_maze;
{
object *obj;
object *alloc_object(), *add_to_pack();
obj = alloc_object();
obj->row = row; obj->col = col;
obj->what_is = GOLD;
obj->quantity = get_rand((2 * current_level), (16 * current_level));
if (is_maze) {
obj->quantity += obj->quantity / 2;
}
dungeon[row][col] |= OBJECT;
add_to_pack(obj, &level_objects, 0);
}
put_object_at(obj, row, col)
object *obj;
{
object *add_to_pack();
obj->row = row;
obj->col = col;
dungeon[row][col] |= OBJECT;
add_to_pack(obj, &level_objects, 0);
}
object *
object_at(pack, row, col)
register object *pack;
short row, col;
{
object *obj;
obj = pack->next_object;
while (obj && ((obj->row != row) || (obj->col != col))) {
obj = obj->next_object;
}
return(obj);
}
object *
get_letter_object(ch)
{
object *obj;
obj = rogue.pack.next_object;
while (obj && (obj->ichar != ch)) {
obj = obj->next_object;
}
return(obj);
}
free_stuff(objlist)
object *objlist;
{
object *obj;
while (objlist->next_object) {
obj = objlist->next_object;
objlist->next_object =
objlist->next_object->next_object;
free_object(obj);
}
}
free_free_list()
{
object *obj;
while (free_list) {
obj = free_list;
free_list = free_list->next_object;
free_object(obj);
}
}
char *
name_of(obj)
object *obj;
{
char *retstring;
switch(obj->what_is) {
case SCROLL:
retstring = obj->quantity > 1 ? "scrolls " : "scroll ";
break;
case POTION:
retstring = obj->quantity > 1 ? "potions " : "potion ";
break;
case FOOD:
if (obj->which_kind == RATION) {
retstring = "food ";
} else {
retstring = fruit;
}
break;
case WAND:
retstring = is_wood[obj->which_kind] ? "staff " : "wand ";
break;
case WEAPON:
switch(obj->which_kind) {
case DART:
retstring=obj->quantity > 1 ? "darts " : "dart ";
break;
case ARROW:
retstring=obj->quantity > 1 ? "arrows " : "arrow ";
break;
case DAGGER:
retstring=obj->quantity > 1 ? "daggers " : "dagger ";
break;
case SHURIKEN:
retstring=obj->quantity > 1?"shurikens ":"shuriken ";
break;
default:
retstring = id_weapons[obj->which_kind].title;
}
break;
case ARMOR:
retstring = "armor ";
break;
case RING:
retstring = "ring ";
break;
case AMULET:
retstring = "amulet ";
break;
default:
retstring = "unknown ";
break;
}
return(retstring);
}
object *
get_rand_object()
{
object *obj, *alloc_object();
unsigned short get_rand_what_is();
obj = alloc_object();
if (foods < (current_level / 3)) {
obj->what_is = FOOD;
foods++;
} else {
obj->what_is = get_rand_what_is();
}
switch(obj->what_is) {
case SCROLL:
get_rand_scroll(obj);
break;
case POTION:
get_rand_potion(obj);
break;
case WEAPON:
get_rand_weapon(obj, 1);
break;
case ARMOR:
get_rand_armor(obj);
break;
case WAND:
get_rand_wand(obj);
break;
case FOOD:
get_food(obj, 0);
break;
case RING:
get_rand_ring(obj, 1);
break;
}
return(obj);
}
unsigned short
get_rand_what_is()
{
short percent;
unsigned short what_is;
percent = get_rand(1, 91);
if (percent <= 30) {
what_is = SCROLL;
} else if (percent <= 60) {
what_is = POTION;
} else if (percent <= 64) {
what_is = WAND;
} else if (percent <= 74) {
what_is = WEAPON;
} else if (percent <= 83) {
what_is = ARMOR;
} else if (percent <= 88) {
what_is = FOOD;
} else {
what_is = RING;
}
return(what_is);
}
get_rand_scroll(obj)
object *obj;
{
short percent;
percent = get_rand(0, 85);
obj->what_is = SCROLL;
if (percent <= 5) {
obj->which_kind = PROTECT_ARMOR;
} else if (percent <= 11) {
obj->which_kind = HOLD_MONSTER;
} else if (percent <= 20) {
obj->which_kind = CREATE_MONSTER;
} else if (percent <= 35) {
obj->which_kind = IDENTIFY;
} else if (percent <= 43) {
obj->which_kind = TELEPORT;
} else if (percent <= 50) {
obj->which_kind = SLEEP;
} else if (percent <= 55) {
obj->which_kind = SCARE_MONSTER;
} else if (percent <= 64) {
obj->which_kind = REMOVE_CURSE;
} else if (percent <= 69) {
obj->which_kind = ENCHANT_ARMOR;
} else if (percent <= 74) {
obj->which_kind = ENCHANT_WEAPON;
} else if (percent <= 80) {
obj->which_kind = AGGRAVATE_MONSTER;
} else {
obj->which_kind = MAGIC_MAPPING;
}
}
get_rand_potion(obj)
object *obj;
{
short percent;
percent = get_rand(1, 118);
obj->what_is = POTION;
if (percent <= 5) {
obj->which_kind = RAISE_LEVEL;
} else if (percent <= 15) {
obj->which_kind = DETECT_OBJECTS;
} else if (percent <= 25) {
obj->which_kind = DETECT_MONSTER;
} else if (percent <= 35) {
obj->which_kind = INCREASE_STRENGTH;
} else if (percent <= 45) {
obj->which_kind = RESTORE_STRENGTH;
} else if (percent <= 55) {
obj->which_kind = HEALING;
} else if (percent <= 65) {
obj->which_kind = EXTRA_HEALING;
} else if (percent <= 75) {
obj->which_kind = BLINDNESS;
} else if (percent <= 85) {
obj->which_kind = HALLUCINATION;
} else if (percent <= 95) {
obj->which_kind = CONFUSION;
} else if (percent <= 105) {
obj->which_kind = POISON;
} else if (percent <= 110) {
obj->which_kind = LEVITATION;
} else if (percent <= 114) {
obj->which_kind = HASTE_SELF;
} else {
obj->which_kind = SEE_INVISIBLE;
}
}
get_rand_weapon(obj, assign_wk)
object *obj;
int assign_wk;
{
short percent;
short i;
short blessing, increment;
obj->what_is = WEAPON;
if (assign_wk) {
obj->which_kind = get_rand(0, (WEAPONS - 1));
}
if ((obj->which_kind == ARROW) || (obj->which_kind == DAGGER) ||
(obj->which_kind == SHURIKEN) | (obj->which_kind == DART)) {
obj->quantity = get_rand(3, 15);
obj->quiver = get_rand(0, 126);
} else {
obj->quantity = 1;
}
obj->to_hit_enchantment = obj->damage_enchantment = 0;
percent = get_rand(1, 96);
blessing = get_rand(1, 3);
if (percent <= 16) {
increment = 1;
} else if (percent <= 32) {
increment = -1;
obj->is_cursed = 1;
}
if (percent <= 32) {
for (i = 0; i < blessing; i++) {
if (coin_toss()) {
obj->to_hit_enchantment += increment;
} else {
obj->damage_enchantment += increment;
}
}
}
switch(obj->which_kind) {
case BOW:
case DART:
obj->damage = "1d1";
break;
case ARROW:
obj->damage = "1d2";
break;
case DAGGER:
obj->damage = "1d3";
break;
case SHURIKEN:
obj->damage = "1d4";
break;
case MACE:
obj->damage = "2d3";
break;
case LONG_SWORD:
obj->damage = "3d4";
break;
case TWO_HANDED_SWORD:
obj->damage = "4d5";
break;
}
}
get_rand_armor(obj)
object *obj;
{
short percent;
short blessing;
obj->what_is = ARMOR;
obj->which_kind = get_rand(0, (ARMORS - 1));
obj->class = obj->which_kind + 2;
if ((obj->which_kind == PLATE) || (obj->which_kind == SPLINT)) {
obj->class--;
}
obj->is_protected = 0;
obj->damage_enchantment = 0;
percent = get_rand(1, 100);
blessing = get_rand(1, 3);
if (percent <= 16) {
obj->is_cursed = 1;
obj->damage_enchantment -= blessing;
} else if (percent <= 33) {
obj->damage_enchantment += blessing;
}
}
get_rand_wand(obj)
object *obj;
{
obj->what_is = WAND;
obj->which_kind = get_rand(0, (WANDS - 1));
if (obj->which_kind == MAGIC_MISSILE) {
obj->class = get_rand(6, 12);
} else if (obj->which_kind == CANCELLATION) {
obj->class = get_rand(5, 9);
} else {
obj->class = get_rand(3, 6);
}
}
get_food(obj, force_ration)
object *obj;
boolean force_ration;
{
obj->what_is = FOOD;
if (force_ration || rand_percent(80)) {
obj->which_kind = RATION;
} else {
obj->which_kind = FRUIT;
}
}
put_stairs()
{
short row, col;
get_rand_row_col(&row, &col, (FLOOR | TUNNEL));
dungeon[row][col] |= STAIRS;
}
get_armor_class(obj)
object *obj;
{
if (obj) {
return(obj->class + obj->damage_enchantment);
}
return(0);
}
object *
alloc_object()
{
object *obj;
char *malloc();
if (free_list) {
obj = free_list;
free_list = free_list->next_object;
} else if (!(obj = (object *) malloc(sizeof(object)))) {
free_free_list();
message("cannot allocate object, saving game", 0);
save_into_file(error_file);
}
obj->quantity = 1;
obj->ichar = 'L';
obj->picked_up = obj->is_cursed = 0;
obj->in_use_flags = NOT_USED;
obj->identified = UNIDENTIFIED;
obj->damage = "1d1";
return(obj);
}
free_object(obj)
object *obj;
{
obj->next_object = free_list;
free_list = obj;
}
make_party()
{
short n;
party_room = get_rand_room();
n = rand_percent(99) ? fill_party_room_with_objects(party_room) : 11;
if (rand_percent(99)) {
fill_party_room_with_monsters(party_room, n);
}
}
show_objects()
{
object *obj;
short mc, rc, row, col;
object *monster, *object_at();
obj = level_objects.next_object;
while (obj) {
row = obj->row;
col = obj->col;
rc = get_mask_char(obj->what_is);
if (dungeon[row][col] & MONSTER) {
if (monster = object_at(&level_monsters, row, col)) {
monster->trail_char = rc;
}
}
mc = mvinch(row, col);
if (((mc < 'A') || (mc > 'Z')) &&
((row != rogue.row) || (col != rogue.col))) {
mvaddch(row, col, rc);
}
obj = obj->next_object;
}
monster = level_monsters.next_object;
while (monster) {
if (monster->m_flags & IMITATES) {
mvaddch(monster->row, monster->col, monster->disguise);
}
monster = monster->next_monster;
}
}
put_amulet()
{
object *obj, *alloc_object();
obj = alloc_object();
obj->what_is = AMULET;
put_object_rand_location(obj);
}
put_object_rand_location(obj)
object *obj;
{
short row, col;
get_rand_row_col(&row, &col, (FLOOR | TUNNEL));
put_object_at(obj, row, col);
}
create_object_for_wizard()
{
short ch, max, wk;
object *obj, *alloc_object(), *add_to_pack();
char buf[80];
if (get_pack_count(0) >= MAX_PACK_COUNT) {
message("pack full", 0);
return;
}
message("type of object?", 0);
while (!index("!?:)]=/,\033", (ch = rgetchar()))) {
sound_bell();
}
check_message();
if (ch == '\033') {
return;
}
obj = alloc_object();
switch(ch) {
case '!':
obj->what_is = POTION;
max = POTIONS - 1;
break;
case '?':
obj->what_is = SCROLL;
max = SCROLLS - 1;
break;
case ',':
obj->what_is = AMULET;
break;
case ':':
get_food(obj, 0);
break;
case ')':
get_rand_weapon(obj, 0);
max = WEAPONS - 1;
break;
case ']':
get_rand_armor(obj);
max = ARMORS - 1;
break;
case '/':
get_rand_wand(obj);
max = WANDS - 1;
break;
case '=':
max = RINGS - 1;
obj->what_is = RING;
break;
}
if ((ch != ',') && (ch != ':')) {
GIL:
if (get_input_line("which kind?", "", buf, "", 0, 1)) {
wk = get_number(buf);
if ((wk >= 0) && (wk <= max)) {
obj->which_kind = (unsigned char) wk;
if (obj->what_is == RING) {
get_rand_ring(obj, 0);
}
} else {
sound_bell();
goto GIL;
}
} else {
free_object(obj);
return;
}
}
get_description(obj, buf);
message(buf, 0);
add_to_pack(obj, &rogue.pack, 1);
}
next_party()
{
int n;
n = current_level;
while (n % PARTY_TIME) {
n++;
}
return(get_rand((n + 1), (n + PARTY_TIME)));
}
SHAR_EOF
echo shar: extracting object.h
cat - << \SHAR_EOF > object.h
/*
* object.h
*
* This source herein may be modified and/or distributed by anybody who
* so desires, with the following restrictions:
* 1.) This notice shall not be removed.
* 2.) Credit shall not be taken for the creation of this source.
* 3.) This code is not to be traded, sold, or used for personal
* gain or profit.
*
*/
#define boolean char
#define NOTHING ((unsigned short) 0)
#define OBJECT ((unsigned short) 01)
#define MONSTER ((unsigned short) 02)
#define STAIRS ((unsigned short) 04)
#define HORWALL ((unsigned short) 010)
#define VERTWALL ((unsigned short) 020)
#define DOOR ((unsigned short) 040)
#define FLOOR ((unsigned short) 0100)
#define TUNNEL ((unsigned short) 0200)
#define TRAP ((unsigned short) 0400)
#define HIDDEN ((unsigned short) 01000)
#define ARMOR ((unsigned short) 01)
#define WEAPON ((unsigned short) 02)
#define SCROLL ((unsigned short) 04)
#define POTION ((unsigned short) 010)
#define GOLD ((unsigned short) 020)
#define FOOD ((unsigned short) 040)
#define WAND ((unsigned short) 0100)
#define RING ((unsigned short) 0200)
#define AMULET ((unsigned short) 0400)
#define ALL_OBJECTS ((unsigned short) 0777)
#define LEATHER 0
#define RINGMAIL 1
#define SCALE 2
#define CHAIN 3
#define BANDED 4
#define SPLINT 5
#define PLATE 6
#define ARMORS 7
#define BOW 0
#define DART 1
#define ARROW 2
#define DAGGER 3
#define SHURIKEN 4
#define MACE 5
#define LONG_SWORD 6
#define TWO_HANDED_SWORD 7
#define WEAPONS 8
#define MAX_PACK_COUNT 24
#define PROTECT_ARMOR 0
#define HOLD_MONSTER 1
#define ENCHANT_WEAPON 2
#define ENCHANT_ARMOR 3
#define IDENTIFY 4
#define TELEPORT 5
#define SLEEP 6
#define SCARE_MONSTER 7
#define REMOVE_CURSE 8
#define CREATE_MONSTER 9
#define AGGRAVATE_MONSTER 10
#define MAGIC_MAPPING 11
#define SCROLLS 12
#define INCREASE_STRENGTH 0
#define RESTORE_STRENGTH 1
#define HEALING 2
#define EXTRA_HEALING 3
#define POISON 4
#define RAISE_LEVEL 5
#define BLINDNESS 6
#define HALLUCINATION 7
#define DETECT_MONSTER 8
#define DETECT_OBJECTS 9
#define CONFUSION 10
#define LEVITATION 11
#define HASTE_SELF 12
#define SEE_INVISIBLE 13
#define POTIONS 14
#define TELEPORT_AWAY 0
#define SLOW_MONSTER 1
#define CONFUSE_MONSTER 2
#define INVISIBILITY 3
#define POLYMORPH 4
#define HASTE_MONSTER 5
#define PUT_TO_SLEEP 6
#define MAGIC_MISSILE 7
#define CANCELLATION 8
#define DO_NOTHING 9
#define WANDS 10
#define STEALTH 0
#define R_TELEPORT 1
#define REGENERATION 2
#define SLOW_DIGEST 3
#define ADD_STRENGTH 4
#define SUSTAIN_STRENGTH 5
#define DEXTERITY 6
#define ADORNMENT 7
#define R_SEE_INVISIBLE 8
#define MAINTAIN_ARMOR 9
#define SEARCHING 10
#define RINGS 11
#define RATION 0
#define FRUIT 1
#define NOT_USED ((unsigned short) 0)
#define BEING_WIELDED ((unsigned short) 01)
#define BEING_WORN ((unsigned short) 02)
#define ON_LEFT_HAND ((unsigned short) 04)
#define ON_RIGHT_HAND ((unsigned short) 010)
#define ON_EITHER_HAND ((unsigned short) 014)
#define BEING_USED ((unsigned short) 017)
#define NO_TRAP -1
#define TRAP_DOOR 0
#define BEAR_TRAP 1
#define TELEPORT_TRAP 2
#define POISON_DART_TRAP 3
#define SLEEPING_GAS_TRAP 4
#define RUST_TRAP 5
#define TRAPS 6
#define STEALTH_FACTOR 3
#define R_TELEPORT_PERCENT 8
#define UNIDENTIFIED ((unsigned char) 00) /* MUST BE ZERO! */
#define IDENTIFIED ((unsigned char) 01)
#define CALLED ((unsigned char) 02)
#define DROWS 24
#define DCOLS 80
#define MAX_TITLE_LENGTH 30
#define MORE "-more-"
#define MAXSYLLABLES 40
#define MAX_METAL 14
#define WAND_MATERIALS 30
#define GEMS 14
#define GOLD_PERCENT 46
struct identify {
short value;
char *title;
char *real;
unsigned char id_status;
};
/*
The following #defines provide more meaningful names for some of the
struct object fields that are used for monsters. This, since each monster
and object (scrolls, potions, etc) are represented by a struct object.
*/
#define m_damage damage
#define hp_to_kill quantity
#define m_char ichar
#define first_level is_protected
#define last_level is_cursed
#define m_hit_chance class
#define stationary_damage identified
#define drop_percent which_kind
#define trail_char damage_enchantment
#define slowed_toggle quiver
#define moves_confused to_hit_enchantment
#define nap_length picked_up
#define disguise what_is
#define next_monster next_object
struct object { /* comment is monster meaning */
unsigned long m_flags; /* monster flags */
char *damage; /* damage it does */
short quantity; /* hit points to kill */
char ichar; /* 'A' is for aquatar */
short kill_exp; /* exp for killing it */
boolean is_protected; /* level starts */
boolean is_cursed; /* level ends */
char class; /* chance of hitting you */
short identified; /* 'F' damage, 1,2,3... */
unsigned char which_kind; /* item carry/drop % */
char o_row, o_col, o; /* o is how many times stuck at o_row, o_col */
char row, col; /* current row, col */
char damage_enchantment;/* room char when detect_monster */
char quiver; /* monster slowed toggle */
char trow, tcol; /* target row, col */
char to_hit_enchantment;/* how many moves is confused */
unsigned short what_is; /* imitator's charactor (?!%: */
boolean picked_up; /* sleep from wand of sleep */
unsigned short in_use_flags;
struct object *next_object; /* next monster */
};
typedef struct object object;
#define INIT_HP 12
struct fighter {
object *armor;
object *weapon;
object *left_ring, *right_ring;
short hp_current;
short hp_max;
char strength_current;
char strength_max;
object pack;
int gold;
char exp;
long exp_points;
short row, col;
char fchar;
short moves_left;
};
typedef struct fighter fighter;
struct door {
char other_room;
char other_row,
other_col;
char door_row,
door_col;
};
typedef struct door door;
struct room {
char bottom_row, right_col, left_col, top_row;
door doors[4];
unsigned short is_room;
};
typedef struct room room;
struct trap {
short trap_type;
short trap_row, trap_col;
};
typedef struct trap trap;
extern fighter rogue;
extern room rooms[];
extern trap traps[];
extern unsigned short dungeon[DROWS][DCOLS];
extern object level_objects;
extern struct identify id_scrolls[];
extern struct identify id_potions[];
extern struct identify id_wands[];
extern struct identify id_rings[];
extern struct identify id_weapons[];
extern struct identify id_armors[];
extern object monster_tab[];
extern object level_monsters;
SHAR_EOF
echo shar: extracting pack.c
cat - << \SHAR_EOF > pack.c
/*
* pack.c
*
* This source herein may be modified and/or distributed by anybody who
* so desires, with the following restrictions:
* 1.) This notice shall not be removed.
* 2.) Credit shall not be taken for the creation of this source.
* 3.) This code is not to be traded, sold, or used for personal
* gain or profit.
*
*/
#include "curses.h"
#include "move.h"
#include "object.h"
#include "room.h"
char *curse_message = "you can't, it appears to be cursed";
object *
add_to_pack(obj, pack, condense)
object *obj, *pack;
{
object *op, *check_duplicate();
if (condense) {
if (op = check_duplicate(obj, pack)) {
free_object(obj);
return(op);
} else {
obj->ichar = next_avail_ichar();
}
}
if (pack->next_object == 0) {
pack->next_object = obj;
} else {
op = pack->next_object;
while (op->next_object) {
op = op->next_object;
}
op->next_object = obj;
}
obj->next_object = 0;
return(obj);
}
remove_from_pack(obj, pack)
object *obj, *pack;
{
while (pack->next_object != obj) {
pack = pack->next_object;
}
pack->next_object = pack->next_object->next_object;
}
object *
pick_up(row, col, status)
short *status;
{
object *obj, *object_at(), *add_to_pack();
obj = object_at(&level_objects, row, col);
*status = 1;
if ((obj->what_is == SCROLL) && (obj->which_kind == SCARE_MONSTER) &&
obj->picked_up) {
message("the scroll turns to dust as you pick it up", 0);
dungeon[row][col] &= (~OBJECT);
vanish(obj, 0, &level_objects);
*status = 0;
if (id_scrolls[SCARE_MONSTER].id_status == UNIDENTIFIED) {
id_scrolls[SCARE_MONSTER].id_status = IDENTIFIED;
}
return(0);
}
if (obj->what_is == GOLD) {
rogue.gold += obj->quantity;
dungeon[row][col] &= ~(OBJECT);
remove_from_pack(obj, &level_objects);
print_stats(STAT_GOLD);
return(obj); /* obj will be free_object()ed in single_move() */
}
if (get_pack_count(obj) >= MAX_PACK_COUNT) {
message("pack too full", 1);
return(0);
}
dungeon[row][col] &= ~(OBJECT);
remove_from_pack(obj, &level_objects);
obj = add_to_pack(obj, &rogue.pack, 1);
obj->picked_up = 1;
return(obj);
}
drop()
{
object *obj, *get_letter_object(), *new;
short ch;
object *alloc_object();
char description[DCOLS];
if (dungeon[rogue.row][rogue.col] & (OBJECT | STAIRS | TRAP)) {
message("there's already something there", 0);
return;
}
if (!rogue.pack.next_object) {
message("you have nothing to drop", 0);
return;
}
if ((ch = get_pack_letter("drop what?", ALL_OBJECTS)) == CANCEL) {
return;
}
if (!(obj = get_letter_object(ch))) {
message("no such item.", 0);
return;
}
if (obj->in_use_flags & BEING_WIELDED) {
if (obj->is_cursed) {
message(curse_message, 0);
return;
}
unwield(rogue.weapon);
} else if (obj->in_use_flags & BEING_WORN) {
if (obj->is_cursed) {
message(curse_message, 0);
return;
}
mv_aquatars();
unwear(rogue.armor);
print_stats(STAT_ARMOR);
} else if (obj->in_use_flags & ON_EITHER_HAND) {
if (obj->is_cursed) {
message(curse_message, 0);
return;
}
un_put_on(obj);
}
obj->row = rogue.row;
obj->col = rogue.col;
if ((obj->quantity > 1) && (obj->what_is != WEAPON)) {
obj->quantity--;
new = alloc_object();
*new = *obj;
new->quantity = 1;
obj = new;
} else {
obj->ichar = 'L';
remove_from_pack(obj, &rogue.pack);
}
put_object_at(obj, rogue.row, rogue.col);
strcpy(description, "dropped ");
get_description(obj, description+8);
message(description, 0);
register_move();
}
object *
check_duplicate(obj, pack)
object *obj, *pack;
{
object *op;
if (!(obj->what_is & (WEAPON | FOOD | SCROLL | POTION))) {
return(0);
}
if ((obj->what_is == FOOD) && (obj->which_kind == FRUIT)) {
return(0);
}
op = pack->next_object;
while (op) {
if ((op->what_is == obj->what_is) &&
(op->which_kind == obj->which_kind)) {
if ((obj->what_is != WEAPON) ||
((obj->what_is == WEAPON) &&
((obj->which_kind == ARROW) ||
(obj->which_kind == DAGGER) ||
(obj->which_kind == DART) ||
(obj->which_kind == SHURIKEN)) &&
(obj->quiver == op->quiver))) {
op->quantity += obj->quantity;
return(op);
}
}
op = op->next_object;
}
return(0);
}
next_avail_ichar()
{
register object *obj;
register i;
boolean ichars[26];
for (i = 0; i < 26; i++) {
ichars[i] = 0;
}
obj = rogue.pack.next_object;
while (obj) {
ichars[(obj->ichar - 'a')] = 1;
obj = obj->next_object;
}
for (i = 0; i < 26; i++) {
if (!ichars[i]) {
return(i + 'a');
}
}
return('?');
}
wait_for_ack(prompt)
{
if (prompt) {
printf("%s ", MORE);
fflush(stdout);
}
while (rgetchar() != ' ') ;
}
get_pack_letter(prompt, mask)
char *prompt;
unsigned short mask;
{
short ch;
unsigned short tmask = mask;
if (!mask_in_pack(&rogue.pack, mask)) {
message("nothing appropriate", 0);
return(CANCEL);
}
for (;;) {
message(prompt, 0);
for (;;) {
ch = rgetchar();
if (!is_pack_letter(&ch, &mask)) {
sound_bell();
} else {
break;
}
}
if (ch == LIST) {
check_message();
inventory(&rogue.pack, mask);
} else {
break;
}
mask = tmask;
}
check_message();
return(ch);
}
take_off()
{
char description[DCOLS];
object *obj;
if (rogue.armor) {
if (rogue.armor->is_cursed) {
message(curse_message, 0);
} else {
mv_aquatars();
obj = rogue.armor;
unwear(rogue.armor);
strcpy(description, "was wearing ");
get_description(obj, description+12);
message(description, 0);
print_stats(STAT_ARMOR);
register_move();
}
} else {
message("not wearing any", 0);
}
}
wear()
{
short ch;
register object *obj;
char description[DCOLS];
if (rogue.armor) {
message("your already wearing some", 0);
return;
}
ch = get_pack_letter("wear what?", ARMOR);
if (ch == CANCEL) {
return;
}
if (!(obj = get_letter_object(ch))) {
message("no such item.", 0);
return;
}
if (obj->what_is != ARMOR) {
message("you can't wear that", 0);
return;
}
obj->identified = 1;
strcpy(description, "wearing ");
get_description(obj, description + 8);
message(description, 0);
do_wear(obj);
print_stats(STAT_ARMOR);
register_move();
}
unwear(obj)
object *obj;
{
if (obj) {
obj->in_use_flags &= (~BEING_WORN);
}
rogue.armor = (object *) 0;
}
do_wear(obj)
object *obj;
{
rogue.armor = obj;
obj->in_use_flags |= BEING_WORN;
obj->identified = 1;
}
wield()
{
short ch;
register object *obj;
char description[DCOLS];
if (rogue.weapon && rogue.weapon->is_cursed) {
message(curse_message, 0);
return;
}
ch = get_pack_letter("wield what?", WEAPON);
if (ch == CANCEL) {
return;
}
if (!(obj = get_letter_object(ch))) {
message("No such item.", 0);
return;
}
if (obj->what_is & (ARMOR | RING)) {
sprintf(description, "you can't wield %s",
((obj->what_is == ARMOR) ? "armor" : "rings"));
message(description, 0);
return;
}
if (obj->in_use_flags & BEING_WIELDED) {
message("in use", 0);
} else {
unwield(rogue.weapon);
strcpy(description, "wielding ");
get_description(obj, description + 9);
message(description, 0);
do_wield(obj);
register_move();
}
}
do_wield(obj)
object *obj;
{
rogue.weapon = obj;
obj->in_use_flags |= BEING_WIELDED;
}
unwield(obj)
object *obj;
{
if (obj) {
obj->in_use_flags &= (~BEING_WIELDED);
}
rogue.weapon = (object *) 0;
}
call_it()
{
short ch;
register object *obj;
struct identify *id_table, *get_id_table();
char buf[MAX_TITLE_LENGTH+2];
ch = get_pack_letter("call what?", (SCROLL | POTION | WAND | RING));
if (ch == CANCEL) {
return;
}
if (!(obj = get_letter_object(ch))) {
message("no such item.", 0);
return;
}
if (!(obj->what_is & (SCROLL | POTION | WAND | RING))) {
message("surely you already know what that's called", 0);
return;
}
id_table = get_id_table(obj);
if (get_input_line("call it:","",buf,id_table[obj->which_kind].title,1,1)) {
id_table[obj->which_kind].id_status = CALLED;
strcpy(id_table[obj->which_kind].title, buf);
}
}
get_pack_count(new_obj)
object *new_obj;
{
object *obj;
short count = 0;
obj = rogue.pack.next_object;
while (obj) {
if (obj->what_is != WEAPON) {
count += obj->quantity;
} else if (!new_obj) {
count++;
} else if ((new_obj->what_is != WEAPON) ||
((obj->which_kind != ARROW) &&
(obj->which_kind != DAGGER) &&
(obj->which_kind != DART) &&
(obj->which_kind != SHURIKEN)) ||
(new_obj->which_kind != obj->which_kind) ||
(obj->quiver != new_obj->quiver)) {
count++;
}
obj = obj->next_object;
}
return(count);
}
mask_in_pack(pack, mask)
object *pack;
unsigned short mask;
{
while (pack->next_object) {
pack = pack->next_object;
if (pack->what_is & mask) {
return(1);
}
}
return(0);
}
is_pack_letter(c, mask)
short *c;
unsigned short *mask;
{
if (((*c == '?') || (*c == '!') || (*c == ':') || (*c == '=') ||
(*c == ')') || (*c == ']') || (*c == '/') || (*c == ','))) {
switch(*c) {
case '?':
*mask = SCROLL;
break;
case '!':
*mask = POTION;
break;
case ':':
*mask = FOOD;
break;
case ')':
*mask = WEAPON;
break;
case ']':
*mask = ARMOR;
break;
case '/':
*mask = WAND;
break;
case '=':
*mask = RING;
break;
case ',':
*mask = AMULET;
break;
}
*c = LIST;
return(1);
}
return(((*c >= 'a') && (*c <= 'z')) || (*c == CANCEL) || (*c == LIST));
}
has_amulet()
{
return(mask_in_pack(&rogue.pack, AMULET));
}
SHAR_EOF
echo shar: extracting play.c
cat - << \SHAR_EOF > play.c
/*
* play.c
*
* This source herein may be modified and/or distributed by anybody who
* so desires, with the following restrictions:
* 1.) This notice shall not be removed.
* 2.) Credit shall not be taken for the creation of this source.
* 3.) This code is not to be traded, sold, or used for personal
* gain or profit.
*
*/
#include <curses.h>
#include "object.h"
#include "move.h"
boolean interrupted = 0;
char *unknown_command = "unknown command";
extern short party_room, bear_trap;
extern char hit_message[];
extern boolean wizard, trap_door;
play_level()
{
short ch;
int count;
for (;;) {
interrupted = 0;
if (hit_message[0]) {
message(hit_message, 1);
hit_message[0] = 0;
}
if (trap_door) {
trap_door = 0;
return;
}
move(rogue.row, rogue.col);
refresh();
ch = rgetchar();
check_message();
count = 0;
CH:
switch(ch) {
case '.':
rest((count > 0) ? count : 1);
break;
case 's':
search(((count > 0) ? count : 1), 0);
break;
case 'i':
inventory(&rogue.pack, ALL_OBJECTS);
break;
case 'f':
fight(0);
break;
case 'F':
fight(1);
break;
case 'h':
case 'j':
case 'k':
case 'l':
case 'y':
case 'u':
case 'n':
case 'b':
single_move_rogue(ch, 1);
break;
case 'H':
case 'J':
case 'K':
case 'L':
case 'B':
case 'Y':
case 'U':
case 'N':
case '\010':
case '\012':
case '\013':
case '\014':
case '\031':
case '\025':
case '\016':
case '\002':
multiple_move_rogue(ch);
break;
case 'e':
eat();
break;
case 'q':
quaff();
break;
case 'r':
read_scroll();
break;
case 'm':
move_onto();
break;
case 'd':
drop();
break;
case 'P':
put_on_ring();
break;
case 'R':
remove_ring();
break;
case '\020':
remessage();
break;
case '\027':
wizardize();
break;
case '>':
if (check_down()) {
return;
}
break;
case '<':
if (check_up()) {
return;
}
break;
case ')':
case ']':
inventory_armor_weapon(ch == ')');
break;
case '=':
inventory_rings();
break;
case '^':
identify_trap();
break;
case 'I':
single_inventory(0);
break;
case 'T':
take_off();
break;
case 'W':
wear();
break;
case 'w':
wield();
break;
case 'c':
call_it();
break;
case 'z':
zapp();
break;
case 't':
throw();
break;
case '!':
shell();
break;
case 'v':
message("rogue-clone: Version II. (Tim Stoehr was here), tektronix!zeus!tims", 0);
break;
case 'Q':
quit(0);
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':
move(rogue.row, rogue.col);
refresh();
do {
if (count < 100) {
count = (10 * count) + (ch - '0');
}
ch = rgetchar();
} while ((ch >= '0') && (ch <= '9'));
if (ch != CANCEL) {
goto CH;
}
break;
case ' ':
break;
case '\011':
if (wizard) {
inventory(&level_objects, ALL_OBJECTS);
} else {
message(unknown_command, 0);
}
break;
case '\023':
if (wizard) {
draw_magic_map();
} else {
message(unknown_command, 0);
}
break;
case '\024':
if (wizard) {
show_traps();
} else {
message(unknown_command, 0);
}
break;
case '\017':
if (wizard) {
show_objects();
} else {
message(unknown_command, 0);
}
break;
case '\001':
show_average_hp();
break;
case '\003':
if (wizard) {
create_object_for_wizard();
} else {
message(unknown_command, 0);
}
break;
case '\015':
if (wizard) {
show_monsters();
} else {
message(unknown_command, 0);
}
break;
case 'S':
save_game();
break;
default:
message(unknown_command, 0);
break;
}
}
}
SHAR_EOF
echo shar: extracting use.c
cat - << \SHAR_EOF > use.c
/*
* use.c
*
* This source herein may be modified and/or distributed by anybody who
* so desires, with the following restrictions:
* 1.) This notice shall not be removed.
* 2.) Credit shall not be taken for the creation of this source.
* 3.) This code is not to be traded, sold, or used for personal
* gain or profit.
*
*/
#include <curses.h>
#include "object.h"
#include "move.h"
#include "monster.h"
#include "room.h"
short halluc = 0;
short blind = 0;
short confused = 0;
short levitate = 0;
short haste_self = 0;
boolean see_invisible = 0;
short extra_hp = 0;
boolean detect_monster = 0;
char *strange_feeling = "you have a strange feeling for a moment, then it passes";
extern short bear_trap;
extern char hunger_str[];
extern short current_room;
extern long level_points[];
extern boolean being_held;
extern char *fruit, *you_can_move_again;
extern boolean sustain_strength;
quaff()
{
short ch;
char buf[80];
object *obj, *get_letter_object();
ch = get_pack_letter("quaff what?", POTION);
if (ch == CANCEL) {
return;
}
if (!(obj = get_letter_object(ch))) {
message("no such item.", 0);
return;
}
if (obj->what_is != POTION) {
message("you can't drink that", 0);
return;
}
switch(obj->which_kind) {
case INCREASE_STRENGTH:
message("you feel stronger now, what bulging muscles!",
0);
rogue.strength_current++;
if (rogue.strength_current > rogue.strength_max) {
rogue.strength_max = rogue.strength_current;
}
break;
case RESTORE_STRENGTH:
rogue.strength_current = rogue.strength_max;
message("this tastes great, you feel warm all over", 0);
break;
case HEALING:
message("you begin to feel better", 0);
potion_heal(0);
break;
case EXTRA_HEALING:
message("you begin to feel much better", 0);
potion_heal(1);
break;
case POISON:
if (!sustain_strength) {
rogue.strength_current -= get_rand(1, 3);
if (rogue.strength_current < 1) {
rogue.strength_current = 1;
}
}
message("you feel very sick now", 0);
if (halluc) {
unhallucinate();
}
break;
case RAISE_LEVEL:
rogue.exp_points = level_points[rogue.exp - 1];
add_exp(1, 1);
break;
case BLINDNESS:
go_blind();
break;
case HALLUCINATION:
message("oh wow, everything seems so cosmic", 0);
halluc += get_rand(500, 800);
break;
case DETECT_MONSTER:
show_monsters();
if (!(level_monsters.next_monster)) {
message(strange_feeling, 0);
}
break;
case DETECT_OBJECTS:
if (level_objects.next_object) {
if (!blind) {
show_objects();
}
} else {
message(strange_feeling, 0);
}
break;
case CONFUSION:
message((halluc ? "what a trippy feeling" :
"you feel confused"), 0);
confuse();
break;
case LEVITATION:
message("you start to float in the air", 0);
levitate += get_rand(15, 30);
being_held = bear_trap = 0;
break;
case HASTE_SELF:
message("you feel yourself moving much faster", 0);
haste_self += get_rand(11, 21);
if (!(haste_self % 2)) {
haste_self++;
}
break;
case SEE_INVISIBLE:
sprintf(buf, "hmm, this potion tastes like %sjuice", fruit);
message(buf, 0);
if (blind) {
unblind();
}
see_invisible = 1;
relight();
break;
}
print_stats((STAT_STRENGTH | STAT_HP));
if (id_potions[obj->which_kind].id_status != CALLED) {
id_potions[obj->which_kind].id_status = IDENTIFIED;
}
vanish(obj, 1, &rogue.pack);
}
read_scroll()
{
short ch;
object *obj, *get_letter_object();
char msg[DCOLS];
char *get_ench_color(), *name_of();
ch = get_pack_letter("read what?", SCROLL);
if (ch == CANCEL) {
return;
}
if (!(obj = get_letter_object(ch))) {
message("no such item.", 0);
return;
}
if (obj->what_is != SCROLL) {
message("you can't read that", 0);
return;
}
switch(obj->which_kind) {
case SCARE_MONSTER:
message("you hear a maniacal laughter in the distance",
0);
break;
case HOLD_MONSTER:
hold_monster();
break;
case ENCHANT_WEAPON:
if (rogue.weapon) {
if (rogue.weapon->what_is == WEAPON) {
sprintf(msg, "your %sglow%s %sfor a moment",
name_of(rogue.weapon),
((rogue.weapon->quantity <= 1) ? "s" : ""),
get_ench_color());
message(msg, 0);
if (coin_toss()) {
rogue.weapon->to_hit_enchantment++;
} else {
rogue.weapon->damage_enchantment++;
}
}
rogue.weapon->is_cursed = 0;
} else {
message("your hands tingle", 0);
}
break;
case ENCHANT_ARMOR:
if (rogue.armor) {
sprintf(msg, "your armor glows %sfor a moment",
get_ench_color());
message(msg, 0);
rogue.armor->damage_enchantment++;
rogue.armor->is_cursed = 0;
print_stats(STAT_ARMOR);
} else {
message("your skin crawls", 0);
}
break;
case IDENTIFY:
message("this is a scroll of identify", 0);
obj->identified = 1;
id_scrolls[obj->which_kind].id_status = IDENTIFIED;
identify();
break;
case TELEPORT:
teleport();
break;
case SLEEP:
message("you fall asleep", 0);
take_a_nap();
break;
case PROTECT_ARMOR:
if (rogue.armor) {
message( "your armor is covered by a shimmering gold shield",0);
rogue.armor->is_protected = 1;
rogue.armor->is_cursed = 0;
} else {
message("your acne seems to have disappeared",
0);
}
break;
case REMOVE_CURSE:
message((!halluc) ?
"you feel as though someone is watching over you" :
"you feel in touch with the universal oneness", 0);
uncurse_all();
break;
case CREATE_MONSTER:
create_monster();
break;
case AGGRAVATE_MONSTER:
aggravate();
break;
case MAGIC_MAPPING:
message("this scroll seems to have a map on it", 0);
draw_magic_map();
break;
}
if (id_scrolls[obj->which_kind].id_status != CALLED) {
id_scrolls[obj->which_kind].id_status = IDENTIFIED;
}
vanish(obj, (obj->which_kind != SLEEP), &rogue.pack);
}
/* vanish() does NOT handle a quiver of weapons with more than one
arrow (or whatever) in the quiver. It will only decrement the count.
*/
vanish(obj, rm, pack)
object *obj;
short rm;
object *pack;
{
if (obj->quantity > 1) {
obj->quantity--;
} else {
if (obj->in_use_flags & BEING_WIELDED) {
unwield(obj);
} else if (obj->in_use_flags & BEING_WORN) {
unwear(obj);
} else if (obj->in_use_flags & ON_EITHER_HAND) {
un_put_on(obj);
}
remove_from_pack(obj, pack);
free_object(obj);
}
if (rm) {
register_move();
}
}
potion_heal(extra)
{
float ratio;
short add;
rogue.hp_current += rogue.exp;
ratio = ((float)rogue.hp_current) / rogue.hp_max;
if (ratio >= 1.00) {
rogue.hp_max += (extra ? 2 : 1);
extra_hp += (extra ? 2 : 1);
rogue.hp_current = rogue.hp_max;
} else if (ratio >= 0.90) {
rogue.hp_max += (extra ? 1 : 0);
extra_hp += (extra ? 1 : 0);
rogue.hp_current = rogue.hp_max;
} else {
if (ratio < 0.33) {
ratio = 0.33;
}
if (extra) {
ratio += ratio;
}
add = (short)(ratio * ((float)rogue.hp_max - rogue.hp_current));
rogue.hp_current += add;
if (rogue.hp_current > rogue.hp_max) {
rogue.hp_current = rogue.hp_max;
}
}
if (blind) {
unblind();
}
if (confused && extra) {
unconfuse();
} else if (confused) {
confused = (confused / 2) + 1;
}
if (halluc && extra) {
unhallucinate();
} else if (halluc) {
halluc = (halluc / 2) + 1;
}
}
identify()
{
short ch;
object *obj, *get_letter_object();
struct identify *id_table, *get_id_table();
char description[DCOLS];
AGAIN:
ch = get_pack_letter("what would you like to identify?", ALL_OBJECTS);
if (ch == CANCEL) {
return;
}
if (!(obj = get_letter_object(ch))) {
message("no such item, try again", 0);
message("", 0);
check_message();
goto AGAIN;
}
obj->identified = 1;
if (obj->what_is & (SCROLL | POTION | WEAPON | ARMOR | WAND | RING)) {
id_table = get_id_table(obj);
id_table[obj->which_kind].id_status = IDENTIFIED;
}
get_description(obj, description);
message(description, 0);
}
eat()
{
short ch;
short moves;
object *obj, *get_letter_object();
char buf[70];
ch = get_pack_letter("eat what?", FOOD);
if (ch == CANCEL) {
return;
}
if (!(obj = get_letter_object(ch))) {
message("no such item.", 0);
return;
}
if (obj->what_is != FOOD) {
message("you can't eat that", 0);
return;
}
if ((obj->which_kind == FRUIT) || rand_percent(60)) {
moves = get_rand(900, 1100);
if (obj->which_kind == RATION) {
message("yum, that tasted good", 0);
} else {
sprintf(buf, "my, that was a yummy %s", fruit);
message(buf, 0);
}
} else {
moves = get_rand(700, 900);
message("yuk, that food tasted awful", 0);
add_exp(2, 1);
}
rogue.moves_left /= 3;
rogue.moves_left += moves;
hunger_str[0] = 0;
print_stats(STAT_HUNGER);
vanish(obj, 1, &rogue.pack);
}
hold_monster()
{
short i, j;
short mcount = 0;
object *monster, *object_at();
short row, col;
for (i = -2; i <= 2; i++) {
for (j = -2; j <= 2; j++) {
row = rogue.row + i;
col = rogue.col + j;
if ((row < MIN_ROW) || (row > (DROWS-2)) || (col < 0) ||
(col > (DCOLS-1))) {
continue;
}
if (dungeon[row][col] & MONSTER) {
monster = object_at(&level_monsters, row, col);
monster->m_flags |= ASLEEP;
monster->m_flags &= (~WAKENS);
mcount++;
}
}
}
if (mcount == 0) {
message("you feel a strange sense of loss", 0);
} else if (mcount == 1) {
message("the monster freezes", 0);
} else {
message("the monsters around you freeze", 0);
}
}
teleport()
{
mvaddch(rogue.row, rogue.col, get_dungeon_char(rogue.row, rogue.col));
if (current_room >= 0) {
darken_room(current_room);
}
put_player(get_room_number(rogue.row, rogue.col));
being_held = bear_trap = 0;
}
hallucinate()
{
object *obj, *monster;
short ch;
if (blind) return;
obj = level_objects.next_object;
while (obj) {
ch = mvinch(obj->row, obj->col);
if (((ch < 'A') || (ch > 'Z')) &&
((obj->row != rogue.row) || (obj->col != rogue.col)))
if ((ch != ' ')&&(ch != '.')&&(ch != '#')&&(ch != '+')) {
addch(get_rand_obj_char());
}
obj = obj->next_object;
}
monster = level_monsters.next_monster;
while (monster) {
ch = mvinch(monster->row, monster->col);
if ((ch >= 'A') && (ch <= 'Z')) {
addch(get_rand('A', 'Z'));
}
monster = monster->next_monster;
}
}
unhallucinate()
{
halluc = 0;
relight();
message("everything looks SO boring now", 1);
}
unblind()
{
blind = 0;
message("the veil of darkness lifts", 1);
relight();
if (halluc) {
hallucinate();
}
if (detect_monster) {
show_monsters();
}
}
relight()
{
if (current_room == PASSAGE) {
light_passage(rogue.row, rogue.col);
} else {
light_up_room();
}
mvaddch(rogue.row, rogue.col, rogue.fchar);
}
take_a_nap()
{
short i;
i = get_rand(2, 5);
sleep(1);
while (i--) {
move_monsters();
}
sleep(1);
message(you_can_move_again, 0);
}
go_blind()
{
short i, j;
if (!blind) {
message("a cloak of darkness falls around you", 0);
}
blind += get_rand(500, 800);
if (detect_monster) {
object *monster;
monster = level_monsters.next_monster;
while (monster) {
mvaddch(monster->row, monster->col, monster->trail_char);
monster = monster->next_monster;
}
}
if (current_room >= 0) {
for (i = rooms[current_room].top_row + 1;
i < rooms[current_room].bottom_row; i++) {
for (j = rooms[current_room].left_col + 1;
j < rooms[current_room].right_col; j++) {
mvaddch(i, j, ' ');
}
}
}
mvaddch(rogue.row, rogue.col, rogue.fchar);
}
char *get_ench_color()
{
if (halluc) {
return(id_potions[get_rand(0, POTIONS-1)].title);
}
return("blue ");
}
confuse()
{
confused += get_rand(12, 22);
}
unconfuse()
{
char msg[80];
confused = 0;
sprintf(msg, "you feel less %s now", (halluc ? "trippy" : "confused"));
message(msg, 1);
}
uncurse_all()
{
object *obj;
obj = rogue.pack.next_object;
while (obj) {
obj->is_cursed = 0;
obj = obj->next_object;
}
}
SHAR_EOF