// parseSentence.js
(function () {
/*global adventurejs A*/
"use strict";
var p = adventurejs.Parser.prototype;
/**
* Parse each word in a sentence.
* @memberOf adventurejs.Parser
* @method adventurejs.Parser#parseSentence
* @TODO Will eventually need to look for "person, do thing"
* or "tell person to do thing"
*/
p.parseSentence = function Parser_parseSentence() {
var this_turn = this.input_history[0];
this.game.log(
"log",
"high",
"parseSentence.js > " + this_turn.input,
"Parser"
);
let last_word_type;
let last_word;
let firstverb;
let count = {
noun: 0,
prep: 0,
verb: 0,
adverb: 0,
adjective: 0,
direction: 0,
exclusion: 0,
unknown: 0,
string: 0,
phrase: 0,
};
for (
let position_in_parsed_input = 0;
position_in_parsed_input < this_turn.parsed_input_array.length;
position_in_parsed_input++
) {
let word = this_turn.parsed_input_array[position_in_parsed_input];
let verb = this.parseVerb(word);
let adverb = this.game.dictionary.getAdverb(word);
let direction = this.game.dictionary.getDirection(word);
let compass_direction =
direction && this.game.dictionary.verbs[word].is_compass_direction;
let spatial_direction =
direction && this.game.dictionary.verbs[word].is_spatial_direction;
let parsed_direction = direction && this.parseNoun(direction);
let preposition = this.game.dictionary.getPreposition(word);
let string = word === "global_string" ? word : false;
let noun =
this.parseNoun(word).matches.all.length > 0 ||
word.indexOf("&") > -1 ||
word.indexOf("=") > -1 ||
"undefined" !== typeof adventurejs[A.propercase(word)];
let exclusion = word.charAt(0) === "-";
let number = !isNaN(Number(word)) ? word : false;
let adjective = this.game.dictionary.getAdjective(word);
let properties = {
word: word,
verb: verb,
direction: direction,
compass_direction: compass_direction,
spatial_direction: spatial_direction,
parsed_direction: parsed_direction,
preposition: preposition,
string: string,
noun: noun,
exclusion: exclusion,
number: number,
adjective: adjective,
};
//this.game.print(
// `F1191 | parseSentence.js | \n<br/> - word/ ${word}\n<br/> - verb/ ${verb}\n<br/> - direction/ ${direction}\n<br/> - preposition/ ${preposition}\n<br/> - adverb/ ${adverb}\n<br/> - number/ ${number}\n<br/> - string/ ${string}\n<br/> - noun/ ${noun}`
//);
if (noun && exclusion) {
// both have & in them, get caught by noun check
// but only exclusion has the leading -
noun = false;
}
// Handle type-of-word ambiguities.
// Any direction can be a verb.
// Check position in sentence:
// - if it's the first word, it's a verb
// - if it's the second word, it's a direction
// Directions that are not verbs can be treated like nouns.
// Later during verification we'll check if direction is a preposition.
if (verb && direction && preposition) {
// this catches 'in' and 'out', which are defined as direction
// verbs in addition to being prepositions
// @TODO 2/4/24 it can be used to catch 'up' and 'down'
// if 'up' and 'down' are added to dictionary.prepositions
// currently evaluating that
if (position_in_parsed_input === 0) {
// almost certainly a verb
direction = false;
preposition = false;
} else if (position_in_parsed_input === 1) {
// could be "go in" - direction and preposition
// could be "look in" or "put in" - prepositions
// treat it like a preposition and let verbs handle it
verb = false;
direction = false;
} else {
// probably preposition
verb = false;
direction = false;
}
}
// not parsing adverbs currently but keep this for future
// if( verb && direction && adverb )
// {
// // this catches 'up' and 'down', which are
// // defined as direction verbs and are also adverbs
// if( position_in_parsed_input === 0 )
// {
// // almost certainly a verb
// direction = false;
// adverb = false;
// noun = false;
// }
// else if ( position_in_parsed_input === 1 || last_word_type === 'verb' )
// {
// // could be "go up" - direction and adverb
// // could be "look up" or "put up" - adverbs
// // treat it like an adverb and let verbs handle it
// verb = false;
// direction = false;
// noun = false;
// }
// else
// {
// // in the case of a phrase like "throw ball up",
// // up would be an adverb
// // in the case of a phrase like "throw ball up the stairs",
// // up would be a preposition
// // at this moment we don't know which, so treat it like a direction
// // which is to say, a noun
// verb = false;
// adverb = false;
// }
// }
if (verb && noun && direction) {
// this catches most directions
if (position_in_parsed_input === 0) {
// almost certainly a verb
direction = false;
noun = false;
} else {
// if it's a verb and a direction, but not an adverb
// or a preposition, treat it as a noun
// as in "go north" or "look north"
direction = false;
verb = false;
}
}
if (verb && noun) {
// consider the verb plug and the noun plug
if (position_in_parsed_input === 0) {
noun = false;
} else {
verb = false;
}
}
if (verb && direction) {
if (position_in_parsed_input === 0) {
direction = false;
} else {
verb = false;
}
}
if (verb && preposition) {
if (position_in_parsed_input === 0) {
preposition = false;
} else {
verb = false;
}
}
/* verb ---------------------------------------- OK */
if (verb) {
this.game.log("log", "high", "parseInput > verb: " + verb, "Parser");
if (count.verb === 0) firstverb = verb;
count.verb++;
this_turn.pushParsedWord({
type: "verb",
word: verb,
properties: properties,
});
last_word_type = "verb";
last_word = word;
continue;
}
/* adverb ---------------------------------------- */
// not parsing adverbs for now but keep this for later
// this block was a git copilot auto-complete and needs to be checked before implementing
// if( adverb )
// {
// this.game.log( "log", "high", "parseInput > adverb: " + adverb, 'Parser' );
// count.adverb++;
// count.phrase++;
// this_turn.pushParsedWord({
// type:'adverb',
// word: adverb,
// properties: properties,
// });
// last_word_type = 'adverb';
// last_word = word;
// continue;
// }
// distinguish directions from nouns,
// but also allow directions to be used as nouns
/* direction ---------------------------------------- */
if (direction) {
this.game.log(
"log",
"high",
"parseInput > direction: " + direction,
"Parser"
);
count.direction++;
count.phrase++;
this_turn.pushParsedWord({
type: "direction",
word: direction,
properties: properties,
});
last_word_type = "direction";
last_word = word;
continue;
}
/* preposition ---------------------------------------- OK */
if (preposition) {
// it's recognized as a preposition
this.game.log(
"log",
"high",
"parseInput > preposition: " + word,
"Parser"
);
count.prep++;
count.phrase++;
// store the typed words in their original order
this_turn.pushParsedWord({
type: "preposition",
word: word,
phrase: count.phrase,
properties: properties,
});
last_word_type = "preposition";
last_word = word;
continue;
}
/* string ---------------------------------------- */
// if( string )
// {
// // it's a string, but we're not handling them that way yet
// this_turn.pushParsedWord( { type:'string',this_turn.parsed_input_array[position_in_parsed_input] } );
// // save it as a string or continue to save it as a noun?
// }
/* noun ---------------------------------------- */
if (noun) {
// Treat it like a noun. We do more checks later to see
// if it's unknown, and if it's not we want to soft prompt
// for "oops"
this.game.log("log", "high", "parseInput > noun: " + word, "Parser");
count.noun++;
this_turn.pushParsedWord({
type: "noun",
word: word,
preposition: null,
properties: properties,
adjective: adjective,
});
last_word_type = "noun";
last_word = word;
continue;
}
/* exclusion ---------------------------------------- */
if (exclusion) {
// it's an exclusionary noun, like "take all but thing"
// the last noun will be the one we want to exclude from
this.game.log(
"log",
"high",
"parseInput > exclude noun: " + word,
"Parser"
);
// remove the leading '-' which has done its job
word = word.slice(1);
if (last_word_type === "noun") {
let l = this_turn.parsed_sentence.length - 1;
this_turn.parsed_sentence[l].exclusion = word;
} else {
// this should not happen
this_turn.pushParsedWord({
type: "exclusion",
word: word,
properties: properties,
});
}
// END BLOCK
last_word_type = "exclusion";
last_word = word;
continue;
}
/* number ---------------------------------------- */
if (number) {
// it's a number
this.game.log("log", "high", "parseInput > number: " + word, "Parser");
count.number++;
count.phrase++;
// store the typed words in their original order
this_turn.pushParsedWord({
type: "number",
word: word,
properties: properties,
});
last_word_type = "number";
last_word = word;
continue;
}
/* adjective ---------------------------------------- */
if (adjective) {
// it's an adjective
this.game.log(
"log",
"high",
"parseInput > adjective: " + word,
"Parser"
);
count.adjective++;
this_turn.pushParsedWord({
type: "adjective",
word: word,
properties: properties,
});
last_word_type = "adjective";
last_word = word;
continue;
}
/* unknown ---------------------------------------- */
// it's unknown
this.game.log("log", "high", "parseInput > unknown: " + word, "Parser");
last_word_type = "unknown";
this_turn.pushParsedWord({
type: "unknown",
word: word,
properties: properties,
});
last_word = word;
} // for position_in_parsed_input loop
return true;
}; // parseSentence
})();