Closed Prulon closed 1 year ago
Note - There may be more cases which I did not cover, whenever you find a new case for example: "Prulon begins to shimmer." --> means Invisibility So I added the word "shimmer" to const specialSpellWords[], and added the word "Invisibility" to const specialSpellNames[]
How I think you can use all this: Before starting your own manipulations on the text, use this code to sort the text, and then run your code.
@Pz1c
I asked ChatGPT to translate the above code to C++, I don't know if it works, but it can give you a quick start I hope :)
Here's the code:
std::vector
std::vector
std::vector
std::vector
std::vector
std::vector
std::vector
size_t pos = 0;
while (pos < inputString.length()) {
size_t nextPos = inputString.find('\n', pos);
if (nextPos == std::string::npos)
nextPos = inputString.length();
splitLines.push_back(inputString.substr(pos, nextPos - pos));
pos = nextPos + 1;
}
std::string currentLine;
bool isInQuote = false;
for (const std::string& line : splitLines) {
std::string trimmedLine = line;
trimmedLine.erase(0, trimmedLine.find_first_not_of(" \t"));
trimmedLine.erase(trimmedLine.find_last_not_of(" \t") + 1);
currentLine += trimmedLine;
size_t quoteCount = std::count(line.begin(), line.end(), '"');
bool hasQuote = (quoteCount % 2 != 0);
if (hasQuote)
isInQuote = !isInQuote;
if (!isInQuote) {
if (!currentLine.empty())
lines.push_back(currentLine);
currentLine.clear();
}
}
if (!currentLine.empty())
lines.push_back(currentLine);
return lines;
}
void switchLines(std::vector
bool isIntroPart(const std::string& sentenceA) { for (const std::string& intro : introWords) { if (sentenceA.find(intro) != std::string::npos) return true; } return false; }
bool isEndPart(const std::string& sentenceB) { for (const std::string& end : endWords) { if (sentenceB.find(end) != std::string::npos) return true; } return false; }
bool isCastPart(const std::string& sentenceA) { return (sentenceA.find("casts") != std::string::npos); }
std::string getFirstSpell(const std::string& sentence) { if (sentence.find("casts") != std::string::npos) { for (const std::string& spell : spellOrder) { if (sentence.find(spell) != std::string::npos) return spell; } }
for (size_t i = 0; i < specialSpellWords.size(); i++) {
if (sentence.find(specialSpellWords[i]) != std::string::npos)
return specialSpellNames[i];
}
for (const std::string& spell : spellOrder) {
if (sentence.find(spell) != std::string::npos)
return spell;
}
return "";
}
std::string getTarget(const std::string& sentence) { std::string spell = getFirstSpell(sentence); if (!spell.empty()) { size_t targetIndex = sentence.find("at") + 3; std::string target = sentence.substr(targetIndex); std::string targetWords[3]; size_t targetWordCount = 0;
for (char c : target) {
if (c == ' ') {
if (targetWordCount == 2)
break;
targetWordCount++;
}
else {
targetWords[targetWordCount] += c;
}
}
return targetWords[0] + " " + targetWords[1] + " " + targetWords[2];
}
return "";
}
std::string customSortLines(const std::string& inputString) {
std::vector
lines.erase(std::remove_if(lines.begin(), lines.end(), [](const std::string& sentence) {
std::string lowercaseSentence = sentence;
std::transform(lowercaseSentence.begin(), lowercaseSentence.end(), lowercaseSentence.begin(), ::tolower);
for (const std::string& word : wordsToRemove) {
if (lowercaseSentence.find(word) != std::string::npos)
return true;
}
return false;
}), lines.end());
if (lines.empty())
return "";
for (size_t i = 0; i < lines.size() - 1; i++) {
for (size_t j = 0; j < lines.size() - i - 1; j++) {
std::string sentenceA = lines[j];
std::string sentenceB = lines[j + 1];
std::string spellA = getFirstSpell(sentenceA);
std::string spellB = getFirstSpell(sentenceB);
size_t indexA = std::find(spellOrder.begin(), spellOrder.end(), spellA) - spellOrder.begin();
size_t indexB = std::find(spellOrder.begin(), spellOrder.end(), spellB) - spellOrder.begin();
bool isIntroA = isIntroPart(sentenceA);
bool isEndB = isEndPart(sentenceB);
bool isSameSpell = (indexA == indexB && !spellA.empty());
bool isHigherTarget = false;
bool isHigherSpell = (indexA > indexB);
bool isBothSpells = (indexA < spellOrder.size() && indexB < spellOrder.size());
if (isSameSpell) {
std::string targetA = getTarget(sentenceA);
std::string targetB = getTarget(sentenceB);
bool castA = isCastPart(sentenceA);
bool castB = isCastPart(sentenceB);
if (!castA)
isHigherTarget = castB || (targetA.compare(targetB) > 0);
}
if (!isIntroA && !isEndB && isBothSpells && (isHigherSpell || isHigherTarget))
switchLines(lines, j);
}
}
std::string sortedString;
for (const std::string& line : lines) {
sortedString += line + '\n';
}
return sortedString;
}
customSortLines() is the place to start - it gets the turn history, and then uses bubble sort to re-order the items.
The logic is this: Start by removing unuseful lines like the Gestures.
Then, If the line is an "intro line" like "Prulon says" --> keep its location. Same also for end lines. If the line is a "cast spell" or an effect of a spell, then reorder based on the order of spells in RB. If 2 lines belong to the same spell then the line that has the "Casts" word starts, like "Prulon casts magic missile" comes before the damage of the magic missile. If 2 lines belong to the same spell but different targets then sort the targets by ABC
move to 2.1.3 because want finish 2.1.2 today
should be fixed in 2.2.0
Hey @Pz1c
I used chatGPT and wrote the following code to re-order the turn order history in a much more meaningful way for the new animation you worked on.
You can try it out on the following website, what you need to do is copy paste a list of turn history from a game that finished and click submit. (the code is at the end of this post)
For example copy paste the following: Turn 7 Prulon proffers the palm of his left hand. Prulon snaps the fingers of his right hand. Prulon casts Shield at Fat Goblin. Ashai proffers the palm of his left hand. Ashai points the digit of his right hand. Ashai casts Counter Spell at himself. Ashai casts Magic Missile at Fat Goblin. Ashai is covered by a magical glowing shield. Fat Goblin is covered by a shimmering shield. A magic missile bounces off Fat Goblin's shield. Prulon directs Fat Goblin to attack Ashai. Fat Goblin attacks Ashai, but is deflected by a shield. Turn 8 Prulon proffers the palm of his left hand. Prulon wiggles the fingers of his right hand. Prulon casts Counter Spell at himself. Prulon casts Maladroitness at Ashai. Ashai proffers the palm of his left hand. Ashai wiggles the fingers of his right hand. Ashai casts Shield at himself. Ashai casts Charm Person at Prulon. Prulon is covered by a magical glowing shield. Ashai starts to lose coordination. Prulon's shield blurs for a moment. Ashai is covered by a shimmering shield. Prulon directs Fat Goblin to attack Ashai. Fat Goblin attacks Ashai, but is deflected by a shield.
Code here:
The function customSortLines(inputString) below will take the orders of a single turn and sort them in a more logical way
const spellOrder = [ "Dispel Magic", "Counter Spell", "Magic Mirror", "Summon Goblin", "Summon Ogre", "Summon Troll", "Summon Giant", "Summon Fire Elemental", "Summon Ice Elemental", "Haste", "Time Stop", "Protection", "Resist Heat", "Resist Cold", "Paralysis", "Amnesia", "Fear", "Confusion", "Maladroit", "Charm Monster", "Charm Person", "Disease", "Poison", "Cure Light Wounds", "Cure Heavy Wounds", "Anti-spell", "Blindness", "Invisibility", "Permanency", "Delay Effect", "Remove Enchantment", "Shield", "Magic Missile", "Cause Light Wounds", "Cause Heavy Wounds", "Clap of Lightning", "Lightning Bolt", "Fireball", "Finger of Death", "Fire Storm", "Ice Storm" ];
const specialSpellWords = [ "Coordination", "Wounds", "Goblin is summoned", "Ogre is summoned", "Troll is summoned", "Giant is summoned", "a magical glowing shield", "a thick shimmering shield", "a shimmering shield", "reflective shield", "intrigued", "healed", "bolt of lightning", "erased!", "magic missile bounces", "blurs", "shimmer", "scared", "speeds up!", "look blank", "stiffen", "baser instincts", "fizzle", "glassy-eyed" ];
const specialSpellNames = [ "Maladroit", "Cause Heavy Wounds", "Summon Goblin", "Summon Ogre", "Summon Troll", "Summon Giant", "Counter Spell", "Protection", "Shield", "Magic Mirror", "Charm Person", "Cure Heavy Wounds", "Lightning Bolt", "Dispel Magic", "Magic Missile", "Counter Spell", "Invisibility", "Fear", "Haste", "Amnesia", "Paralysis", "Charm Monster", "Anti-spell", "Charm Monster" ];
const introWords = [ "Says", "charmed into", "rendered maladroit!", "quakes in fear!", "sneak in", "same gestures", "paralysed" ];
const endWords = [ "attacks", "dies" ];
const wordsToRemove = [ "directs", "wiggles", "proffers", "stabs", "waves", "points", "snaps", "claps", "no gesture", "bows" ];
function customSortLines(inputString) {
}
function breakIntoLines(inputString) { let lines = []; //this will be the output let splitLines = inputString.split('\n');
}
function switchLines(lines, j) { let temp = lines[j]; lines[j] = lines[j + 1]; lines[j + 1] = temp;
}
function isIntroPart(sentenceA) {
}
function isEndPart(sentenceB) {
}
function isCastPart(sentenceA) {
}
function getFirstSpell(sentence) { if (sentence.includes("casts")) {
}
function getTarget(sentence) { let spell = getFirstSpell(sentence); if (spell !== '') { let targetIndex = sentence.indexOf("at") + 3; let target = sentence.substring(targetIndex).trim(); let targetWords = target.split(" ", 3); return targetWords.join(" "); } return ''; }