home *** CD-ROM | disk | FTP | other *** search
- Path: uunet!news.tek.com!master!saab!billr
- From: billr@saab.CNA.TEK.COM (Bill Randle)
- Newsgroups: comp.sources.games
- Subject: v16i031: nethack31 - display oriented dungeons & dragons (Ver. 3.1), Part31/108
- Message-ID: <4319@master.CNA.TEK.COM>
- Date: 29 Jan 93 20:46:17 GMT
- Sender: news@master.CNA.TEK.COM
- Lines: 1960
- Approved: billr@saab.CNA.TEK.COM
- Xref: uunet comp.sources.games:1588
-
- Submitted-by: izchak@linc.cis.upenn.edu (Izchak Miller)
- Posting-number: Volume 16, Issue 31
- Archive-name: nethack31/Part31
- Supersedes: nethack3p9: Volume 10, Issue 46-102
- Environment: Amiga, Atari, Mac, MS-DOS, OS2, Unix, VMS, X11
-
-
-
- #! /bin/sh
- # This is a shell archive. Remove anything before this line, then unpack
- # it by saving it into a file and typing "sh file". To overwrite existing
- # files, type "sh file -c". You can also feed this as standard input via
- # unshar, or by typing "sh <file", e.g.. If this archive is complete, you
- # will see the following message at the end:
- # "End of archive 31 (of 108)."
- # Contents: dat/Elf.des src/makemon.c
- # Wrapped by billr@saab on Wed Jan 27 16:08:58 1993
- PATH=/bin:/usr/bin:/usr/ucb ; export PATH
- if test -f 'dat/Elf.des' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'dat/Elf.des'\"
- else
- echo shar: Extracting \"'dat/Elf.des'\" \(12738 characters\)
- sed "s/^X//" >'dat/Elf.des' <<'END_OF_FILE'
- X# SCCS Id: @(#)Elf.des 3.1 91/12/24
- X# Copyright (c) 1989 by Jean-Christophe Collet
- X# Copyright (c) 1991 by M. Stephenson
- X# NetHack may be freely redistributed. See license for details.
- X#
- X# The "start" level for the quest.
- X#
- X# Here you meet your (besieged) class leader, Earendil/Elwing
- X# and receive your quest assignment.
- X#
- XMAZE: "E-start",' '
- XFLAGS: noteleport,hardfloor
- XGEOMETRY:center,center
- XMAP
- X.................................... . .....................................
- X................................... ... ....................................
- X.................................... . .....................................
- X................................... ... ....................................
- X.................................... . .....................................
- X..............................}}}}}}}.}}}}}}}...............................
- X............................}}}|----...----|}}}.............................
- X...........................}}|--...........--|}}............................
- X.................... . . . }|-...............-|} . . . .....................
- X................... . . . .}|.................|}. . . . ....................
- X............................................................................
- X................... . . . .}|.................|}. . . . ....................
- X.................... . . . }|-...............-|} . . . .....................
- X...........................}}|--...........--|}}............................
- X............................}}}|----...----|}}}.............................
- X..............................}}}}}}}.}}}}}}}...............................
- X.................................... . .....................................
- X................................... ... ....................................
- X.................................... . .....................................
- X................................... ... ....................................
- XENDMAP
- X# Random Monsters
- XRANDOM_MONSTERS: 'o', 'O'
- X# Dungeon Description
- XREGION:(00,00,75,19),lit,"ordinary"
- X# Stairs
- XSTAIR:(40,13),down
- X# Portal arrival point
- XBRANCH:(00,14,00,14),(0,0,0,0)
- X# Altar
- XALTAR:(37,10),chaos,altar
- X# Earendil/Elwing
- XMONSTER:'@',"Earendil",(37,10)
- X# The treasure of Earendil/Elwing
- XOBJECT:'(',"chest",(37,10)
- X# elf guards for the audience chamber
- XMONSTER:'@',"High-elf",(38,09)
- XMONSTER:'@',"High-elf",(38,10)
- XMONSTER:'@',"High-elf",(38,11)
- XMONSTER:'@',"High-elf",(36,09)
- XMONSTER:'@',"High-elf",(36,10)
- XMONSTER:'@',"High-elf",(36,11)
- XMONSTER:'@',"High-elf",(37,09)
- XMONSTER:'@',"High-elf",(37,11)
- X# Non diggable walls
- XNON_DIGGABLE:(00,00,75,19)
- X# traps
- X# One pit at each cardinal point.
- XTRAP:"pit",(37,05)
- XTRAP:"pit",(46,10)
- XTRAP:"pit",(37,15)
- XTRAP:"pit",(28,10)
- XTRAP:random,random
- XTRAP:random,random
- X# Monsters on siege duty.
- XMONSTER: 'o',"Uruk-hai",(35,04),hostile
- XMONSTER: 'o',"Uruk-hai",(36,03),hostile
- XMONSTER: 'o',"goblin",(37,03),hostile
- XMONSTER: 'o',"goblin",(38,03),hostile
- XMONSTER: 'o',"goblin",(39,04),hostile
- XMONSTER: 'o',"Uruk-hai",(48,09),hostile
- XMONSTER: 'o',"goblin",(48,10),hostile
- XMONSTER: 'o',"goblin",(48,11),hostile
- XMONSTER: 'o',"Uruk-hai",(35,16),hostile
- XMONSTER: 'o',"Uruk-hai",(36,17),hostile
- XMONSTER: 'o',"goblin",(37,17),hostile
- XMONSTER: 'o',"goblin",(38,17),hostile
- XMONSTER: 'o',"goblin",(39,16),hostile
- XMONSTER: 'o',"Uruk-hai",(26,09),hostile
- XMONSTER: 'o',"goblin",(26,10),hostile
- XMONSTER: 'o',"goblin",(26,11),hostile
- X
- X#
- X# The "locate" level for the quest.
- X#
- X# Here you have to infiltrate the Goblins' Cave to go
- X# further towards your assigned quest.
- X#
- X
- XMAZE: "E-locate",' '
- XFLAGS: hardfloor
- XGEOMETRY:center,center
- XMAP
- X
- X .. .... ...... ... ....... ..
- X .. ......S... .......... ..... ........ ....
- X .. .. ... . ......... .. . ..... ....
- X .. .. . ..... .. . .. .....
- X .... . .. .. S .. ..
- X .... S .. .. .... .. ..
- X ..... ... .. .. ........ .. ..
- X ...... ...... ... .. ............ ... ...
- X .... .. .... .... ........................S....S......
- X .. .. .. ... ........................ ..
- X .. .. .. ........................ ..
- X .... .... .. ........................ ..
- X ...... .. .. ... .................... ..
- X .... .... .. ..... ............ ..
- X .. .. .. .. ... .S ............ .... ...
- X .. .. .............. .... ............ .... .. .....
- X ... .. .. .... ..... .. ....
- X .............. ...... .....
- X
- XENDMAP
- X# Random Monsters
- XRANDOM_MONSTERS: 'o', 'O'
- X# Dungeon Description
- XREGION:(00,00,75,19),unlit,"ordinary"
- X# Doors
- XDOOR:closed,(15,02)
- XDOOR:closed,(18,06)
- XDOOR:closed,(35,15)
- XDOOR:closed,(45,05)
- XDOOR:closed,(59,09)
- XDOOR:closed,(64,09)
- X# Stairs
- XSTAIR:(01,01),up
- XSTAIR:(45,01),down
- X# Non diggable walls
- XNON_DIGGABLE:(00,00,75,19)
- X# Objects
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- X# Random traps
- XTRAP:"pit",(13,10)
- XTRAP:"spiked pit",(45,03)
- XTRAP:"board",(41,16)
- XTRAP:"magic",(60,09)
- XTRAP:random,random
- XTRAP:random,random
- X# Random monsters.
- XMONSTER:'o',"Uruk-hai",(40,10),hostile
- XMONSTER:'o',"Uruk-hai",(41,10),hostile
- XMONSTER:'o',"Uruk-hai",(42,10),hostile
- XMONSTER:'o',"Uruk-hai",(43,10),hostile
- XMONSTER:'o',"goblin",(44,10),hostile
- XMONSTER:'o',"goblin",(45,10),hostile
- XMONSTER:'o',"goblin",(40,11),hostile
- XMONSTER:'o',"goblin",(41,11),hostile
- XMONSTER:'o',"goblin",(42,11),hostile
- XMONSTER:'o',"goblin",(43,11),hostile
- XMONSTER:'o',"goblin",(44,11),hostile
- XMONSTER:'o',"goblin",(45,11),hostile
- XMONSTER:'o',"goblin",(41,12),hostile
- XMONSTER:'o',"goblin",(42,12),hostile
- XMONSTER:'o',"goblin",(43,12),hostile
- XMONSTER:'o',"goblin",(44,12),hostile
- XMONSTER:'o',"goblin",random,hostile
- XMONSTER:'o',random,random,hostile
- XMONSTER:'O',random,random,hostile
- XMONSTER:'O',"ogre",(42,13),hostile
- XMONSTER:'O',"ogre",(43,13),hostile
- XMONSTER:'O',"ogre",(44,13),hostile
- XMONSTER:'O',"ogre",random,hostile
- X
- XWALLIFY
- X
- X#
- X# The "goal" level for the quest.
- X#
- X# Here you meet The Goblin King your nemesis monster. You have to
- X# defeat The Goblin King in combat to gain the artifact you have
- X# been assigned to retrieve.
- X#
- X
- XMAZE: "E-goal", ' '
- XGEOMETRY:center,center
- XMAP
- X
- X ... ...
- X ..........................................................................
- X ... + ...
- X . ............ ....... . ....... .
- X . ............................. . ........ .........S.. .
- X . ............ . ...... . . . ....... .. .
- X . ......... . .... + . ... . .. .
- X . S . ......... .S. .S............... .
- X . ... . ... . ......... . .
- X . ........ .....S.+.......+....\....+........+. .
- X . ... ... S ......... .. ..... .
- X . .. ......... .. ...... .
- X . ....... ... + .... .... .......... .
- X . .............. .. . ...... .. ............. .
- X . ............. . .......... ...... .
- X ... + ...
- X ..........................................................................
- X ... ...
- X
- XENDMAP
- X# Random Monsters
- XRANDOM_MONSTERS: 'o', 'O'
- X# Dungeon Description
- XREGION:(00,00,75,19),lit,"ordinary"
- X# Stairs
- XSTAIR:(19,10),up
- X# Non diggable walls
- XNON_DIGGABLE:(00,00,75,19)
- X# Objects
- XOBJECT:'(',"crystal ball",(37,10),blessed,0,"The Palantir of Westernesse"
- XOBJECT:'(',"chest",(37,10)
- XOBJECT:random,random,(36,09)
- XOBJECT:random,random,(36,10)
- XOBJECT:random,random,(36,11)
- XOBJECT:random,random,(37,09)
- XOBJECT:random,random,(37,11)
- XOBJECT:random,random,(38,09)
- XOBJECT:random,random,(38,10)
- XOBJECT:random,random,(38,11)
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- XOBJECT:random,random,random
- X# Random traps
- XTRAP:random,random
- XTRAP:random,random
- XTRAP:random,random
- XTRAP:random,random
- XTRAP:random,random
- XTRAP:random,random
- X# doors
- XDOOR:locked,(12,08)
- XDOOR:closed,(22,10)
- XDOOR:locked,(24,10)
- XDOOR:closed,(25,11)
- XDOOR:closed,(32,10)
- XDOOR:closed,(37,03)
- XDOOR:closed,(37,07)
- XDOOR:closed,(37,13)
- XDOOR:closed,(37,16)
- XDOOR:closed,(42,10)
- XDOOR:locked,(46,08)
- XDOOR:closed,(51,10)
- XDOOR:locked,(53,08)
- XDOOR:closed,(65,05)
- X# Random monsters.
- XMONSTER:'o',"Goblin King",(37,10),hostile
- XMONSTER:'o',"Uruk-hai",(36,09),hostile
- XMONSTER:'o',"Uruk-hai",(36,10),hostile
- XMONSTER:'o',"Uruk-hai",(36,11),hostile
- XMONSTER:'o',"Uruk-hai",(37,09),hostile
- XMONSTER:'o',"Uruk-hai",(37,11),hostile
- XMONSTER:'o',"Uruk-hai",(38,09),hostile
- XMONSTER:'o',"goblin",(38,10),hostile
- XMONSTER:'o',"goblin",(38,11),hostile
- XMONSTER:'o',"goblin",(02,02),hostile
- XMONSTER:'o',"goblin",(71,02),hostile
- XMONSTER:'o',"goblin",(02,16),hostile
- XMONSTER:'o',"goblin",(71,16),hostile
- XMONSTER:'o',"Uruk-hai",random,hostile
- XMONSTER:'o',"Uruk-hai",random,hostile
- XMONSTER:'o',"goblin",random,hostile
- XMONSTER:'o',"goblin",random,hostile
- XMONSTER:'o',random,random,hostile
- XMONSTER:'o',random,random,hostile
- XMONSTER:'O',"ogre",(03,02),hostile
- XMONSTER:'O',"ogre",(72,02),hostile
- XMONSTER:'O',"ogre",(03,17),hostile
- XMONSTER:'O',"ogre",(72,17),hostile
- XMONSTER:'O',"ogre",(41,10),hostile
- XMONSTER:'O',"ogre",(33,09),hostile
- XMONSTER:'O',"ogre",random,hostile
- XMONSTER:'O',"ogre",random,hostile
- XMONSTER:'O',random,random,hostile
- X
- XWALLIFY
- X
- X#
- X# The "fill" levels for the quest.
- X#
- X# These levels are used to fill out any levels not occupied by specific
- X# levels as defined above. "filla" is the upper filler, between the
- X# start and locate levels, and "fillb" the lower between the locate
- X# and goal levels.
- X#
- X
- XMAZE: "E-filla" , ' '
- XINIT_MAP: '.' , ' ', true, true, random, true
- XNOMAP
- X# Random Monsters
- XRANDOM_MONSTERS: 'o', 'O'
- X#
- XSTAIR: random, up
- XSTAIR: random, down
- X#
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- X#
- XTRAP: random, random
- XTRAP: random, random
- XTRAP: random, random
- XTRAP: random, random
- X#
- XMONSTER: 'o', "goblin", random, hostile
- XMONSTER: 'o', "goblin", random, hostile
- XMONSTER: 'o', "goblin", random, hostile
- XMONSTER: 'o', "goblin", random, hostile
- XMONSTER: 'o', "Uruk-hai", random, hostile
- XMONSTER: 'o', random, random, hostile
- XMONSTER: 'O', "ogre", random, hostile
- X
- XMAZE: "E-fillb" , ' '
- XINIT_MAP: '.' , ' ', true, true, random, true
- XNOMAP
- X# Random Monsters
- XRANDOM_MONSTERS: 'o', 'O'
- X#
- XSTAIR: random, up
- XSTAIR: random, down
- X#
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- XOBJECT: random, random, random
- X#
- XTRAP: random, random
- XTRAP: random, random
- XTRAP: random, random
- XTRAP: random, random
- X#
- XMONSTER: 'o', "goblin", random, hostile
- XMONSTER: 'o', "Uruk-hai", random, hostile
- XMONSTER: 'o', "Uruk-hai", random, hostile
- XMONSTER: 'o', "Uruk-hai", random, hostile
- XMONSTER: 'o', random, random, hostile
- XMONSTER: 'O', "ogre", random, hostile
- XMONSTER: 'O', "ogre", random, hostile
- END_OF_FILE
- if test 12738 -ne `wc -c <'dat/Elf.des'`; then
- echo shar: \"'dat/Elf.des'\" unpacked with wrong size!
- fi
- # end of 'dat/Elf.des'
- fi
- if test -f 'src/makemon.c' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'src/makemon.c'\"
- else
- echo shar: Extracting \"'src/makemon.c'\" \(40817 characters\)
- sed "s/^X//" >'src/makemon.c' <<'END_OF_FILE'
- X/* SCCS Id: @(#)makemon.c 3.1 92/11/01 */
- X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
- X/* NetHack may be freely redistributed. See license for details. */
- X
- X#include "hack.h"
- X#include "epri.h"
- X#include "emin.h"
- X#ifdef REINCARNATION
- X# include <ctype.h>
- X#endif
- X
- XSTATIC_VAR struct monst NEARDATA zeromonst;
- X
- X#define uncommon(ptr) \
- X (((ptr)->geno & (G_GENOD | G_EXTINCT | G_NOGEN | G_UNIQ)) || \
- X (!Inhell ? ((ptr)->geno & G_HELL) : ((ptr)->maligntyp > A_NEUTRAL)))
- X
- X#ifdef OVL0
- Xstatic boolean NDECL(cmavail);
- Xstatic int FDECL(align_shift, (struct permonst *));
- X#endif /* OVL0 */
- XSTATIC_DCL boolean FDECL(is_home_elemental,(struct permonst *));
- XSTATIC_DCL boolean FDECL(wrong_elem_type, (struct permonst *));
- XSTATIC_DCL void FDECL(m_initgrp,(struct monst *,int,int,int));
- XSTATIC_DCL void FDECL(m_initthrow,(struct monst *,int,int));
- XSTATIC_DCL void FDECL(m_initweap,(struct monst *));
- X#ifdef OVL1
- Xstatic void FDECL(m_initinv,(struct monst *));
- X#endif /* OVL1 */
- X
- Xextern int monstr[];
- X
- X#define m_initsgrp(mtmp, x, y) m_initgrp(mtmp, x, y, 3)
- X#define m_initlgrp(mtmp, x, y) m_initgrp(mtmp, x, y, 10)
- X#define toostrong(monindx, lev) (monstr[monindx] > lev)
- X#define tooweak(monindx, lev) (monstr[monindx] < lev)
- X
- X#ifdef OVLB
- XSTATIC_OVL boolean
- Xis_home_elemental(ptr)
- Xregister struct permonst *ptr;
- X{
- X if (ptr->mlet != S_ELEMENTAL) return FALSE;
- X if (!In_endgame(&u.uz)) return FALSE;
- X switch(monsndx(ptr)) {
- X case PM_AIR_ELEMENTAL: return Is_airlevel(&u.uz);
- X case PM_FIRE_ELEMENTAL: return Is_firelevel(&u.uz);
- X case PM_EARTH_ELEMENTAL: return Is_earthlevel(&u.uz);
- X case PM_WATER_ELEMENTAL: return Is_waterlevel(&u.uz);
- X }
- X return FALSE; /* shouldn't be reached */
- X}
- X
- X/*
- X * Return true if the given monster cannot exist on this elemental level.
- X */
- XSTATIC_OVL boolean
- Xwrong_elem_type(ptr)
- X register struct permonst *ptr;
- X{
- X if (Is_earthlevel(&u.uz)) {
- X /* no restrictions? */
- X } else if (Is_waterlevel(&u.uz)) {
- X /* just monsters that can swim */
- X if(!is_swimmer(ptr)) return TRUE;
- X } else if (Is_firelevel(&u.uz)) {
- X if(!resists_fire(ptr)) return TRUE;
- X } else if (Is_airlevel(&u.uz)) {
- X if(!(is_flyer(ptr) && ptr->mlet != S_TRAPPER) && !is_floater(ptr)
- X && !amorphous(ptr) && !noncorporeal(ptr) && !is_whirly(ptr))
- X return TRUE;
- X }
- X return FALSE;
- X}
- X
- XSTATIC_OVL void
- Xm_initgrp(mtmp, x, y, n) /* make a group just like mtmp */
- Xregister struct monst *mtmp;
- Xregister int x, y, n;
- X{
- X coord mm;
- X register int cnt = rnd(n);
- X struct monst *mon;
- X
- X/*
- X * Temporary kludge to cut down on swarming at lower character levels
- X * till we can get this game a little more balanced. [mrs]
- X */
- X cnt /= (u.ulevel < 3) ? 4 : (u.ulevel < 5) ? 2 : 1;
- X if(!cnt) cnt++;
- X
- X mm.x = x;
- X mm.y = y;
- X while(cnt--) {
- X if (peace_minded(mtmp->data)) continue;
- X /* Don't create groups of peaceful monsters since they'll get
- X * in our way. If the monster has a percentage chance so some
- X * are peaceful and some are not, the result will just be a
- X * smaller group.
- X */
- X if (enexto(&mm, mm.x, mm.y, mtmp->data)) {
- X mon = makemon(mtmp->data, mm.x, mm.y);
- X mon->mpeaceful = FALSE;
- X set_malign(mon);
- X /* Undo the second peace_minded() check in makemon(); if the
- X * monster turned out to be peaceful the first time we
- X * didn't create it at all; we don't want a second check.
- X */
- X }
- X }
- X}
- X
- XSTATIC_OVL
- Xvoid
- Xm_initthrow(mtmp,otyp,oquan)
- Xstruct monst *mtmp;
- Xint otyp,oquan;
- X{
- X register struct obj *otmp;
- X
- X otmp = mksobj(otyp, TRUE, FALSE);
- X otmp->quan = (long) rn1(oquan, 3);
- X otmp->owt = weight(otmp);
- X if (otyp == ORCISH_ARROW) otmp->opoisoned = TRUE;
- X mpickobj(mtmp, otmp);
- X}
- X
- X#endif /* OVLB */
- X#ifdef OVL2
- X
- XSTATIC_OVL void
- Xm_initweap(mtmp)
- Xregister struct monst *mtmp;
- X{
- X register struct permonst *ptr = mtmp->data;
- X register int mm = monsndx(ptr);
- X#ifdef REINCARNATION
- X if (Is_rogue_level(&u.uz)) return;
- X#endif
- X/*
- X * first a few special cases:
- X *
- X * giants get a boulder to throw sometimes.
- X * ettins get clubs
- X * kobolds get darts to throw
- X * centaurs get some sort of bow & arrows or bolts
- X * soldiers get all sorts of things.
- X * kops get clubs & cream pies.
- X */
- X switch (mtmp->data->mlet) {
- X case S_GIANT:
- X if (rn2(2)) (void)mongets(mtmp, (ptr != &mons[PM_ETTIN]) ?
- X BOULDER : CLUB);
- X break;
- X case S_HUMAN:
- X if(is_mercenary(ptr)) {
- X int w1 = 0, w2 = 0;
- X switch (mm) {
- X
- X case PM_WATCHMAN:
- X#ifdef ARMY
- X case PM_SOLDIER:
- X#endif
- X if (!rn2(3)) {
- X w1 = rn1(BEC_DE_CORBIN - PARTISAN + 1, PARTISAN);
- X w2 = rn2(2) ? DAGGER : KNIFE;
- X } else w1 = rn2(2) ? SPEAR : SHORT_SWORD;
- X break;
- X#ifdef ARMY
- X case PM_SERGEANT:
- X w1 = rn2(2) ? FLAIL : MACE;
- X break;
- X case PM_LIEUTENANT:
- X w1 = rn2(2) ? BROADSWORD : LONG_SWORD;
- X break;
- X case PM_CAPTAIN:
- X#endif
- X case PM_WATCH_CAPTAIN:
- X w1 = rn2(2) ? LONG_SWORD : SILVER_SABER;
- X break;
- X default:
- X if (!rn2(4)) w1 = DAGGER;
- X if (!rn2(7)) w2 = SPEAR;
- X break;
- X }
- X if (w1) (void)mongets(mtmp, w1);
- X if (!w2 && w1 != DAGGER && !rn2(4)) w2 = KNIFE;
- X if (w2) (void)mongets(mtmp, w2);
- X } else if (is_elf(ptr)) {
- X if (rn2(2))
- X (void) mongets(mtmp,
- X rn2(2) ? ELVEN_MITHRIL_COAT : ELVEN_CLOAK);
- X if (rn2(2)) (void)mongets(mtmp, ELVEN_LEATHER_HELM);
- X else if (!rn2(4)) (void)mongets(mtmp, ELVEN_BOOTS);
- X if (rn2(2)) (void)mongets(mtmp, ELVEN_DAGGER);
- X switch (rn2(3)) {
- X case 0:
- X if (!rn2(4)) (void)mongets(mtmp, ELVEN_SHIELD);
- X if (rn2(3)) (void)mongets(mtmp, ELVEN_SHORT_SWORD);
- X (void)mongets(mtmp, ELVEN_BOW);
- X m_initthrow(mtmp, ELVEN_ARROW, 12);
- X break;
- X case 1:
- X (void)mongets(mtmp, ELVEN_BROADSWORD);
- X if (rn2(2)) (void)mongets(mtmp, ELVEN_SHIELD);
- X break;
- X case 2:
- X if (rn2(2)) {
- X (void)mongets(mtmp, ELVEN_SPEAR);
- X (void)mongets(mtmp, ELVEN_SHIELD);
- X }
- X break;
- X }
- X if(mtmp->data == &mons[PM_ELVENKING])
- X (void)mongets(mtmp, PICK_AXE);
- X }
- X break;
- X
- X case S_ANGEL:
- X {
- X int spe2;
- X /* create minion stuff; can't use mongets */
- X struct obj *otmp = mksobj(LONG_SWORD, FALSE, FALSE);
- X
- X /* maybe make it special */
- X if(!rn2(20) || is_lord(mtmp->data))
- X otmp = oname(otmp, artiname(
- X rn2(2) ? ART_DEMONBANE : ART_SUNSWORD), 0);
- X bless(otmp);
- X otmp->oerodeproof = TRUE;
- X spe2 = rn2(4);
- X otmp->spe = max(otmp->spe, spe2);
- X mpickobj(mtmp, otmp);
- X
- X otmp = mksobj(!rn2(4) || is_lord(mtmp->data) ?
- X SHIELD_OF_REFLECTION : LARGE_SHIELD,
- X FALSE, FALSE);
- X otmp->cursed = FALSE;
- X otmp->oerodeproof = TRUE;
- X otmp->spe = 0;
- X mpickobj(mtmp, otmp);
- X }
- X break;
- X
- X case S_HUMANOID:
- X if (mm == PM_HOBBIT) {
- X switch (rn2(3)) {
- X case 0:
- X (void)mongets(mtmp, DAGGER);
- X break;
- X case 1:
- X (void)mongets(mtmp, ELVEN_DAGGER);
- X break;
- X case 2:
- X (void)mongets(mtmp, SLING);
- X break;
- X }
- X if (!rn2(10)) (void)mongets(mtmp, ELVEN_MITHRIL_COAT);
- X if (!rn2(10)) (void)mongets(mtmp, DWARVISH_CLOAK);
- X } else if (is_dwarf(ptr)) {
- X if (rn2(7)) (void)mongets(mtmp, DWARVISH_CLOAK);
- X if (rn2(7)) (void)mongets(mtmp, IRON_SHOES);
- X if (!rn2(4)) {
- X (void)mongets(mtmp, DWARVISH_SHORT_SWORD);
- X /* note: you can't use a mattock with a shield */
- X if (rn2(2)) (void)mongets(mtmp, DWARVISH_MATTOCK);
- X else {
- X (void)mongets(mtmp, AXE);
- X (void)mongets(mtmp, DWARVISH_ROUNDSHIELD);
- X }
- X (void)mongets(mtmp, DWARVISH_IRON_HELM);
- X if (!rn2(3))
- X (void)mongets(mtmp, DWARVISH_MITHRIL_COAT);
- X } else {
- X (void)mongets(mtmp, !rn2(3) ? PICK_AXE : DAGGER);
- X }
- X }
- X break;
- X# ifdef KOPS
- X case S_KOP: /* create Keystone Kops with cream pies to
- X * throw. As suggested by KAA. [MRS]
- X */
- X if (!rn2(4)) m_initthrow(mtmp, CREAM_PIE, 2);
- X if (!rn2(3)) (void)mongets(mtmp,(rn2(2)) ? CLUB : RUBBER_HOSE);
- X break;
- X# endif
- X case S_ORC:
- X if(rn2(2)) (void)mongets(mtmp, ORCISH_HELM);
- X switch (mm != PM_ORC_CAPTAIN ? mm :
- X rn2(2) ? PM_MORDOR_ORC : PM_URUK_HAI) {
- X case PM_MORDOR_ORC:
- X if(!rn2(3)) (void)mongets(mtmp, SCIMITAR);
- X if(!rn2(3)) (void)mongets(mtmp, ORCISH_SHIELD);
- X if(!rn2(3)) (void)mongets(mtmp, KNIFE);
- X if(!rn2(3)) (void)mongets(mtmp, ORCISH_CHAIN_MAIL);
- X break;
- X case PM_URUK_HAI:
- X if(!rn2(3)) (void)mongets(mtmp, ORCISH_CLOAK);
- X if(!rn2(3)) (void)mongets(mtmp, ORCISH_SHORT_SWORD);
- X if(!rn2(3)) (void)mongets(mtmp, IRON_SHOES);
- X if(!rn2(3)) {
- X (void)mongets(mtmp, ORCISH_BOW);
- X m_initthrow(mtmp, ORCISH_ARROW, 12);
- X }
- X if(!rn2(3)) (void)mongets(mtmp, URUK_HAI_SHIELD);
- X break;
- X default:
- X if (mm != PM_ORC_SHAMAN && rn2(2))
- X (void)mongets(mtmp, (mm == PM_GOBLIN || rn2(2) == 0)
- X ? ORCISH_DAGGER : SCIMITAR);
- X }
- X break;
- X case S_OGRE:
- X if (!rn2(mm == PM_OGRE_KING ? 3 : mm == PM_OGRE_LORD ? 6 : 12))
- X (void) mongets(mtmp, BATTLE_AXE);
- X break;
- X case S_KOBOLD:
- X if (!rn2(4)) m_initthrow(mtmp, DART, 12);
- X break;
- X
- X case S_CENTAUR:
- X if (rn2(2)) {
- X if(ptr == &mons[PM_FOREST_CENTAUR]) {
- X (void)mongets(mtmp, BOW);
- X m_initthrow(mtmp, ARROW, 12);
- X } else {
- X (void)mongets(mtmp, CROSSBOW);
- X m_initthrow(mtmp, CROSSBOW_BOLT, 12);
- X }
- X }
- X break;
- X case S_WRAITH:
- X (void)mongets(mtmp, KNIFE);
- X (void)mongets(mtmp, LONG_SWORD);
- X break;
- X case S_DEMON:
- X switch (mm) {
- X case PM_BALROG:
- X (void)mongets(mtmp, BULLWHIP);
- X (void)mongets(mtmp, BROADSWORD);
- X break;
- X case PM_ORCUS:
- X (void)mongets(mtmp, WAN_DEATH); /* the Wand of Orcus */
- X break;
- X case PM_HORNED_DEVIL:
- X (void)mongets(mtmp, rn2(4) ? TRIDENT : BULLWHIP);
- X break;
- X case PM_ICE_DEVIL:
- X if (!rn2(4)) (void)mongets(mtmp, SPEAR);
- X break;
- X case PM_ASMODEUS:
- X (void)mongets(mtmp, WAN_COLD);
- X break;
- X case PM_DISPATER:
- X (void)mongets(mtmp, WAN_STRIKING);
- X break;
- X case PM_YEENOGHU:
- X (void)mongets(mtmp, FLAIL);
- X break;
- X }
- X /* prevent djinnis and mail daemons from leaving objects when
- X * they vanish
- X */
- X if (!is_demon(ptr)) break;
- X /* fall thru */
- X/*
- X * Now the general case, ~40% chance of getting some type
- X * of weapon. TODO: Add more weapons types (use bigmonst());
- X */
- X default:
- X switch(rnd(12)) {
- X case 1:
- X m_initthrow(mtmp, DART, 12);
- X break;
- X case 2:
- X (void) mongets(mtmp, CROSSBOW);
- X m_initthrow(mtmp, CROSSBOW_BOLT, 12);
- X break;
- X case 3:
- X (void) mongets(mtmp, BOW);
- X m_initthrow(mtmp, ARROW, 12);
- X break;
- X case 4:
- X m_initthrow(mtmp, DAGGER, 3);
- X break;
- X case 5:
- X (void) mongets(mtmp, AKLYS);
- X break;
- X default:
- X break;
- X }
- X break;
- X }
- X#ifdef MUSE
- X if ((int) mtmp->m_lev > rn2(70))
- X (void) mongets(mtmp, rnd_offensive_item(mtmp));
- X#endif
- X}
- X
- X#endif /* OVL2 */
- X#ifdef OVL1
- X
- Xstatic void
- Xm_initinv(mtmp)
- Xregister struct monst *mtmp;
- X{
- X register int cnt;
- X register struct obj *otmp;
- X register struct permonst *ptr = mtmp->data;
- X#ifdef REINCARNATION
- X if (Is_rogue_level(&u.uz)) return;
- X#endif
- X/*
- X * Soldiers get armour & rations - armour approximates their ac.
- X * Nymphs may get mirror or potion of object detection.
- X */
- X switch(ptr->mlet) {
- X
- X case S_HUMAN:
- X if(is_mercenary(ptr)) {
- X register int mac;
- X#ifdef MUSE
- X switch(monsndx(ptr)) {
- X case PM_GUARD: mac = -1; break;
- X# ifdef ARMY
- X case PM_SOLDIER: mac = 3; break;
- X case PM_SERGEANT: mac = 0; break;
- X case PM_LIEUTENANT: mac = -2; break;
- X case PM_CAPTAIN: mac = -3; break;
- X# endif
- X case PM_WATCHMAN: mac = 3; break;
- X case PM_WATCH_CAPTAIN: mac = -2; break;
- X default: impossible("odd mercenary %d?", monsndx(ptr));
- X mac = 0;
- X break;
- X }
- X#else
- X mac = ptr->ac;
- X#endif
- X
- X if (mac < -1 && rn2(5))
- X mac += 7 + mongets(mtmp, (rn2(5)) ?
- X PLATE_MAIL : CRYSTAL_PLATE_MAIL);
- X else if (mac < 3 && rn2(5))
- X mac += 6 + mongets(mtmp, (rn2(3)) ?
- X SPLINT_MAIL : BANDED_MAIL);
- X else if (rn2(5))
- X mac += 3 + mongets(mtmp, (rn2(3)) ?
- X RING_MAIL : STUDDED_LEATHER_ARMOR);
- X else
- X mac += 2 + mongets(mtmp, LEATHER_ARMOR);
- X
- X if (mac < 10 && rn2(3))
- X mac += 1 + mongets(mtmp, HELMET);
- X else if (mac < 10 && rn2(2))
- X mac += 1 + mongets(mtmp, DENTED_POT);
- X if (mac < 10 && rn2(3))
- X mac += 1 + mongets(mtmp, SMALL_SHIELD);
- X else if (mac < 10 && rn2(2))
- X mac += 2 + mongets(mtmp, LARGE_SHIELD);
- X if (mac < 10 && rn2(3))
- X mac += 1 + mongets(mtmp, LOW_BOOTS);
- X else if (mac < 10 && rn2(2))
- X mac += 2 + mongets(mtmp, HIGH_BOOTS);
- X if (mac < 10 && rn2(3))
- X mac += 1 + mongets(mtmp, LEATHER_GLOVES);
- X else if (mac < 10 && rn2(2))
- X mac += 1 + mongets(mtmp, ELVEN_CLOAK);
- X
- X#ifndef MUSE
- X if (mac != 10 && rn2(5)) { /* make up the difference */
- X otmp = mksobj(RIN_PROTECTION, FALSE, FALSE);
- X otmp->spe = (10 - mac + rn2(3) - rn2(3));
- X if(otmp->spe < 0) curse(otmp);
- X mpickobj(mtmp, otmp);
- X }
- X#endif
- X#ifdef ARMY
- X if(ptr != &mons[PM_GUARD] &&
- X ptr != &mons[PM_WATCHMAN] &&
- X ptr != &mons[PM_WATCH_CAPTAIN]) {
- X if (!rn2(3)) (void) mongets(mtmp, K_RATION);
- X if (!rn2(2)) (void) mongets(mtmp, C_RATION);
- X# ifdef MUSE
- X if (ptr != &mons[PM_SOLDIER] && !rn2(3))
- X (void) mongets(mtmp, BUGLE);
- X# endif
- X } else
- X#endif
- X if (ptr == &mons[PM_WATCHMAN] && rn2(3))
- X (void) mongets(mtmp, TIN_WHISTLE);
- X } else if (ptr == &mons[PM_SHOPKEEPER]) {
- X (void) mongets(mtmp,SKELETON_KEY);
- X }
- X break;
- X
- X case S_NYMPH:
- X if(!rn2(2)) (void) mongets(mtmp, MIRROR);
- X if(!rn2(2)) (void) mongets(mtmp, POT_OBJECT_DETECTION);
- X break;
- X
- X case S_GIANT:
- X if (ptr == &mons[PM_MINOTAUR])
- X (void) mongets(mtmp, WAN_DIGGING);
- X else if (is_giant(ptr)) {
- X for(cnt = rn2((int)(mtmp->m_lev / 2)); cnt; cnt--) {
- X otmp = mksobj(rnd_class(DILITHIUM_CRYSTAL,LUCKSTONE-1),FALSE,FALSE);
- X otmp->quan = (long) rn1(2, 3);
- X otmp->owt = weight(otmp);
- X mpickobj(mtmp, otmp);
- X }
- X }
- X break;
- X case S_WRAITH:
- X if (ptr == &mons[PM_NAZGUL]) {
- X otmp = mksobj(RIN_INVISIBILITY, FALSE, FALSE);
- X curse(otmp);
- X mpickobj(mtmp, otmp);
- X }
- X break;
- X case S_QUANTMECH:
- X if (!rn2(20)) {
- X struct obj *cat;
- X
- X otmp = mksobj(LARGE_BOX, FALSE, FALSE);
- X /* actually, whether this is a corpse or a live cat shouldn't
- X really be decided until the box is opened... */
- X cat = mksobj(CORPSE, FALSE, FALSE);
- X cat->corpsenm = PM_HOUSECAT;
- X cat->owt = weight(cat);
- X cat = oname(cat, "Schroedinger's Cat", FALSE);
- X cat->nobj = otmp->cobj;
- X otmp->cobj = cat;
- X otmp->owt = weight(otmp);
- X mpickobj(mtmp, otmp);
- X }
- X break;
- X case S_LEPRECHAUN:
- X mtmp->mgold = (long) d(level_difficulty(), 30);
- X break;
- X default:
- X break;
- X }
- X
- X#ifdef ARMY /* ordinary soldiers rarely have access to magic (or gold :-) */
- X if (ptr == &mons[PM_SOLDIER] && rn2(13)) return;
- X#endif
- X#ifdef MUSE
- X if ((int) mtmp->m_lev > rn2(30))
- X (void) mongets(mtmp, rnd_defensive_item(mtmp));
- X if ((int) mtmp->m_lev > rn2(100))
- X (void) mongets(mtmp, rnd_misc_item(mtmp));
- X#endif
- X if (likes_gold(ptr) && !mtmp->mgold && !rn2(5))
- X mtmp->mgold =
- X (long) d(level_difficulty(), mtmp->minvent ? 5 : 10);
- X}
- X
- X/*
- X * called with [x,y] = coordinates;
- X * [0,0] means anyplace
- X * [u.ux,u.uy] means: near player (if !in_mklev)
- X *
- X * In case we make a monster group, only return the one at [x,y].
- X */
- Xstruct monst *
- Xmakemon(ptr, x, y)
- Xregister struct permonst *ptr;
- Xregister int x, y;
- X{
- X register struct monst *mtmp;
- X register int ct;
- X boolean anything = (!ptr);
- X boolean byyou = (x == u.ux && y == u.uy);
- X
- X /* if caller wants random location, do it here */
- X if(x == 0 && y == 0) {
- X int tryct = 0; /* careful with bigrooms */
- X do {
- X x = rn1(COLNO-3,2);
- X y = rn2(ROWNO);
- X } while(!goodpos(x, y, (struct monst *)0, ptr) ||
- X (!in_mklev && tryct++ < 50 && cansee(x, y)));
- X } else if (byyou && !in_mklev) {
- X coord bypos;
- X
- X if(enexto(&bypos, u.ux, u.uy, ptr)) {
- X x = bypos.x;
- X y = bypos.y;
- X } else
- X return((struct monst *)0);
- X }
- X
- X /* if a monster already exists at the position, return */
- X if(MON_AT(x, y))
- X return((struct monst *) 0);
- X
- X if(ptr){
- X /* if you are to make a specific monster and it has
- X already been genocided, return */
- X if(ptr->geno & G_GENOD) return((struct monst *) 0);
- X } else {
- X /* make a random (common) monster that can survive here.
- X * (the special levels ask for random monsters at specific
- X * positions, causing mass drowning on the medusa level,
- X * for instance.)
- X */
- X int tryct = 0; /* maybe there are no good choices */
- X do {
- X if(!(ptr = rndmonst())) {
- X#ifdef DEBUG
- X pline("Warning: no monster.");
- X#endif
- X return((struct monst *) 0); /* no more monsters! */
- X }
- X } while(!goodpos(x, y, (struct monst *)0, ptr) && tryct++ < 50);
- X }
- X /* if it's unique, don't ever make it again */
- X if (ptr->geno & G_UNIQ) ptr->geno |= G_EXTINCT;
- X
- X mtmp = newmonst(ptr->pxlth);
- X *mtmp = zeromonst; /* clear all entries in structure */
- X for(ct = 0; ct < ptr->pxlth; ct++)
- X ((char *) &(mtmp->mextra[0]))[ct] = 0;
- X mtmp->nmon = fmon;
- X fmon = mtmp;
- X mtmp->m_id = flags.ident++;
- X mtmp->data = ptr;
- X mtmp->mxlth = ptr->pxlth;
- X
- X mtmp->m_lev = adj_lev(ptr);
- X if (is_golem(ptr))
- X mtmp->mhpmax = mtmp->mhp = golemhp(monsndx(ptr));
- X else if (is_rider(ptr)) {
- X /* We want low HP, but a high mlevel so they can attack well */
- X mtmp->mhpmax = mtmp->mhp = d(10,8);
- X } else if(ptr->mlevel > 49) {
- X /* "special" fixed hp monster
- X * the hit points are encoded in the mlevel in a somewhat strange
- X * way to fit in the 50..127 positive range of a signed character
- X * above the 1..49 that indicate "normal" monster levels */
- X mtmp->mhpmax = mtmp->mhp = 2*(ptr->mlevel - 6);
- X mtmp->m_lev = mtmp->mhp / 4; /* approximation */
- X } else if((ptr->mlet == S_DRAGON) && (ptr >= &mons[PM_GRAY_DRAGON]))
- X mtmp->mhpmax = mtmp->mhp = mtmp->m_lev*8;
- X else if(!mtmp->m_lev) mtmp->mhpmax = mtmp->mhp = rnd(4);
- X else if(is_home_elemental(ptr))
- X mtmp->mhpmax = mtmp->mhp = 3 * d((int)mtmp->m_lev, 8);
- X else mtmp->mhpmax = mtmp->mhp = d((int)mtmp->m_lev, 8);
- X
- X if (is_female(ptr)) mtmp->female = TRUE;
- X else if (is_male(ptr)) mtmp->female = FALSE;
- X else mtmp->female = rn2(2); /* ignored for neuters */
- X
- X place_monster(mtmp, x, y);
- X mtmp->mcansee = mtmp->mcanmove = TRUE;
- X mtmp->mpeaceful = peace_minded(ptr);
- X
- X switch(ptr->mlet) {
- X case S_MIMIC:
- X set_mimic_sym(mtmp);
- X break;
- X case S_SPIDER:
- X case S_SNAKE:
- X if(in_mklev)
- X if(x && y)
- X (void) mkobj_at(0, x, y, TRUE);
- X if(hides_under(ptr) && OBJ_AT(x, y))
- X mtmp->mundetected = TRUE;
- X break;
- X case S_STALKER:
- X case S_EEL:
- X mtmp->minvis = TRUE;
- X break;
- X case S_LEPRECHAUN:
- X mtmp->msleep = TRUE;
- X break;
- X case S_JABBERWOCK:
- X case S_NYMPH:
- X if(rn2(5) && !u.uhave.amulet) mtmp->msleep = TRUE;
- X break;
- X case S_ORC:
- X if(pl_character[0] == 'E') mtmp->mpeaceful = FALSE;
- X break;
- X case S_UNICORN:
- X if (sgn(u.ualign.type) == sgn(ptr->maligntyp))
- X mtmp->mpeaceful = TRUE;
- X break;
- X }
- X if (ptr == &mons[PM_CHAMELEON]) {
- X /* If you're protected with a ring, don't create
- X * any shape-changing chameleons -dgk
- X */
- X if (Protection_from_shape_changers)
- X mtmp->cham = FALSE;
- X else {
- X mtmp->cham = TRUE;
- X (void) newcham(mtmp, rndmonst());
- X }
- X } else if (ptr == &mons[PM_WIZARD_OF_YENDOR]) {
- X mtmp->iswiz = TRUE;
- X flags.no_of_wizards++;
- X } else if (ptr == &mons[PM_VLAD_THE_IMPALER])
- X (void) mongets(mtmp, CANDELABRUM_OF_INVOCATION);
- X#ifdef MULDGN
- X else if (ptr->msound == MS_NEMESIS)
- X (void) mongets(mtmp, BELL_OF_OPENING);
- X#else
- X else if (ptr == &mons[PM_MEDUSA])
- X (void) mongets(mtmp, BELL_OF_OPENING);
- X#endif
- X
- X if(in_mklev) {
- X if(((is_ndemon(ptr)) ||
- X (ptr == &mons[PM_WUMPUS]) ||
- X (ptr == &mons[PM_LONG_WORM]) ||
- X (ptr == &mons[PM_GIANT_EEL])) && !u.uhave.amulet && rn2(5))
- X mtmp->msleep = TRUE;
- X } else {
- X if(byyou) {
- X newsym(mtmp->mx,mtmp->my);
- X set_apparxy(mtmp);
- X }
- X }
- X if(is_dprince(ptr)) {
- X mtmp->mpeaceful = mtmp->minvis = TRUE;
- X if (uwep && uwep->oartifact == ART_EXCALIBUR)
- X mtmp->mpeaceful = mtmp->mtame = FALSE;
- X }
- X if ( (ptr == &mons[PM_LONG_WORM]) && (mtmp->wormno = get_wormno()) ) {
- X /* we can now create worms with tails - 11/91 */
- X initworm(mtmp, rn2(5));
- X if (count_wsegs(mtmp)) place_worm_tail_randomly(mtmp, x, y);
- X }
- X set_malign(mtmp); /* having finished peaceful changes */
- X if(anything) {
- X if((ptr->geno & G_SGROUP) && rn2(2))
- X m_initsgrp(mtmp, mtmp->mx, mtmp->my);
- X else if(ptr->geno & G_LGROUP) {
- X if(rn2(3)) m_initlgrp(mtmp, mtmp->mx, mtmp->my);
- X else m_initsgrp(mtmp, mtmp->mx, mtmp->my);
- X }
- X }
- X
- X if(is_armed(ptr))
- X m_initweap(mtmp); /* equip with weapons / armor */
- X m_initinv(mtmp); /* add on a few special items incl. more armor */
- X#ifdef MUSE
- X m_dowear(mtmp, TRUE);
- X#endif
- X
- X if (!in_mklev)
- X newsym(mtmp->mx,mtmp->my); /* make sure the mon shows up */
- X
- X return(mtmp);
- X}
- X
- Xboolean
- Xenexto(cc, xx, yy, mdat)
- Xcoord *cc;
- Xregister xchar xx, yy;
- Xstruct permonst *mdat;
- X{
- X register xchar x,y;
- X coord foo[15], *tfoo;
- X int range, i;
- X int xmin, xmax, ymin, ymax;
- X
- X tfoo = foo;
- X range = 1;
- X do { /* full kludge action. */
- X xmin = max(1, xx-range);
- X xmax = min(COLNO-1, xx+range);
- X ymin = max(0, yy-range);
- X ymax = min(ROWNO-1, yy+range);
- X
- X for(x = xmin; x <= xmax; x++)
- X if(goodpos(x, ymin, (struct monst *)0, mdat)) {
- X tfoo->x = x;
- X#ifdef MAC_MPW32
- X ( tfoo ) -> y = ymin ;
- X tfoo ++ ;
- X#else
- X (tfoo++)->y = ymin;
- X#endif
- X if(tfoo == &foo[15]) goto foofull;
- X }
- X for(x = xmin; x <= xmax; x++)
- X if(goodpos(x, ymax, (struct monst *)0, mdat)) {
- X tfoo->x = x;
- X#ifdef MAC_MPW32
- X ( tfoo ) -> y = ymax ;
- X tfoo ++ ;
- X#else
- X (tfoo++)->y = ymax;
- X#endif
- X if(tfoo == &foo[15]) goto foofull;
- X }
- X for(y = ymin+1; y < ymax; y++)
- X if(goodpos(xmin, y, (struct monst *)0, mdat)) {
- X tfoo->x = xmin;
- X#ifdef MAC_MPW32
- X ( tfoo ) -> y = y ;
- X tfoo ++ ;
- X#else
- X (tfoo++)->y = y;
- X#endif
- X if(tfoo == &foo[15]) goto foofull;
- X }
- X for(y = ymin+1; y < ymax; y++)
- X if(goodpos(xmax, y, (struct monst *)0, mdat)) {
- X tfoo->x = xmax;
- X#ifdef MAC_MPW32
- X ( tfoo ) -> y = y ;
- X tfoo ++ ;
- X#else
- X (tfoo++)->y = y;
- X#endif
- X if(tfoo == &foo[15]) goto foofull;
- X }
- X range++;
- X if(range > ROWNO && range > COLNO) return FALSE;
- X } while(tfoo == foo);
- Xfoofull:
- X i = rn2((int)(tfoo - foo));
- X cc->x = foo[i].x;
- X cc->y = foo[i].y;
- X return TRUE;
- X}
- X
- Xint
- Xgoodpos(x, y, mtmp, mdat)
- Xint x,y;
- Xstruct monst *mtmp; /* existing monster being moved, if any */
- Xstruct permonst *mdat;
- X{
- X struct monst *mtmp2;
- X
- X if (x < 1 || x > COLNO-2 || y < 1 || y > ROWNO-2 || MON_AT(x, y))
- X return 0;
- X
- X /* in many cases, we're trying to create a new monster, which
- X * can't go on top of the player or any existing monster.
- X * however, occasionally we are relocating engravings or objects,
- X * which could be colocated and thus get restricted a bit too much.
- X * oh well.
- X */
- X if (x == u.ux && y == u.uy) return 0;
- X if ((mtmp2 = m_at(x, y)) && mtmp != mtmp2) return 0;
- X
- X if (mdat) {
- X if (IS_POOL(levl[x][y].typ))
- X if (mdat == &playermon &&
- X (HLevitation || Wwalking || Magical_breathing))
- X return 1;
- X else return (is_flyer(mdat) || is_swimmer(mdat));
- X if (levl[x][y].typ == LAVAPOOL)
- X if (mdat == &playermon && (HLevitation))
- X return 1;
- X else return
- X (is_flyer(mdat) || (mdat == &mons[PM_FIRE_ELEMENTAL]));
- X if (passes_walls(mdat)) return 1;
- X }
- X if (!ACCESSIBLE(levl[x][y].typ)) return 0;
- X if (closed_door(x, y) && (!mdat || !amorphous(mdat)))
- X return 0;
- X if (sobj_at(BOULDER, x, y) && (!mdat || !throws_rocks(mdat)))
- X return 0;
- X return 1;
- X}
- X
- X#endif /* OVL1 */
- X#ifdef OVLB
- X
- X/*
- X * rloc_to()
- X *
- X * Pulls a monster from its current position and places a monster at
- X * a new x and y. If oldx is 0, then the monster was not in the levels.monsters
- X * array. However, if oldx is 0, oldy may still have a value because mtmp is a
- X * migrating_mon. Worm tails are always placed randomly around the head of
- X * the worm.
- X */
- X
- Xvoid
- Xrloc_to(mtmp, x, y)
- X struct monst *mtmp;
- X register int x, y;
- X{
- X register int oldx = mtmp->mx, oldy = mtmp->my;
- X
- X if(x == mtmp->mx && y == mtmp->my) /* that was easy */
- X return;
- X
- X if (oldx) { /* "pick up" monster */
- X if(mtmp->wormno)
- X remove_worm(mtmp);
- X else {
- X remove_monster(oldx, oldy);
- X newsym(oldx, oldy); /* update old location */
- X }
- X }
- X
- X place_monster(mtmp, x, y); /* put monster down */
- X
- X if(mtmp->wormno) /* now put down tail */
- X place_worm_tail_randomly(mtmp, x, y);
- X
- X if(u.ustuck == mtmp){
- X if(u.uswallow) {
- X u.ux = x;
- X u.uy = y;
- X docrt();
- X } else u.ustuck = 0;
- X }
- X
- X newsym(x, y); /* update new location */
- X set_apparxy(mtmp); /* orient monster */
- X}
- X
- X#endif /* OVLB */
- X#ifdef OVL2
- X
- Xvoid
- Xrloc(mtmp)
- X struct monst *mtmp;
- X{
- X register int x = xupstair, y = yupstair, trycount;
- X
- X /* if the wiz teleports away to heal, try the up staircase,
- X to block the player's escaping before he's healed */
- X if (!mtmp->iswiz || !goodpos(x, y, mtmp, mtmp->data)) {
- X trycount = 0;
- X do {
- X x = rn1(COLNO-3,2);
- X y = rn2(ROWNO);
- X } while(!goodpos(x,y,mtmp,mtmp->data) && ++trycount < 1000);
- X /* last ditch attempt to find a good place */
- X if (trycount >= 1000) {
- X for (x = 2; x < COLNO - 1; x++)
- X for (y = 0; y < ROWNO; y++)
- X if (goodpos(x,y,mtmp,mtmp->data))
- X goto found_atlast;
- X /* level either full of monsters or somehow faulty */
- X impossible("rloc(): couldn't relocate monster");
- X return;
- X }
- X }
- Xfound_atlast:;
- X rloc_to(mtmp, x, y);
- X}
- X
- Xvoid
- Xrloc_shk(mtmp) /* to be used when teleporting a shopkeeper */
- Xstruct monst *mtmp;
- X{
- X register int x, y, ox, oy, trycount;
- X
- X if(!mtmp->isshk) return;
- X trycount = 0;
- X do {
- X x = rn1(COLNO-3,2);
- X y = rn2(ROWNO);
- X } while(!goodpos(x,y,mtmp,mtmp->data) && ++trycount < 1000);
- X /* last ditch attempt to find a good place */
- X if (trycount >= 1000) {
- X for (x = 2; x < COLNO - 1; x++)
- X for (y = 0; y < ROWNO; y++)
- X if (goodpos(x,y,mtmp,mtmp->data))
- X goto found_ok;
- X /* this really shouldn't happen - after all, shopkeeper's
- X original position should always be available */
- X impossible("rloc_shk(): couldn't relocate shopkeeper");
- X return;
- X }
- Xfound_ok:;
- X ox = mtmp->mx;
- X oy = mtmp->my;
- X rloc_to(mtmp, x, y);
- X make_angry_shk(mtmp, ox, oy);
- X}
- X
- X#endif /* OVL2 */
- X#ifdef OVLB
- X
- Xvoid
- Xvloc(mtmp)
- Xstruct monst *mtmp;
- X{
- X register struct mkroom *croom = search_special(VAULT);
- X coord c;
- X
- X if(croom && somexy(croom, &c) && goodpos(c.x, c.y, mtmp, mtmp->data)) {
- X rloc_to(mtmp, c.x, c.y);
- X return;
- X }
- X rloc(mtmp);
- X}
- X
- X#endif /* OVLB */
- X#ifdef OVL0
- X
- Xstatic boolean
- Xcmavail() /* return TRUE if "common" monsters can be generated */
- X{
- X struct permonst *ptr;
- X
- X for(ptr = &mons[0]; ptr != &mons[NUMMONS]; ptr++)
- X if(!uncommon(ptr)) return TRUE;
- X
- X return FALSE;
- X}
- X
- X/*
- X * shift the probability of a monster's generation by
- X * comparing the dungeon alignment and monster alignment.
- X * return an integer in the range of 0-5.
- X */
- Xstatic int
- Xalign_shift(ptr)
- Xregister struct permonst *ptr;
- X{
- X static long NEARDATA oldmoves = 0L; /* != 1, starting value of moves */
- X static s_level NEARDATA *lev;
- X register int alshift;
- X
- X if(oldmoves != moves) {
- X lev = Is_special(&u.uz);
- X oldmoves = moves;
- X }
- X switch((lev) ? lev->flags.align : dungeons[u.uz.dnum].flags.align) {
- X default: /* just in case */
- X case AM_NONE: alshift = 0;
- X break;
- X case AM_LAWFUL: alshift = (ptr->maligntyp+20)/(2*ALIGNWEIGHT);
- X break;
- X case AM_NEUTRAL: alshift = (20 - abs(ptr->maligntyp))/ALIGNWEIGHT;
- X break;
- X case AM_CHAOTIC: alshift = (-(ptr->maligntyp-20))/(2*ALIGNWEIGHT);
- X break;
- X }
- X return alshift;
- X}
- X
- Xstruct permonst *
- Xrndmonst() /* select a random monster */
- X{
- X register struct permonst *ptr;
- X register int i, ct;
- X register int zlevel;
- X static int NEARDATA minmlev, NEARDATA maxmlev, NEARDATA accept;
- X static long NEARDATA oldmoves = 0L; /* != 1, starting value of moves */
- X#ifdef REINCARNATION
- X static boolean NEARDATA upper;
- X#endif
- X static boolean NEARDATA elemlevel;
- X
- X#ifdef MULDGN
- X if(u.uz.dnum == quest_dnum && (ptr = qt_montype())) return(ptr);
- X#endif
- X if(oldmoves != moves) { /* must recalculate accept */
- X oldmoves = moves;
- X zlevel = level_difficulty();
- X if(!cmavail()) {
- X#ifdef DEBUG
- X pline("cmavail() fails!");
- X#endif
- X return((struct permonst *) 0);
- X }
- X
- X /* determine the level of the weakest monster to make. */
- X minmlev = zlevel/6;
- X /* determine the level of the strongest monster to make. */
- X maxmlev = (zlevel + u.ulevel)>>1;
- X#ifdef REINCARNATION
- X upper = Is_rogue_level(&u.uz);
- X#endif
- X elemlevel = In_endgame(&u.uz) && !Is_astralevel(&u.uz);
- X/*
- X * Find out how many monsters exist in the range we have selected.
- X */
- X accept = 0;
- X for(ct = 0, ptr = &mons[0] ; ptr != &mons[NUMMONS]; ct++, ptr++) {
- X if(tooweak(ct, minmlev) || toostrong(ct, maxmlev))
- X continue;
- X#ifdef REINCARNATION
- X if(upper && !isupper(def_monsyms[ptr->mlet])) continue;
- X#endif
- X if(elemlevel && wrong_elem_type(ptr)) continue;
- X if(uncommon(ptr)) continue;
- X accept += (ptr->geno & G_FREQ);
- X accept += align_shift(ptr);
- X }
- X }
- X
- X if(!accept) {
- X#ifdef DEBUG
- X pline("no accept!");
- X#endif
- X return((struct permonst *) 0);
- X }
- X/*
- X * Now, select a monster at random.
- X */
- X ct = rnd(accept);
- X for(i = 0,ptr = &mons[0]; ptr != &mons[NUMMONS] && ct > 0; i++,ptr++) {
- X if(tooweak(i, minmlev) || toostrong(i, maxmlev))
- X continue;
- X#ifdef REINCARNATION
- X if(upper & !isupper(def_monsyms[ptr->mlet])) continue;
- X#endif
- X if(elemlevel && wrong_elem_type(ptr)) continue;
- X if(uncommon(ptr)) continue;
- X ct -= (ptr->geno & G_FREQ);
- X ct -= align_shift(ptr);
- X }
- X if(ct > 0) {
- X#ifdef DEBUG
- X pline("no count!");
- X#endif
- X return((struct permonst *) 0);
- X }
- X return(--ptr); /* subtract extra increment */
- X}
- X
- X#endif /* OVL0 */
- X#ifdef OVL1
- X
- X/* The routine below is used to make one of the multiple types
- X * of a given monster class. The second parameter specifies a
- X * special casing bit mask to allow any of the normal genesis
- X * masks to be deactivated. Returns 0 if no monsters
- X * in that class can be made.
- X */
- X
- Xstruct permonst *
- Xmkclass(class,spc)
- Xchar class;
- Xint spc;
- X{
- X register int first, last, num = 0;
- X int maxmlev, mask = (G_GENOD | G_EXTINCT | G_NOGEN | G_UNIQ) & ~spc;
- X
- X maxmlev = level_difficulty() >> 1;
- X if(class < 1 || class >= MAXMCLASSES) {
- X impossible("mkclass called with bad class!");
- X return((struct permonst *) 0);
- X }
- X/* Assumption #1: monsters of a given class are contiguous in the
- X * mons[] array.
- X */
- X for(first = 0; first < NUMMONS; first++)
- X if (mons[first].mlet == class) break;
- X if (first == NUMMONS) return((struct permonst *) 0);
- X
- X for(last = first; last < NUMMONS && mons[last].mlet == class; last++)
- X if(!(mons[last].geno & mask)) {
- X /* consider it */
- X if(num && toostrong(last, maxmlev) && rn2(2)) break;
- X num += mons[last].geno & G_FREQ;
- X }
- X
- X if(!num) return((struct permonst *) 0);
- X
- X/* Assumption #2: monsters of a given class are presented in ascending
- X * order of strength.
- X */
- X for(num = rnd(num); num > 0; first++)
- X if(!(mons[first].geno & mask)) {
- X /* skew towards lower value monsters at lower exp. levels */
- X if(adj_lev(&mons[first]) > (u.ulevel*2)) num--;
- X num -= mons[first].geno & G_FREQ;
- X }
- X first--; /* correct an off-by-one error */
- X
- X return(&mons[first]);
- X}
- X
- Xint
- Xadj_lev(ptr) /* adjust strength of monsters based on u.uz and u.ulevel */
- Xregister struct permonst *ptr;
- X{
- X int tmp, tmp2;
- X
- X if((tmp = ptr->mlevel) > 49) return(50); /* "special" demons/devils */
- X tmp2 = (level_difficulty() - tmp);
- X if(tmp2 < 0) tmp--; /* if mlevel > u.uz decrement tmp */
- X else tmp += (tmp2 / 5); /* else increment 1 per five diff */
- X
- X tmp2 = (u.ulevel - ptr->mlevel); /* adjust vs. the player */
- X if(tmp2 > 0) tmp += (tmp2 / 4); /* level as well */
- X
- X tmp2 = (3 * ((int) ptr->mlevel))/ 2; /* crude upper limit */
- X return((tmp > tmp2) ? tmp2 : (tmp > 0 ? tmp : 0)); /* 0 lower limit */
- X}
- X
- X#endif /* OVL1 */
- X#ifdef OVLB
- X
- Xstruct permonst *
- Xgrow_up(mtmp,victim) /* mon mtmp "grows up" to a bigger version. */
- Xregister struct monst *mtmp;
- Xregister struct monst *victim;
- X{
- X register int newtype;
- X register struct permonst *ptr = mtmp->data;
- X
- X if (ptr->mlevel >= 50 || is_golem(ptr) || is_home_elemental(ptr)
- X || is_mplayer(ptr))
- X /* doesn't grow up, has strange hp calculation so might be
- X * weakened by tests below */
- X return ptr;
- X
- X if (victim) {
- X mtmp->mhpmax = mtmp->mhpmax + (1 + rn2((int)victim->m_lev+1));
- X if (mtmp->mhpmax <= (8 * (int)mtmp->m_lev)
- X || (mtmp->m_lev == 0 && mtmp->mhpmax <= 4))
- X /* not ready to grow up */
- X return ptr;
- X }
- X#ifdef MUSE
- X /* else it's a gain level potion; always go up a level */
- X else {
- X int foo=rnd(8);
- X
- X mtmp->mhp += foo;
- X mtmp->mhpmax += foo;
- X }
- X#endif
- X
- X newtype = little_to_big(monsndx(ptr));
- X if ((int) (++mtmp->m_lev) >= mons[newtype].mlevel
- X && newtype != monsndx(ptr)) {
- X if (mons[newtype].geno & G_GENOD) { /* allow G_EXTINCT */
- X pline("As %s grows up into %s, %s dies!",
- X mon_nam(mtmp),
- X an(mons[newtype].mname),
- X mon_nam(mtmp));
- X mondied(mtmp);
- X return (struct permonst *)0;
- X }
- X mtmp->data = &mons[newtype];
- X mtmp->m_lev = mons[newtype].mlevel;
- X }
- X if (newtype == monsndx(ptr) && victim &&
- X (int) mtmp->m_lev > (3*(int)mtmp->data->mlevel) / 2)
- X mtmp->m_lev = (3*(int)mtmp->data->mlevel) / 2;
- X if (mtmp->m_lev > 0) {
- X if (mtmp->mhp > (int) mtmp->m_lev * 8)
- X mtmp->mhp = mtmp->m_lev * 8;
- X if (mtmp->mhpmax > (int) mtmp->m_lev * 8)
- X mtmp->mhpmax = mtmp->m_lev * 8;
- X }
- X return(mtmp->data);
- X}
- X
- X#endif /* OVLB */
- X#ifdef OVL1
- X
- Xint
- Xmongets(mtmp, otyp)
- Xregister struct monst *mtmp;
- Xregister int otyp;
- X{
- X register struct obj *otmp;
- X
- X#ifdef MUSE
- X if (!otyp) return 0;
- X#endif
- X if((otmp = (otyp) ? mksobj(otyp,TRUE,FALSE) : mkobj((char)otyp,FALSE))) {
- X if (mtmp->data->mlet == S_DEMON) {
- X /* demons always get cursed objects */
- X curse(otmp);
- X } else if(is_lminion(mtmp->data)) {
- X /* lawful minions don't get cursed, bad, or rusting objects */
- X otmp->cursed = FALSE;
- X if(otmp->spe < 0) otmp->spe = 0;
- X otmp->oerodeproof = TRUE;
- X } else if(is_mplayer(mtmp->data) && is_sword(otmp))
- X otmp->spe = (3 + rn2(4));
- X if(otmp->otyp == CANDELABRUM_OF_INVOCATION) {
- X otmp->spe = 0;
- X otmp->age = 0L;
- X otmp->lamplit = FALSE;
- X otmp->blessed = otmp->cursed = FALSE;
- X }
- X mpickobj(mtmp, otmp);
- X return(otmp->spe);
- X } else return(0);
- X}
- X
- X#endif /* OVL1 */
- X#ifdef OVLB
- X
- Xint
- Xgolemhp(type)
- Xint type;
- X{
- X switch(type) {
- X case PM_STRAW_GOLEM: return 20;
- X case PM_ROPE_GOLEM: return 30;
- X case PM_LEATHER_GOLEM: return 40;
- X case PM_WOOD_GOLEM: return 50;
- X case PM_FLESH_GOLEM: return 40;
- X case PM_CLAY_GOLEM: return 50;
- X case PM_STONE_GOLEM: return 60;
- X case PM_IRON_GOLEM: return 80;
- X default: return 0;
- X }
- X}
- X
- X#endif /* OVLB */
- X#ifdef OVL1
- X
- X/*
- X * Alignment vs. yours determines monster's attitude to you.
- X * ( some "animal" types are co-aligned, but also hungry )
- X */
- Xboolean
- Xpeace_minded(ptr)
- Xregister struct permonst *ptr;
- X{
- X aligntyp mal = ptr->maligntyp, ual = u.ualign.type;
- X
- X if (always_peaceful(ptr)) return TRUE;
- X if (always_hostile(ptr)) return FALSE;
- X#ifdef MULDGN
- X if (ptr->msound == MS_LEADER || ptr->msound == MS_GUARDIAN)
- X return TRUE;
- X if (ptr->msound == MS_NEMESIS) return FALSE;
- X#endif
- X
- X /* the monster is hostile if its alignment is different from the
- X * player's */
- X if (sgn(mal) != sgn(ual)) return FALSE;
- X
- X /* Negative monster hostile to player with Amulet. */
- X if (mal < A_NEUTRAL && u.uhave.amulet) return FALSE;
- X
- X /* minions are hostile to players that have strayed at all */
- X if (is_minion(ptr)) return(u.ualign.record >= 0);
- X
- X /* Last case: a chance of a co-aligned monster being
- X * hostile. This chance is greater if the player has strayed
- X * (u.ualign.record negative) or the monster is not strongly aligned.
- X */
- X return !!rn2(16 + (u.ualign.record < -15 ? -15 : u.ualign.record)) &&
- X !!rn2(2 + abs(mal));
- X}
- X
- X/* Set malign to have the proper effect on player alignment if monster is
- X * killed. Negative numbers mean it's bad to kill this monster; positive
- X * numbers mean it's good. Since there are more hostile monsters than
- X * peaceful monsters, the penalty for killing a peaceful monster should be
- X * greater than the bonus for killing a hostile monster to maintain balance.
- X * Rules:
- X * it's bad to kill peaceful monsters, potentially worse to kill always-
- X * peaceful monsters
- X * it's never bad to kill a hostile monster, although it may not be good
- X */
- Xvoid
- Xset_malign(mtmp)
- Xstruct monst *mtmp;
- X{
- X schar mal = mtmp->data->maligntyp;
- X boolean coaligned;
- X
- X if (mtmp->ispriest || mtmp->isminion) {
- X /* some monsters have individual alignments; check them */
- X if (mtmp->ispriest)
- X mal = EPRI(mtmp)->shralign;
- X else if (mtmp->isminion)
- X mal = EMIN(mtmp)->min_align;
- X /* unless alignment is none, set mal to -5,0,5 */
- X /* (see align.h for valid aligntyp values) */
- X if(mal != A_NONE)
- X mal *= 5;
- X }
- X
- X coaligned = (sgn(mal) == sgn(u.ualign.type));
- X#ifdef MULDGN
- X if (mtmp->data->msound == MS_LEADER) {
- X mtmp->malign = -20;
- X } else
- X#endif
- X if (mal == A_NONE) {
- X if (mtmp->mpeaceful)
- X mtmp->malign = 0;
- X else
- X mtmp->malign = 20; /* really hostile */
- X } else if (always_peaceful(mtmp->data)) {
- X if (mtmp->mpeaceful)
- X mtmp->malign = -3*max(5,abs(mal));
- X else
- X mtmp->malign = 3*max(5,abs(mal)); /* renegade */
- X } else if (always_hostile(mtmp->data)) {
- X if (coaligned)
- X mtmp->malign = 0;
- X else
- X mtmp->malign = max(5,abs(mal));
- X } else if (coaligned) {
- X if (mtmp->mpeaceful)
- X mtmp->malign = -3*max(3,abs(mal));
- X else /* renegade */
- X mtmp->malign = max(3,abs(mal));
- X } else /* not coaligned and therefore hostile */
- X mtmp->malign = abs(mal);
- X}
- X
- X#endif /* OVL1 */
- X#ifdef OVLB
- X
- Xstatic char NEARDATA syms[] = {
- X MAXOCLASSES, MAXOCLASSES+1, RING_CLASS, WAND_CLASS, WEAPON_CLASS,
- X FOOD_CLASS, GOLD_CLASS, SCROLL_CLASS, POTION_CLASS, ARMOR_CLASS,
- X AMULET_CLASS, TOOL_CLASS, ROCK_CLASS, GEM_CLASS, SPBOOK_CLASS,
- X S_MIMIC_DEF, S_MIMIC_DEF, S_MIMIC_DEF,
- X};
- X
- Xvoid
- Xset_mimic_sym(mtmp) /* KAA, modified by ERS */
- Xregister struct monst *mtmp;
- X{
- X int typ, roomno, rt;
- X unsigned appear, ap_type;
- X int s_sym;
- X struct obj *otmp;
- X int mx, my;
- X
- X if (!mtmp) return;
- X mx = mtmp->mx; my = mtmp->my;
- X typ = levl[mx][my].typ;
- X /* only valid for INSIDE of room */
- X roomno = levl[mx][my].roomno - ROOMOFFSET;
- X if (roomno >= 0)
- X rt = rooms[roomno].rtype;
- X#ifdef SPECIALIZATION
- X else if (IS_ROOM(typ))
- X rt = OROOM, roomno = 0;
- X#endif
- X else rt = 0; /* roomno < 0 case for GCC_WARN */
- X
- X if (OBJ_AT(mx, my)) {
- X ap_type = M_AP_OBJECT;
- X appear = level.objects[mx][my]->otyp;
- X } else if (IS_DOOR(typ) || IS_WALL(typ) ||
- X typ == SDOOR || typ == SCORR) {
- X ap_type = M_AP_FURNITURE;
- X /*
- X * If there is a wall to the left that connects to this
- X * location, then the mimic mimics a horizontal closed door.
- X * This does not allow doors to be in corners of rooms.
- X */
- X if (mx != 0 &&
- X (levl[mx-1][my].typ == HWALL ||
- X levl[mx-1][my].typ == TLCORNER ||
- X levl[mx-1][my].typ == TRWALL ||
- X levl[mx-1][my].typ == BLCORNER ||
- X levl[mx-1][my].typ == TDWALL ||
- X levl[mx-1][my].typ == CROSSWALL||
- X levl[mx-1][my].typ == TUWALL ))
- X appear = S_hcdoor;
- X else
- X appear = S_vcdoor;
- X
- X if(!mtmp->minvis || See_invisible)
- X block_point(mx,my); /* vision */
- X } else if (level.flags.is_maze_lev && rn2(2)) {
- X ap_type = M_AP_OBJECT;
- X appear = STATUE;
- X } else if (roomno < 0) {
- X ap_type = M_AP_OBJECT;
- X appear = BOULDER;
- X if(!mtmp->minvis || See_invisible)
- X block_point(mx,my); /* vision */
- X } else if (rt == ZOO || rt == VAULT) {
- X ap_type = M_AP_OBJECT;
- X appear = GOLD_PIECE;
- X } else if (rt == DELPHI) {
- X if (rn2(2)) {
- X ap_type = M_AP_OBJECT;
- X appear = STATUE;
- X } else {
- X ap_type = M_AP_FURNITURE;
- X appear = S_fountain;
- X }
- X } else if (rt == TEMPLE) {
- X ap_type = M_AP_FURNITURE;
- X appear = S_altar;
- X /*
- X * We won't bother with beehives, morgues, barracks, throne rooms
- X * since they shouldn't contain too many mimics anyway...
- X */
- X } else if (rt >= SHOPBASE) {
- X s_sym = get_shop_item(rt - SHOPBASE);
- X if (s_sym < 0) {
- X ap_type = M_AP_OBJECT;
- X appear = -s_sym;
- X } else {
- X if (s_sym == RANDOM_CLASS)
- X s_sym = syms[rn2((int)sizeof(syms)-2) + 2];
- X goto assign_sym;
- X }
- X } else {
- X s_sym = syms[rn2((int)sizeof(syms))];
- Xassign_sym:
- X if (s_sym >= MAXOCLASSES) {
- X ap_type = M_AP_FURNITURE;
- X appear = s_sym == MAXOCLASSES ? S_upstair : S_dnstair;
- X } else if (s_sym == GOLD_CLASS) {
- X ap_type = M_AP_OBJECT;
- X appear = GOLD_PIECE;
- X } else {
- X ap_type = M_AP_OBJECT;
- X if (s_sym == S_MIMIC_DEF) {
- X appear = STRANGE_OBJECT;
- X } else {
- X otmp = mkobj( (char) s_sym, FALSE );
- X appear = otmp->otyp;
- X /* make sure container contents are free'ed */
- X obfree(otmp, (struct obj *) 0);
- X }
- X }
- X }
- X mtmp->m_ap_type = ap_type;
- X mtmp->mappearance = appear;
- X}
- X
- X#endif /* OVLB */
- X
- X/*makemon.c*/
- END_OF_FILE
- if test 40817 -ne `wc -c <'src/makemon.c'`; then
- echo shar: \"'src/makemon.c'\" unpacked with wrong size!
- fi
- # end of 'src/makemon.c'
- fi
- echo shar: End of archive 31 \(of 108\).
- cp /dev/null ark31isdone
- MISSING=""
- for I in 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 \
- 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 \
- 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 \
- 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 \
- 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 \
- 101 102 103 104 105 106 107 108 ; do
- if test ! -f ark${I}isdone ; then
- MISSING="${MISSING} ${I}"
- fi
- done
- if test "${MISSING}" = "" ; then
- echo You have unpacked all 108 archives.
- echo "Now execute 'rebuild.sh'"
- rm -f ark10[0-8]isdone ark[1-9]isdone ark[1-9][0-9]isdone
- else
- echo You still need to unpack the following archives:
- echo " " ${MISSING}
- fi
- ## End of shell archive.
- exit 0
-