-+-+-+-+-+-+-+-+ START OF PART 40 -+-+-+-+-+-+-+-+ X return( (i>=1) ? i : xx ); X `7D X X/* X * direct(spnum,dam,str,arg) Routine to direct spell damage 1 square in 1 V dir X * int spnum,dam,arg; X * char *str; X * X * Routine to ask for a direction to a spell and then hit the monster X * Enter with the spell number in spnum, the damage to be done in dam, X * lprintf format string in str, and lprintf's argument in arg. X * Returns no value. X */ Xstatic direct(spnum,dam,str,arg) X int spnum,dam,arg; X char *str; X `7B X extern char lastmonst`5B`5D; X int x,y; X register int m; X if (spnum<0 `7C`7C spnum>=SPNUM `7C`7C str==0) return; /* bad arguments V */ X if (isconfuse()) return; X dirsub(&x,&y); X m = mitem`5Bx`5D`5By`5D; X if (item`5Bx`5D`5By`5D==OMIRROR) X `7B X if (spnum==3) /* sleep */ X `7B X lprcat("You fall asleep! "); beep(); X fool: X arg += 2; X while (arg-- > 0) `7B parse2(); nap(1000); `7D X return; X `7D X else if (spnum==6) /* web */ X `7B X lprcat("You get stuck in your own web! "); beep(); X goto fool; X `7D X else X `7B X lastnum=278;`20 X lprintf(str,"spell caster (thats you)",(long)arg); X beep(); losehp(dam); return; X `7D X `7D X if (m==0) X `7B lprcat(" There wasn't anything there!"); return; `7D X ifblind(x,y); X if (nospell(spnum,m)) `7B lasthx=x; lasthy=y; return; `7D X lprintf(str,lastmonst,(long)arg); hitm(x,y,dam); X `7D X X/* X * godirect(spnum,dam,str,delay,cshow) Function to perform missile atta Vcks X * int spnum,dam,delay; X * char *str,cshow; X * X * Function to hit in a direction from a missile weapon and have it keep X * on going in that direction until its power is exhausted X * Enter with the spell number in spnum, the power of the weapon in hp, X * lprintf format string in str, the # of milliseconds to delay between`2 V0 X * locations in delay, and the character to represent the weapon in cshow V. X * Returns no value. X */ Xgodirect(spnum,dam,str,delay,cshow) X int spnum,dam,delay; X char *str,cshow; X `7B X extern char lastmonst`5B`5D ; X register char *p; X register int x,y,m; X int dx,dy; X if (spnum<0 `7C`7C spnum>=SPNUM `7C`7C str==0 `7C`7C delay<0) return; /* V bad args */ X if (isconfuse()) return; X dirsub(&dx,&dy); x=dx; y=dy; X dx = x-playerx; dy = y-playery; x = playerx; y = playery; X while (dam>0) X `7B X x += dx; y += dy; X if ((x > MAXX-1) `7C`7C (y > MAXY-1) `7C`7C (x < 0) `7C`7C (y < 0)) X `7B X dam=0; break; /* out of bounds */ X `7D X if ((x==playerx) && (y==playery)) /* if energy hits player */ X `7B X cursors(); lprcat("\nYou are hit my your own magic!"); beep(); X lastnum=278; losehp(dam); return; X `7D X if (c`5BBLINDCOUNT`5D==0) /* if not blind show effect */ X `7B X cursor(x+1,y+1); lprc(cshow); nap(delay); show1cell(x,y); X `7D X if ((m=mitem`5Bx`5D`5By`5D)) /* is there a monster there? */ X `7B X ifblind(x,y); X if (nospell(spnum,m)) `7B lasthx=x; lasthy=y; return; `7D X cursors(); lprc('\n'); X lprintf(str,lastmonst); dam -= hitm(x,y,dam); X show1cell(x,y); nap(1000); x -= dx; y -= dy; X `7D X else switch (*(p= &item`5Bx`5D`5By`5D)) X `7B X case OWALL: X cursors(); X lprc('\n'); X lprintf(str,"wall"); X if (dam>=50+c`5BHARDGAME`5D) /* enough damage? */ X if (level=40) X `7B X lprcat(" The door is blasted apart"); X *p = 0; X know`5Bx`5D`5By`5D = 0; X show1cell( x, y ); X `7D X dam = 0 ; X break; X X case OSTATUE: X cursors(); X lprc('\n'); X lprintf(str,"statue"); X if (c`5BHARDGAME`5D<3) X if (dam>44) X `7B X lprcat(" The statue crumbles"); X *p=OBOOK; X iarg`5Bx`5D`5By`5D=level; X know`5Bx`5D`5By`5D = 0; X show1cell( x, y ); X `7D X dam = 0 ; X break; X X case OTHRONE: X cursors(); X lprc('\n'); X lprintf(str,"throne"); X if (dam>39) X `7B X *p = OTHRONE2; X create_guardian( GNOMEKING, x, y ); X show1cell( x, y ); X `7D X dam = 0; X break; X X case OALTAR: X cursors(); X lprc('\n'); X lprintf(str, "altar"); X if ( dam > 75 - ( c`5BHARDGAME`5D >> 2 )) X `7B X create_guardian( DEMONPRINCE, x, y ); X show1cell( x, y ); X `7D X dam = 0 ; X break; X X case OFOUNTAIN: X cursors(); X lprc('\n'); X lprintf(str, "fountain"); X if ( dam > 55 ) X `7B X create_guardian( WATERLORD, x, y ); X show1cell( x, y ); X `7D X dam = 0 ; X break; X X case OMIRROR: X `7B X int bounce = FALSE, odx=dx, ody=dy ; X /* spells may bounce directly back or off at an angle X */ X if (rnd(100) < 50 ) X `7B X bounce = TRUE ; X dx *= -1; X `7D X if (rnd(100) < 50 ) X `7B X bounce = TRUE ; X dy *= -1; X `7D X if (!bounce `7C`7C ((odx==dx) && (ody==dy))) /* guarentee a bounce */ X `7B X dx = -odx; X dy = -ody; X `7D X `7D X break; X `7D; X dam -= 3 + (c`5BHARDGAME`5D>>1); X `7D X `7D X X/* X * ifblind(x,y) Routine to put "monster" or the monster name into lastmo Vsnt X * int x,y; X * X * Subroutine to copy the word "monster" into lastmonst if the player is bl Vind X * Enter with the coordinates (x,y) of the monster X * Returns no value. X */ Xifblind(x,y) X int x,y; X `7B X extern char lastmonst`5B`5D ; X char *p; X vxy(&x,&y); /* verify correct x,y coordinates */ X if (c`5BBLINDCOUNT`5D) `7B lastnum=279; p="monster"; `7D X else `7B lastnum=mitem`5Bx`5D`5By`5D; p=monster`5Blastnum`5D.name; V `7D X strcpy(lastmonst,p); X `7D X X/* X * tdirect(spnum) Routine to teleport away a monster X * int spnum; X * X * Routine to ask for a direction to a spell and then teleport away monster X * Enter with the spell number that wants to teleport away X * Returns no value. X */ Xstatic tdirect(spnum) X int spnum; X `7B X int x,y; X register int m; X if (spnum<0 `7C`7C spnum>=SPNUM) return; /* bad args */ X if (isconfuse()) return; X dirsub(&x,&y); X if ((m=mitem`5Bx`5D`5By`5D)==0) X `7B lprcat(" There wasn't anything there!"); return; `7D X ifblind(x,y); X if (nospell(spnum,m)) `7B lasthx=x; lasthy=y; return; `7D X fillmonst(m); mitem`5Bx`5D`5By`5D=0; know`5Bx`5D`5By`5D &= `7EKNOWHERE; X `7D X X/* X * omnidirect(sp,dam,str) Routine to damage all monsters 1 square from pl Vayer X * int sp,dam; X * char *str; X * X * Routine to cast a spell and then hit the monster in all directions X * Enter with the spell number in sp, the damage done to wach square in dam V, X * and the lprintf string to identify the spell in str. X * Returns no value. X */ Xstatic omnidirect(spnum,dam,str) X int spnum,dam; X char *str; X `7B X extern char lastmonst`5B`5D ; X register int x,y,m; X if (spnum<0 `7C`7C spnum>=SPNUM `7C`7C str==0) return; /* bad args */ X for (x=playerx-1; x=SPNUM) return; /* bad args */ X if (isconfuse()) return; /* if he is confused, he can't aim his magic V */ X dirsub(&x,&y); X if (mitem`5Bx`5D`5By`5D==0) X `7B lprcat(" There wasn't anything there!"); return; `7D X ifblind(x,y); X if (nospell(spnum,mitem`5Bx`5D`5By`5D)) `7B lasthx=x; lasthy=y; return; V `7D X# ifdef MSDOS X do `7B X m = rnd(MAXMONST+7); X mitem`5Bx`5D`5By`5D = m; X `7D while ( monster`5Bm`5D.genocided ); X# else X while ( monster`5Bm = mitem`5Bx`5D`5By`5D = rnd(MAXMONST+7)`5D.genocided V ); X# endif X hitp`5Bx`5D`5By`5D = monster`5Bm`5D.hitpoints; X show1cell(x,y); /* show the new monster */ X `7D X X/* X * annihilate() Routine to annihilate all monsters around player (player Vx,playery) X * X * Gives player experience, but no dropped objects X * Returns the experience gained from all monsters killed X */ Xannihilate() X `7B X int i,j; X register long k; X register char *p; X for (k=0, i=playerx-1; i<=playerx+1; i++) X for (j=playery-1; j<=playery+1; j++) X if (!vxy(&i,&j)) /* if not out of bounds */ X if (*(p= &mitem`5Bi`5D`5Bj`5D)) /* if a monster there */ X if (*p>1) + 1; /* los Ve half hit points*/ X `7D X if (k>0) X `7B X lprcat("\nYou hear loud screams of agony!"); raiseexperience((lon Vg)k); X `7D X return(k); X `7D X X/* X * genmonst() Function to ask for monster and genocide from game X * X * This is done by setting a flag in the monster`5B`5D structure X */ Xstatic genmonst() X `7B X register int i,j; X cursors(); lprcat("\nGenocide what monster? "); X for (i=0; (!isalpha(i)) && (i!=' '); i=ttgetch()); X lprc(i); X for (j=0; j(y))?(y):(x)) X#define max(x,y) (((x)>(y))?(x):(y)) X X/* X * newsphere(x,y,dir,lifetime) Function to create a new sphere of annihila Vtion X * int x,y,dir,lifetime; X * X * Enter with the coordinates of the sphere in x,y X * the direction (0-8 diroffx format) in dir, and the lifespan of the X * sphere in lifetime (in turns) X * Returns the number of spheres currently in existence X */ Xnewsphere(x,y,dir,life) X int x,y,dir,life; X `7B X int m; X struct sphere *sp; X if (((sp=(struct sphere *)malloc(sizeof(struct sphere)))) == 0) X return(c`5BSPHCAST`5D); /* can't malloc, therefore failure */ X if (dir>=9) dir=0; /* no movement if direction not found */ X if (level==0) vxy(&x,&y); /* don't go out of bounds */ X else X `7B X if (x<1) x=1; if (x>=MAXX-1) x=MAXX-2; X if (y<1) y=1; if (y>=MAXY-1) y=MAXY-2; X `7D +-+-+-+-+-+-+-+- END OF PART 40 +-+-+-+-+-+-+-+-