diff --git a/src/lib/src/parsing/parse-blocks.ts b/src/lib/src/parsing/parse-blocks.ts index efe2423..8a643c9 100644 --- a/src/lib/src/parsing/parse-blocks.ts +++ b/src/lib/src/parsing/parse-blocks.ts @@ -8,7 +8,13 @@ import { parseNP } from "./parse-np"; import { parsePastPart } from "./parse-past-part"; import { parsePH } from "./parse-ph"; import { parseVerb } from "./parse-verb"; -import { bindParseResult, returnParseResult } from "./utils"; +import { + bindParseResult, + returnParseResult, + isParsedVBE, + isParsedVBP, + startsVerbSection, +} from "./utils"; export function parseBlocks( tokens: Readonly, @@ -22,19 +28,13 @@ export function parseBlocks( if (tokens.length === 0) { return returnParseResult(tokens, { blocks, kids }); } - const inPreVerbSection = blocks.every( - (b) => - b.type !== "PH" && - b.type !== "VB" && - b.type !== "welded" && - b.type !== "negative" - ); + const inVerbSection = blocks.some(startsVerbSection); const prevPh: T.ParsedPH | undefined = blocks.find( (b): b is T.ParsedPH => b.type === "PH" ); const allBlocks: T.ParseResult[] = [ - ...(inPreVerbSection + ...(!inVerbSection ? [...parseAP(tokens, lookup), ...parseNP(tokens, lookup)] : []), // ensure at most one of each PH, VBE, VBP @@ -108,17 +108,3 @@ function getPhFromVerb(v: T.VerbEntry, base: "root" | "stem"): string { } return "و"; } - -function isParsedVBP(b: T.ParsedBlock): boolean { - return ( - (b.type === "VB" || b.type === "welded") && - (b.info.type === "ability" || b.info.type === "ppart") - ); -} - -function isParsedVBE(b: T.ParsedBlock): boolean { - return ( - (b.type === "VB" || b.type === "welded") && - (b.info.type === "verb" || b.info.type === "equative") - ); -} diff --git a/src/lib/src/parsing/parse-phrase.ts b/src/lib/src/parsing/parse-phrase.ts index 36b7489..1266572 100644 --- a/src/lib/src/parsing/parse-phrase.ts +++ b/src/lib/src/parsing/parse-phrase.ts @@ -22,9 +22,7 @@ export function parsePhrase(s: T.Token[]): { ...parseVP(s, lookup), ]; - console.log({ res }); const success = res.filter((x) => !x.tokens.length).map((x) => x.body); - console.log({ success }); return { success, errors: [ diff --git a/src/lib/src/parsing/parse-vp.ts b/src/lib/src/parsing/parse-vp.ts index 41bc64c..9358891 100644 --- a/src/lib/src/parsing/parse-vp.ts +++ b/src/lib/src/parsing/parse-vp.ts @@ -1,5 +1,14 @@ import * as T from "../../../types"; -import { bindParseResult, returnParseResult } from "./utils"; +import { + bindParseResult, + isNeg, + isNonOoPh, + isPH, + isParsedVBE, + isParsedVBP, + returnParseResult, + startsVerbSection, +} from "./utils"; import { makeObjectSelectionComplete, makeSubjectSelectionComplete, @@ -14,7 +23,7 @@ import { makePronounSelection } from "../phrase-building/make-selections"; import { isFirstOrSecondPersPronoun } from "../phrase-building/render-vp"; import { LookupFunction } from "./lookup"; import { personToGenNum } from "../misc-helpers"; -import { equals } from "rambda"; +import { equals, zip } from "rambda"; // to hide equatives type-doubling issue // TODO: word query for kawul/kedul/stat/dyn @@ -80,20 +89,13 @@ function getTenses( const negative = negIndex !== -1; const phIndex = blocks.findIndex((x) => x.type === "PH"); const vbeIndex = blocks.findIndex((x) => x.type === "VB"); + const verbSection = blocks.findIndex(startsVerbSection); const ph = phIndex !== -1 ? (blocks[phIndex] as T.ParsedPH) : undefined; const verb = vbeIndex !== -1 ? (blocks[vbeIndex] as T.ParsedVBE) : undefined; if (!verb || verb.type !== "VB") { return []; } - if ( - !negativeInPlace({ - neg: negIndex, - v: vbeIndex, - phIndex: phIndex, - ph, - kids: hasKids, - }) - ) { + if (!verbSectionOK(blocks.slice(verbSection))) { return []; } if (verb.info.type === "verb") { @@ -895,41 +897,25 @@ function getTenseFromRootsStems( } } -// possible neg setups -// NEG VBE -// PH NEG VBE -// NEG (Non-و PH) VBE - -// (PH) NEG VBE VBP -// (PH) VBP NEG VBE -// (with non-و negative things?) - -function negativeInPlace({ - neg, - v, - phIndex, - ph, - kids, -}: { - neg: number; - v: number; - phIndex: number; - ph: T.ParsedPH | undefined; - kids: boolean; -}): boolean { - if (neg === -1) { - return true; - } - if (ph) { - if (!kids && !["و", "وا"].includes(ph.s) && neg === phIndex - 1) { - return true; - } - return neg === phIndex + 1; - } - if (neg < v - 1) { - return false; - } - return true; +function verbSectionOK(blocks: T.ParsedBlock[]): boolean { + const possibilites = [ + [isParsedVBE], + [isNeg, isParsedVBE], + [isPH, isParsedVBE], + [isPH, isNeg, isParsedVBE], + [isNeg, isNonOoPh, isParsedVBE], + [isParsedVBP, isParsedVBE], + [isNeg, isParsedVBE, isParsedVBP], + [isParsedVBP, isNeg, isParsedVBE], + // could be more clever with optional isPH here + [isPH, isParsedVBP, isParsedVBE], + [isPH, isNeg, isParsedVBE, isParsedVBP], + [isPH, isParsedVBP, isNeg, isParsedVBE], + ]; + return possibilites.some( + (ps) => + ps.length === blocks.length && zip(ps, blocks).every(([p, b]) => p(b)) + ); } function pronounConflictInBlocks(blocks: T.VPSBlockComplete[]): boolean { diff --git a/src/lib/src/parsing/utils.ts b/src/lib/src/parsing/utils.ts index bc63448..0af788c 100644 --- a/src/lib/src/parsing/utils.ts +++ b/src/lib/src/parsing/utils.ts @@ -133,3 +133,42 @@ export function getPeople( ? people.filter((p) => p > 5) : people; } + +export function isPH(b: T.ParsedBlock): b is T.ParsedPH { + return b.type === "PH"; +} + +export function isNeg(b: T.ParsedBlock): b is T.NegativeBlock { + return b.type === "negative"; +} + +export function isOoPh(b: T.ParsedBlock): b is T.ParsedPH { + return b.type === "PH" && ["و", "وا"].includes(b.s); +} + +export function isNonOoPh(b: T.ParsedBlock): b is T.ParsedPH { + return b.type === "PH" && !["و", "وا"].includes(b.s); +} + +export function isParsedVBP(b: T.ParsedBlock): b is T.ParsedVBP { + return ( + (b.type === "VB" || b.type === "welded") && + (b.info.type === "ability" || b.info.type === "ppart") + ); +} + +export function isParsedVBE(b: T.ParsedBlock): b is T.ParsedVBE { + return ( + (b.type === "VB" || b.type === "welded") && + (b.info.type === "verb" || b.info.type === "equative") + ); +} + +export function startsVerbSection(b: T.ParsedBlock): boolean { + return ( + b.type === "PH" || + b.type === "VB" || + b.type === "welded" || + b.type === "negative" + ); +}