added getting armor and attacks to stat parser

This commit is contained in:
TheLastScrub
2024-07-13 15:11:13 -07:00
parent 00aead4dd5
commit 21753ee142
9 changed files with 291 additions and 0 deletions
+1
View File
@@ -43,6 +43,7 @@
"DG.Skills.swim": "Nedar",
"DG.Skills.unarmed_combat": "Combat sense armes",
"DG.Skills.unnatural": "Sobrenatural",
"DG.Skills.flight": "Flight",
"DG.Skills.AddTypedOrCustomSkill": "Afegir tipus o habilitat personalitzada",
"DG.Skills.AddSkill": "Afegir habilitat",
+1
View File
@@ -43,6 +43,7 @@
"DG.Skills.swim": "Schwimmen",
"DG.Skills.unarmed_combat": "Waffenloser Kampf",
"DG.Skills.unnatural": "Mythos",
"DG.Skills.flight": "Flight",
"DG.Skills.AddTypedOrCustomSkill": "Eigene Fertigkeit hinzufügen",
"DG.Skills.AddSkill": "Fertigkeit hinzufügen",
+1
View File
@@ -44,6 +44,7 @@
"DG.Skills.swim": "Swim",
"DG.Skills.unarmed_combat": "Unarmed Combat",
"DG.Skills.unnatural": "Unnatural",
"DG.Skills.flight": "Flight",
"DG.Skills.AddTypedOrCustomSkill": "Add Typed/Custom Skill",
"DG.Skills.AddSkill": "Add Skill",
+1
View File
@@ -43,6 +43,7 @@
"DG.Skills.swim": "Nadar",
"DG.Skills.unarmed_combat": "Combate sin Armas",
"DG.Skills.unnatural": "Antinatural",
"DG.Skills.flight": "Flight",
"DG.Skills.AddTypedOrCustomSkill": "Añadir Tipo o Habilidad Personalizada",
"DG.Skills.AddSkill": "Añadir Habilidad",
+1
View File
@@ -43,6 +43,7 @@
"DG.Skills.swim": "Natation",
"DG.Skills.unarmed_combat": "Corps à corps",
"DG.Skills.unnatural": "Paranaturel",
"DG.Skills.flight": "Flight",
"DG.Skills.AddTypedOrCustomSkill": "Ajouter une compétence personnalisée",
"DG.Skills.AddSkill": "Ajout Compétence",
+1
View File
@@ -43,6 +43,7 @@
"DG.Skills.swim": "泳ぎ",
"DG.Skills.unarmed_combat": "非武装戦闘",
"DG.Skills.unnatural": "不自然",
"DG.Skills.flight": "飛び",
"DG.Skills.AddTypedOrCustomSkill": "スキルを加える",
"DG.Skills.AddSkill": "スキルを加える",
+2
View File
@@ -41,6 +41,8 @@
"DG.Skills.swim": "Nadar",
"DG.Skills.unarmed_combat": "Combate Desarmado",
"DG.Skills.unnatural": "Antinatural",
"DG.Skills.flight": "Flight",
"DG.Skills.AddTypedOrCustomSkill": "Adicionar Habilidade Personalizada",
"DG.Skills.AddSkill": "Adicionar Habilidade",
"DG.Skills.EditTypedOrCustomSkill": "Edit Typed or Custom Skill",
+60
View File
@@ -363,4 +363,64 @@ export default class DeltaGreenActor extends Actor {
console.log(ex);
}
}
async AddArmorItemToSheet(
name,
description,
protection,
isEquipped,
expense = "NA",
) {
const armorData = {
type: "armor",
name: name,
system: {
description: description,
protection: protection,
equipped: isEquipped,
expense: expense,
},
};
await this.createEmbeddedDocuments("Item", [armorData]);
}
async AddWeaponItemToSheet(
name,
description,
damage,
skill = "custom",
skillModifier = 0,
customSkillTarget = 50,
armorPiercing = 0,
lethality = 0,
isLethal = false,
range = "10M",
killRadius = "N/A",
ammo = "",
expense = "NA",
equipped = true,
) {
const weaponData = {
type: "weapon",
name: name,
system: {
description: description,
skill: skill, //custom
skillModifier: skillModifier,
customSkillTarget: customSkillTarget,
range: range,
damage: damage,
armorPiercing: armorPiercing,
lethality: lethality,
isLethal: isLethal,
killRadius: killRadius,
ammo: ammo,
expense: expense,
equipped: equipped,
},
};
await this.createEmbeddedDocuments("Item", [weaponData]);
}
}
+223
View File
@@ -1,3 +1,135 @@
function GetAttacksFromInput(inputText) {
const attacks = [];
try {
// some attacks split onto multiple lines, usually separated by semicolons,
// try to get these back on the same line before splitting...
const lines = inputText
.replace("; \r\n", ";")
.replace(";\r\n", ";")
.replace(";\n", ";")
.replace("; \n", ";")
.split(/\r?\n/);
let isInAttackSection = false;
if (lines !== null && lines.length > 0) {
for (var i = 0; i < lines.length; i++) {
if (lines[i].toString().toUpperCase().indexOf("ATTACKS:") >= 0) {
isInAttackSection = true;
} else if (
isInAttackSection &&
lines[i].toString().toUpperCase().indexOf(":") > 0
) {
isInAttackSection = false;
}
if (isInAttackSection) {
const attackLine = lines[i]
.toString()
.toUpperCase()
.replace("ATTACKS:", "");
console.log(attackLine);
const weaponData = {
type: "weapon",
name: "New Attack",
description: attackLine,
system: {
skill: "custom",
skillModifier: 0,
customSkillTarget: 0,
range: "0M",
damage: "1D10",
armorPiercing: 0,
lethality: 0,
isLethal: false,
killRadius: "N/A",
ammo: "N/A",
expense: "NA",
equipped: true,
},
};
// try to determine if it's a lethality attack, as those will have two % values in them
if (attackLine.indexOf("LETHALITY") >= 0) {
weaponData.isLethal = true;
const lethalityMatchStr = "(\\w.*?)(\\d\\d?%)"; // test with 'Black box 50%, Lethality 40% (see BLACK BOX).'
const re = new RegExp(lethalityMatchStr, "i");
const lethalityResults = attackLine.match(re);
if (
lethalityResults !== null &&
lethalityResults.length > 0 &&
lethalityResults[1] !== null &&
lethalityResults[1] !== undefined
) {
weaponData.name = lethalityResults[1].toString().trim();
weaponData.lethality = parseInt(
lethalityResults[2]
.toString()
.replace("%", "")
.replace(";", ""),
);
}
} else {
// assume only percent value will be the skill test associated with it
const skillMatchStr = `(\\w.*?)(\\d?\\d%)([\\S\\s]*?damage\\s.*?)?(\\d?d\\d?\\d?\\d([\\+\\-]\\d+)?)?`; // test with 'SIG Sauer P228 pistol 94%, damage 1D10.'
const re1 = new RegExp(skillMatchStr, "i");
const skillResults = attackLine.match(re1);
if (
skillResults !== null &&
skillResults.length > 0 &&
skillResults[1] !== null &&
skillResults[1] !== undefined
) {
weaponData.name = skillResults[1].toString().trim();
if (
skillResults.length > 2 &&
skillResults[2] !== null &&
skillResults[2] !== undefined
) {
weaponData.customSkillTarget = parseInt(
skillResults[2].toString().replace("%", "").replace(";", ""),
);
}
// have to be careful, some unnatural attacks don't actually deal damage, they just grab or something.
// don't have a great way to indicate that in the system, so just set it to zero if we can't find it.
if (
skillResults.length > 4 &&
skillResults[4] !== null &&
skillResults[4] !== undefined
) {
weaponData.damage = skillResults[4].toString().replace(";", "");
} else {
weaponData.damage = 0;
}
}
// look for armor piercing
if (attackLine.indexOf("ARMOR PIERCING") >= 0) {
}
}
if (weaponData.customSkillTarget > 0 || weaponData.isLethal) {
attacks.push(weaponData);
}
}
}
}
} catch (ex) {
console.log("GetAttacksFromInput Error");
console.log(ex);
}
return attacks;
}
function GetNotesFromInput(inputText) {
const matchStr = "(?:ATTACKS:[\\S\\s]*?\\.\\n)([\\S\\s]*)";
const re = new RegExp(matchStr, "gi");
@@ -17,6 +149,55 @@ function GetNotesFromInput(inputText) {
return notes;
}
function GetArmorFromInput(inputText) {
try {
let armor = { name: "Armor", description: "", armor: 0 };
const lines = inputText.split(/\r?\n/);
if (lines !== null && lines.length > 0) {
for (var i = 0; i < lines.length; i++) {
if (lines[i].toString().toUpperCase().indexOf("ARMOR:") >= 0) {
armor.description = lines[i]
.replace("Armor:", "")
.replace("ARMOR:", "")
.trim();
const matchStr = `(\\d\\d?)`;
const re = new RegExp(matchStr, "i");
const results = lines[i].match(re);
try {
if (results != null && results.length > 0) {
armor.armor = parseInt(results[0]);
armor.name = armor.description
.replace(`(Armor ${armor.armor})`, "")
.trim();
armor.name = armor.name
.replace(`${armor.armor} points of`, "")
.replace(`${armor.armor} point of`, "")
.replace(".", "")
.trim();
}
} catch (ex) {
console.log("GetArmorFromInput Error");
console.log(ex);
}
return armor;
}
}
}
} catch (ex) {
console.log("GetArmorFromInput Error");
console.log(ex);
}
return null;
}
// this is the main stat call, it's exposed as part of the system itself for users to access
// call this within a world as: game.deltagreen.ParseDeltaGreenStatBlock()
function GetTypeSkillRatingsFromInput(inputText) {
const matchStr =
@@ -128,6 +309,14 @@ async function RegexParseNpcStatBlock(inputStr, actorType) {
actorData.name = "Unknown";
}
let armor = GetArmorFromInput(inputStr);
let attacks = GetAttacksFromInput(inputStr);
if (armor !== null) {
console.log(armor);
}
if (actorType === "agent") {
actorData.system.physical = {
description: shortDescription,
@@ -402,6 +591,40 @@ async function RegexParseNpcStatBlock(inputStr, actorType) {
const newActors = await Actor.createDocuments([actorData]);
if (armor !== null) {
if (armor.description === null || armor.description.trim() === "") {
armor.description = "Armor";
}
await newActors[0].AddArmorItemToSheet(
armor.name,
armor.description,
armor.armor,
true,
);
}
if (attacks !== null && attacks.length > 0) {
for (const a of attacks) {
await newActors[0].AddWeaponItemToSheet(
a.name,
a.description,
a.damage,
a.skill,
a.skillModifier,
a.customSkillTarget,
a.armorPiercing,
a.lethality,
a.isLethal,
a.range,
a.killRadius,
a.ammo,
a.expense,
a.equipped,
);
}
}
newActors[0].sheet.render(true);
}