Pre-release
AdventureJS Docs Downloads
Score: 0 Moves: 0
// qualifyParsedNoun.js

(function () {
  /*global adventurejs A*/

  var p = adventurejs.Parser.prototype;

  /**
   * Exclude nouns found by parseNoun that don't meet qualifications for verb found by parseVerb.
   * @memberOf adventurejs.Parser
   * @method adventurejs.Parser#qualifyParsedNoun
   * @param {Object} params
   * @returns {adventurejs.parsedNoun}
   */
  p.qualifyParsedNoun = function Parser_qualifyParsedNoun(params) {
    this.game.log(
      "L1111",
      "log",
      "high",
      "qualifyParsedNoun.js > BEGIN",
      "Parser"
    );
    console.warn("qualifyParsedNoun", { params });
    var input = this.game.getInput();
    var parsedNoun = params.parsedNoun;
    var parsedVerb = params.parsedVerb;
    var nounIndex = params.nounIndex;
    var player = this.game.getPlayer();
    var output_class = "";
    // var roomObjects = this.game.getCurrentRoom().getListableContents();
    // var playerObjects = player.getListableContents();
    var msg = "";
    var prettyverb = this.dictionary.verbs[parsedVerb].prettyname;
    var gerund = this.dictionary.verbs[parsedVerb].gerund;

    console.warn(`qualifyParsedNoun.js > parsedVerb`, parsedVerb);

    var i, index, query, msg;
    var mustBe =
      this.dictionary.verbs[parsedVerb]["phrase" + nounIndex].noun_must_be;

    if (mustBe.known) {
      this.game.log(
        "L1112",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.known receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      let qualified_id, qualified_name, qualified_asset;
      if (1 === parsedNoun.matches.qualified.length) {
        qualified_id = parsedNoun.matches.qualified[0];
      }
      parsedNoun.matches.qualified = this.selectKnown(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1113",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.known eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1056 | qualifyParsedNoun.js | ${parsedVerb} phrase ${nounIndex}.noun.mustBe.known`
        );
        /**
         * Try to get base noun or original player input for this object.
         * Player might have entered a partial name for this.
         * Since player doesn't know this object, if they input
         * a partial name, we might accidentally reveal too
         * much information if we return the full name.
         * ex player asks for "sword" and we return "cursed bronze sword"
         * Now player knows there is a cursed bronze sword.
         */
        if (qualified_id) {
          qualified_asset = this.game.getAsset(qualified_id);
          if (this.game.getInput().replacements[qualified_id]?.source) {
            qualified_name =
              this.game.getInput().replacements[qualified_id].source;
          } else {
            qualified_name = qualified_asset.noun;
          }
        }
        if (qualified_name) {
          msg += `$(We) don't know of any ${qualified_name}. `;
        } else {
          // This response doesn't read well if player has asked for a substance.
          // msg += "$(We) don't know of anything matching that description. ";

          // This response is a little too anonymous.
          // msg += "$(We) don't see any of that here. ";

          // This response is sketchy because player input might have been substituted
          // with a list of possible matches.
          msg += `$(We) don't know of any ${A.deserialize(parsedNoun.input)}. `;
        }
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.present) {
      this.game.log(
        "L1114",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.present receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      let qualified_id, qualified_name, qualified_asset;
      if (1 === parsedNoun.matches.qualified.length) {
        qualified_id = parsedNoun.matches.qualified[0];
      }
      parsedNoun.matches.qualified = this.selectPresent(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1115",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.present eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1067 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.present`
        );
        // try to get base noun or original player input for this object
        if (qualified_id) {
          qualified_asset = this.game.getAsset(qualified_id);
          if (this.game.getInput().replacements[qualified_id]?.source) {
            qualified_name =
              this.game.getInput().replacements[qualified_id].source;
          } else {
            qualified_name = qualified_asset.noun;
          }
        }
        if (qualified_name) {
          msg += `There doesn't appear to be any ${qualified_name} present. `;
        } else {
          msg += `There doesn't appear to be any ${parsedNoun.original_input} present. `;
        }
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.present_if_tangible) {
      this.game.log(
        "L1116",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.present receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      let qualified_id, qualified_name, qualified_asset;
      if (1 === parsedNoun.matches.qualified.length) {
        qualified_id = parsedNoun.matches.qualified[0];
      }

      parsedNoun.matches.qualified = this.selectPresentIfTangible(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1117",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.present_if_tangible eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1596 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.present_if_tangible`
        );
        // try to get base noun or original player input for this object
        if (qualified_id) {
          qualified_asset = this.game.getAsset(qualified_id);
          if (this.game.getInput().replacements[qualified_id]?.source) {
            qualified_name =
              this.game.getInput().replacements[qualified_id].source;
          } else {
            qualified_name = qualified_asset.noun;
          }
        }
        if (qualified_name) {
          msg += `There doesn't appear to be any ${qualified_name} present. `;
        } else {
          msg += `There doesn't appear to be any ${parsedNoun.original_input} present. `;
        }
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.direction) {
      if (false === parsedNoun.matches.direction) {
        this.game.log(
          "L1118",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.direction eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1054 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.direction`
        );
        msg += `It appears that $(we) meant to specify a direction, but that wasn't recognized as such. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.not_direction) {
      if (parsedNoun.matches.direction) {
        this.game.log(
          "L1119",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.not_direction eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1055 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.not_direction`
        );
        msg += `$(We) can't ${prettyverb} a direction. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.not_global) {
      this.game.log(
        "L1120",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.not_global receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectNotGlobal(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1121",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.not_global eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1058 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.not_global`
        );
        msg += `$(We) can't ${input.getInput()}. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.not_scenery) {
      this.game.log(
        "L1122",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.not_scenery receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectNotScenery(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1123",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.not_scenery eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1059 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.not_scenery`
        );
        msg += `$(We) can't ${input.getInput()}. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.not_exit) {
      this.game.log(
        "L1124",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.not_exit receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectNotExit(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1125",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.not_exit eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1060 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.not_exit`
        );
        msg += `$(We) can't ${input.getInput()}. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.intangible) {
      this.game.log(
        "L1126",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.intangible receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectIntangible(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1127",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.intangible eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1061 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.intangible`
        );
        msg += `No intangible "${parsedNoun.original_input}" to ${prettyverb}. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.not_substance) {
      this.game.log(
        "L1128",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.not_substance receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectNotSubstance(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1129",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.not_substance eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1062 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.not_substance`
        );
        msg += `$(We) need to specify a source. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.matter) {
      this.game.log(
        "L1130",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.matter receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectMatter(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1131",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.matter eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1534 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.matter`
        );
        msg += `$(We) can't ${prettyverb} ${parsedNoun.original_input}. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.tangible) {
      this.game.log(
        "L1132",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.tangible receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectTangible(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1133",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.tangible eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1063 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.tangible`
        );
        msg += `$(We) don't see any ${parsedNoun.original_input} to ${prettyverb}. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.dov) {
      this.game.log(
        "L1134",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.dov receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      let qualified_count = parsedNoun.matches.qualified.length;
      let qualified_id, qualified_name, qualified_asset;
      if (1 === qualified_count) {
        qualified_id = parsedNoun.matches.qualified[0];
      }

      parsedNoun.matches.qualified = this.selectDOV(
        parsedNoun.matches.qualified,
        parsedVerb
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1135",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.dov eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1585 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.dov`
        );
        if (qualified_id) {
          qualified_asset = this.game.getAsset(qualified_id);
          qualified_name = `${qualified_asset.definite_article} `;
          if (this.game.getInput().replacements[qualified_id]?.source) {
            qualified_name +=
              this.game.getInput().replacements[qualified_id].source;
          } else {
            qualified_name += qualified_asset.noun;
          }
        }
        if (qualified_name) {
          msg += `$(We) can't ${prettyverb} ${qualified_name}. `;
        } else {
          msg += `$(We) can't ${prettyverb} any ${A.deserialize(
            parsedNoun.input
          )}. `;
        }
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.iov) {
      this.game.log(
        "L1136",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.iov receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      let qualified_count = parsedNoun.matches.qualified.length;
      let qualified_id, qualified_name, qualified_asset;
      if (1 === qualified_count) {
        qualified_id = parsedNoun.matches.qualified[0];
      }

      parsedNoun.matches.qualified = this.selectIOV(
        parsedNoun.matches.qualified,
        parsedVerb
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1137",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.iov eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1057 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.iov`
        );

        let prep = this.game.getInput().getPreposition(nounIndex) || "";
        let dasset;
        let dname = "";
        if (nounIndex > 1) {
          dasset = this.game.getInput().getAsset(1);
          dname =
            dasset.noun ||
            (dasset.singlePluralPairs[0] && dasset.singlePluralPairs[0][0]
              ? dasset.singlePluralPairs[0][0]
              : this.game.getInput().getParsedNoun(1).input);
        }
        qualified_asset = this.game.getAsset(qualified_id);
        qualified_asset = this.game.getAsset(qualified_id);
        qualified_name = `${qualified_asset.definite_article} `;
        if (this.game.getInput().replacements[qualified_id]?.source) {
          qualified_name +=
            this.game.getInput().replacements[qualified_id].source;
        } else {
          qualified_name += qualified_asset.noun;
        }
        // if player entered, for example, "wear jacket over bed"...
        // ...this version returns "You can't wear the jacket over the bed."
        // if (qualified_name) {
        //   msg += `$(We) can't ${prettyverb} ${
        //     this.game.getInput().getAsset(1).definite_article
        //   } ${dname} ${prep} ${qualified_name}. `;
        // } else {
        //   msg += `$(We) can't ${prettyverb} ${
        //     this.game.getInput().getAsset(1).definite_article
        //   } ${dname} ${prep} any ${A.deserialize(parsedNoun.input)}. `;
        // }
        // ...this version returns "You can't use the bed to wear the jacket."
        if (qualified_name) {
          msg += `$(We) can't use ${qualified_name} to ${prettyverb} ${
            this.game.getInput().getAsset(1).definite_article
          } ${dname}. `;
        } else {
          msg += `$(We) can't any ${A.deserialize(
            parsedNoun.input
          )} to ${prettyverb} ${
            this.game.getInput().getAsset(1).definite_article
          } ${dname}. `;
        }

        this.game.print(msg, output_class);
        return false;
      }
    }

    // if(mustBe.tangible_or_substance)
    // {
    //   this.game.log( "log", "high", "qualifyParsedNoun.js > mustBe.tangible_or_substance receives: " + parsedNoun.matches.qualified , 'Parser' );
    //   parsedNoun.matches.qualified = this.selectTangibleOrSubstance( parsedNoun.matches.qualified );
    //   if( !parsedNoun.matches.qualified.length )
    //   {
    //     this.game.log( "log", "high", "qualifyParsedNoun.js > mustBe.tangible_or_substance eliminated remaining assets " , 'Parser' );
    //     this.game.debug(` | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.tangible_or_substance`);
    //     msg += `$(We) don't see any "${parsedNoun.original_input}" $(we) can ${this.dictionary.verbs[ parsedVerb ].prettyname}. `;
    //     if(msg) this.game.print( msg, output_class );
    //     return false;
    //   }
    //   this.game.log( "log", "high", "qualifyParsedNoun.js > tangible_or_substance " + parsedNoun.matches.qualified , 'Parser' );
    // }

    if (mustBe.global_substance) {
      this.game.log(
        "L1138",
        "L1139",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.global_substance receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectGlobalSubstance(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1140",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.global_substance eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1064 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.global_substance`
        );
        msg += `$(We) can't ${prettyverb} that. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.substance) {
      this.game.log(
        "L1141",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.substance receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectSubstance(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1142",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.substance eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1065 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.substance`
        );
        msg += `$(We) can't ${prettyverb} that. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.reservoir) {
      this.game.log(
        "L1143",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.reservoir receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectReservoir(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1144",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.reservoir eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D2099 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.reservoir`
        );
        msg += `$(We) can't ${prettyverb} that. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.reservoir_if_substance) {
      this.game.log(
        "L1145",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.reservoir_if_substance receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      let substance_id, substance;
      if (parsedNoun?.matches?.substance) {
        substance_id = parsedNoun.matches.substance;
        substance = this.game.getAsset(parsedNoun.matches.substance);
      }
      parsedNoun.matches.qualified = this.selectReservoirIfSubstance(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1146",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.reservoir_if_substance eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D2101 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.reservoir_if_substance`
        );

        msg += `$(We) don't see any ${
          substance ? substance.name : ""
        } suitable for ${gerund}. `;

        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.reservoir_or_carried_if_substance) {
      this.game.log(
        "L1147",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.reservoir_or_carried_if_substance receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      let substance_id, substance;
      if (parsedNoun?.matches?.substance) {
        substance_id = parsedNoun.matches.substance;
        substance = this.game.getAsset(parsedNoun.matches.substance);
      }
      parsedNoun.matches.qualified = this.selectReservoirOrCarriedIfSubstance(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1148",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.reservoir_or_carried_if_substance eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D2126 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.reservoir_or_carried_if_substance`
        );

        msg += `$(We) don't see any ${
          substance ? substance.name : ""
        } suitable for ${gerund}. `;

        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.character) {
      this.game.log(
        "L1149",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.character receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      let qualified_id;
      if (1 === parsedNoun.matches.qualified.length)
        qualified_id = parsedNoun.matches.qualified[0];
      parsedNoun.matches.qualified = this.selectCharacter(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1150",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.character eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1066 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.character`
        );

        let prep = this.game.getInput().getPreposition(nounIndex) || "";
        let dobj = "";
        if (nounIndex === 2)
          dobj = this.game.getInput().getAsset(1)?.articlename || "";
        if (qualified_id) {
          msg += `$(We) can't ${prettyverb} ${dobj} ${prep} ${
            this.game.getAsset(qualified_id).articlename
          }. `;
        }
        // otherwise offer generic response
        else {
          msg += `$(We) don't know of anyone named "${parsedNoun.original_input}". `;
        }

        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.player_parent) {
      this.game.log(
        "L1151",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.player_parent receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      let qualified_id;
      if (1 === parsedNoun.matches.qualified.length)
        qualified_id = parsedNoun.matches.qualified[0];
      parsedNoun.matches.qualified = this.selectPlayerParent(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1152",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.player_parent eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1069 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.player_parent`
        );
        // if we'd already narrowed qualified list down to
        // one object we can use its name in the response
        if (qualified_id) {
          msg += `$(We're) not on ${
            this.game.getAsset(qualified_id).articlename
          }. `;
        }
        // otherwise offer generic response
        else {
          msg += `$(We're) not on that. `;
        }
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.not_player_parent) {
      this.game.log(
        "L1153",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.not_player_parent receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectNotPlayerParent(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1154",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.not_player_parent eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1071 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.not_player_parent`
        );
        // if there was one unambiguous reference to parent
        // we can use its name in the response
        if (parsedNoun.matches.unambiguous) {
          msg += `$(We're) already on ${
            this.game.world[parsedNoun.matches.unambiguous].articlename
          }. `;
        }
        // otherwise offer generic response
        else {
          msg += `$(We're) already on that. `;
        }
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.singular) {
      this.game.log(
        "L1155",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.singular receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectSingular(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1156",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.singular eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1073 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.singular`
        );
        msg += `$(We'll) have to do that one at a time. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.in_inventory_if_takeable) {
      this.game.log(
        "L1157",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.in_inventory_if_takeable receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      let qualified_id;
      if (1 === parsedNoun.matches.qualified.length)
        qualified_id = parsedNoun.matches.qualified[0];
      parsedNoun.matches.qualified = this.selectInInventoryIfTakeable(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1158",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.in_inventory_if_takeable eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1074 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.in_inventory_if_takeable`
        );
        if (qualified_id) {
          var object = this.game.world[qualified_id];
          msg += `$(We're) not carrying ${object.articlename}. `;
        } else {
          let it = parsedNoun.original_input;
          msg += `$(We're) not carrying any${
            it === "all" ? "thing" : " " + it
          }. `;
        }

        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.in_inventory) {
      this.game.log(
        "L1159",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.in_inventory receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      let qualified_id;
      if (1 === parsedNoun.matches.qualified.length)
        qualified_id = parsedNoun.matches.qualified[0];
      parsedNoun.matches.qualified = this.selectInInventory(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1160",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.in_inventory eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1075 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.in_inventory`
        );
        if (qualified_id) {
          var object = this.game.world[qualified_id];
          msg += `$(We're) not carrying ${object.articlename}. `;
        } else {
          let it = parsedNoun.original_input;
          msg += `$(We're) not carrying any${
            it === "all" ? "thing" : " " + it
          }. `;
        }

        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.in_hands) {
      this.game.log(
        "L1161",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.in_hands receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectInHands(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1162",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.in_hands eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1076 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.in_hands`
        );
        msg += `$(We're) not holding any ${parsedNoun.original_input}. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.in_hands_unless_reservoir) {
      this.game.log(
        "L1163",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.in_hands_unless_reservoir receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectInHandsUnlessReservoir(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1164",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.in_hands_unless_reservoir eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1448 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.in_hands_unless_reservoir`
        );
        msg += `$(We're) not holding any ${parsedNoun.original_input}. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.not_in_hands) {
      this.game.log(
        "L1165",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.not_in_hands receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectNotInHands(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1166",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.not_in_hands eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1077 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.not_in_hands`
        );
        msg += `$(We're) carrying the ${parsedNoun.original_input}. `;

        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.held) {
      this.game.log(
        "L1167",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.held receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectHeld(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1168",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.held eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1716 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.held`
        );
        msg += `$(We're) not holding any ${parsedNoun.original_input}. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.not_in_inventory) {
      this.game.log(
        "L1169",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.not_in_inventory receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectNotInInventory(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1170",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.not_in_inventory eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1078 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.not_in_inventory`
        );
        msg += `$(We're) carrying the ${parsedNoun.original_input}. `;

        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.worn) {
      this.game.log(
        "L1171",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.worn receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectWorn(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1172",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.worn eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1079 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.worn`
        );
        msg += `$(We're) not wearing any ${parsedNoun.original_input}. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.not_worn) {
      this.game.log(
        "L1173",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.not_worn receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectNotWorn(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1174",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.not_worn eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1080 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.not_worn`
        );
        msg += `$(We're) wearing the ${parsedNoun.original_input}. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if ("all" === parsedNoun.input && mustBe.not_worn_if_all) {
      this.game.log(
        "L1175",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.not_worn_if_all receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectNotWornIfAll(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1176",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.not_worn_if_all eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1081 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.not_worn_if_all`
        );
        msg += `$(We're) not carrying anything. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if ("all" === parsedNoun.input && mustBe.not_nested_inventory_if_all) {
      this.game.log(
        "L1177",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.not_nested_inventory_if_all receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectNotNestedInventoryIfAll(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1178",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.not_nested_inventory_if_all eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1082 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.not_nested_in_inventory_if_all`
        );
        msg += `$(We're) not carrying anything. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.visible) {
      this.game.log(
        "L1179",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.visible receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectVisible(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1180",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.visible eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1083 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.visible`
        );
        msg += `$(We) can't see any ${parsedNoun.original_input}. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.visible_if_tangible) {
      this.game.log(
        "L1181",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.visible_if_tangible receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectVisibleIfTangible(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1182",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.visible_if_tangible eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1610 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.visible`
        );
        msg += `$(We) can't see any ${parsedNoun.original_input}`;
        if (player.isNested()) {
          msg += ` from your position ${player.getPostureGerund()} ${player.getNestPreposition()} ${
            player.getNestAsset().articlename
          }`;
        }
        msg += `. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.reachable) {
      this.game.log(
        "L1183",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.reachable receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectReachable(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1184",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.reachable eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1084 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.reachable`
        );
        msg += `$(We) can't reach the ${parsedNoun.original_input}`;
        if (player.isNested()) {
          msg += ` from your position ${player.getPostureGerund()} ${player.getNestPreposition()} ${
            player.getNestAsset().articlename
          }`;
        } else if (player.posture !== "stand") {
          msg += ` while ${player.getPostureGerund()}`;
          msg += `${player.isOnFloor() ? " on the floor" : ""}`;
        }
        msg += `. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.reachable_if_tangible) {
      this.game.log(
        "L1185",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.reachable_if_tangible receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectReachableIfTangible(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1186",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.reachable_if_tangible eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1176 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.reachable`
        );
        msg += `$(We) can't reach the ${parsedNoun.original_input}`;
        if (player.isNested()) {
          msg += ` from your position ${player.getPostureGerund()} ${player.getNestPreposition()} ${
            player.getNestAsset().articlename
          }`;
        }
        msg += `. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.takeable) {
      this.game.log(
        "L1187",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.takeable receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      let qualified_id, qualified_name, qualified_asset;
      if (1 === parsedNoun.matches.qualified.length) {
        qualified_id = parsedNoun.matches.qualified[0];
      }
      parsedNoun.matches.qualified = this.selectTakeable(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length && "all" === parsedNoun.input) {
        this.game.log(
          "L1188",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.takeable eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1085 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.takeable`
        );
        msg += `There's nothing takeable in reach. `;
        this.game.print(msg, output_class);
        return false;
      }
      if (!parsedNoun.matches.qualified.length) {
        this.game.debug(
          `D1086 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.takeable`
        );
        var plural = false;
        if (parsedNoun.input.split("&").length > 1) {
          plural = true;
        } else if (parsedNoun.isPlural || parsedNoun.isGroup) {
          plural = true;
        }
        msg += `$(We) can't take `;
        if (plural) {
          msg += `them`;
        } else if (qualified_id) {
          qualified_asset = this.game.getAsset(qualified_id);
          qualified_name = `${qualified_asset.definite_article} `;
          if (this.game.getInput().replacements[qualified_id]?.source) {
            qualified_name +=
              this.game.getInput().replacements[qualified_id].source;
          } else {
            qualified_name += qualified_asset.noun;
          }
          msg += qualified_name;
        } else {
          msg += parsedNoun.original_input;
        }
        msg += `. `;

        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.extant) {
      this.game.log(
        "L1189",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.extant receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectExtant(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1190",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.visible eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D1310 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.extant`
        );
        msg += `Was there any ${parsedNoun.original_input}? $(We) can't recall. `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.player) {
      this.game.log(
        "L1191",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.player receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectPlayer(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1192",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.player eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D2109 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.player`
        );
        msg += `$(We) can only do that to $(ourself). `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    if (mustBe.not_player) {
      this.game.log(
        "L1193",
        "log",
        "high",
        "qualifyParsedNoun.js > mustBe.not_player receives: " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.matches.qualified = this.selectNotPlayer(
        parsedNoun.matches.qualified
      );
      if (!parsedNoun.matches.qualified.length) {
        this.game.log(
          "L1194",
          "log",
          "high",
          "qualifyParsedNoun.js > mustBe.not_player eliminated remaining assets ",
          "Parser"
        );
        this.game.debug(
          `D2110 | qualifyParsedNoun.js | ${parsedVerb} phrase${nounIndex}.noun.mustBe.not_player`
        );
        msg += `$(We) can't do that to $(ourself). `;
        this.game.print(msg, output_class);
        return false;
      }
    }

    // check qualified for exact match(es)
    if (1 < parsedNoun.matches.qualified.length) {
      var exactMatches = [];
      for (i = 0; i < parsedNoun.matches.qualified.length; i++) {
        var object = this.game.getAsset(parsedNoun.matches.qualified[i]);
        if (object.id === parsedNoun.serialized_input) {
          exactMatches.push(object.id);
          continue;
        }
        for (var s = 0; s < object.synonyms.length; s++) {
          if (object.synonyms[s] === parsedNoun.serialized_input) {
            exactMatches.push(object.id);
            continue;
          }
        }
      }
      // copy exactMatches back to qualified
      if (0 < exactMatches.length) {
        // parsedNoun.matches.qualified = exactMatches.splice(0);
        // @TODO 1/4/25 this was revealed to be a point of failure
        // ex: I have "window" and "playground_window" and searching
        // for "window" fails to return valid "playground_window"
      }
    }

    // can we narrow by class?
    var ajsclass = A.propercase(parsedNoun.serialized_input.toLowerCase());
    if (1 < parsedNoun.matches.qualified.length && adventurejs[ajsclass]) {
      var classMatches = [];
      for (i = 0; i < parsedNoun.matches.qualified.length; i++) {
        var object = this.game.getAsset(parsedNoun.matches.qualified[i]);
        if (object instanceof adventurejs[ajsclass]) {
          classMatches.push(object.id);
          continue;
        }
      }
      // copy classMatches back to qualified
      if (0 < classMatches.length) {
        parsedNoun.matches.qualified = classMatches.splice(0);
      }
    }

    /**
     *
     * If there are multiple qualified, check them all
     * for verb_hooks methods.
     *
     * If present, move them to the end of the queue.
     * This is to minimize the chances of awkward output on
     * interacting with multiple objects, for example:
     * "You take x. You take y. Oh no, taking y
     * transported you to the nether realms! You take z."
     *
     * It's possible that an author might want control over
     * this, so for instance picking up an explosive
     * preceeds all other things. Author can swap order.
     *
     * Set with:
     * game.settings.move_verb_hooks_to_end_of_queue
     */
    // @TODO this block no longer works since moving verb_hooks into verb subscriptions
    // if( 1 < parsedNoun.matches.qualified.length
    // && this.game.settings.enqueue_assets_with_verb_hooks.order === 1 )
    // {
    //   for( i = parsedNoun.matches.qualified.length - 2; i > -1; i--)
    //   {
    //     var asset = this.game.getAsset( parsedNoun.matches.qualified[i] );
    //     if( asset && asset.verb_hooks[parsedVerb] )
    //     {
    //       parsedNoun.matches.qualified = parsedNoun.matches.qualified.concat(
    //         parsedNoun.matches.qualified.splice( i, 1 )
    //       );
    //     }
    //   }
    // }

    /**
     * Samesies, but moves objects with custom verb responses to
     * beginning of queue.
     *
     * Set with:
     * game.settings.move_verb_hooks_to_end_of_queue
     */
    // @TODO this block no longer works since moving verb_hooks into verb subscriptions
    // if( 1 < parsedNoun.matches.qualified.length
    // && this.game.settings.enqueue_assets_with_verb_hooks.order === -1 )
    // {
    //   for( i = parsedNoun.matches.qualified.length - 2; i > -1; i--)
    //   {
    //     var asset = this.game.getAsset( parsedNoun.matches.qualified[i] );
    //     if( asset && asset.verb_hooks[parsedVerb] )
    //     {
    //       parsedNoun.matches.qualified = parsedNoun.matches.qualified.concat(
    //         parsedNoun.matches.qualified.splice( i, 1 )
    //       );
    //     }
    //   }
    // }

    /**
     * If there's only one qualified match, we make a shortcut
     * reference at parsedNoun.qualified_object_id, mostly for use with
     * singular verbs.
     */
    parsedNoun.matches.qualifiedIndex = 0;
    if (1 === parsedNoun.matches.qualified.length) {
      this.game.log(
        "L1195",
        "log",
        "high",
        "qualifyParsedNoun.js > found singular qualified " +
          parsedNoun.matches.qualified,
        "Parser"
      );
      parsedNoun.qualified_object_id = parsedNoun.matches.qualified[0];
    }

    this.game.log(
      "L1196",
      "log",
      "high",
      "qualifyParsedNoun.js > END return " + parsedNoun.matches.qualified,
      "Parser"
    );
    return parsedNoun;
  };
})();