FULLY SUPPORT GROUPS FOIASHFOIASHFOIASFDH :D
This commit is contained in:
parent
ad0aef6c94
commit
d989e9d473
|
@ -6,6 +6,7 @@ type RollType = '' | 'roll20' | 'fate' | 'cwod' | 'ova';
|
||||||
// RollSet is used to preserve all information about a calculated roll
|
// RollSet is used to preserve all information about a calculated roll
|
||||||
export interface RollSet {
|
export interface RollSet {
|
||||||
type: RollType;
|
type: RollType;
|
||||||
|
rollGrpIdx?: number;
|
||||||
origIdx: number;
|
origIdx: number;
|
||||||
roll: number;
|
roll: number;
|
||||||
size: number;
|
size: number;
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
import { log, LogTypes as LT } from '@Log4Deno';
|
import { log, LogTypes as LT } from '@Log4Deno';
|
||||||
|
|
||||||
import { FormattedRoll, RollModifiers } from 'artigen/dice/dice.d.ts';
|
import { ExecutedRoll, FormattedRoll, RollModifiers } from 'artigen/dice/dice.d.ts';
|
||||||
import { executeRoll } from 'artigen/dice/executeRoll.ts';
|
|
||||||
|
|
||||||
import { loopCountCheck } from 'artigen/managers/loopManager.ts';
|
import { loopCountCheck } from 'artigen/managers/loopManager.ts';
|
||||||
|
|
||||||
|
@ -9,23 +8,21 @@ import { rollCounter } from 'artigen/utils/counter.ts';
|
||||||
import { loggingEnabled } from 'artigen/utils/logFlag.ts';
|
import { loggingEnabled } from 'artigen/utils/logFlag.ts';
|
||||||
import { createRollDistMap } from 'artigen/utils/rollDist.ts';
|
import { createRollDistMap } from 'artigen/utils/rollDist.ts';
|
||||||
|
|
||||||
// generateFormattedRoll(rollConf, modifiers) returns one SolvedStep
|
// generateFormattedRoll(executedRoll, modifiers) returns one SolvedStep
|
||||||
// generateFormattedRoll handles creating and formatting the completed rolls into the SolvedStep format
|
// generateFormattedRoll handles creating and formatting the completed rolls into the SolvedStep format
|
||||||
export const generateFormattedRoll = (rollConf: string, modifiers: RollModifiers): FormattedRoll => {
|
export const formatRoll = (executedRoll: ExecutedRoll, modifiers: RollModifiers): FormattedRoll => {
|
||||||
let tempTotal = 0;
|
let tempTotal = 0;
|
||||||
let tempDetails = '[';
|
let tempDetails = '[';
|
||||||
let tempCrit = false;
|
let tempCrit = false;
|
||||||
let tempFail = false;
|
let tempFail = false;
|
||||||
let tempComplex = false;
|
let tempComplex = false;
|
||||||
|
|
||||||
// Generate the roll, passing flags thru
|
|
||||||
const executedRoll = executeRoll(rollConf, modifiers);
|
|
||||||
|
|
||||||
// Loop thru all parts of the roll to document everything that was done to create the total roll
|
// Loop thru all parts of the roll to document everything that was done to create the total roll
|
||||||
|
loggingEnabled && log(LT.LOG, `Formatting roll ${JSON.stringify(executedRoll)}`);
|
||||||
executedRoll.rollSet.forEach((e) => {
|
executedRoll.rollSet.forEach((e) => {
|
||||||
loopCountCheck();
|
loopCountCheck();
|
||||||
|
|
||||||
loggingEnabled && log(LT.LOG, `Formatting roll ${rollConf} | ${JSON.stringify(e)}`);
|
loggingEnabled && log(LT.LOG, `At ${JSON.stringify(e)}`);
|
||||||
let preFormat = '';
|
let preFormat = '';
|
||||||
let postFormat = '';
|
let postFormat = '';
|
||||||
|
|
||||||
|
|
|
@ -208,26 +208,23 @@ export const handleGroup = (
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
loggingEnabled && log(LT.LOG, `In single-mode ${JSON.stringify(commaParts)} ${groupModifiers} ${JSON.stringify(groupConf)}`);
|
loggingEnabled && log(LT.LOG, `In single-mode ${JSON.stringify(commaParts)} ${groupModifiers} ${JSON.stringify(groupConf)}`);
|
||||||
if (groupModifiers.trim()) {
|
const [tempData, tempCounts, tempDists] = tokenizeMath(
|
||||||
// Handle special case where the group modifiers are applied across the dice rolled
|
commaParts[0],
|
||||||
// ex from roll20 docs: {4d6+3d8}k4 - Roll 4 d6's and 3 d8's, out of those 7 dice the highest 4 are kept and summed up.
|
modifiers,
|
||||||
// TODO AAAAAAAAAAAAAAAAA
|
previousResults,
|
||||||
retData = <ReturnData> {};
|
prevGrpReturnData,
|
||||||
} else {
|
groupModifiers.trim() ? groupConf : null,
|
||||||
// why did you put this in a group, that was entirely pointless
|
);
|
||||||
loggingEnabled && log(LT.LOG, `Solving commaPart: ${commaParts[0]}`);
|
|
||||||
const [tempData, tempCounts, tempDists] = tokenizeMath(commaParts[0], modifiers, previousResults, prevGrpReturnData);
|
|
||||||
const data = tempData[0];
|
const data = tempData[0];
|
||||||
|
|
||||||
loggingEnabled && log(LT.LOG, `Solved Math for Group is back ${JSON.stringify(data)} | ${JSON.stringify(tempCounts)} ${JSON.stringify(tempDists)}`);
|
loggingEnabled && log(LT.LOG, `Solved Math for Group is back ${JSON.stringify(data)} | ${JSON.stringify(tempCounts)} ${JSON.stringify(tempDists)}`);
|
||||||
|
|
||||||
countDetails.push(...tempCounts);
|
countDetails.push(...tempCounts);
|
||||||
rollDists.push(...tempDists);
|
rollDists.push(...tempDists);
|
||||||
data.initConfig = `{${data.initConfig}}`;
|
data.initConfig = `{${data.initConfig}}${groupModifiers.trim() ? groupModifiers.replaceAll(' ', '') : ''}`;
|
||||||
data.rollDetails = `{${data.rollDetails}}`;
|
data.rollDetails = `{${data.rollDetails}}`;
|
||||||
retData = data;
|
retData = data;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
// Handle merging back any nested groups to prevent an internalGrp marker from sneaking out
|
// Handle merging back any nested groups to prevent an internalGrp marker from sneaking out
|
||||||
const initConf = retData.initConfig.split(internalGrpWrapRegex).filter((x) => x);
|
const initConf = retData.initConfig.split(internalGrpWrapRegex).filter((x) => x);
|
||||||
|
|
|
@ -4,8 +4,8 @@ import { ReturnData } from 'artigen/artigen.d.ts';
|
||||||
|
|
||||||
import { MathConf, SolvedStep } from 'artigen/math/math.d.ts';
|
import { MathConf, SolvedStep } from 'artigen/math/math.d.ts';
|
||||||
|
|
||||||
import { CountDetails, RollDistributionMap, RollModifiers } from 'artigen/dice/dice.d.ts';
|
import { CountDetails, ExecutedRoll, GroupConf, RollDistributionMap, RollModifiers, RollSet } from 'artigen/dice/dice.d.ts';
|
||||||
import { generateFormattedRoll } from 'artigen/dice/generateFormattedRoll.ts';
|
import { formatRoll } from 'artigen/dice/generateFormattedRoll.ts';
|
||||||
|
|
||||||
import { loopCountCheck } from 'artigen/managers/loopManager.ts';
|
import { loopCountCheck } from 'artigen/managers/loopManager.ts';
|
||||||
|
|
||||||
|
@ -15,6 +15,8 @@ import { closeInternalGrp, cmdSplitRegex, internalWrapRegex, mathSplitRegex, ope
|
||||||
import { legalMathOperators } from 'artigen/utils/legalMath.ts';
|
import { legalMathOperators } from 'artigen/utils/legalMath.ts';
|
||||||
import { loggingEnabled } from 'artigen/utils/logFlag.ts';
|
import { loggingEnabled } from 'artigen/utils/logFlag.ts';
|
||||||
import { assertParenBalance } from 'artigen/utils/parenBalance.ts';
|
import { assertParenBalance } from 'artigen/utils/parenBalance.ts';
|
||||||
|
import { executeRoll } from 'artigen/dice/executeRoll.ts';
|
||||||
|
import { compareOrigIdx, compareRolls } from 'artigen/utils/sortFuncs.ts';
|
||||||
|
|
||||||
// minusOps are operators that will cause a negative sign to collapse into a number (in cases like + - 1)
|
// minusOps are operators that will cause a negative sign to collapse into a number (in cases like + - 1)
|
||||||
const minusOps = ['(', '^', '**', '*', '/', '%', '+', '-'];
|
const minusOps = ['(', '^', '**', '*', '/', '%', '+', '-'];
|
||||||
|
@ -25,9 +27,11 @@ export const tokenizeMath = (
|
||||||
modifiers: RollModifiers,
|
modifiers: RollModifiers,
|
||||||
previousResults: number[],
|
previousResults: number[],
|
||||||
groupResults: ReturnData[],
|
groupResults: ReturnData[],
|
||||||
|
groupConf: GroupConf | null = null,
|
||||||
): [ReturnData[], CountDetails[], RollDistributionMap[]] => {
|
): [ReturnData[], CountDetails[], RollDistributionMap[]] => {
|
||||||
const countDetails: CountDetails[] = [];
|
const countDetails: CountDetails[] = [];
|
||||||
const rollDists: RollDistributionMap[] = [];
|
const rollDists: RollDistributionMap[] = [];
|
||||||
|
const executedRolls: Map<number, ExecutedRoll> = new Map();
|
||||||
|
|
||||||
loggingEnabled && log(LT.LOG, `Parsing roll ${cmd} | ${JSON.stringify(modifiers)} | ${JSON.stringify(previousResults)}`);
|
loggingEnabled && log(LT.LOG, `Parsing roll ${cmd} | ${JSON.stringify(modifiers)} | ${JSON.stringify(previousResults)}`);
|
||||||
|
|
||||||
|
@ -177,11 +181,16 @@ export const tokenizeMath = (
|
||||||
}
|
}
|
||||||
} else if (![...allOps, ...legalMathOperators].includes(curMathConfStr)) {
|
} else if (![...allOps, ...legalMathOperators].includes(curMathConfStr)) {
|
||||||
// If nothing else has handled it by now, try it as a roll
|
// If nothing else has handled it by now, try it as a roll
|
||||||
const formattedRoll = generateFormattedRoll(curMathConfStr, modifiers);
|
const executedRoll = executeRoll(curMathConfStr, modifiers);
|
||||||
|
if (groupConf) {
|
||||||
|
executedRolls.set(i, executedRoll);
|
||||||
|
} else {
|
||||||
|
const formattedRoll = formatRoll(executedRoll, modifiers);
|
||||||
mathConf[i] = formattedRoll.solvedStep;
|
mathConf[i] = formattedRoll.solvedStep;
|
||||||
countDetails.push(formattedRoll.countDetails);
|
countDetails.push(formattedRoll.countDetails);
|
||||||
rollDists.push(formattedRoll.rollDistributions);
|
rollDists.push(formattedRoll.rollDistributions);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Identify if we are in a state where the current number is a negative number
|
// Identify if we are in a state where the current number is a negative number
|
||||||
if (mathConf[i - 1] === '-' && ((!mathConf[i - 2] && mathConf[i - 2] !== 0) || minusOps.includes(<string> mathConf[i - 2]))) {
|
if (mathConf[i - 1] === '-' && ((!mathConf[i - 2] && mathConf[i - 2] !== 0) || minusOps.includes(<string> mathConf[i - 2]))) {
|
||||||
|
@ -203,6 +212,103 @@ export const tokenizeMath = (
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Handle applying the group config
|
||||||
|
if (groupConf) {
|
||||||
|
loggingEnabled && log(LT.LOG, `Applying groupConf to executedRolls | ${JSON.stringify(groupConf)} ${JSON.stringify(executedRolls.entries().toArray())}`);
|
||||||
|
// Merge all rollSets into one array, adding the idx into each rollSet to allow separating them back out
|
||||||
|
const allRollSets: RollSet[] = [];
|
||||||
|
const executedRollArr = executedRolls.entries().toArray();
|
||||||
|
executedRollArr.forEach(([rollGroupIdx, executedRoll]) => {
|
||||||
|
executedRoll.rollSet.forEach((roll) => (roll.rollGrpIdx = rollGroupIdx));
|
||||||
|
allRollSets.push(...executedRoll.rollSet);
|
||||||
|
});
|
||||||
|
loggingEnabled && log(LT.LOG, `raw rollSets: ${JSON.stringify(allRollSets)}`);
|
||||||
|
|
||||||
|
// Handle drop or keep operations
|
||||||
|
if (groupConf.drop.on || groupConf.keep.on || groupConf.dropHigh.on || groupConf.keepLow.on) {
|
||||||
|
allRollSets.sort(compareRolls);
|
||||||
|
let dropCount = 0;
|
||||||
|
|
||||||
|
// For normal drop and keep, simple subtraction is enough to determine how many to drop
|
||||||
|
// Protections are in to prevent the dropCount from going below 0 or more than the valid rolls to drop
|
||||||
|
if (groupConf.drop.on) {
|
||||||
|
dropCount = groupConf.drop.count;
|
||||||
|
if (dropCount > allRollSets.length) {
|
||||||
|
dropCount = allRollSets.length;
|
||||||
|
}
|
||||||
|
} else if (groupConf.keep.on) {
|
||||||
|
dropCount = allRollSets.length - groupConf.keep.count;
|
||||||
|
if (dropCount < 0) {
|
||||||
|
dropCount = 0;
|
||||||
|
}
|
||||||
|
} // For inverted drop and keep, order must be flipped to greatest to least before the simple subtraction can determine how many to drop
|
||||||
|
// Protections are in to prevent the dropCount from going below 0 or more than the valid rolls to drop
|
||||||
|
else if (groupConf.dropHigh.on) {
|
||||||
|
allRollSets.reverse();
|
||||||
|
dropCount = groupConf.dropHigh.count;
|
||||||
|
if (dropCount > allRollSets.length) {
|
||||||
|
dropCount = allRollSets.length;
|
||||||
|
}
|
||||||
|
} else if (groupConf.keepLow.on) {
|
||||||
|
allRollSets.reverse();
|
||||||
|
dropCount = allRollSets.length - groupConf.keepLow.count;
|
||||||
|
if (dropCount < 0) {
|
||||||
|
dropCount = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
let i = 0;
|
||||||
|
while (dropCount > 0 && i < allRollSets.length) {
|
||||||
|
loopCountCheck();
|
||||||
|
|
||||||
|
loggingEnabled && log(LT.LOG, `Handling group dropping | Dropping ${dropCount}, looking at ${JSON.stringify(allRollSets[i])}`);
|
||||||
|
|
||||||
|
if (!allRollSets[i].dropped && !allRollSets[i].rerolled) {
|
||||||
|
allRollSets[i].dropped = true;
|
||||||
|
allRollSets[i].success = false;
|
||||||
|
allRollSets[i].fail = false;
|
||||||
|
allRollSets[i].matchLabel = '';
|
||||||
|
dropCount--;
|
||||||
|
}
|
||||||
|
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
|
||||||
|
allRollSets.sort(compareOrigIdx);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Handle marking new successes/fails
|
||||||
|
if (groupConf.success.on || groupConf.fail.on) {
|
||||||
|
allRollSets.forEach((rs) => {
|
||||||
|
loopCountCheck();
|
||||||
|
|
||||||
|
if (!rs.dropped && !rs.rerolled) {
|
||||||
|
if (groupConf.success.on && groupConf.success.range.includes(rs.roll)) {
|
||||||
|
rs.success = true;
|
||||||
|
rs.matchLabel = 'S';
|
||||||
|
}
|
||||||
|
if (groupConf.fail.on && groupConf.fail.range.includes(rs.roll)) {
|
||||||
|
rs.fail = true;
|
||||||
|
rs.matchLabel = 'F';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// Handle separating the rollSets back out, recalculating the success/fail count, assigning them to the correct mathConf slots
|
||||||
|
executedRollArr.forEach(([rollGroupIdx, executedRoll]) => {
|
||||||
|
// Update flags on executedRoll
|
||||||
|
executedRoll.countSuccessOverride = executedRoll.countSuccessOverride || groupConf.success.on;
|
||||||
|
executedRoll.countFailOverride = executedRoll.countFailOverride || groupConf.fail.on;
|
||||||
|
executedRoll.rollSet = allRollSets.filter((rs) => rs.rollGrpIdx === rollGroupIdx);
|
||||||
|
|
||||||
|
const formattedRoll = formatRoll(executedRoll, modifiers);
|
||||||
|
mathConf[rollGroupIdx] = formattedRoll.solvedStep;
|
||||||
|
countDetails.push(formattedRoll.countDetails);
|
||||||
|
rollDists.push(formattedRoll.rollDistributions);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
// Now that mathConf is parsed, send it into the solver
|
// Now that mathConf is parsed, send it into the solver
|
||||||
const tempSolved = mathSolver(mathConf);
|
const tempSolved = mathSolver(mathConf);
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue