C SVERBS- SIMPLE VERBS PROCESSOR C ALL VERBS IN THIS ROUTINE MUST BE INDEPENDANT C OF OBJECT ACTIONS 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 LOGICAL FUNCTION SVERBS(RI) IMPLICIT INTEGER (A-Z) LOGICAL MOVETO,YESNO LOGICAL RMDESC LOGICAL QOPEN LOGICAL FINDXT,QHERE,F INTEGER JOKES(25) CHARACTER ANSSTR(78) CHARACTER PP1(6),PP2(6),CH(6) INTEGER ANSWER(28) #include "parser.h" #include "gamestate.h" #include "state.h" #include "screen.h" C C MISCELLANEOUS VARIABLES C CHARACTER VEDIT COMMON /VERS/ VMAJ,VMIN,VEDIT #include "io.h" #include "rooms.h" #include "rflag.h" #include "rindex.h" #include "exits.h" #include "curxt.h" #include "xpars.h" #include "xsrch.h" #include "objects.h" #include "oflags.h" #include "oindex.h" #include "clock.h" #include "advers.h" #include "verbs.h" #include "flags.h" C C FUNCTIONS AND DATA C QOPEN(R)=and(OFLAG2(R),OPENBT).NE.0 DATA MXNOP/39/,MXJOKE/64/ DATA JOKES/4,5,3,304,305,306,307,308,309,310,311,312, & 313,5314,5319,324,325,883,884,120,120,0,0,0,0/ DATA ANSWER/0,6,1,6,2,5,3,5,4,3,4,6,4,6,4,5, & 5,5,5,4,5,6,6,10,7,4,7,6/ DATA ANSSTR/'T','E','M','P','L','E', & 'F','O','R','E','S','T', & '3','0','0','0','3', & 'F','L','A','S','K', & 'R','U','B', & 'F','O','N','D','L','E', & 'C','A','R','R','E','S', & 'T','O','U','C','H', & 'B','O','N','E','S', & 'B','O','D','Y', & 'S','K','E','L','E','T', & 'R','U','S','T','Y','K','N','I','F','E', & 'N','O','N','E', & 'N','O','W','H','E','R','\0'/ C SVERBS, PAGE 2 C SVERBS=.TRUE. C !ASSUME WINS. IF(PRSO.NE.0) ODO2=ODESC2(PRSO) C !SET UP DESCRIPTORS. IF(PRSI.NE.0) ODI2=ODESC2(PRSI) C IF(RI.EQ.0) CALL BUG(7,RI) C !ZERO IS VERBOTEN. IF(RI.LE.MXNOP) RETURN C !NOP? IF(RI.LE.MXJOKE) GO TO 100 C !JOKE? GO TO (65000,66000,67000,68000,69000, & 1000,2000,3000,4000,5000,6000,7000,8000,9000,10000, & 11000,12000,13000,14000,15000,16000,17000,18000,19000,20000, & 21000,22000,23000,24000,25000,26000,27000), & (RI-MXJOKE) CALL BUG(7,RI) C C ALL VERB PROCESSORS RETURN HERE TO DECLARE FAILURE. C 10 SVERBS=.FALSE. C !LOSE. RETURN C C JOKE PROCESSOR. C FIND PROPER ENTRY IN JOKES, USE IT TO SELECT STRING TO PRINT. C 100 I=JOKES(RI-MXNOP) C !GET TABLE ENTRY. J=I/1000 C !ISOLATE # STRINGS. IF(J.NE.0) I=MOD(I,1000)+RND(J) C !IF RANDOM, CHOOSE. CALL RSPEAK(I) C !PRINT JOKE. RETURN C SVERBS, PAGE 2A C C V65-- ROOM C 65000 SVERBS=RMDESC(2) C !DESCRIBE ROOM ONLY. RETURN C C V66-- OBJECTS C 66000 SVERBS=RMDESC(1) C !DESCRIBE OBJ ONLY. IF(.NOT.TELFLG) CALL RSPEAK(138) C !NO OBJECTS. RETURN C C V67-- RNAME C 67000 CALL RSPEAK(RDESC2-HERE) C !SHORT ROOM NAME. RETURN C C V68-- RESERVED C 68000 RETURN C C V69-- RESERVED C 69000 RETURN C SVERBS, PAGE 3 C C V70-- BRIEF. SET FLAG. C 1000 BRIEFF=.TRUE. C !BRIEF DESCRIPTIONS. SUPERF=.FALSE. CALL RSPEAK(326) RETURN C C V71-- VERBOSE. CLEAR FLAGS. C 2000 BRIEFF=.FALSE. C !LONG DESCRIPTIONS. SUPERF=.FALSE. CALL RSPEAK(327) RETURN C C V72-- SUPERBRIEF. SET FLAG. C 3000 SUPERF=.TRUE. CALL RSPEAK(328) RETURN C C V73-- STAY (USED IN ENDGAME). C 4000 IF(WINNER.NE.AMASTR) GO TO 4100 C !TELL MASTER, STAY. CALL RSPEAK(781) C !HE DOES. CTICK(CEVFOL)=0 C !NOT FOLLOWING. RETURN C 4100 IF(WINNER.EQ.PLAYER) CALL RSPEAK(664) C !JOKE. RETURN C C V74-- VERSION. PRINT INFO. C #ifdef PDP 5000 call prvers(vmaj,vmin,vedit) #else 5000 WRITE(OUTCH,5010) VMAJ,VMIN,VEDIT #ifdef NOCC 5010 FORMAT('V',I1,'.',I2,A1) #else NOCC 5010 FORMAT(' V',I1,'.',I2,A1) #endif NOCC #endif PDP TELFLG=.TRUE. RETURN C C V75-- SWIM. ALWAYS A JOKE. C 6000 I=330 C !ASSUME WATER. IF(and(RFLAG(HERE),(RWATER+RFILL)).EQ.0) & I=331+RND(3) CALL RSPEAK(I) RETURN C C V76-- GERONIMO. IF IN BARREL, FATAL, ELSE JOKE. C 7000 IF(HERE.EQ.MBARR) GO TO 7100 C !IN BARREL? CALL RSPEAK(334) C !NO, JOKE. RETURN C 7100 CALL JIGSUP(335) C !OVER FALLS. RETURN C C V77-- SINBAD ET AL. CHASE CYCLOPS, ELSE JOKE. C 8000 IF((HERE.EQ.MCYCL).AND.QHERE(CYCLO,HERE)) GO TO 8100 CALL RSPEAK(336) C !NOT HERE, JOKE. RETURN C 8100 CALL NEWSTA(CYCLO,337,0,0,0) C !CYCLOPS FLEES. CYCLOF=.TRUE. C !SET ALL FLAGS. MAGICF=.TRUE. OFLAG2(CYCLO)=and(OFLAG2(CYCLO), not(FITEBT)) RETURN C C V78-- WELL. OPEN DOOR, ELSE JOKE. C 9000 IF(RIDDLF.OR.(HERE.NE.RIDDL)) GO TO 9100 C !IN RIDDLE ROOM? RIDDLF=.TRUE. C !YES, SOLVED IT. CALL RSPEAK(338) RETURN C 9100 CALL RSPEAK(339) C !WELL, WHAT? RETURN C C V79-- PRAY. IF IN TEMP2, POOF C ! C 10000 IF(HERE.NE.TEMP2) GO TO 10050 C !IN TEMPLE? IF(MOVETO(FORE1,WINNER)) GO TO 10100 C !FORE1 STILL THERE? 10050 CALL RSPEAK(340) C !JOKE. RETURN C 10100 F=RMDESC(3) C !MOVED, DESCRIBE. RETURN C C V80-- TREASURE. IF IN TEMP1, POOF C ! C 11000 IF(HERE.NE.TEMP1) GO TO 11050 C !IN TEMPLE? IF(MOVETO(TREAS,WINNER)) GO TO 10100 C !TREASURE ROOM THERE? 11050 CALL RSPEAK(341) C !NOTHING HAPPENS. RETURN C C V81-- TEMPLE. IF IN TREAS, POOF C ! C 12000 IF(HERE.NE.TREAS) GO TO 12050 C !IN TREASURE? IF(MOVETO(TEMP1,WINNER)) GO TO 10100 C !TEMP1 STILL THERE? 12050 CALL RSPEAK(341) C !NOTHING HAPPENS. RETURN C C V82-- BLAST. USUALLY A JOKE. C 13000 I=342 C !DONT UNDERSTAND. IF(PRSO.EQ.SAFE) I=252 C !JOKE FOR SAFE. CALL RSPEAK(I) RETURN C C V83-- SCORE. PRINT SCORE. C 14000 CALL SCORE(.FALSE.) RETURN C C V84-- QUIT. FINISH OUT THE GAME. C 15000 CALL SCORE(.TRUE.) C !TELLL SCORE. IF(.NOT.YESNO(343,0,0)) RETURN C !ASK FOR Y/N DECISION. #ifdef PDP C close routine moved to exit for pdp version #else CLOSE (DBCH) #endif PDP CALL EXIT C !BYE. C SVERBS, PAGE 4 C C V85-- FOLLOW (USED IN ENDGAME) C 16000 IF(WINNER.NE.AMASTR) RETURN C !TELL MASTER, FOLLOW. CALL RSPEAK(782) CTICK(CEVFOL)=-1 C !STARTS FOLLOWING. RETURN C C V86-- WALK THROUGH C 17000 IF((SCOLRM.EQ.0).OR.((PRSO.NE.SCOL).AND. & ((PRSO.NE.WNORT).OR.(HERE.NE.BKBOX)))) GO TO 17100 SCOLAC=SCOLRM C !WALKED THRU SCOL. PRSO=0 C !FAKE OUT FROMDR. CTICK(CEVSCL)=6 C !START ALARM. CALL RSPEAK(668) C !DISORIENT HIM. F=MOVETO(SCOLRM,WINNER) C !INTO ROOM. F=RMDESC(3) C !DESCRIBE. RETURN C 17100 IF(HERE.NE.SCOLAC) GO TO 17300 C !ON OTHER SIDE OF SCOL? DO 17200 I=1,12,3 C !WALK THRU PROPER WALL? IF((SCOLWL(I).EQ.HERE).AND.(SCOLWL(I+1).EQ.PRSO)) & GO TO 17500 17200 CONTINUE C 17300 IF(and(OFLAG1(PRSO),TAKEBT).NE.0) GO TO 17400 I=669 C !NO, JOKE. IF(PRSO.EQ.SCOL) I=670 C !SPECIAL JOKE FOR SCOL. CALL RSPSUB(I,ODO2) RETURN C 17400 I=671 C !JOKE. IF(OROOM(PRSO).NE.0) I=552+RND(5) C !SPECIAL JOKES IF CARRY. CALL RSPEAK(I) RETURN C 17500 PRSO=SCOLWL(I+2) C !THRU SCOL WALL... DO 17600 I=1,8,2 C !FIND MATCHING ROOM. IF(PRSO.EQ.SCOLDR(I)) SCOLRM=SCOLDR(I+1) 17600 CONTINUE C !DECLARE NEW SCOLRM. CTICK(CEVSCL)=0 C !CANCEL ALARM. CALL RSPEAK(668) C !DISORIENT HIM. F=MOVETO(BKBOX,WINNER) C !BACK IN BOX ROOM. F=RMDESC(3) RETURN C C V87-- RING. A JOKE. C 18000 I=359 C !CANT RING. IF(PRSO.EQ.BELL) I=360 C !DING, DONG. CALL RSPEAK(I) C !JOKE. RETURN C C V88-- BRUSH. JOKE WITH OBSCURE TRAP. C 19000 IF(PRSO.EQ.TEETH) GO TO 19100 C !BRUSH TEETH? CALL RSPEAK(362) C !NO, JOKE. RETURN C 19100 IF(PRSI.NE.0) GO TO 19200 C !WITH SOMETHING? CALL RSPEAK(363) C !NO, JOKE. RETURN C 19200 IF((PRSI.EQ.PUTTY).AND.(OADV(PUTTY).EQ.WINNER)) & GO TO 19300 CALL RSPSUB(364,ODI2) C !NO, JOKE. RETURN C 19300 CALL JIGSUP(365) C !YES, DEAD C ! C ! C ! C ! C ! RETURN C SVERBS, PAGE 5 C C V89-- DIG. UNLESS SHOVEL, A JOKE. C 20000 IF(PRSO.EQ.SHOVE) RETURN C !SHOVEL? I=392 C !ASSUME TOOL. IF(and(OFLAG1(PRSO),TOOLBT).EQ.0) I=393 CALL RSPSUB(I,ODO2) RETURN C C V90-- TIME. PRINT OUT DURATION OF GAME. C #ifdef PDP C no duration time available for pdp version (removed C to make things fit) 21000 TELFLG=.TRUE. RETURN #else 21000 CALL GTTIME(K) C !GET PLAY TIME. I=K/60 J=MOD(K,60) C #ifdef NOCC IF(I.EQ.0.AND.J.EQ.1) WRITE(OUTCH,21010) J IF(I.EQ.0.AND.J.NE.1) WRITE(OUTCH,21011) J IF(I.EQ.1.AND.J.EQ.1) WRITE(OUTCH,21012) I,J IF(I.EQ.1.AND.J.NE.1) WRITE(OUTCH,21013) I,J IF(I.GE.2.AND.J.EQ.1) WRITE(OUTCH,21014) I,J IF(I.GE.2.AND.J.NE.1) WRITE(OUTCH,21015) I,J TELFLG=.TRUE. RETURN C 21010 FORMAT('You have been playing Dungeon for ',I2,' minute.') 21011 FORMAT('You have been playing Dungeon for ',I2,' minutes.') 21012 FORMAT('You have been playing Dungeon for ',I3,' hour and ', & I2,' minute.') 21013 FORMAT('You have been playing Dungeon for ',I3,' hour and ', & I2,' minutes.') 21014 FORMAT('You have been playing Dungeon for ',I3,' hours and ', & I2,' minute.') 21015 FORMAT('You have been playing Dungeon for ',I3,' hours and ', & I2,' minutes.') #else NOCC WRITE(OUTCH,21010) IF(I.NE.0) WRITE(OUTCH,21011) I IF(I.GE.2) WRITE(OUTCH,21012) IF(I.EQ.1) WRITE(OUTCH,21013) IF(J.EQ.1) WRITE(OUTCH,21014) J IF(J.NE.1) WRITE(OUTCH,21015) J TELFLG=.TRUE. RETURN C 21010 FORMAT(' You have been playing Dungeon for ',$) 21011 FORMAT('+',I3,' hour',$) 21012 FORMAT('+s and ',$) 21013 FORMAT('+ and ',$) 21014 FORMAT('+',I2,' minute.') 21015 FORMAT('+',I2,' minutes.') #endif NOCC #endif PDP C C V91-- LEAP. USUALLY A JOKE, WITH A CATCH. C 22000 IF(PRSO.EQ.0) GO TO 22200 C !OVER SOMETHING? IF(QHERE(PRSO,HERE)) GO TO 22100 C !HERE? CALL RSPEAK(447) C !NO, JOKE. RETURN C 22100 IF(and(OFLAG2(PRSO),VILLBT).EQ.0) GO TO 22300 CALL RSPSUB(448,ODO2) C !CANT JUMP VILLAIN. RETURN C 22200 IF(.NOT.FINDXT(XDOWN,HERE)) GO TO 22300 C !DOWN EXIT? IF((XTYPE.EQ.XNO).OR.((XTYPE.EQ.XCOND).AND. & .NOT.FLAGS(XFLAG))) GO TO 22400 22300 CALL RSPEAK(314+RND(5)) C !WHEEEE C ! RETURN C 22400 CALL JIGSUP(449+RND(4)) C !FATAL LEAP. RETURN C SVERBS, PAGE 6 C C V92-- LOCK. C 23000 IF((PRSO.EQ.GRATE).AND.(HERE.EQ.MGRAT)) & GO TO 23200 23100 CALL RSPEAK(464) C !NOT LOCK GRATE. RETURN C 23200 GRUNLF=.FALSE. C !GRATE NOW LOCKED. CALL RSPEAK(214) TRAVEL(REXIT(HERE)+1)=214 C !CHANGE EXIT STATUS. RETURN C C V93-- UNLOCK C 24000 IF((PRSO.NE.GRATE).OR.(HERE.NE.MGRAT)) & GO TO 23100 IF(PRSI.EQ.KEYS) GO TO 24200 C !GOT KEYS? CALL RSPSUB(465,ODI2) C !NO, JOKE. RETURN C 24200 GRUNLF=.TRUE. C !UNLOCK GRATE. CALL RSPEAK(217) TRAVEL(REXIT(HERE)+1)=217 C !CHANGE EXIT STATUS. RETURN C C V94-- DIAGNOSE. C 25000 I=FIGHTS(WINNER,.FALSE.) C !GET FIGHTS STRENGTH. J=ASTREN(WINNER) C !GET HEALTH. K=MIN0(I+J,4) C !GET STATE. IF(.NOT.CFLAG(CEVCUR)) J=0 C !IF NO WOUNDS. L=MIN0(4,IABS(J)) C !SCALE. CALL RSPEAK(473+L) C !DESCRIBE HEALTH. I=(30*(-J-1))+CTICK(CEVCUR) C !COMPUTE WAIT. C #ifdef PDP if(J .ne. 0) call cured(I) #else IF(J.NE.0) WRITE(OUTCH,25100) I #ifdef NOCC 25100 FORMAT('You will be cured after ',I3,' moves.') #else NOCC 25100 FORMAT(' You will be cured after ',I3,' moves.') #endif NOCC #endif PDP C CALL RSPEAK(478+K) C !HOW MUCH MORE? IF(DEATHS.NE.0) CALL RSPEAK(482+DEATHS) C !HOW MANY DEATHS? RETURN C SVERBS, PAGE 7 C C V95-- INCANT C 26000 DO 26100 I=1,6 C !SET UP PARSE. PP1(I)=' ' PP2(I)=' ' 26100 CONTINUE WP=1 C !WORD POINTER. CP=1 C !CHAR POINTER. IF(PRSCON.LE.1) GO TO 26300 DO 26200 I=PRSCON,INLNT C !PARSE INPUT IF(INBUF(I).EQ.',') GO TO 26300 C !END OF PHRASE? IF(INBUF(I).NE.' ') GO TO 26150 C !SPACE? IF(CP.NE.1) WP=WP+1 CP=1 GO TO 26200 26150 IF(WP.EQ.1) PP1(CP)=INBUF(I) C !STUFF INTO HOLDER. IF(WP.EQ.2) PP2(CP)=INBUF(I) CP=MIN0(CP+1,6) 26200 CONTINUE C 26300 PRSCON=1 C !KILL REST OF LINE. IF(PP1(1).NE.' ') GO TO 26400 C !ANY INPUT? CALL RSPEAK(856) C !NO, HO HUM. RETURN C 26400 CALL ENCRYP(PP1,CH) C !COMPUTE RESPONSE. IF(PP2(1).NE.' ') GO TO 26600 C !TWO PHRASES? C IF(SPELLF) GO TO 26550 C !HE'S TRYING TO LEARN. IF(and(RFLAG(TSTRS),RSEEN).EQ.0) GO TO 26575 SPELLF=.TRUE. C !TELL HIM. TELFLG=.TRUE. #ifdef PDP call voice(PP1,CH) #else WRITE(OUTCH,26510) PP1,CH #ifdef NOCC 26510 FORMAT('A hollow voice replies: "',6A1,1X,6A1,'".') #else NOCC 26510 FORMAT(' A hollow voice replies: "',6A1,1X,6A1,'".') #endif NOCC #endif PDP C RETURN C 26550 CALL RSPEAK(857) C !HE'S GOT ONE ALREADY. RETURN C 26575 CALL RSPEAK(858) C !HE'S NOT IN ENDGAME. RETURN C 26600 IF(and(RFLAG(TSTRS),RSEEN).NE.0) GO TO 26800 DO 26700 I=1,6 IF(PP2(I).NE.CH(I)) GO TO 26575 C !WRONG. 26700 CONTINUE SPELLF=.TRUE. C !IT WORKS. CALL RSPEAK(859) CTICK(CEVSTE)=1 C !FORCE START. RETURN C 26800 CALL RSPEAK(855) C !TOO LATE. RETURN C SVERBS, PAGE 8 C C V96-- ANSWER C 27000 IF((PRSCON.GT.1).AND. & (HERE.EQ.FDOOR).AND.INQSTF) & GO TO 27100 CALL RSPEAK(799) C !NO ONE LISTENS. PRSCON=1 RETURN C 27100 K=1 C !POINTER INTO ANSSTR. DO 27300 J=1,28,2 C !CHECK ANSWERS. NEWK=K+ANSWER(J+1) C !COMPUTE NEXT K. IF(QUESNO.NE.ANSWER(J)) GO TO 27300 C !ONLY CHECK PROPER ANS. I=PRSCON-1 C !SCAN ANSWER. DO 27200 L=K,NEWK-1 27150 I=I+1 C !SKIP INPUT BLANKS. IF(I.GT.INLNT) GO TO 27300 C !END OF INPUT? LOSE. IF(INBUF(I).EQ.' ') GO TO 27150 IF(INBUF(I).NE.ANSSTR(L)) GO TO 27300 27200 CONTINUE GO TO 27500 C !RIGHT ANSWER. 27300 K=NEWK C PRSCON=1 C !KILL REST OF LINE. NQATT=NQATT+1 C !WRONG, CRETIN. IF(NQATT.GE.5) GO TO 27400 C !TOO MANY WRONG? CALL RSPEAK(800+NQATT) C !NO, TRY AGAIN. RETURN C 27400 CALL RSPEAK(826) C !ALL OVER. CFLAG(CEVINQ)=.FALSE. C !LOSE. RETURN C 27500 PRSCON=1 C !KILL REST OF LINE. CORRCT=CORRCT+1 C !GOT IT RIGHT. CALL RSPEAK(800) C !HOORAY. IF(CORRCT.GE.3) GO TO 27600 C !WON TOTALLY? CTICK(CEVINQ)=2 C !NO, START AGAIN. QUESNO=MOD(QUESNO+3,8) NQATT=0 CALL RSPEAK(769) C !ASK NEXT QUESTION. CALL RSPEAK(770+QUESNO) RETURN C 27600 CALL RSPEAK(827) C !QUIZ OVER, CFLAG(CEVINQ)=.FALSE. OFLAG2(QDOOR)=or(OFLAG2(QDOOR),OPENBT) RETURN C END