File indexing completed on 2024-05-12 05:39:33
0001 /*************************************************************************** 0002 * Copyright (C) 2011 by Renaud Guezennec * 0003 * http://renaudguezennec.homelinux.org/accueil,3.html * 0004 * * 0005 * Rolisteam is free software; you can redistribute it and/or modify * 0006 * it under the terms of the GNU General Public License as published by * 0007 * the Free Software Foundation; either version 2 of the License, or * 0008 * (at your option) any later version. * 0009 * * 0010 * This program is distributed in the hope that it will be useful, * 0011 * but WITHOUT ANY WARRANTY; without even the implied warranty of * 0012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * 0013 * GNU General Public License for more details. * 0014 * * 0015 * You should have received a copy of the GNU General Public License * 0016 * along with this program; if not, write to the * 0017 * Free Software Foundation, Inc., * 0018 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * 0019 ***************************************************************************/ 0020 0021 #include <QtCore/QCoreApplication> 0022 #include <QtCore/QString> 0023 #include <QtTest/QtTest> 0024 0025 #include "diceparser/dicealias.h" 0026 #include "diceparser/diceparser.h" 0027 #include "die.h" 0028 0029 // node 0030 #include "booleancondition.h" 0031 #include "diceparser/parsingtoolbox.h" 0032 #include "node/bind.h" 0033 #include "node/countexecutenode.h" 0034 #include "node/explodedicenode.h" 0035 #include "node/filternode.h" 0036 #include "node/groupnode.h" 0037 #include "node/ifnode.h" 0038 #include "node/jumpbackwardnode.h" 0039 #include "node/keepdiceexecnode.h" 0040 #include "node/numbernode.h" 0041 #include "node/occurencecountnode.h" 0042 #include "node/rerolldicenode.h" 0043 #include "node/sortresult.h" 0044 #include "node/splitnode.h" 0045 #include "node/stringnode.h" 0046 #include "node/switchcasenode.h" 0047 #include "node/uniquenode.h" 0048 #include "node/valueslistnode.h" 0049 #include "operationcondition.h" 0050 #include "result/stringresult.h" 0051 #include "testnode.h" 0052 #include "validatorlist.h" 0053 0054 void makeResult(DiceResult& result, const QVector<int>& values, const QVector<int>& subvalues= QVector<int>(), 0055 int base= 1, int max= 10) 0056 { 0057 int i= 0; 0058 for(int val : values) 0059 { 0060 auto die= new Die(); 0061 die->setBase(base); 0062 die->setMaxValue(max); 0063 die->insertRollValue(val); 0064 if(i == 0 && !subvalues.empty()) 0065 { 0066 for(int sval : subvalues) 0067 { 0068 die->insertRollValue(sval); 0069 } 0070 } 0071 result.insertResult(die); 0072 ++i; 0073 } 0074 } 0075 0076 void makeResultExplode(DiceResult& result, const QVector<int>& values) 0077 { 0078 auto die= new Die(); 0079 die->setBase(1); 0080 die->setMaxValue(10); 0081 for(int val : values) 0082 { 0083 die->insertRollValue(val); 0084 } 0085 result.insertResult(die); 0086 } 0087 0088 ValidatorList* makeValidator(QVector<int> number, Dice::CompareOperator op, 0089 QVector<Dice::LogicOperation> vector= QVector<Dice::LogicOperation>()) 0090 { 0091 ValidatorList* list= new ValidatorList(); 0092 QList<Validator*> validList; 0093 for(auto num : number) 0094 { 0095 BooleanCondition* validator= new BooleanCondition(); 0096 NumberNode* node= new NumberNode(); 0097 node->setNumber(num); 0098 validator->setValueNode(node); 0099 validator->setOperator(op); 0100 validList.append(validator); 0101 } 0102 list->setValidators(validList); 0103 if(!vector.isEmpty()) 0104 list->setOperationList(vector); 0105 return list; 0106 } 0107 0108 class TestDice : public QObject 0109 { 0110 Q_OBJECT 0111 0112 public: 0113 TestDice(); 0114 0115 private slots: 0116 void init(); 0117 void getAndSetTest(); 0118 0119 void validatorListTest(); 0120 void validatorListTest_data(); 0121 0122 void diceRollD10Test(); 0123 void diceRollD20Test(); 0124 void commandEndlessLoop(); 0125 0126 void mathPriority(); 0127 void mathPriority_data(); 0128 0129 void commandsTest(); 0130 void commandsTest_data(); 0131 0132 void rangedCommandsTest(); 0133 void rangedCommandsTest_data(); 0134 0135 void dangerousCommandsTest(); 0136 void dangerousCommandsTest_data(); 0137 0138 void wrongCommandsTest(); 0139 void wrongCommandsTest_data(); 0140 0141 void wrongCommandsExecutionTimeTest(); 0142 void scopeDF(); 0143 void scopeDF_data(); 0144 0145 void severalInstruction(); 0146 void testAlias(); 0147 void testAlias_data(); 0148 void cleanupTestCase(); 0149 0150 void keepTest(); 0151 void keepTest_data(); 0152 0153 void sortTest(); 0154 void sortTest_data(); 0155 0156 void countTest(); 0157 void countTest_data(); 0158 0159 void rerollTest(); 0160 void rerollTest_data(); 0161 0162 void explodeTest(); 0163 void explodeTest_data(); 0164 0165 void rerollUntilTest(); 0166 void rerollUntilTest_data(); 0167 0168 void rerollAddTest(); 0169 void rerollAddTest_data(); 0170 0171 void mergeTest(); 0172 void mergeTest_data(); 0173 0174 void ifTest(); 0175 void ifTest_data(); 0176 0177 void ifCommandTest(); 0178 void ifCommandTest_data(); 0179 0180 void paintTest(); 0181 void paintTest_data(); 0182 0183 void filterTest(); 0184 void filterTest_data(); 0185 0186 void uniqueTest(); 0187 void uniqueTest_data(); 0188 0189 void spreadTest(); 0190 void spreadTest_data(); 0191 0192 void groupTest(); 0193 void groupTest_data(); 0194 0195 void bindTest(); 0196 void bindTest_data(); 0197 0198 void occurenceTest(); 0199 void occurenceTest_data(); 0200 0201 void operatoionConditionValidatorTest(); 0202 0203 void switchCaseTest(); 0204 void switchCaseTest_data(); 0205 0206 void deterministTest(); 0207 void deterministTest_data(); 0208 0209 private: 0210 std::unique_ptr<Die> m_die; 0211 std::unique_ptr<DiceParser> m_diceParser; 0212 std::unique_ptr<ParsingToolBox> m_parsingToolBox; 0213 }; 0214 0215 TestDice::TestDice() {} 0216 0217 void TestDice::init() 0218 { 0219 m_die.reset(new Die()); 0220 m_diceParser.reset(new DiceParser()); 0221 m_parsingToolBox.reset(new ParsingToolBox()); 0222 } 0223 0224 void TestDice::getAndSetTest() 0225 { 0226 for(unsigned int i= 0; i < 2000; i++) 0227 { 0228 m_die->setMaxValue(i); 0229 QVERIFY(m_die->getMaxValue() == i); 0230 } 0231 0232 m_die->setSelected(true); 0233 QVERIFY(m_die->isSelected() == true); 0234 0235 m_die->setSelected(false); 0236 QVERIFY(m_die->isSelected() == false); 0237 } 0238 0239 void TestDice::validatorListTest() 0240 { 0241 QFETCH(QString, cmd); 0242 QFETCH(int, result); 0243 0244 auto parsing= m_diceParser->parseLine(cmd); 0245 QVERIFY2(parsing, "parsing"); 0246 0247 m_diceParser->start(); 0248 QVERIFY2(m_diceParser->humanReadableError().isEmpty(), "no error"); 0249 QVERIFY2(m_diceParser->humanReadableWarning().isEmpty(), "no warning"); 0250 0251 auto resultCmd= m_diceParser->scalarResultsFromEachInstruction(); 0252 0253 QCOMPARE(resultCmd.size(), 1); 0254 0255 QCOMPARE(resultCmd.first(), result); 0256 } 0257 0258 void TestDice::validatorListTest_data() 0259 { 0260 QTest::addColumn<QString>("cmd"); 0261 QTest::addColumn<int>("result"); 0262 0263 QTest::addRow("cmd1") << "2d[6..6]c6" << 2; 0264 QTest::addRow("cmd2") << "[6,2]c[:>6&%2=0]" << 2; 0265 QTest::addRow("cmd3") << "[6,1,1]c[=6|=1]" << 3; 0266 } 0267 0268 void TestDice::diceRollD10Test() 0269 { 0270 m_die->setMaxValue(10); 0271 for(int i= 0; i < 2000; i++) 0272 { 0273 m_die->roll(false); 0274 QVERIFY(m_die->getValue() > 0); 0275 QVERIFY(m_die->getValue() < 11); 0276 } 0277 } 0278 void TestDice::diceRollD20Test() 0279 { 0280 m_die->setMaxValue(20); 0281 for(int i= 0; i < 2000; i++) 0282 { 0283 m_die->roll(false); 0284 QVERIFY(m_die->getValue() > 0); 0285 QVERIFY(m_die->getValue() < 21); 0286 } 0287 } 0288 0289 void TestDice::commandEndlessLoop() 0290 { 0291 bool a= m_diceParser->parseLine("1D10e[>0]"); 0292 QVERIFY(!a); 0293 } 0294 0295 void TestDice::commandsTest() 0296 { 0297 QFETCH(QString, cmd); 0298 0299 bool a= m_diceParser->parseLine(cmd); 0300 QVERIFY2(a, "parsing"); 0301 0302 m_diceParser->start(); 0303 QVERIFY2(m_diceParser->humanReadableError().isEmpty(), "no error"); 0304 QVERIFY2(m_diceParser->humanReadableWarning().isEmpty(), "no warning"); 0305 } 0306 0307 void TestDice::commandsTest_data() 0308 { 0309 QTest::addColumn<QString>("cmd"); 0310 0311 QTest::addRow("cmd1") << "1L[cheminée,chocolat,épée,arc,chute de pierre]"; 0312 QTest::addRow("cmd2") << "10d10c[>=6]-@c[=1]"; 0313 QTest::addRow("cmd3") << "10d10c[>=6]-@c[=1]-@c[=1]"; 0314 QTest::addRow("cmd4") << "10d10c[>6]+@c[=10]"; 0315 QTest::addRow("cmd5") << "1+1D10"; 0316 QTest::addRow("cmd6") << "3d10c[>=5]"; 0317 QTest::addRow("cmd7") << "1+(4*3)D10"; 0318 QTest::addRow("cmd8") << "2+4/4"; 0319 QTest::addRow("cmd9") << "2D10*2D20*8"; 0320 QTest::addRow("cmd10") << "1+(4*3)D10"; 0321 QTest::addRow("cmd11") << "(4D6)D10"; 0322 QTest::addRow("cmd12") << "1D100a[>=95]a[>=96]a[>=97]a[>=98]a[>=99]e[>=100]"; 0323 QTest::addRow("cmd13") << "3D100"; 0324 QTest::addRow("cmd14") << "4k3"; 0325 0326 QTest::addRow("cmd15") << "10D10e[>=6]sc[>=6]"; 0327 QTest::addRow("cmd16") << "10D10e10s"; 0328 QTest::addRow("cmd17") << "10D10s"; 0329 QTest::addRow("cmd18") << "15D10e10c[8..10]"; 0330 QTest::addRow("cmd19") << "10d10e10"; 0331 QTest::addRow("cmd30") << "(4+4)**4"; 0332 QTest::addRow("cmd31") << "(1d20+20)*7/10"; 0333 QTest::addRow("cmd32") << "20*7/10"; 0334 QTest::addRow("cmd33") << "1D8+2D6+7"; 0335 QTest::addRow("cmd34") << "D25"; 0336 QTest::addRow("cmd35") << "1L[tete[10],ventre[50],jambe[40]]"; 0337 QTest::addRow("cmd36") << "2d6c[%2=0]"; 0338 QTest::addRow("cmd37") << "D25+D10"; 0339 QTest::addRow("cmd38") << "D25;D10"; 0340 QTest::addRow("cmd39") << "8+8+8"; 0341 QTest::addRow("cmd40") << "1D20-88"; 0342 QTest::addRow("cmd41") << "100*1D20*2D6"; 0343 QTest::addRow("cmd42") << "2D6 # two 6sided dice"; 0344 QTest::addRow("cmd43") << "100/28*3"; 0345 QTest::addRow("cmd44") << "100/8"; 0346 QTest::addRow("cmd45") << "100*3*8"; 0347 QTest::addRow("cmd46") << "help"; 0348 QTest::addRow("cmd47") << "la"; 0349 QTest::addRow("cmd48") << "10D10c[<2|>7]"; 0350 QTest::addRow("cmd49") << "10D6c[=2|=4|=6]"; 0351 QTest::addRow("cmd50") << "10D10e[=1|=10]k4"; 0352 QTest::addRow("cmd51") << "1L[tete,bras droit,bras gauche,jambe droite,jambe " 0353 "gauche,ventre[6..7],buste[8..10]]"; 0354 QTest::addRow("cmd52") << "10+10s"; 0355 QTest::addRow("cmd53") << "1d6e6;1d4e4mk1"; 0356 QTest::addRow("cmd54") << "1d6e6;1d4e4mk1"; 0357 QTest::addRow("cmd55") << "400D20/400000"; 0358 QTest::addRow("cmd56") << "1d100e[>=95]i[<5]{-1d100e95}"; 0359 QTest::addRow("cmd57") << "100*3*8"; 0360 QTest::addRow("cmd58") << "1d100i[<70]{1d10i[=10]{1d100i[<70]{1d10e10}}}"; 0361 QTest::addRow("cmd59") << "10d6c[<2|>5]"; 0362 QTest::addRow("cmd60") << "5-5*5+5"; 0363 QTest::addRow("cmd61") << "((3+4)*2)d6"; 0364 QTest::addRow("cmd62") << "4d6i[=6]{+1d6}"; 0365 QTest::addRow("cmd63") << "10d[-8..-1]"; 0366 QTest::addRow("cmd64") << "4d6e6i[=4]{-4}+2"; 0367 QTest::addRow("cmd65") << "4d6e6f[!=4]+2"; 0368 QTest::addRow("cmd66") << "5d10g10"; 0369 QTest::addRow("cmd67") << "4d6p[4:blue]c[>=4];1d6p[1:#FFFFFF]c6-@c1;1d6p[1:#" 0370 "FF0000]c[>=4]+@c6-@c1"; 0371 QTest::addRow("cmd68") << "10d[0..9]"; 0372 QTest::addRow("cmd69") << "1d8e8;1d6e6mk1+2"; 0373 QTest::addRow("cmd70") << "3d100g50"; 0374 QTest::addRow("cmd71") << "3d100g33"; 0375 QTest::addRow("cmd72") << "3d100g5"; 0376 QTest::addRow("cmd73") << "3d100g40"; 0377 QTest::addRow("cmd74") << "2d10k1+2d10k1+2d10k1"; 0378 QTest::addRow("cmd75") << "2d10k1-2d10k1-2d10k1"; 0379 QTest::addRow("cmd76") << "(2d10k1)-2d10k1-2d10k1"; 0380 QTest::addRow("cmd77") << "2d10k1-(2d10k1)-2d10k1"; 0381 QTest::addRow("cmd78") << "2d10k1-2d10k1-(2d10k1)"; 0382 QTest::addRow("cmd79") << "1d6-2d6e6"; 0383 QTest::addRow("cmd80") << "(1)-1d6e6"; 0384 QTest::addRow("cmd81") << "(1)-(1d6e6)"; 0385 QTest::addRow("cmd82") << "8d10o"; 0386 QTest::addRow("cmd83") << "8d10o2,4"; 0387 QTest::addRow("cmd84") << "8d10o2[>2]"; 0388 QTest::addRow("cmd85") << "8d10ok2"; 0389 QTest::addRow("cmd86") << "[100,200,300]k2"; 0390 QTest::addRow("cmd87") << "100;200;300;[$1,$2,$3]k2"; 0391 QTest::addRow("cmd88") << "1d20|3i:[>1]{\"Success\"}{\"Failure\"}"; 0392 QTest::addRow("cmd89") << "1L[-3,-2,2,3]+10"; 0393 QTest::addRow("cmd90") << "1L[-3,-2,2,3]+10;1L[-3,-2,2,3]"; 0394 QTest::addRow("cmd91") << "1d20|3i:[>1]{\"Success\"}{\"Failure\"}"; 0395 QTest::addRow("cmd92") << "4d10k3;4d10k3;4d10k3;[$1,$2,$3]s;\"Score @4\""; 0396 QTest::addRow("cmd93") << "4d10e(10)10"; 0397 } 0398 0399 void TestDice::rangedCommandsTest() 0400 { 0401 QFETCH(QString, cmd); 0402 QFETCH(int, min); 0403 QFETCH(int, max); 0404 0405 bool a= m_diceParser->parseLine(cmd); 0406 QVERIFY2(a, "parsing"); 0407 0408 m_diceParser->start(); 0409 auto results= m_diceParser->scalarResultsFromEachInstruction(); 0410 0411 QVERIFY(results.size() == 1); 0412 0413 auto score= results.first(); 0414 0415 QVERIFY(score >= min); 0416 QVERIFY(score <= max); 0417 0418 QVERIFY2(m_diceParser->humanReadableError().isEmpty(), "no error"); 0419 QVERIFY2(m_diceParser->humanReadableError().isEmpty(), "no error"); 0420 0421 QVERIFY2(m_diceParser->humanReadableError().isEmpty(), "no error"); 0422 QVERIFY2(m_diceParser->humanReadableWarning().isEmpty(), "no warning"); 0423 } 0424 0425 void TestDice::rangedCommandsTest_data() 0426 { 0427 QTest::addColumn<QString>("cmd"); 0428 QTest::addColumn<int>("min"); 0429 QTest::addColumn<int>("max"); 0430 0431 QTest::addRow("cmd1") << "1L[5,6,7,8]+10" << 15 << 18; 0432 QTest::addRow("cmd2") << "2L[5,6,7,8]+10" << 20 << 26; 0433 } 0434 0435 void TestDice::wrongCommandsTest() 0436 { 0437 // << "pajaejlbnmàw"; 0438 QFETCH(QString, cmd); 0439 QFETCH(bool, valid); 0440 bool a= m_diceParser->parseLine(cmd); 0441 if(a) 0442 { 0443 m_diceParser->start(); 0444 auto map= m_diceParser->errorMap(); 0445 a= map.isEmpty(); 0446 } 0447 QCOMPARE(a, valid); 0448 } 0449 0450 void TestDice::wrongCommandsTest_data() 0451 { 0452 QTest::addColumn<QString>("cmd"); 0453 QTest::addColumn<bool>("valid"); 0454 0455 QTest::newRow("test1") << "1L[cheminée,chocolat,épée,arc,chute de pierre" << false; 0456 QTest::newRow("test2") << "10d10c" << false; 0457 QTest::newRow("test3") << "10d10a" << false; 0458 QTest::newRow("test4") << "10d0a[>7]" << false; 0459 QTest::newRow("test5") << "aiteanetauearuteurn" << false; 0460 QTest::newRow("test6") << "meregue" << false; 0461 QTest::newRow("test7") << "p i follow rivers" << false; 0462 QTest::newRow("test8") << "manga violet evergarden" << false; 0463 QTest::newRow("test9") << "((1d8e8+2);(1d6e6+2))" << true; 0464 } 0465 0466 void TestDice::wrongCommandsExecutionTimeTest() 0467 { 0468 QStringList commands; 0469 0470 //<< "8D20+10*@c[=20]" 0471 commands << "1/0" 0472 << "" 0473 << "0d10" 0474 << "10d10k11" 0475 << "!!!!"; 0476 0477 for(QString cmd : commands) 0478 { 0479 bool test= m_diceParser->parseLine(cmd); 0480 m_diceParser->start(); 0481 0482 QVERIFY2(m_diceParser->errorMap().isEmpty() == false || !test, cmd.toStdString().c_str()); 0483 } 0484 } 0485 void TestDice::scopeDF() 0486 { 0487 QFETCH(QString, cmd); 0488 QFETCH(int, min); 0489 QFETCH(int, max); 0490 QFETCH(bool, valid); 0491 0492 bool test= m_diceParser->parseLine(cmd); 0493 QVERIFY2(test == valid, cmd.toStdString().c_str()); 0494 m_diceParser->start(); 0495 auto results= m_diceParser->scalarResultsFromEachInstruction(); 0496 0497 for(auto const& result : qAsConst(results)) 0498 QVERIFY(result >= min && result <= max); 0499 } 0500 0501 void TestDice::scopeDF_data() 0502 { 0503 QTest::addColumn<QString>("cmd"); 0504 QTest::addColumn<int>("min"); 0505 QTest::addColumn<int>("max"); 0506 QTest::addColumn<bool>("valid"); 0507 0508 QTest::newRow("test1") << "1D[-1..1]" << -1 << 1 << true; 0509 QTest::newRow("test2") << "1D[-10..-5]" << -10 << -5 << true; 0510 QTest::newRow("test3") << "1D[-100..100]" << -100 << 100 << true; 0511 QTest::newRow("test4") << "1D[-1..0]" << -1 << 0 << true; 0512 QTest::newRow("test5") << "1D[10..20]" << 10 << 20 << true; 0513 QTest::newRow("test6") << "1D[30..100]" << 30 << 100 << true; 0514 QTest::newRow("test7") << "1D[0..99]" << 0 << 99 << true; 0515 QTest::newRow("test8") << "5-5*5+5" << -15 << -15 << true; 0516 QTest::newRow("test9") << "2d20c[<=13]+@c[<=3]" << 0 << 4 << true; 0517 QTest::newRow("test10") << "6d10c[>=6]-@c1" << -6 << 6 << true; 0518 QTest::newRow("test11") << "2d6k1+2d8k1+2d10k1" << 3 << 30 << true; 0519 QTest::newRow("test12") << "1D[-2..50]" << -2 << 50 << true; 0520 } 0521 void TestDice::testAlias() 0522 { 0523 m_parsingToolBox->insertAlias(new DiceAlias("!", "3d6c"), 0); 0524 m_parsingToolBox->insertAlias(new DiceAlias("g", "d10k"), 1); 0525 m_parsingToolBox->insertAlias(new DiceAlias("(.*)C(.*)", QStringLiteral("\\1d10e10c[>=\\2]"), QString(), false), 2); 0526 0527 QFETCH(QString, cmd); 0528 QFETCH(QString, expected); 0529 0530 auto result= m_parsingToolBox->convertAlias(cmd); 0531 QCOMPARE(result, expected); 0532 } 0533 0534 void TestDice::testAlias_data() 0535 { 0536 QTest::addColumn<QString>("cmd"); 0537 QTest::addColumn<QString>("expected"); 0538 0539 QTest::newRow("test1") << "!2" 0540 << "3d6c2"; 0541 QTest::newRow("test2") << "${rang}g4" 0542 << "${rang}d10k4"; 0543 QTest::newRow("test3") << "${rang}g4 # gerald" 0544 << "${rang}d10k4 # gerald"; 0545 QTest::newRow("test4") << "5C3" 0546 << "5d10e10c[>=3]"; 0547 QTest::newRow("test5") << "1d100i:[<101]{\"great!\"}{\"try again\"}" 0548 << "1d100i:[<101]{\"great!\"}{\"try again\"}"; 0549 } 0550 0551 void TestDice::severalInstruction() 0552 { 0553 QStringList commands; 0554 0555 commands << "1d10;2d20;$1+$2"; 0556 0557 QList<int> results; 0558 results << 3; 0559 0560 int i= 0; 0561 for(auto const& cmd : qAsConst(commands)) 0562 { 0563 auto test= m_diceParser->parseLine(cmd); 0564 QVERIFY2(test, cmd.toStdString().c_str()); 0565 QVERIFY2(m_diceParser->startNodeCount() == results[i], "Wrong number of instruction"); 0566 } 0567 } 0568 void TestDice::mathPriority() 0569 { 0570 QFETCH(QString, cmd); 0571 QFETCH(int, expected); 0572 0573 bool test= m_diceParser->parseLine(cmd); 0574 QVERIFY(test); 0575 m_diceParser->start(); 0576 auto resultList= m_diceParser->scalarResultsFromEachInstruction(); 0577 QCOMPARE(resultList.size(), 1); 0578 0579 auto value= resultList.first(); 0580 QCOMPARE(value, expected); 0581 } 0582 0583 void TestDice::mathPriority_data() 0584 { 0585 QTest::addColumn<QString>("cmd"); 0586 QTest::addColumn<int>("expected"); 0587 0588 QTest::addRow("cmd1") << "10+2" << 12; 0589 QTest::addRow("cmd2") << "2-10" << -8; 0590 QTest::addRow("cmd3") << "5+2*3" << 11; 0591 QTest::addRow("cmd4") << "5-5*5+5" << -15; 0592 QTest::addRow("cmd5") << "5-5/5+5" << 9; 0593 QTest::addRow("cmd6") << "10*(3*2)" << 60; 0594 QTest::addRow("cmd7") << "60/(3*2)" << 10; 0595 QTest::addRow("cmd8") << "5-(5*5+5)" << -25; 0596 } 0597 0598 void TestDice::dangerousCommandsTest() 0599 { 0600 QFETCH(QString, cmd); 0601 0602 auto b= m_diceParser->parseLine(cmd); 0603 QVERIFY(b); 0604 m_diceParser->start(); 0605 } 0606 void TestDice::dangerousCommandsTest_data() 0607 { 0608 QTest::addColumn<QString>("cmd"); 0609 0610 QTest::addRow("cmd1") << "10d6g10"; 0611 QTest::addRow("cmd2") << "10d2g10"; 0612 QTest::addRow("cmd3") << "10d10g10"; 0613 // QTest::addRow("cmd4") << "10d10g10"; 0614 // QTest::addRow("cmd5") << "10d10g10"; 0615 } 0616 0617 void TestDice::keepTest() 0618 { 0619 QFETCH(QVector<int>, values); 0620 QFETCH(int, keep); 0621 QFETCH(int, score); 0622 QFETCH(bool, error); 0623 0624 TestNode node; 0625 KeepDiceExecNode keepN; 0626 NumberNode* numberNode= new NumberNode(); 0627 numberNode->setNumber(keep); 0628 keepN.setDiceKeepNumber(numberNode); 0629 0630 DiceResult result; 0631 0632 makeResult(result, values); 0633 0634 node.setResult(&result); 0635 node.setNextNode(&keepN); 0636 0637 node.run(nullptr); 0638 0639 bool isErrorEmpty= !keepN.getExecutionErrorMap().isEmpty(); 0640 0641 QCOMPARE(isErrorEmpty, error); 0642 0643 if(error) 0644 return; 0645 0646 auto resultScore= keepN.getResult()->getResult(Dice::RESULT_TYPE::SCALAR).toInt(); 0647 0648 QCOMPARE(score, resultScore); 0649 } 0650 0651 void TestDice::keepTest_data() 0652 { 0653 QTest::addColumn<QVector<int>>("values"); 0654 QTest::addColumn<int>("keep"); 0655 QTest::addColumn<int>("score"); 0656 QTest::addColumn<bool>("error"); 0657 0658 QTest::addRow("cmd1") << QVector<int>({10, 9, 2}) << 1 << 10 << false; 0659 QTest::addRow("cmd2") << QVector<int>({10, 9, 2}) << 2 << 19 << false; 0660 QTest::addRow("cmd3") << QVector<int>({10, 9, 2}) << 3 << 21 << false; 0661 QTest::addRow("cmd4") << QVector<int>({10, 9, 2}) << 4 << 0 << true; 0662 } 0663 0664 void TestDice::sortTest() 0665 { 0666 QFETCH(QVector<int>, values); 0667 QFETCH(bool, ascending); 0668 QFETCH(QVector<int>, scores); 0669 0670 TestNode node; 0671 SortResultNode sortN; 0672 sortN.setSortAscending(ascending); 0673 0674 DiceResult result; 0675 0676 makeResult(result, values); 0677 0678 node.setResult(&result); 0679 node.setNextNode(&sortN); 0680 0681 DiceResult expectedScore; 0682 makeResult(expectedScore, scores); 0683 0684 node.run(nullptr); 0685 0686 auto list= dynamic_cast<DiceResult*>(sortN.getResult())->getResultList(); 0687 0688 int i= 0; 0689 auto expected= expectedScore.getResultList(); 0690 for(auto sortedDie : list) 0691 { 0692 QCOMPARE(expected[i]->getValue(), sortedDie->getValue()); 0693 ++i; 0694 } 0695 } 0696 0697 void TestDice::sortTest_data() 0698 { 0699 QTest::addColumn<QVector<int>>("values"); 0700 QTest::addColumn<bool>("ascending"); 0701 QTest::addColumn<QVector<int>>("scores"); 0702 0703 QTest::addRow("cmd1") << QVector<int>({10, 9, 2}) << true << QVector<int>({2, 9, 10}); 0704 QTest::addRow("cmd2") << QVector<int>({1, 2, 3}) << false << QVector<int>({3, 2, 1}); 0705 QTest::addRow("cmd3") << QVector<int>({10, 9, 2}) << false << QVector<int>({10, 9, 2}); 0706 QTest::addRow("cmd4") << QVector<int>({2, 9, 10}) << true << QVector<int>({2, 9, 10}); 0707 QTest::addRow("cmd5") << QVector<int>({1, 25, 10}) << false << QVector<int>({25, 10, 1}); 0708 QTest::addRow("cmd6") << QVector<int>({10, 2, 100}) << false << QVector<int>({100, 10, 2}); 0709 } 0710 0711 void TestDice::countTest() 0712 { 0713 QFETCH(QVector<int>, values); 0714 QFETCH(QVector<int>, condition); 0715 QFETCH(int, score); 0716 QFETCH(QVector<int>, subvalues); 0717 QFETCH(int, boolOp); 0718 0719 TestNode node; 0720 CountExecuteNode countN; 0721 0722 QVector<Dice::LogicOperation> vector; 0723 0724 bool first= true; 0725 for(const auto& i : condition) 0726 { 0727 Q_UNUSED(i) 0728 if(!first) 0729 { 0730 first= !first; 0731 continue; 0732 } 0733 0734 vector.push_back(Dice::LogicOperation::OR); 0735 } 0736 0737 auto validator= makeValidator(condition, static_cast<Dice::CompareOperator>(boolOp), vector); 0738 0739 countN.setValidatorList(validator); 0740 DiceResult result; 0741 node.setResult(&result); 0742 node.setNextNode(&countN); 0743 0744 makeResult(result, values, subvalues); 0745 0746 node.run(nullptr); 0747 0748 QCOMPARE(score, countN.getResult()->getResult(Dice::RESULT_TYPE::SCALAR).toInt()); 0749 0750 countN.setValidatorList(nullptr); 0751 } 0752 0753 void TestDice::countTest_data() 0754 { 0755 QTest::addColumn<QVector<int>>("values"); 0756 QTest::addColumn<QVector<int>>("condition"); 0757 QTest::addColumn<int>("score"); 0758 QTest::addColumn<QVector<int>>("subvalues"); 0759 QTest::addColumn<int>("boolOp"); 0760 0761 // clang-format off 0762 QTest::addRow("cmd1") << QVector<int>({10, 9, 2}) << QVector<int>({3}) << 2 << QVector<int>() << static_cast<int>(Dice::CompareOperator::GreaterThan); 0763 QTest::addRow("cmd2") << QVector<int>({1, 2, 3}) << QVector<int>({3}) << 0 << QVector<int>() << static_cast<int>(Dice::CompareOperator::GreaterThan); 0764 QTest::addRow("cmd3") << QVector<int>({10, 7, 4}) << QVector<int>({7}) << 3 << QVector<int>({10, 10, 2}) << static_cast<int>(Dice::CompareOperator::GreaterThan); 0765 QTest::addRow("cmd4") << QVector<int>({1, 1, 6}) << QVector<int>({1,6}) << 3 << QVector<int>() << static_cast<int>(Dice::CompareOperator::Equal); 0766 // clang-format on 0767 } 0768 0769 void TestDice::rerollTest() 0770 { 0771 QFETCH(QVector<int>, values); 0772 QFETCH(int, condition); 0773 QFETCH(bool, different); 0774 0775 TestNode node; 0776 RerollDiceNode reroll(true, false); 0777 0778 DiceResult result; 0779 makeResult(result, values); 0780 node.setResult(&result); 0781 0782 auto validator= makeValidator(QVector<int>() << condition, Dice::CompareOperator::GreaterThan); 0783 reroll.setValidatorList(validator); 0784 node.setNextNode(&reroll); 0785 0786 node.run(nullptr); 0787 0788 auto list= dynamic_cast<DiceResult*>(reroll.getResult())->getResultList(); 0789 0790 int i= 0; 0791 auto expected= result.getResultList(); 0792 bool resultDiff= false; 0793 for(auto rerolled : list) 0794 { 0795 if(!resultDiff && rerolled->getValue() != expected[i]->getValue()) 0796 resultDiff= true; 0797 ++i; 0798 } 0799 0800 QCOMPARE(different, resultDiff); 0801 } 0802 0803 void TestDice::rerollTest_data() 0804 { 0805 QTest::addColumn<QVector<int>>("values"); 0806 QTest::addColumn<int>("condition"); 0807 QTest::addColumn<bool>("different"); 0808 0809 QTest::addRow("cmd1") << QVector<int>({8, 9, 2}) << 10 << false; 0810 QTest::addRow("cmd2") << QVector<int>({0, 0, 0}) << -1 << true; 0811 } 0812 0813 void TestDice::explodeTest() 0814 { 0815 QFETCH(QVector<int>, values); 0816 QFETCH(int, condition); 0817 QFETCH(bool, different); 0818 0819 TestNode node; 0820 ExplodeDiceNode explode; 0821 0822 DiceResult result; 0823 makeResult(result, values); 0824 node.setResult(&result); 0825 0826 auto validator= makeValidator(QVector<int>() << condition, Dice::CompareOperator::Equal); 0827 explode.setValidatorList(validator); 0828 node.setNextNode(&explode); 0829 0830 node.run(nullptr); 0831 0832 auto list= dynamic_cast<DiceResult*>(explode.getResult())->getResultList(); 0833 0834 int i= 0; 0835 auto expected= result.getResultList(); 0836 bool resultDiff= false; 0837 for(auto rerolled : list) 0838 { 0839 if(!resultDiff && rerolled->getValue() != expected[i]->getValue()) 0840 resultDiff= true; 0841 ++i; 0842 } 0843 0844 QCOMPARE(different, resultDiff); 0845 } 0846 0847 void TestDice::explodeTest_data() 0848 { 0849 QTest::addColumn<QVector<int>>("values"); 0850 QTest::addColumn<int>("condition"); 0851 QTest::addColumn<bool>("different"); 0852 0853 QTest::addRow("cmd1") << QVector<int>({8, 9, 2}) << 10 << false; 0854 QTest::addRow("cmd2") << QVector<int>({0, 0, 0}) << 0 << true; 0855 } 0856 0857 void TestDice::rerollUntilTest() 0858 { 0859 QFETCH(QVector<int>, values); 0860 QFETCH(int, condition); 0861 QFETCH(bool, different); 0862 0863 TestNode node; 0864 RerollDiceNode reroll(false, false); 0865 0866 DiceResult result; 0867 makeResult(result, values, QVector<int>(), 0); 0868 node.setResult(&result); 0869 0870 auto validator= makeValidator(QVector<int>() << condition, Dice::CompareOperator::Equal); 0871 reroll.setValidatorList(validator); 0872 node.setNextNode(&reroll); 0873 0874 node.run(nullptr); 0875 0876 auto list= dynamic_cast<DiceResult*>(reroll.getResult())->getResultList(); 0877 0878 int i= 0; 0879 auto expected= result.getResultList(); 0880 bool resultDiff= false; 0881 for(auto rerolled : list) 0882 { 0883 if(!resultDiff && rerolled->getValue() != expected[i]->getValue()) 0884 resultDiff= true; 0885 ++i; 0886 } 0887 QCOMPARE(different, resultDiff); 0888 } 0889 void TestDice::rerollUntilTest_data() 0890 { 0891 QTest::addColumn<QVector<int>>("values"); 0892 QTest::addColumn<int>("condition"); 0893 QTest::addColumn<bool>("different"); 0894 0895 QTest::addRow("cmd1") << QVector<int>({8, 9, 2}) << 10 << false; 0896 QTest::addRow("cmd2") << QVector<int>({0, 0, 0}) << 0 << true; 0897 } 0898 0899 void TestDice::rerollAddTest() 0900 { 0901 QFETCH(QVector<int>, values); 0902 QFETCH(int, condition); 0903 QFETCH(bool, different); 0904 0905 TestNode node; 0906 RerollDiceNode reroll(true, true); 0907 0908 DiceResult result; 0909 makeResult(result, values); 0910 node.setResult(&result); 0911 0912 auto validator= makeValidator(QVector<int>() << condition, Dice::CompareOperator::Equal); 0913 reroll.setValidatorList(validator); 0914 node.setNextNode(&reroll); 0915 0916 node.run(nullptr); 0917 0918 auto list= dynamic_cast<DiceResult*>(reroll.getResult())->getResultList(); 0919 0920 int i= 0; 0921 auto expected= result.getResultList(); 0922 bool resultDiff= false; 0923 for(auto rerolled : list) 0924 { 0925 if(!resultDiff && rerolled->getValue() != expected[i]->getValue()) 0926 resultDiff= true; 0927 ++i; 0928 } 0929 0930 QCOMPARE(different, resultDiff); 0931 } 0932 void TestDice::rerollAddTest_data() 0933 { 0934 QTest::addColumn<QVector<int>>("values"); 0935 QTest::addColumn<int>("condition"); 0936 QTest::addColumn<bool>("different"); 0937 0938 QTest::addRow("cmd1") << QVector<int>({8, 9, 2}) << 10 << false; 0939 QTest::addRow("cmd2") << QVector<int>({0, 0, 0}) << 0 << true; 0940 } 0941 0942 void TestDice::mergeTest() {} 0943 void TestDice::mergeTest_data() {} 0944 0945 void TestDice::ifTest() 0946 { 0947 QFETCH(QVector<int>, values); 0948 QFETCH(int, condition); 0949 QFETCH(int, valCondition); 0950 QFETCH(QString, expectedResult); 0951 0952 Dice::ConditionType conditionType= static_cast<Dice::ConditionType>(condition); 0953 0954 TestNode node; 0955 IfNode ifNode; 0956 ifNode.setConditionType(conditionType); 0957 0958 DiceResult result; 0959 makeResult(result, values); 0960 node.setResult(&result); 0961 0962 StringNode trueNode; 0963 trueNode.setString(QStringLiteral("True")); 0964 StringNode falseNode; 0965 falseNode.setString(QStringLiteral("False")); 0966 0967 ifNode.setInstructionTrue(&trueNode); 0968 ifNode.setInstructionFalse(&falseNode); 0969 0970 auto validator= makeValidator(QVector<int>() << valCondition, Dice::CompareOperator::Equal); 0971 ifNode.setValidatorList(validator); 0972 node.setNextNode(&ifNode); 0973 0974 node.run(nullptr); 0975 0976 auto text= dynamic_cast<StringResult*>(ifNode.getNextNode()->getResult())->getText(); 0977 0978 QCOMPARE(expectedResult, text); 0979 0980 ifNode.setNextNode(nullptr); 0981 } 0982 void TestDice::ifTest_data() 0983 { 0984 QTest::addColumn<QVector<int>>("values"); 0985 QTest::addColumn<int>("condition"); 0986 QTest::addColumn<int>("valCondition"); 0987 QTest::addColumn<QString>("expectedResult"); 0988 0989 int onEach= 0; 0990 int onEachValue= 1; 0991 int oneOfThem= 2; 0992 int allOfThem= 3; 0993 int onScalar= 4; 0994 0995 QTest::addRow("cmd1") << QVector<int>({8, 9, 2}) << onEach << 0 << "False"; 0996 QTest::addRow("cmd2") << QVector<int>({2, 2, 2}) << onEach << 2 << "True"; 0997 0998 QTest::addRow("cmd3") << QVector<int>({0, 0, 0}) << oneOfThem << 10 << "False"; 0999 QTest::addRow("cmd4") << QVector<int>({10, 9, 5}) << oneOfThem << 10 << "True"; 1000 QTest::addRow("cmd5") << QVector<int>({9, 9, 9}) << oneOfThem << 9 << "True"; 1001 1002 QTest::addRow("cmd6") << QVector<int>({8, 9, 2}) << allOfThem << 1 << "False"; 1003 QTest::addRow("cmd7") << QVector<int>({8, 9, 2}) << allOfThem << 9 << "False"; 1004 QTest::addRow("cmd8") << QVector<int>({8, 8, 8}) << allOfThem << 8 << "True"; 1005 1006 QTest::addRow("cmd9") << QVector<int>({25, 8, 14}) << onScalar << 1 << "False"; 1007 QTest::addRow("cmd10") << QVector<int>({25, 8, 14}) << onScalar << 47 << "True"; 1008 1009 // QTest::addRow("cmd11") << QVector<int>({25, 8, 14}) << onEachValue << 47 << 1010 // "True"; 1011 } 1012 1013 void TestDice::paintTest() {} 1014 void TestDice::paintTest_data() {} 1015 1016 void TestDice::filterTest() 1017 { 1018 QFETCH(QString, cmd); 1019 QFETCH(int, result); 1020 1021 auto parsing= m_diceParser->parseLine(cmd); 1022 QVERIFY2(parsing, "parsing"); 1023 1024 m_diceParser->start(); 1025 QVERIFY2(m_diceParser->humanReadableError().isEmpty(), "no error"); 1026 QVERIFY2(m_diceParser->humanReadableWarning().isEmpty(), "no warning"); 1027 1028 auto resultCmd= m_diceParser->scalarResultsFromEachInstruction(); 1029 1030 QCOMPARE(resultCmd.size(), 1); 1031 1032 QCOMPARE(resultCmd.first(), result); 1033 } 1034 1035 void TestDice::filterTest_data() 1036 { 1037 QTest::addColumn<QString>("cmd"); 1038 QTest::addColumn<int>("result"); 1039 1040 QTest::addRow("cmd1") << "[8, 4, 2]f4" << 4; 1041 QTest::addRow("cmd2") << "[0, 0, 0]f1" << 0; 1042 QTest::addRow("cmd3") << "[1, 2, 3]f[.>2&:>5]" << 6; 1043 QTest::addRow("cmd4") << "[1, 2, 6]f[.<2&>5]" << 6; 1044 QTest::addRow("cmd5") << "[2, 2, 6]f[.<2&>5]" << 0; 1045 QTest::addRow("cmd5") << "[1, 5, 1]f[.<2&>5]" << 0; 1046 } 1047 1048 void TestDice::uniqueTest() 1049 { 1050 QFETCH(QVector<int>, values); 1051 QFETCH(QVector<int>, expected); 1052 1053 TestNode node; 1054 UniqueNode unique; 1055 1056 DiceResult result; 1057 makeResult(result, values); 1058 node.setResult(&result); 1059 1060 node.setNextNode(&unique); 1061 node.run(nullptr); 1062 1063 auto list= dynamic_cast<DiceResult*>(unique.getResult())->getResultList(); 1064 QVector<int> resultVal; 1065 1066 std::transform(list.begin(), list.end(), std::back_inserter(resultVal), [](Die* die) { return die->getValue(); }); 1067 1068 QVERIFY(resultVal == expected); 1069 } 1070 1071 void TestDice::uniqueTest_data() 1072 { 1073 QTest::addColumn<QVector<int>>("values"); 1074 QTest::addColumn<QVector<int>>("expected"); 1075 1076 QTest::addRow("cmd1") << QVector<int>({8, 4, 2, 8}) << QVector<int>({8, 4, 2}); 1077 QTest::addRow("cmd2") << QVector<int>({8, 4, 2}) << QVector<int>({8, 4, 2}); 1078 } 1079 1080 void TestDice::spreadTest() 1081 { 1082 QFETCH(QVector<int>, values); 1083 1084 TestNode node; 1085 SplitNode split; 1086 1087 DiceResult result; 1088 makeResultExplode(result, values); 1089 node.setResult(&result); 1090 1091 node.setNextNode(&split); 1092 1093 node.run(nullptr); 1094 1095 auto list= dynamic_cast<DiceResult*>(split.getResult())->getResultList(); 1096 1097 auto expected= result.getResultList(); 1098 QVERIFY(list.size() == values.size()); 1099 } 1100 1101 void TestDice::spreadTest_data() 1102 { 1103 QTest::addColumn<QVector<int>>("values"); 1104 1105 QTest::addRow("cmd1") << QVector<int>({8, 4, 2}); 1106 } 1107 1108 void TestDice::groupTest() {} 1109 void TestDice::groupTest_data() {} 1110 1111 void TestDice::bindTest() {} 1112 void TestDice::bindTest_data() {} 1113 1114 void TestDice::occurenceTest() 1115 { 1116 QFETCH(QVector<int>, values); 1117 QFETCH(int, condition); 1118 QFETCH(QString, expected); 1119 1120 TestNode node; 1121 OccurenceCountNode count; 1122 1123 DiceResult result; 1124 makeResult(result, values); 1125 node.setResult(&result); 1126 1127 auto validator= makeValidator(QVector<int>() << condition, Dice::CompareOperator::GreaterThan); 1128 count.setValidatorList(validator); 1129 node.setNextNode(&count); 1130 1131 node.run(nullptr); 1132 1133 auto text= dynamic_cast<StringResult*>(count.getResult())->getText(); 1134 1135 QVERIFY(text.startsWith(expected)); 1136 } 1137 void TestDice::occurenceTest_data() 1138 { 1139 QTest::addColumn<QVector<int>>("values"); 1140 QTest::addColumn<int>("condition"); 1141 QTest::addColumn<QString>("expected"); 1142 1143 QTest::addRow("cmd1") << QVector<int>({8, 8, 2}) << 7 << "2x8"; 1144 QTest::addRow("cmd2") << QVector<int>({0, 0, 0}) << 1 << "No matching result"; 1145 } 1146 1147 void TestDice::ifCommandTest() 1148 { 1149 QFETCH(QString, cmd); 1150 QFETCH(Dice::CompareOperator, compare); 1151 QFETCH(QList<int>, level); 1152 QFETCH(QStringList, startExperted); 1153 1154 bool test= m_diceParser->parseLine(cmd); 1155 QVERIFY2(test, cmd.toStdString().c_str()); 1156 m_diceParser->start(); 1157 auto results= m_diceParser->scalarResultsFromEachInstruction(); 1158 auto strResult= m_diceParser->finalStringResult([](const QString& result, const QString&, bool) { return result; }); 1159 1160 QCOMPARE(results.size(), 1); 1161 1162 auto result= results.first(); 1163 auto it= std::find_if(level.begin(), level.end(), [compare, result](int level) { 1164 if(compare == Dice::CompareOperator::GreaterOrEqual) 1165 return result >= level; 1166 else if(compare == Dice::CompareOperator::GreaterThan) 1167 return result > level; 1168 else if(compare == Dice::CompareOperator::LesserThan) 1169 return result < level; 1170 else if(compare == Dice::CompareOperator::LesserOrEqual) 1171 return result <= level; 1172 else if(compare == Dice::CompareOperator::Equal) 1173 return qFuzzyCompare(result, level); 1174 else // if(compare == BooleanCondition::Different) 1175 return !qFuzzyCompare(result, level); 1176 }); 1177 1178 auto index= std::distance(level.begin(), it); 1179 1180 auto strResultExpected= startExperted[index]; 1181 auto resultText= strResult; 1182 1183 QVERIFY2(resultText.startsWith(strResultExpected), "string result does not fit the expectation"); 1184 } 1185 1186 void TestDice::ifCommandTest_data() 1187 { 1188 QTest::addColumn<QString>("cmd"); 1189 QTest::addColumn<Dice::CompareOperator>("compare"); 1190 QTest::addColumn<QList<int>>("level"); 1191 QTest::addColumn<QStringList>("startExperted"); 1192 1193 QTest::addRow("cmd1") << "2d10i:[>=15]{\"Complete Success: %1 " 1194 "[%2]\"}{i:[>=10]{\"Success with Complications: %1 " 1195 "[%2]\"}{\"Failure: %1 [%2]\"}}" 1196 << Dice::CompareOperator::GreaterOrEqual << QList<int>({15, 10, 1}) 1197 << QStringList({"Complete Success:", "Success with Complications:", "Failure:"}); 1198 QTest::addRow("cmd2") << "2d10;$1i:[>=15]{\"Complete Success: %1 [%2]\"}{$1i:[>=10]{\"Success " 1199 "with Complications: %1 " 1200 "[%2]\"}{\"Failure: %1 [%2]\"}}" 1201 << Dice::CompareOperator::GreaterOrEqual << QList<int>({15, 10, 1}) 1202 << QStringList({"Complete Success:", "Success with Complications:", "Failure:"}); 1203 } 1204 1205 void TestDice::operatoionConditionValidatorTest() 1206 { 1207 OperationCondition validator; 1208 NumberNode number; 1209 number.setNumber(2); 1210 validator.setValueNode(&number); 1211 1212 BooleanCondition subValidator; 1213 subValidator.setOperator(Dice::CompareOperator::Equal); 1214 NumberNode subnumber; 1215 subnumber.setNumber(0); 1216 subValidator.setValueNode(&subnumber); 1217 1218 validator.setBoolean(&subValidator); 1219 1220 std::set<qint64> data= {2, 4, 6, 8, 10}; 1221 auto value= validator.getPossibleValues(std::make_pair<qint64, qint64>(1, 10)); 1222 1223 subValidator.setValueNode(nullptr); 1224 validator.setValueNode(nullptr); 1225 validator.setBoolean(nullptr); 1226 1227 QCOMPARE(value, data); 1228 } 1229 1230 void TestDice::switchCaseTest() 1231 { 1232 QFETCH(int, value); 1233 QFETCH(QList<Dice::CompareOperator>, operatorList); 1234 QFETCH(QList<int>, threshold); 1235 QFETCH(QStringList, values); 1236 QFETCH(QString, expected); 1237 QFETCH(bool, stopatfirt); 1238 1239 NumberNode* valNode= new NumberNode(); 1240 ValuesListNode* node1= new ValuesListNode(); 1241 valNode->setNumber(value); 1242 node1->insertValue(valNode); 1243 1244 SwitchCaseNode* node2= new SwitchCaseNode(); 1245 node2->setStopAtFirt(stopatfirt); 1246 1247 int i= 0; 1248 for(const auto& val : values) 1249 { 1250 ValidatorList* validatorList= nullptr; 1251 if(i < threshold.size()) 1252 { 1253 validatorList= makeValidator(QVector<int>{threshold[i]}, operatorList[i]); 1254 } 1255 auto stringNode= new StringNode(); 1256 stringNode->setString(val); 1257 node2->insertCase(stringNode, validatorList); 1258 ++i; 1259 } 1260 1261 node1->setNextNode(node2); 1262 1263 node1->run(nullptr); 1264 1265 auto result= node2->getResult(); 1266 auto stringResult= result->getStringResult(); 1267 1268 QCOMPARE(stringResult, expected); 1269 } 1270 1271 void TestDice::switchCaseTest_data() 1272 { 1273 using BC= Dice::CompareOperator; 1274 QTest::addColumn<int>("value"); 1275 QTest::addColumn<QList<Dice::CompareOperator>>("operatorList"); 1276 QTest::addColumn<QList<int>>("threshold"); 1277 QTest::addColumn<QStringList>("values"); 1278 QTest::addColumn<QString>("expected"); 1279 QTest::addColumn<bool>("stopatfirt"); 1280 1281 QTest::addRow("cmd1") << 75 << QList<BC>{BC::Equal, BC::Equal} << QList<int>{75, 1} << QStringList{"a", "b"} 1282 << QStringLiteral("a") << false; 1283 1284 QTest::addRow("cmd2") << 1 << QList<BC>{BC::Equal, BC::Equal} << QList<int>{75, 1} << QStringList{"a", "b"} 1285 << QStringLiteral("b") << true; 1286 1287 QTest::addRow("cmd3") << 7 1288 << QList<BC>{BC::GreaterThan, BC::GreaterThan, BC::GreaterThan, BC::GreaterThan, 1289 BC::GreaterThan} 1290 << QList<int>{8, 29, 99, 54, 1} << QStringList{"a", "b", "c", "d", "e"} << QStringLiteral("e") 1291 << false; 1292 1293 QTest::addRow("cmd4") << 75 << QList<BC>{BC::LesserThan, BC::LesserThan, BC::LesserThan} << QList<int>{8, 7} 1294 << QStringList{"a", "b", "c"} << QStringLiteral("c") << false; 1295 1296 QTest::addRow("cmd5") << 2 << QList<BC>{BC::Different, BC::Different} << QList<int>{1, 2} << QStringList{"a", "b"} 1297 << QStringLiteral("a") << false; 1298 1299 QTest::addRow("cmd6") << 3 1300 << QList<BC>{BC::GreaterOrEqual, BC::GreaterOrEqual, BC::GreaterOrEqual, BC::GreaterOrEqual} 1301 << QList<int>{1, 2, 3, 4} << QStringList{"a", "b", "c", "d"} << QStringLiteral("a,b,c") 1302 << false; 1303 1304 QTest::addRow("cmd7") << 3 << QList<BC>{BC::LesserOrEqual, BC::LesserOrEqual, BC::LesserOrEqual, BC::LesserOrEqual} 1305 << QList<int>{1, 2, 3, 4} << QStringList{"a", "b", "c", "d"} << QStringLiteral("c") << true; 1306 } 1307 1308 void TestDice::deterministTest() 1309 { 1310 QFETCH(QString, command); 1311 QFETCH(QList<qreal>, results); 1312 1313 auto parsing= m_diceParser->parseLine(command); 1314 QVERIFY2(parsing, "parsing"); 1315 m_diceParser->start(); 1316 QVERIFY2(m_diceParser->humanReadableError().isEmpty(), "no error"); 1317 QVERIFY2(m_diceParser->humanReadableWarning().isEmpty(), "no warning"); 1318 1319 auto resultCmd= m_diceParser->scalarResultsFromEachInstruction(); 1320 QCOMPARE(results, resultCmd); 1321 } 1322 1323 void TestDice::deterministTest_data() 1324 { 1325 QTest::addColumn<QString>("command"); 1326 QTest::addColumn<QList<qreal>>("results"); 1327 1328 QTest::addRow("cmd1") << "10;20;10+20;5-3;[$1,$2,$3]k$4" << QList<qreal>{10, 20, 30, 2, 50}; 1329 QTest::addRow("cmd2") << "6;[10,7,8,4,4,3,2,2,1]k$1" << QList<qreal>{6, 36}; 1330 1331 // 1d6;10d10e10k\$1 1332 } 1333 1334 void TestDice::cleanupTestCase() {} 1335 1336 QTEST_MAIN(TestDice) 1337 1338 #include "tst_dice.moc"