date and time created 93/06/01 16:44:41 by bostic
[unix-history] / usr / src / contrib / dungeon / demons.F
C FIGHTD- INTERMOVE FIGHT DEMON
C
C COPYRIGHT 1980, INFOCOM COMPUTERS AND COMMUNICATIONS, CAMBRIDGE MA. 02142
C ALL RIGHTS RESERVED, COMMERCIAL USAGE STRICTLY PROHIBITED
C WRITTEN BY R. M. SUPNIK
C
C DECLARATIONS
C
SUBROUTINE FIGHTD
IMPLICIT INTEGER (A-Z)
LOGICAL PROB,OAPPLI
#include "parser.h"
#include "gamestate.h"
#include "objects.h"
#include "oflags.h"
#include "oindex.h"
#include "villians.h"
#include "advers.h"
#include "verbs.h"
#include "flags.h"
C
LOGICAL F
C
C FUNCTIONS AND DATA
C
DATA ROUT/1/
C FIGHTD, PAGE 2
C
DO 2400 I=1,VLNT
C !LOOP THRU VILLAINS.
VOPPS(I)=0
C !CLEAR OPPONENT SLOT.
OBJ=VILLNS(I)
C !GET OBJECT NO.
RA=OACTIO(OBJ)
C !GET HIS ACTION.
IF(HERE.NE.OROOM(OBJ)) GO TO 2200
C !ADVENTURER STILL HERE?
IF((OBJ.EQ.THIEF).AND.THFENF) GO TO 2400
C !THIEF ENGROSSED?
IF(OCAPAC(OBJ).GE.0) GO TO 2050
C !YES, VILL AWAKE?
IF((VPROB(I).EQ.0).OR..NOT.PROB(VPROB(I),VPROB(I)))
& GO TO 2025
OCAPAC(OBJ)=IABS(OCAPAC(OBJ))
VPROB(I)=0
IF(RA.EQ.0) GO TO 2400
C !ANYTHING TO DO?
PRSA=INXW
C !YES, WAKE HIM UP.
F=OAPPLI(RA,0)
GO TO 2400
C !NOTHING ELSE HAPPENS.
C
2025 VPROB(I)=VPROB(I)+10
C !INCREASE WAKEUP PROB.
GO TO 2400
C !NOTHING ELSE.
C
2050 IF((and(OFLAG2(OBJ),FITEBT)).EQ.0) GO TO 2100
VOPPS(I)=OBJ
C !FIGHTING, SET UP OPP.
GO TO 2400
C
2100 IF(RA.EQ.0) GO TO 2400
C !NOT FIGHTING,
PRSA=FRSTQW
C !SET UP PROBABILITY
IF(.NOT.OAPPLI(RA,0)) GO TO 2400
C !OF FIGHTING.
OFLAG2(OBJ)=or(OFLAG2(OBJ),FITEBT)
VOPPS(I)=OBJ
C !SET UP OPP.
GO TO 2400
C
2200 IF((and(OFLAG2(OBJ),FITEBT).EQ.0).OR.(RA.EQ.0))
& GO TO 2300
PRSA=FIGHTW
C !HAVE A FIGHT.
F=OAPPLI(RA,0)
2300 IF(OBJ.EQ.THIEF) THFENF=.FALSE.
C !TURN OFF ENGROSSED.
AFLAG(PLAYER)=and(AFLAG(PLAYER), not(ASTAG))
OFLAG2(OBJ)=and(OFLAG2(OBJ), not(STAGBT+FITEBT))
IF((OCAPAC(OBJ).GE.0).OR.(RA.EQ.0))
& GO TO 2400
PRSA=INXW
C !WAKE HIM UP.
F=OAPPLI(RA,0)
OCAPAC(OBJ)=IABS(OCAPAC(OBJ))
2400 CONTINUE
C FIGHTD, PAGE 3
C
C NOW DO ACTUAL COUNTERBLOWS.
C
OUT=0
C !ASSUME HERO OK.
2600 DO 2700 I=1,VLNT
C !LOOP THRU OPPS.
J=VOPPS(I)
IF(J.EQ.0) GO TO 2700
C !SLOT EMPTY?
PRSCON=1
C !STOP CMD STREAM.
RA=OACTIO(J)
IF(RA.EQ.0) GO TO 2650
C !VILLAIN ACTION?
PRSA=FIGHTW
C !SEE IF
IF(OAPPLI(RA,0)) GO TO 2700
C !SPECIAL ACTION.
2650 RES=BLOW(PLAYER,J,VMELEE(I),.FALSE.,OUT)
C !STRIKE BLOW.
IF(RES.LT.0) RETURN
C !IF HERO DEAD, EXIT.
IF(RES.EQ.ROUT) OUT=2+RND(3)
C !IF HERO OUT, SET FLG.
2700 CONTINUE
OUT=OUT-1
C !DECREMENT OUT COUNT.
IF(OUT.GT.0) GO TO 2600
C !IF STILL OUT, GO AGAIN.
RETURN
C
END
C BLOW- STRIKE BLOW
C
C DECLARATIONS
C
INTEGER FUNCTION BLOW(H,V,RMK,HFLG,OUT)
IMPLICIT INTEGER (A-Z)
LOGICAL HFLG,OAPPLI,PROB
INTEGER DEF1R(3),DEF2R(4),DEF3R(5)
INTEGER RVECTR(66),RSTATE(45)
#include "gamestate.h"
#include "debug.h"
C
C PARSE VECTOR
C
LOGICAL PRSWON
#include "parser.h"
C
C MISCELLANEOUS VARIABLES
C
COMMON /STAR/ MBASE,STRBIT
#include "objects.h"
#include "oflags.h"
C
#include "clock.h"
#include "advers.h"
#include "verbs.h"
C
LOGICAL F
C
C FUNCTIONS AND DATA
C
DATA RMISS/0/,ROUT/1/,RKILL/2/,RLIGHT/3/
DATA RSER/4/,RSTAG/5/,RLOSE/6/,RHES/7/,RSIT/8/
DATA DEF1R/1,2,3/
DATA DEF2R/13,23,24,25/
DATA DEF3R/35,36,46,47,57/
C
DATA RVECTR/0,0,0,0,5,5,1,1,2,2,2,2,
& 0,0,0,0,0,5,5,3,3,1,
& 0,0,0,5,5,3,3,3,1,2,2,2,
& 0,0,0,0,0,5,5,3,3,4,4,
& 0,0,0,5,5,3,3,3,4,4,4,
& 0,5,5,3,3,3,3,4,4,4/
DATA RSTATE/5000,3005,3008,4011,3015,3018,1021,0,0,
& 5022,3027,3030,4033,3037,3040,1043,0,0,
& 4044,2048,4050,4054,5058,4063,4067,3071,1074,
& 4075,1079,4080,4084,4088,4092,4096,4100,1104,
& 4105,2109,4111,4115,4119,4123,4127,3131,3134/
C BLOW, PAGE 3
C
RA=OACTIO(V)
C !GET VILLAIN ACTION,
DV=ODESC2(V)
C !DESCRIPTION.
BLOW=RMISS
C !ASSUME NO RESULT.
#ifdef debug
IF(DFLAG) PRINT 10,H,V,RMK,HFLG,OUT
#ifdef NOCC
10 FORMAT('BLOW 10-- ',3I7,L7,I7)
#else NOCC
10 FORMAT(' BLOW 10-- ',3I7,L7,I7)
#endif NOCC
#endif debug
IF(.NOT.HFLG) GO TO 1000
C !HERO STRIKING BLOW?
C
C HERO IS ATTACKER, VILLAIN IS DEFENDER.
C
PBLOSE=10
C !BAD LK PROB.
OFLAG2(V)=or(OFLAG2(V),FITEBT)
IF(and(AFLAG(H),ASTAG).EQ.0) GO TO 100
CALL RSPEAK(591)
C !YES, CANT FIGHT.
AFLAG(H)=and(AFLAG(H), not(ASTAG))
RETURN
C
100 ATT=FIGHTS(H,.TRUE.)
C !GET HIS STRENGTH.
OA=ATT
DEF=VILSTR(V)
C !GET VILL STRENGTH.
OD=DEF
DWEAP=0
C !ASSUME NO WEAPON.
DO 200 I=1,OLNT
C !SEARCH VILLAIN.
IF((OCAN(I).EQ.V).AND.(and(OFLAG2(I),WEAPBT).NE.0))
& DWEAP=I
200 CONTINUE
IF(V.EQ.AOBJ(PLAYER)) GO TO 300
C !KILLING SELF?
IF(DEF.NE.0) GO TO 2000
C !DEFENDER ALIVE?
CALL RSPSUB(592,DV)
C !VILLAIN DEAD.
RETURN
C
300 CALL JIGSUP(593)
C !KILLING SELF.
RETURN
C
C VILLAIN IS ATTACKER, HERO IS DEFENDER.
C
1000 PBLOSE=50
C !BAD LK PROB.
AFLAG(H)=and(AFLAG(H),not(ASTAG))
IF(and(OFLAG2(V),STAGBT).EQ.0) GO TO 1200
OFLAG2(V)=and(OFLAG2(V), not(STAGBT))
CALL RSPSUB(594,DV)
C !DESCRIBE.
RETURN
C
1200 ATT=VILSTR(V)
C !SET UP ATT, DEF.
OA=ATT
DEF=FIGHTS(H,.TRUE.)
IF(DEF.LE.0) RETURN
C !DONT ALLOW DEAD DEF.
OD=FIGHTS(H,.FALSE.)
DWEAP=IABS(FWIM(0,WEAPBT,0,0,H,.TRUE.))
C !FIND A WEAPON.
C BLOW, PAGE 4
C
C PARTIES ARE NOW EQUIPPED. DEF CANNOT BE ZERO.
C ATT MUST BE > 0.
C
2000 CONTINUE
#ifdef debug
IF(DFLAG) PRINT 2050,ATT,OA,DEF,OD,DWEAP
#ifdef NOCC
2050 FORMAT('BLOW 2050-- ',5I7)
#else NOCC
2050 FORMAT(' BLOW 2050-- ',5I7)
#endif NOCC
#endif debug
IF(DEF.GT.0) GO TO 2100
C !DEF ALIVE?
RES=RKILL
IF(HFLG) CALL RSPSUB(595,DV)
C !DEADER.
GO TO 3000
C
2100 IF(DEF-2) 2200,2300,2400
C !DEF <2,=2,>2
2200 ATT=MIN0(ATT,3)
C !SCALE ATT.
TBL=DEF1R(ATT)
C !CHOOSE TABLE.
GO TO 2500
C
2300 ATT=MIN0(ATT,4)
C !SCALE ATT.
TBL=DEF2R(ATT)
C !CHOOSE TABLE.
GO TO 2500
C
2400 ATT=ATT-DEF
C !SCALE ATT.
ATT=MIN0(2,MAX0(-2,ATT))+3
TBL=DEF3R(ATT)
C
2500 RES=RVECTR(TBL+RND(10))
C !GET RESULT.
IF(OUT.EQ.0) GO TO 2600
C !WAS HE OUT?
IF(RES.EQ.RSTAG) GO TO 2550
C !YES, STAG--> HES.
RES=RSIT
C !OTHERWISE, SITTING.
GO TO 2600
2550 RES=RHES
2600 IF((RES.EQ.RSTAG).AND.(DWEAP.NE.0).AND.PROB(25,PBLOSE))
& RES=RLOSE
C
MI=RSTATE(((RMK-1)*9)+RES+1)
C !CHOOSE TABLE ENTRY.
IF(MI.EQ.0) GO TO 3000
I=(MOD(MI,1000)+RND(MI/1000))+MBASE+1
J=DV
IF(.NOT.HFLG .AND.(DWEAP.NE.0)) J=ODESC2(DWEAP)
#ifdef debug
IF(DFLAG) PRINT 2650,RES,MI,I,J,MBASE
#ifdef NOCC
2650 FORMAT('BLOW 2650-- ',5I7)
#else NOCC
2650 FORMAT(' BLOW 2650-- ',5I7)
#endif NOCC
#endif debug
CALL RSPSUB(I,J)
C !PRESENT RESULT.
C BLOW, PAGE 5
C
C NOW APPLY RESULT
C
3000 GO TO (4000,3100,3200,3300,3400,3500,3600,4000,3200),RES+1
C
3100 IF(HFLG) DEF=-DEF
C !UNCONSCIOUS.
GO TO 4000
C
3200 DEF=0
C !KILLED OR SITTING DUCK.
GO TO 4000
C
3300 DEF=MAX0(0,DEF-1)
C !LIGHT WOUND.
GO TO 4000
C
3400 DEF=MAX0(0,DEF-2)
C !SERIOUS WOUND.
GO TO 4000
C
3500 IF(HFLG) GO TO 3550
C !STAGGERED.
AFLAG(H)=or(AFLAG(H),ASTAG)
GO TO 4000
C
3550 OFLAG2(V)=or(OFLAG2(V),STAGBT)
GO TO 4000
C
3600 CALL NEWSTA(DWEAP,0,HERE,0,0)
C !LOSE WEAPON.
DWEAP=0
IF(HFLG) GO TO 4000
C !IF HERO, DONE.
DWEAP=IABS(FWIM(0,WEAPBT,0,0,H,.TRUE.))
C !GET NEW.
IF(DWEAP.NE.0) CALL RSPSUB(605,ODESC2(DWEAP))
C BLOW, PAGE 6
C
4000 BLOW=RES
C !RETURN RESULT.
IF(.NOT.HFLG) GO TO 4500
C !HERO?
OCAPAC(V)=DEF
C !STORE NEW CAPACITY.
IF(DEF.NE.0) GO TO 4100
C !DEAD?
OFLAG2(V)=and(OFLAG2(V), not(FITEBT))
CALL RSPSUB(572,DV)
C !HE DIES.
CALL NEWSTA(V,0,0,0,0)
C !MAKE HIM DISAPPEAR.
IF(RA.EQ.0) RETURN
C !IF NX TO DO, EXIT.
PRSA=DEADXW
C !LET HIM KNOW.
F=OAPPLI(RA,0)
RETURN
C
4100 IF((RES.NE.ROUT).OR.(RA.EQ.0)) RETURN
PRSA=OUTXW
C !LET HIM BE OUT.
F=OAPPLI(RA,0)
RETURN
C
4500 ASTREN(H)=-10000
C !ASSUME DEAD.
IF(DEF.NE.0) ASTREN(H)=DEF-OD
IF(DEF.GE.OD) GO TO 4600
CTICK(CEVCUR)=30
CFLAG(CEVCUR)=.TRUE.
4600 IF(FIGHTS(H,.TRUE.).GT.0) RETURN
ASTREN(H)=1-FIGHTS(H,.FALSE.)
C !HE'S DEAD.
CALL JIGSUP(596)
BLOW=-1
RETURN
C
END
C SWORDD- SWORD INTERMOVE DEMON
C
C DECLARATIONS
C
SUBROUTINE SWORDD
IMPLICIT INTEGER(A-Z)
LOGICAL INFEST,FINDXT
#include "gamestate.h"
#include "curxt.h"
#include "xsrch.h"
#include "objects.h"
#include "oindex.h"
#include "villians.h"
#include "advers.h"
C SWORDD, PAGE 2
C
IF(OADV(SWORD).NE.PLAYER) GO TO 500
C !HOLDING SWORD?
NG=2
C !ASSUME VILL CLOSE.
IF(INFEST(HERE)) GO TO 300
C !VILL HERE?
NG=1
DO 200 I=XMIN,XMAX,XMIN
C !NO, SEARCH ROOMS.
IF(.NOT.FINDXT(I,HERE)) GO TO 200
C !ROOM THAT WAY?
GO TO (50,200,50,50),XTYPE
C !SEE IF ROOM AT ALL.
50 IF(INFEST(XROOM1)) GO TO 300
C !CHECK ROOM.
200 CONTINUE
NG=0
C !NO GLOW.
C
300 IF(NG.EQ.SWDSTA) RETURN
C !ANY STATE CHANGE?
CALL RSPEAK(NG+495)
C !YES, TELL NEW STATE.
SWDSTA=NG
RETURN
C
500 SWDACT=.FALSE.
C !DROPPED SWORD,
RETURN
C !DISABLE DEMON.
END
C INFEST- SUBROUTINE TO TEST FOR INFESTED ROOM
C
C DECLARATIONS
C
LOGICAL FUNCTION INFEST(R)
IMPLICIT INTEGER(A-Z)
C
C ROOMS
#include "rindex.h"
#include "objects.h"
#include "oindex.h"
#include "villians.h"
#include "flags.h"
C
IF(.NOT.ENDGMF) INFEST=(OROOM(CYCLO).EQ.R).OR.
& (OROOM(TROLL).EQ.R).OR.
& ((OROOM(THIEF).EQ.R).AND.THFACT)
IF(ENDGMF) INFEST=(R.EQ.MRG).OR.(R.EQ.MRGE).OR.
& (R.EQ.MRGW).OR.
& ((R.EQ.INMIR).AND.(MLOC.EQ.MRG))
RETURN
END