Completely wire vocab words in YAML to the code.
This massive patch: * Finishes working all the vocab words into YAML structures. * Adds vocab ID generator functions. * Redoes the input-getting system, removing the need for GETIN(), GETTXT(), etc. * Changes advent<->ascii mapping to avoid the special 'shift' character. * Works around some bad behavior in the dragon attack logic. * Handles the reservoir magic word without changing the database contents.
This commit is contained in:
parent
9d918edeaa
commit
50435465a6
11 changed files with 460 additions and 52 deletions
58
main.c
58
main.c
|
@ -20,6 +20,7 @@
|
|||
#include <getopt.h>
|
||||
#include <signal.h>
|
||||
#include <time.h>
|
||||
#include <string.h>
|
||||
#include "advent.h"
|
||||
#include "database.h"
|
||||
#include "linenoise/linenoise.h"
|
||||
|
@ -61,7 +62,7 @@ static void sig_handler(int signo)
|
|||
* Revived 2017 as Open Adventure.
|
||||
*/
|
||||
|
||||
static bool do_command(FILE *);
|
||||
static bool do_command(void);
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
|
@ -136,7 +137,7 @@ int main(int argc, char *argv[])
|
|||
initialise();
|
||||
|
||||
/* Start-up, dwarf stuff */
|
||||
game.zzword = rndvoc(3, 0);
|
||||
make_zzword(game.zzword);
|
||||
game.newloc = LOC_START;
|
||||
game.loc = LOC_START;
|
||||
game.limit = GAMELIMIT;
|
||||
|
@ -153,7 +154,7 @@ int main(int argc, char *argv[])
|
|||
|
||||
/* interpret commands until EOF or interrupt */
|
||||
for (;;) {
|
||||
if (!do_command(stdin))
|
||||
if (!do_command())
|
||||
break;
|
||||
}
|
||||
/* show score and exit */
|
||||
|
@ -170,7 +171,7 @@ static bool fallback_handler(char *buf)
|
|||
// autogenerated, so don't charge user time for it.
|
||||
--game.turns;
|
||||
// here we reconfigure any global game state that uses random numbers
|
||||
game.zzword = rndvoc(3, 0);
|
||||
make_zzword(game.zzword);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
|
@ -931,7 +932,7 @@ static void listobjects(void)
|
|||
}
|
||||
}
|
||||
|
||||
static bool do_command(FILE *cmdin)
|
||||
static bool do_command()
|
||||
/* Get and execute a command */
|
||||
{
|
||||
long V1, V2;
|
||||
|
@ -1024,8 +1025,25 @@ L2600:
|
|||
game.knfloc = 0;
|
||||
|
||||
/* This is where we get a new command from the user */
|
||||
if (!GETIN(cmdin, &command.wd1, &command.wd1x, &command.wd2, &command.wd2x))
|
||||
return false;
|
||||
char* input;
|
||||
for (;;) {
|
||||
input = get_input();
|
||||
if (input == NULL)
|
||||
return(false);
|
||||
if (word_count(input) > 2)
|
||||
{
|
||||
rspeak(TWO_WORDS);
|
||||
continue;
|
||||
}
|
||||
if (strcmp(input, "") != 0)
|
||||
break;
|
||||
}
|
||||
long tokens[4];
|
||||
tokenize(input, tokens);
|
||||
command.wd1 = tokens[0];
|
||||
command.wd1x = tokens[1];
|
||||
command.wd2 = tokens[2];
|
||||
command.wd2x = tokens[3];
|
||||
|
||||
/* Every input, check "game.foobar" flag. If zero, nothing's
|
||||
* going on. If pos, make neg. If neg, he skipped a word,
|
||||
|
@ -1057,8 +1075,12 @@ L2607:
|
|||
} else
|
||||
lampcheck();
|
||||
|
||||
V1 = vocab(command.wd1, -1);
|
||||
V2 = vocab(command.wd2, -1);
|
||||
char word1[6];
|
||||
char word2[6];
|
||||
packed_to_token(command.wd1, word1);
|
||||
packed_to_token(command.wd2, word2);
|
||||
V1 = get_vocab_id(word1);
|
||||
V2 = get_vocab_id(word2);
|
||||
if (V1 == ENTER && (V2 == STREAM || V2 == 1000 + WATER)) {
|
||||
if (LIQLOC(game.loc) == WATER) {
|
||||
rspeak(FEET_WET);
|
||||
|
@ -1076,26 +1098,27 @@ L2607:
|
|||
if (!((V1 != 1000 + WATER && V1 != 1000 + OIL) ||
|
||||
(V2 != 1000 + PLANT && V2 != 1000 + DOOR))) {
|
||||
if (AT(V2 - 1000))
|
||||
command.wd2 = MAKEWD(WORD_POUR);
|
||||
command.wd2 = token_to_packed("POUR");
|
||||
}
|
||||
if (V1 == 1000 + CAGE && V2 == 1000 + BIRD && HERE(CAGE) && HERE(BIRD))
|
||||
command.wd1 = MAKEWD(WORD_CATCH);
|
||||
command.wd1 = token_to_packed("CATCH");
|
||||
}
|
||||
L2620:
|
||||
if (wordeq(command.wd1, MAKEWD(WORD_WEST))) {
|
||||
if (wordeq(command.wd1, token_to_packed("WEST"))) {
|
||||
++game.iwest;
|
||||
if (game.iwest == 10)
|
||||
rspeak(W_IS_WEST);
|
||||
}
|
||||
if (wordeq(command.wd1, MAKEWD(WORD_GO)) && !wordempty(command.wd2)) {
|
||||
if (wordeq(command.wd1, token_to_packed("GO")) && !wordempty(command.wd2)) {
|
||||
if (++igo == 10)
|
||||
rspeak(GO_UNNEEDED);
|
||||
}
|
||||
Lookup:
|
||||
defn = vocab(command.wd1, -1);
|
||||
packed_to_token(command.wd1, word1);
|
||||
defn = get_vocab_id(word1);
|
||||
if (defn == -1) {
|
||||
/* Gee, I don't understand. */
|
||||
if (fallback_handler(rawbuf))
|
||||
if (fallback_handler(input))
|
||||
continue;
|
||||
rspeak(DONT_KNOW, command.wd1, command.wd1x);
|
||||
goto L2600;
|
||||
|
@ -1116,14 +1139,14 @@ Lookup:
|
|||
command.verb = kmod;
|
||||
break;
|
||||
case 3:
|
||||
rspeak(kmod);
|
||||
rspeak(specials[kmod].message);
|
||||
goto L2012;
|
||||
default:
|
||||
BUG(VOCABULARY_TYPE_N_OVER_1000_NOT_BETWEEN_0_AND_3); // LCOV_EXCL_LINE
|
||||
}
|
||||
|
||||
Laction:
|
||||
switch (action(cmdin, &command)) {
|
||||
switch (action(&command)) {
|
||||
case GO_TERMINATE:
|
||||
return true;
|
||||
case GO_MOVE:
|
||||
|
@ -1158,6 +1181,7 @@ Laction:
|
|||
default:
|
||||
BUG(ACTION_RETURNED_PHASE_CODE_BEYOND_END_OF_SWITCH); // LCOV_EXCL_LINE
|
||||
}
|
||||
linenoiseFree(input);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue