File indexing completed on 2024-10-06 06:48:45
0001 // kate: space-indent on; indent-width 2; replace-tabs on; 0002 /* This file is part of KsirK. 0003 Copyright (C) 2006-2007 Gael de Chalendar <kleag@free.fr> 0004 0005 This file was initialy part of XFrisk 0006 Copyright (C) 1995 and later Jean-Claude Colson and Others <who@nowhere.org> 0007 0008 KsirK is free software; you can redistribute it and/or 0009 modify it under the terms of the GNU General Public 0010 License as published by the Free Software Foundation, either version 2 0011 of the License, or (at your option) any later version. 0012 0013 This program is distributed in the hope that it will be useful, 0014 but WITHOUT ANY WARRANTY; without even the implied warranty of 0015 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 0016 General Public License for more details. 0017 0018 * You should have received a copy of the GNU General Public License 0019 * along with this program; if not, write to the Free Software 0020 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 0021 * 02110-1301, USA 0022 */ 0023 /*********************************************************************** 0024 * 0025 * 18-8-95 Created by Jean-Claude Colson. 0026 * 0027 * RISK game player. 0028 * $Id: aiColson.c,v 1.5 1999/11/07 15:57:29 tony Exp $ 0029 * 0030 ***********************************************************************/ 0031 0032 #include "aiColsonPlayer.h" 0033 0034 #include "onu.h" 0035 #include "goal.h" 0036 #include "continent.h" 0037 #include "gameautomaton.h" 0038 #include "kgamewin.h" 0039 #include "xfriskaiclient.h" 0040 #include "aiplayerio.h" 0041 #include "dice.h" 0042 0043 #include <assert.h> 0044 0045 namespace Ksirk 0046 { 0047 0048 namespace GameLogic 0049 { 0050 0051 0052 AIColsonPlayer::AIColsonPlayer( 0053 const QString & nomPlayer, unsigned int nbArmies, 0054 Nationality * myNation, PlayersArray& players, ONU* world, 0055 GameAutomaton* game ) : 0056 AIPlayer(nomPlayer, nbArmies, myNation, players, world, game ), 0057 m_levelEnemy(0), 0058 m_initialized(false), 0059 Attack_SrcCountry(-1), 0060 Attack_DestCountry(-1), 0061 m_placeData(nullptr) 0062 { 0063 qCDebug(KSIRK_LOG); 0064 } 0065 0066 AIColsonPlayer::~AIColsonPlayer() 0067 { 0068 delete m_placeData; 0069 } 0070 0071 ////////////////////////////////////////////////////////// 0072 // Virtual functions reimplemented from AIPlayer 0073 ////////////////////////////////////////////////////////// 0074 0075 QPair< const Country*, const Country* > AIColsonPlayer::chooseBelligerant() 0076 { 0077 qCDebug(KSIRK_LOG); 0078 Fortify(); 0079 Country* src = nullptr; 0080 Country* dest = nullptr; 0081 0082 // Attack_SrcCountry = -1; 0083 // Attack_DestCountry = -1; 0084 0085 // no attack was tempted 0086 if (!Attack()) 0087 { 0088 Attack_SrcCountry = -1; 0089 Attack_DestCountry = -1; 0090 return qMakePair<const Country*, const Country*>(static_cast<Country*>(nullptr), static_cast<Country*>(nullptr)); 0091 } 0092 0093 if ( (Attack_SrcCountry>=0) && (Attack_SrcCountry<m_world->getCountries().size() ) ) 0094 src = m_world->getCountries().at(Attack_SrcCountry); 0095 if ( (Attack_DestCountry>=0) && (Attack_DestCountry<m_world->getCountries().size() ) ) 0096 dest = m_world->getCountries().at(Attack_DestCountry); 0097 // qCDebug(KSIRK_LOG) << "chose belligerants " << src << " and " << dest; 0098 return qMakePair(src,dest); 0099 } 0100 0101 /** 0102 * Chooses the next action. Attack by default and if no attack is possible, 0103 * try to move armies and in the last resort, choose next player 0104 */ 0105 void AIColsonPlayer::chooseAttackMoveArmiesOrNextPlayer() 0106 { 0107 qCDebug(KSIRK_LOG); 0108 if (m_game->game()->haveAnimFighters() || m_game->game()->haveMovingArmies()) 0109 { 0110 return; 0111 } 0112 if (!m_initialized) 0113 { 0114 finalize(); 0115 } 0116 0117 if (!attackAction()) 0118 { 0119 if (!moveArmiesAction()) 0120 { 0121 nextPlayerAction(); 0122 } 0123 } 0124 // qCDebug(KSIRK_LOG) <<"OUT AIColsonPlayer::chooseAttackMoveArmiesOrNextPlayer()"; 0125 } 0126 0127 /** 0128 * Chooses a country to receive a new army in dotation 0129 */ 0130 Country* AIColsonPlayer::chooseReceivingCountry() 0131 { 0132 qCDebug(KSIRK_LOG); 0133 if (m_placeData == nullptr) 0134 { 0135 if (!Place()) 0136 { 0137 return nullptr; 0138 } 0139 } 0140 Country* res = m_placeData->dest; 0141 m_placeData->nb--; 0142 if (m_placeData->nb == 0) 0143 { 0144 delete m_placeData; 0145 m_placeData = nullptr; 0146 } 0147 return res; 0148 } 0149 0150 /** 0151 * chooses to continue invasion with a certain amount of armies or to stop it 0152 */ 0153 void AIColsonPlayer::chooseInvasionAction() 0154 { 0155 qCDebug(KSIRK_LOG); 0156 qCDebug(KSIRK_LOG) << " Attack_SrcCountry = " << Attack_SrcCountry; 0157 qCDebug(KSIRK_LOG) << " Attack_DestCountry = " << Attack_DestCountry; 0158 if (Attack_SrcCountry == - 1 || Attack_DestCountry == -1) 0159 { 0160 stop(); 0161 QByteArray buffer; 0162 QDataStream stream(&buffer, QIODevice::WriteOnly); 0163 QPointF point; 0164 stream << QString("actionInvasionFinished") << point; 0165 aiPlayerIO()->sendInput(stream,true); 0166 m_toMove = std::numeric_limits< unsigned int>::max(); 0167 return; 0168 } 0169 0170 if (m_toMove == std::numeric_limits< unsigned int>::max()) 0171 { 0172 int nbEnemiesAdjacentToSrc = NbToEqualEnemyAdjacent(m_world->getCountries().at(Attack_SrcCountry)); 0173 int nbEnemiesAdjacentToDest = NbToEqualEnemyAdjacent(m_world->getCountries().at(Attack_DestCountry)); 0174 qCDebug(KSIRK_LOG) << " nb on src = " << RISK_GetNumArmiesOfCountry(Attack_SrcCountry); 0175 qCDebug(KSIRK_LOG) << " nb adj to src = " << nbEnemiesAdjacentToSrc; 0176 qCDebug(KSIRK_LOG) << " nb adj to dest = " << nbEnemiesAdjacentToDest; 0177 int diff = nbEnemiesAdjacentToDest - nbEnemiesAdjacentToSrc; 0178 qCDebug(KSIRK_LOG) << " diff = " << diff; 0179 0180 0181 0182 m_toMove = (diff>RISK_GetNumArmiesOfCountry(Attack_SrcCountry)-1)?RISK_GetNumArmiesOfCountry(Attack_SrcCountry)-1:(diff<0?0:diff); 0183 qCDebug(KSIRK_LOG) << " moves " << m_toMove; 0184 } 0185 0186 QByteArray buffer; 0187 QDataStream stream(&buffer, QIODevice::WriteOnly); 0188 QPoint point; 0189 qCDebug(KSIRK_LOG) << "Moves *****************" << m_toMove; 0190 if (m_toMove >= 10) 0191 { 0192 qCDebug(KSIRK_LOG) << " choosing actionInvade10"; 0193 stop(); 0194 stream << QString("actionInvade10") << point; 0195 aiPlayerIO()->sendInput(stream,true); 0196 m_toMove -= 10; 0197 } 0198 else if (m_toMove >= 5) 0199 { 0200 qCDebug(KSIRK_LOG) << " choosing actionInvade5"; 0201 stop(); 0202 stream << QString("actionInvade5") << point; 0203 aiPlayerIO()->sendInput(stream,true); 0204 m_toMove -= 5; 0205 } 0206 else if (m_toMove >= 1) 0207 { 0208 qCDebug(KSIRK_LOG) << " choosing actionInvade1"; 0209 stop(); 0210 stream << QString("actionInvade1") << point; 0211 aiPlayerIO()->sendInput(stream,true); 0212 m_toMove--; 0213 } 0214 else 0215 { 0216 qCDebug(KSIRK_LOG) << " choosing actionInvasionFinished"; 0217 stop(); 0218 stream << QString("actionInvasionFinished") << point; 0219 aiPlayerIO()->sendInput(stream,true); 0220 m_toMove = std::numeric_limits< unsigned int>::max(); 0221 } 0222 } 0223 0224 /** 0225 * makes all what is necessary to prepare and start the moving of armies 0226 */ 0227 bool AIColsonPlayer::moveArmiesAction() 0228 { 0229 qCDebug(KSIRK_LOG); 0230 bool res = Move(); 0231 qCDebug(KSIRK_LOG) << "Move got " << res; 0232 return res; 0233 } 0234 0235 ////////////////////////////////////////////////////////// 0236 // XFrisk AIColson functions 0237 ////////////////////////////////////////////////////////// 0238 int AIColsonPlayer::getTotalArmiesOfPlayer(const Player* player) 0239 { 0240 int nb = 0; 0241 for (int i=0; i<m_world->getCountries().size(); i++) 0242 { 0243 if (m_world->getCountries().at(i)->owner() == player) 0244 { 0245 nb += m_world->getCountries().at(i)->nbArmies(); 0246 } 0247 } 0248 return nb; 0249 } 0250 0251 0252 bool AIColsonPlayer::isContinentOfMission(const Player* player, const Continent* continent) 0253 { 0254 if (player->goal().type() != Goal::Continents) 0255 return false; 0256 return (player->goal().continents().contains(continent->name())); 0257 } 0258 0259 bool AIColsonPlayer::isEnemyPlayer(const Player* player) 0260 { 0261 return m_isEnemyPlayer[player]; 0262 } 0263 0264 bool AIColsonPlayer::isFriendPlayer(const Player* player) 0265 { 0266 return (player==this); 0267 // return m_isEnemyPlayer[player] < m_levelEnemy; 0268 } 0269 0270 int AIColsonPlayer::getNumEnemy() 0271 { 0272 qCDebug(KSIRK_LOG); 0273 int nb = 0; 0274 0275 PlayersArray::iterator it = m_game->playerList()->begin(); 0276 PlayersArray::iterator it_end = m_game->playerList()->end(); 0277 for (; it != it_end; it++) 0278 { 0279 if (m_isEnemyPlayer[((Player*)(*it))]>= m_levelEnemy) 0280 { 0281 nb++; 0282 } 0283 } 0284 if (m_levelEnemy == 1) 0285 nb--; 0286 return(nb); 0287 } 0288 0289 bool AIColsonPlayer::isStrongerPlayer(const Player* player) 0290 { 0291 int nb; 0292 0293 nb = getTotalArmiesOfPlayer(player); 0294 nb = nb + nb/5; 0295 PlayersArray::iterator it = m_game->playerList()->begin(); 0296 PlayersArray::iterator it_end = m_game->playerList()->end(); 0297 for (; it != it_end; it++) 0298 { 0299 if (getTotalArmiesOfPlayer(((Player*)(*it))) > nb) 0300 { 0301 return false; 0302 } 0303 } 0304 return true; 0305 } 0306 0307 bool AIColsonPlayer::isSmallerPlayer(const Player* player) 0308 { 0309 int nb = 3 * getTotalArmiesOfPlayer(player); 0310 PlayersArray::iterator it = m_game->playerList()->begin(); 0311 PlayersArray::iterator it_end = m_game->playerList()->end(); 0312 for (; it != it_end; it++) 0313 { 0314 if (getTotalArmiesOfPlayer(((Player*)(*it))) > nb) 0315 { 0316 return false; 0317 } 0318 } 0319 return false; 0320 } 0321 0322 bool AIColsonPlayer::isContinentOfPlayer(const Continent* continent, const Player* player) 0323 { 0324 if (continent == nullptr) 0325 { 0326 return false; 0327 } 0328 return (continent->owner() == player); 0329 } 0330 0331 const Continent* AIColsonPlayer::computeChoiceOfContinent(void) 0332 { 0333 // qCDebug(KSIRK_LOG); 0334 std::map< const KPlayer*, std::map <const Continent*, int > > piCount; 0335 std::map< const KPlayer*, std::map <const Continent*, bool > > maxContinent; 0336 std::map< const KPlayer*, std::map <const Continent*, bool > > posContinent; 0337 std::map<const KPlayer*, const Continent*> m_piContinent; 0338 0339 QList<Continent*>::iterator continentsIt = (m_world->getContinents().begin()); 0340 QList<Continent*>::iterator continentsIt_end = (m_world->getContinents().end()); 0341 0342 PlayersArray::iterator it = m_game->playerList()->begin(); 0343 PlayersArray::iterator it_end = m_game->playerList()->end(); 0344 for (; it != it_end; it++) 0345 { 0346 0347 continentsIt = m_world->getContinents().begin(); 0348 continentsIt_end = m_world->getContinents().end(); 0349 for (; continentsIt != continentsIt_end; continentsIt++) 0350 { 0351 Continent *continent = *continentsIt; 0352 // qCDebug(KSIRK_LOG) << " " << continent; 0353 if (continent == nullptr) continue; 0354 // qCDebug(KSIRK_LOG) << " " << continent->name(); 0355 piCount[((Player*)(*it))][continent] = 0; 0356 maxContinent[((Player*)(*it))][continent] = false; 0357 posContinent[((Player*)(*it))][continent] = false; 0358 } 0359 } 0360 0361 for (int i=0; i<m_world->getCountries().size(); i++) 0362 { 0363 /* QList<Country*>::iterator countriesIt(m_world->getCountries().begin()); 0364 QList<Country*>::iterator countriesIt_end(m_world->getCountries().end()); 0365 for (; countriesIt != countriesIt_end; countriesIt++) 0366 {*/ 0367 Country* country = m_world->getCountries().at(i); 0368 // qCDebug(KSIRK_LOG) << "country " << country << ; 0369 // qCDebug(KSIRK_LOG) << "country " << country->name().toUtf8().data(); 0370 if ( country->owner() != nullptr && country->continent() != nullptr) 0371 { 0372 piCount[country->owner()][country->continent()]++; 0373 // qCDebug(KSIRK_LOG) << "piCount[" << country->owner()->name().toUtf8().data() << "][" << country->continent()->name().toUtf8().data() << "] "; 0374 // qCDebug(KSIRK_LOG) << " is now " << piCount[country->owner()][country->continent()]; 0375 } 0376 else 0377 { 0378 // qCDebug(KSIRK_LOG) << "owner or continent of country " << country->name().toUtf8().data() << " is null..."; 0379 } 0380 } 0381 0382 it = m_game->playerList()->begin(); 0383 it_end = m_game->playerList()->end(); 0384 for (; it != it_end; it++) 0385 { 0386 int min = 10000; 0387 int max = 0; 0388 int bonus = 0; 0389 for (continentsIt = m_world->getContinents().begin(); 0390 continentsIt!=continentsIt_end; ++continentsIt) 0391 { 0392 const Continent* continent = *continentsIt; 0393 if (piCount[*it][continent] > 0) 0394 { 0395 if (min == 0) 0396 { 0397 if ( (piCount[*it][continent] == continent->getMembers().size()) 0398 && (continent->getBonus()>bonus)) 0399 { 0400 qCDebug(KSIRK_LOG) << "pt2"; 0401 max = piCount[*it][continent]; 0402 bonus = continent->getBonus(); 0403 maxContinent[*it][continent] = true; 0404 m_piContinent[*it] = continent; 0405 } 0406 } 0407 else if (piCount[*it][continent] == continent->getMembers().size()) 0408 { 0409 min = 0; 0410 max = piCount[*it][continent]; 0411 maxContinent[*it][continent] = true; 0412 m_piContinent[*it] = continent; 0413 } 0414 else if (piCount[*it][continent] > max) 0415 { 0416 QList<Continent*>::iterator jit(m_world->getContinents().begin()); 0417 QList<Continent*>::iterator jit_end(m_world->getContinents().end()); 0418 for (; jit!=jit_end; jit++) 0419 { 0420 Continent* j = *jit; 0421 maxContinent[*it][j] = false; 0422 if (piCount[*it][j] < max-1) 0423 posContinent[*it][j] = (piCount[*it][continent] < continent->getMembers().size()/2); 0424 else 0425 posContinent[*it][j] = true; 0426 } 0427 min = continent->getMembers().size() - piCount[*it][continent]; 0428 max = piCount[*it][continent]; 0429 bonus = continent->getBonus(); 0430 maxContinent[*it][continent] = true; 0431 } 0432 else if ( (piCount[*it][continent] == max) 0433 && isContinentOfMission(dynamic_cast<Player*>(*it), continent)) 0434 { 0435 min = continent->getMembers().size() 0436 - piCount[*it][continent]; 0437 bonus = 2 * continent->getBonus(); 0438 maxContinent[*it][continent] = true; 0439 } 0440 else if ( (piCount[*it][continent] == max) 0441 && (continent->getBonus() > bonus)) 0442 { 0443 min = continent->getMembers().size() - piCount[*it][continent]; 0444 bonus = continent->getBonus(); 0445 maxContinent[*it][continent] = true; 0446 } 0447 else if (piCount[*it][continent] >= continent->getMembers().size()/2) 0448 { 0449 posContinent[*it][continent] = true; 0450 } 0451 } 0452 } 0453 } 0454 0455 /* Search a continent with no conflict */ 0456 const Continent* continent = nullptr; 0457 QList<Continent*>::iterator contIt(m_world->getContinents().begin()); 0458 QList<Continent*>::iterator contIt_end(m_world->getContinents().end()); 0459 for (;(contIt!=contIt_end) && (continent==nullptr);contIt++) 0460 { 0461 const Continent* cont = *contIt; 0462 0463 if (maxContinent[this][cont]) 0464 { 0465 continent = cont; 0466 0467 PlayersArray::iterator iit = m_game->playerList()->begin(); 0468 PlayersArray::iterator iit_end = m_game->playerList()->end(); 0469 for (;iit!=iit_end;iit++) 0470 { 0471 Player* i = static_cast<Player*>(*iit); 0472 if (i != this) 0473 { 0474 if ( m_piContinent[i] == cont) 0475 continent = *(m_world->getContinents().begin()); 0476 else if ( (maxContinent[i][cont]) 0477 && (piCount[i][cont] > piCount[this][cont])) 0478 continent = nullptr; 0479 } 0480 } 0481 } 0482 } 0483 0484 if (isFriendPlayer(this) && (continent!=nullptr)) 0485 { 0486 QList<Continent*>::iterator contIt(m_world->getContinents().begin()); 0487 QList<Continent*>::iterator contIt_end(m_world->getContinents().end()); 0488 0489 // FIXME: continent can not be 0 in this code path - everything in this for loop is dead code 0490 0491 for (;(contIt!=contIt_end) && (continent==nullptr);contIt++) 0492 { 0493 const Continent* cont = *contIt; 0494 if (cont != continent) 0495 { 0496 maxContinent[this][cont] = false; 0497 posContinent[this][cont] = false; 0498 } 0499 } 0500 PlayersArray::iterator iit = m_game->playerList()->begin(); 0501 PlayersArray::iterator iit_end = m_game->playerList()->end(); 0502 for (;iit!=iit_end;iit++) 0503 { 0504 Player* i = static_cast<Player*>(*iit); 0505 posContinent[i][continent] = false; 0506 } 0507 return continent; 0508 } 0509 0510 /* Search a continent with no computer conflict */ 0511 continent = nullptr; 0512 contIt = m_world->getContinents().begin(); 0513 contIt_end = m_world->getContinents().end(); 0514 for (;(contIt!=contIt_end) && (continent==nullptr);contIt++) 0515 { 0516 const Continent* cont = *contIt; 0517 if (maxContinent[this][cont]) 0518 { 0519 continent = cont; 0520 PlayersArray::iterator iit = m_game->playerList()->begin(); 0521 PlayersArray::iterator iit_end = m_game->playerList()->end(); 0522 for (;iit!=iit_end;iit++) 0523 { 0524 Player* i = static_cast<Player*>(*iit); 0525 if (isFriendPlayer(i) && (i != this)) 0526 { 0527 if ( m_piContinent[i] == cont) 0528 continent = nullptr; 0529 else if ( (maxContinent[i][cont]) 0530 && (piCount[i][cont] > piCount[this][cont])) 0531 continent = nullptr; 0532 } 0533 } 0534 } 0535 } 0536 0537 if (continent!=nullptr) 0538 { 0539 QList<Continent*>::iterator contIt(m_world->getContinents().begin()); 0540 QList<Continent*>::iterator contIt_end(m_world->getContinents().end()); 0541 for (;contIt!=contIt_end;contIt++) 0542 { 0543 const Continent* cont = *contIt; 0544 //for (cont=0; cont!=m_world->getContinents().count(); cont++) 0545 if (cont != continent) 0546 { 0547 maxContinent[this][cont] = false; 0548 posContinent[this][cont] = false; 0549 } 0550 } 0551 PlayersArray::iterator iit = m_game->playerList()->begin(); 0552 PlayersArray::iterator iit_end = m_game->playerList()->end(); 0553 for (;iit!=iit_end;iit++) 0554 { 0555 Player* pi = static_cast<Player*>(*iit); 0556 posContinent[pi][continent] = false; 0557 } 0558 qCDebug(KSIRK_LOG) << "pt5"; 0559 return continent; 0560 } 0561 0562 0563 /* Search a possible continent with no conflict */ 0564 continent = nullptr; 0565 contIt = m_world->getContinents().begin(); 0566 contIt_end = m_world->getContinents().end(); 0567 for (;(contIt!=contIt_end) && (continent==nullptr);contIt++) 0568 { 0569 const Continent* cont = *contIt; 0570 if (posContinent[this][cont]) 0571 { 0572 continent = cont; 0573 PlayersArray::iterator iit = m_game->playerList()->begin(); 0574 PlayersArray::iterator iit_end = m_game->playerList()->end(); 0575 for (;iit!=iit_end;iit++) 0576 { 0577 Player* pi = static_cast<Player*>(*iit); 0578 if (isFriendPlayer(pi) && (pi != this)) 0579 { 0580 if ( m_piContinent[pi] == cont) 0581 continent = nullptr; 0582 else if ( (maxContinent[pi][cont]) 0583 && (piCount[pi][cont] > piCount[this][cont])) 0584 continent = nullptr; 0585 } 0586 } 0587 } 0588 } 0589 0590 if (continent!=nullptr) 0591 { 0592 QList<Continent*>::iterator contIt(m_world->getContinents().begin()); 0593 QList<Continent*>::iterator contIt_end(m_world->getContinents().end()); 0594 for (;contIt!=contIt_end;contIt++) 0595 { 0596 const Continent* cont = *contIt; 0597 //for (cont=0; cont!=m_world->getContinents().count(); cont++) 0598 if (cont != continent) 0599 { 0600 maxContinent[this][cont] = false; 0601 posContinent[this][cont] = false; 0602 } 0603 } 0604 PlayersArray::iterator iit = m_game->playerList()->begin(); 0605 PlayersArray::iterator iit_end = m_game->playerList()->end(); 0606 for (;iit!=iit_end;iit++) 0607 { 0608 Player* pi = static_cast<Player*>(*iit); 0609 posContinent[pi][continent] = false; 0610 } 0611 qCDebug(KSIRK_LOG) << "pt6"; 0612 return continent; 0613 } 0614 0615 /* Search a possible continent with no computer conflict */ 0616 continent = nullptr; 0617 contIt = m_world->getContinents().begin(); 0618 contIt_end = m_world->getContinents().end(); 0619 for (;(contIt!=contIt_end) && (continent==nullptr);contIt++) 0620 { 0621 const Continent* cont = *contIt; 0622 if (posContinent[this][cont]) 0623 { 0624 continent = cont; 0625 PlayersArray::iterator iit = m_game->playerList()->begin(); 0626 PlayersArray::iterator iit_end = m_game->playerList()->end(); 0627 for (;iit!=iit_end;iit++) 0628 { 0629 Player* pi = static_cast<Player*>(*iit); 0630 if (isFriendPlayer(pi) && (pi != this)) 0631 { 0632 if ( m_piContinent[pi] == cont) 0633 continent = nullptr; 0634 else if ( (maxContinent[pi][cont]) 0635 && (piCount[pi][cont] > piCount[this][cont])) 0636 continent = nullptr; 0637 } 0638 } 0639 } 0640 } 0641 0642 if (continent!=nullptr) 0643 { 0644 QList<Continent*>::iterator contIt(m_world->getContinents().begin()); 0645 QList<Continent*>::iterator contIt_end(m_world->getContinents().end()); 0646 for (;contIt!=contIt_end;contIt++) 0647 { 0648 const Continent* cont = *contIt; 0649 if (cont != continent) 0650 { 0651 maxContinent[this][cont] = false; 0652 } 0653 } 0654 qCDebug(KSIRK_LOG) << "pt7"; 0655 return continent; 0656 } 0657 0658 continent = nullptr; 0659 0660 /* Search a continent */ 0661 contIt = m_world->getContinents().begin(); 0662 contIt_end = m_world->getContinents().end(); 0663 for (;(contIt!=contIt_end) && (continent==nullptr);contIt++) 0664 { 0665 const Continent* cont = *contIt; 0666 if (piCount[this][cont]>0) 0667 { 0668 continent = cont; 0669 PlayersArray::iterator iit = m_game->playerList()->begin(); 0670 PlayersArray::iterator iit_end = m_game->playerList()->end(); 0671 for (;iit!=iit_end;iit++) 0672 { 0673 Player* pi = static_cast<Player*>(*iit); 0674 if (isFriendPlayer(pi) && (pi != this)) 0675 continent = nullptr; 0676 } 0677 } 0678 } 0679 0680 if (continent!=nullptr) 0681 { 0682 QList<Continent*>::iterator contIt(m_world->getContinents().begin()); 0683 QList<Continent*>::iterator contIt_end(m_world->getContinents().end()); 0684 for (;contIt!=contIt_end;contIt++) 0685 { 0686 const Continent* cont = *contIt; 0687 if (cont!=continent) 0688 { 0689 maxContinent[this][cont] = false; 0690 } 0691 } 0692 qCDebug(KSIRK_LOG) << "pt8"; 0693 return continent; 0694 } 0695 0696 continent = nullptr; 0697 0698 /* Search a continent */ 0699 contIt = m_world->getContinents().begin(); 0700 contIt_end = m_world->getContinents().end(); 0701 for (;(contIt!=contIt_end) && (continent==nullptr);contIt++) 0702 { 0703 const Continent* cont = *contIt; 0704 if (maxContinent[this][cont]) 0705 continent = cont; 0706 } 0707 0708 // qCDebug(KSIRK_LOG) << "AIColsonPlayer::computeChoiceOfContinent for " << name().toUtf8().data() 0709 // << " is " << continent; 0710 return continent; 0711 } 0712 0713 /** 0714 * Gets the continent already selected for this player 0715 * @param attack This is the number of countries of the selected continent 0716 * that have at least one adjacent enemy 0717 */ 0718 const Continent* AIColsonPlayer::GetContinentToFortify(int *attack) 0719 { 0720 qCDebug(KSIRK_LOG); 0721 const Continent* continent = computeChoiceOfContinent(); 0722 qCDebug(KSIRK_LOG) << " computeChoiceOfContinent got " << continent; 0723 *attack = 0; 0724 for (int i=0; i!=m_world->getCountries().size(); i++) 0725 { 0726 if ( (RISK_GetOwnerOfCountry(i) == this) 0727 && (RISK_GetContinentOfCountry(i) == continent) 0728 && GAME_IsEnemyAdjacent(i)) 0729 { 0730 (*attack)++; 0731 } 0732 } 0733 qCDebug(KSIRK_LOG) << "found " << continent; 0734 return(continent); 0735 } 0736 0737 /** 0738 * @param attack Number of countries with adjacent ennemies in the selected 0739 * continent 0740 */ 0741 const Continent* AIColsonPlayer::getContinentToConquier(int *attack) 0742 { 0743 qCDebug(KSIRK_LOG); 0744 std::map<const Continent*, int> piCount; 0745 std::map<const Continent*, int> piOppo; 0746 std::map<const Continent*, int> piAttac; 0747 0748 /* Init. */ 0749 QList<Continent*>::iterator contIt(m_world->getContinents().begin()); 0750 QList<Continent*>::iterator contIt_end(m_world->getContinents().end()); 0751 for (;contIt!=contIt_end;contIt++) 0752 { 0753 const Continent* cont = *contIt; 0754 piCount[cont] = 0; 0755 piOppo[cont] = 0; 0756 piAttac[cont] = 0; 0757 } 0758 0759 /* Count up how many countries the player has in each of the continents */ 0760 QList<Country*>::iterator countriesIt(m_world->getCountries().begin()); 0761 QList<Country*>::iterator countriesIt_end(m_world->getCountries().end()); 0762 for (; countriesIt != countriesIt_end; countriesIt++) 0763 { 0764 Country* country = *countriesIt; 0765 if (country->owner() == this) 0766 { 0767 piCount[country->continent()]++; 0768 piOppo[country->continent()] -= country->nbArmies(); 0769 if (country->hasAdjacentEnemy()) 0770 piAttac[country->continent()]++; 0771 } 0772 else 0773 { 0774 if (isEnemyPlayer(country->owner())) 0775 piOppo[country->continent()] += country->nbArmies(); 0776 else 0777 piOppo[country->continent()] += 2 * country->nbArmies(); 0778 } 0779 } 0780 0781 const Continent* continent = nullptr; 0782 int min = 10000; 0783 contIt = m_world->getContinents().begin(); 0784 contIt_end = m_world->getContinents().end(); 0785 for (; contIt != contIt_end; contIt++) 0786 { 0787 const Continent* cont = *contIt; 0788 qCDebug(KSIRK_LOG) << " " << cont; 0789 if (cont != nullptr) 0790 qCDebug(KSIRK_LOG) << " " << cont->name(); 0791 if (isContinentOfMission(this, cont)) 0792 { 0793 piOppo[cont] -= piOppo[cont]/3; 0794 } 0795 if (piCount[cont] < cont->getMembers().size()) 0796 { 0797 if (piOppo[cont] < min) 0798 { 0799 continent = cont; 0800 min = piOppo[cont]; 0801 } 0802 } 0803 } 0804 0805 *attack = piAttac[continent]; 0806 return(continent); 0807 } 0808 0809 int AIColsonPlayer::NbEnemyAdjacent(Country* iCountry) 0810 { 0811 std::map<Player*, unsigned int> NumEnemy; 0812 std::map<Player*, bool> fIsEnemy; 0813 bool fIAmStrong; 0814 0815 Player* player = iCountry->owner(); 0816 fIAmStrong = isStrongerPlayer(player); 0817 PlayersArray::iterator pit = m_game->playerList()->begin(); 0818 PlayersArray::iterator pit_end = m_game->playerList()->end(); 0819 for (; pit != pit_end; pit++) 0820 { 0821 fIsEnemy[(Player*)(*pit)] = false; 0822 } 0823 Player* iEnemy = nullptr; 0824 Country* destCountry; 0825 QList<Country*>::const_iterator it, it_end; 0826 it = iCountry->neighbours().constBegin(); 0827 it_end = iCountry->neighbours().constEnd(); 0828 for (;it != it_end; it++) 0829 { 0830 destCountry = *it; 0831 iEnemy = destCountry->owner(); 0832 if (iEnemy != player) 0833 { 0834 if (NumEnemy[iEnemy] < destCountry->nbArmies()) 0835 NumEnemy[iEnemy] = destCountry->nbArmies(); 0836 fIsEnemy[iEnemy] = true; 0837 } 0838 } 0839 int max = 0; 0840 pit = m_game->playerList()->begin(); 0841 pit_end = m_game->playerList()->end(); 0842 for (; pit != pit_end; pit++) 0843 { 0844 Player* i = (Player*)(*pit); 0845 if ((i != player) && fIsEnemy[i]) 0846 { 0847 int nb = NumEnemy[iEnemy]; 0848 if (!fIAmStrong && isStrongerPlayer(i)) 0849 nb = nb + 10; 0850 if (isEnemyPlayer(i)) 0851 nb = nb + 5; 0852 if (nb > max) 0853 max = nb; 0854 } 0855 } 0856 return max; 0857 } 0858 0859 int AIColsonPlayer::NbToAverageEnemyAdjacent(Country* iCountry) 0860 { 0861 int nbe = 0; 0862 int nb = 0; 0863 int i = 0; 0864 QList<Country*>::const_iterator neighbourIt, neighbourIt_end; 0865 neighbourIt = iCountry->neighbours().constBegin(); 0866 neighbourIt_end = iCountry->neighbours().constEnd(); 0867 for (;neighbourIt != neighbourIt_end; neighbourIt++) 0868 { 0869 Country* destCountry = *neighbourIt; 0870 Player* iEnemy = destCountry->owner(); 0871 if (iEnemy != this) 0872 { 0873 nbe -= destCountry->nbArmies(); 0874 nb++; 0875 } 0876 i++; 0877 } 0878 int nbi = iCountry->nbArmies(); 0879 nbe = (nbe + nbi)/nb; 0880 // if ((nbi - nbe)< 10) 0881 // nbe = nbi - 10; 0882 qCDebug(KSIRK_LOG) << "NbToAverageEnemyAdjacent of " << iCountry->name() << " is " << nbe; 0883 return nbe; 0884 } 0885 0886 0887 int AIColsonPlayer::NbToEqualEnemyAdjacent(Country* iCountry) 0888 { 0889 int nbe = 0; 0890 QList<Country*>::const_iterator neighbourIt, neighbourIt_end; 0891 neighbourIt = iCountry->neighbours().constBegin(); 0892 neighbourIt_end = iCountry->neighbours().constEnd(); 0893 for (;neighbourIt != neighbourIt_end; neighbourIt++) 0894 { 0895 Country* destCountry = *neighbourIt; 0896 Player* iEnemy = destCountry->owner(); 0897 if (iEnemy != this) 0898 { 0899 nbe += destCountry->nbArmies(); 0900 } 0901 } 0902 int nbi = iCountry->nbArmies(); 0903 int nb = (nbe - nbi); 0904 qCDebug(KSIRK_LOG) << "NbToEqualEnemyAdjacent of " << iCountry->name() << " is " << nb; 0905 return nb; 0906 } 0907 0908 0909 /************************************************************************/ 0910 0911 bool AIColsonPlayer::ComputerAttack(int destCountry, bool die, int dif) 0912 { 0913 qCDebug(KSIRK_LOG) << destCountry; 0914 0915 if (Attack_SrcCountry!=-1 && Attack_DestCountry!=-1 0916 && (RISK_GetOwnerOfCountry(Attack_SrcCountry) == this) 0917 && (RISK_GetOwnerOfCountry(Attack_DestCountry) != this) 0918 && (RISK_GetNumArmiesOfCountry(Attack_SrcCountry) > 1) 0919 && (die || ( RISK_GetNumArmiesOfCountry(Attack_SrcCountry) 0920 > RISK_GetNumArmiesOfCountry(Attack_DestCountry)))) 0921 { 0922 qCDebug(KSIRK_LOG) << " Retry attack"; 0923 return true; 0924 } 0925 0926 int srcCountry = -1; 0927 int max = RISK_GetNumArmiesOfCountry(destCountry) + dif; 0928 int i = 0; 0929 while ((i < 6) && (RISK_GetAdjCountryOfCountry(destCountry, i) != -1)) 0930 { 0931 int iCountry = RISK_GetAdjCountryOfCountry(destCountry, i); 0932 if ( (RISK_GetOwnerOfCountry(iCountry) == this) 0933 && (RISK_GetNumArmiesOfCountry(iCountry) > max) ) 0934 { 0935 max = RISK_GetNumArmiesOfCountry(iCountry); 0936 srcCountry = iCountry; 0937 } 0938 i++; 0939 } 0940 if (srcCountry == -1) 0941 { 0942 Attack_SrcCountry = -1; 0943 Attack_DestCountry = -1; 0944 return false; 0945 } 0946 qCDebug(KSIRK_LOG) << " srcCountry = " << srcCountry; 0947 0948 Attack_SrcCountry = srcCountry; 0949 Attack_DestCountry = destCountry; 0950 // AI_Attack (srcCountry, destCountry, ATTACK_DOORDIE, DICE_MAXIMUM, iMove); 0951 return true; 0952 } 0953 0954 bool AIColsonPlayer::Fortify() 0955 { 0956 qCDebug(KSIRK_LOG) << "1"; 0957 0958 int nb; 0959 const Continent* continent = GetContinentToFortify(&nb); 0960 0961 qCDebug(KSIRK_LOG) << "2"; 0962 if (nb > 0) 0963 { 0964 nb = rand() % nb; 0965 for ( int iCountry = 0; 0966 iCountry < m_world->getCountries().size(); 0967 iCountry++) 0968 { 0969 if ((RISK_GetOwnerOfCountry(iCountry) == this) && 0970 (RISK_GetContinentOfCountry(iCountry) == continent) && 0971 GAME_IsEnemyAdjacent(iCountry)) 0972 { 0973 if (nb <= 0) 0974 { 0975 AI_Place (iCountry, 1); 0976 return true; 0977 } 0978 nb--; 0979 } 0980 } 0981 } 0982 0983 qCDebug(KSIRK_LOG) << "3"; 0984 for ( int iCountry = 0; 0985 iCountry < m_world->getCountries().size(); 0986 iCountry++) 0987 { 0988 if ( (RISK_GetOwnerOfCountry(iCountry) == this) 0989 && GAME_IsEnemyAdjacent(iCountry)) 0990 { 0991 AI_Place (iCountry, 1); 0992 return true; 0993 } 0994 } 0995 0996 qCDebug(KSIRK_LOG) << "4"; 0997 for ( int iCountry = 0; 0998 iCountry < m_world->getCountries().size(); 0999 iCountry++) 1000 { 1001 if (RISK_GetOwnerOfCountry(iCountry) == this) 1002 { 1003 AI_Place (iCountry, 1); 1004 return true; 1005 } 1006 } 1007 return false; 1008 } 1009 1010 bool AIColsonPlayer::Place() 1011 { 1012 qCDebug(KSIRK_LOG); 1013 1014 /* Try to destroy a weak enemy player. 1015 * NOTE this could be an error 1016 * if destroying this player is another player goal... */ 1017 qCDebug(KSIRK_LOG) << "1. Try to destroy a enemy player"; 1018 1019 for (int iCountry = 0; iCountry < m_world->getCountries().size(); iCountry++) 1020 { 1021 if ((RISK_GetOwnerOfCountry(iCountry) == this) && 1022 GAME_IsEnemyAdjacent(iCountry)) 1023 { 1024 int i = 0; 1025 while ((i < 6) && (RISK_GetAdjCountryOfCountry(iCountry, i) != -1)) 1026 { 1027 int destCountry = RISK_GetAdjCountryOfCountry(iCountry, i); 1028 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1029 if ( (iEnemy != this) && isEnemyPlayer(iEnemy) 1030 && (getTotalArmiesOfPlayer(iEnemy) 1031 < ( RISK_GetNumArmiesOfPlayer(this) 1032 + RISK_GetNumArmiesOfCountry(iCountry) - 5)) 1033 && (RISK_GetNumArmiesOfCountry(iCountry) < (2*RISK_GetNumArmiesOfCountry(destCountry))+3) ) 1034 { 1035 qCDebug(KSIRK_LOG) << " iCountry: " << RISK_GetNumArmiesOfCountry(iCountry) 1036 << " ; destCountry: " << RISK_GetNumArmiesOfCountry(destCountry); 1037 AI_Place (iCountry, 1); 1038 return true; 1039 } 1040 i++; 1041 } 1042 } 1043 } 1044 1045 int nbCountriesWithAdjacentEnemies; 1046 const Continent* continent = GetContinentToFortify(&nbCountriesWithAdjacentEnemies); 1047 /* Try to conquier an entire continent, attack enemy */ 1048 qCDebug(KSIRK_LOG) << "2. Try to conquier an entire continent, attack enemy"; 1049 1050 for (int destCountry = 0; 1051 destCountry < m_world->getCountries().size(); 1052 destCountry++) 1053 { 1054 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1055 if ( (iEnemy != this) && isEnemyPlayer(iEnemy) 1056 && (RISK_GetContinentOfCountry(destCountry) == continent)) 1057 { 1058 int i = 0; 1059 while ((i < 6) && (RISK_GetAdjCountryOfCountry(destCountry, i) != -1)) 1060 { 1061 int iCountry = RISK_GetAdjCountryOfCountry(destCountry, i); 1062 if ( (RISK_GetOwnerOfCountry(iCountry) == this) 1063 && (RISK_GetNumArmiesOfCountry(iCountry) < (1.5*RISK_GetNumArmiesOfCountry(destCountry))+3) 1064 ) 1065 { 1066 AI_Place (iCountry, 1); 1067 return true; 1068 } 1069 i++; 1070 } 1071 } 1072 } 1073 1074 /* Try to destroy a player */ 1075 qCDebug(KSIRK_LOG) << "3. Try to destroy a player"; 1076 for (int iCountry = 0; 1077 iCountry < m_world->getCountries().size(); 1078 iCountry++) 1079 { 1080 if ((RISK_GetOwnerOfCountry(iCountry) == this) && 1081 GAME_IsEnemyAdjacent(iCountry)) 1082 { 1083 int i = 0; 1084 while ((i < 6) && (RISK_GetAdjCountryOfCountry(iCountry, i) != -1)) 1085 { 1086 int destCountry = RISK_GetAdjCountryOfCountry(iCountry, i); 1087 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1088 if ( (iEnemy != this) 1089 && (getTotalArmiesOfPlayer(iEnemy) 1090 < ( RISK_GetNumArmiesOfPlayer(this) 1091 + RISK_GetNumArmiesOfCountry(iCountry) - 5)) 1092 && (RISK_GetNumArmiesOfCountry(iCountry) < (1.5*RISK_GetNumArmiesOfCountry(destCountry))+3) 1093 1094 ) 1095 { 1096 AI_Place (iCountry, 1); 1097 return true; 1098 } 1099 i++; 1100 } 1101 } 1102 } 1103 1104 /* Try to conquier an entire continent */ 1105 qCDebug(KSIRK_LOG) << "4. Try to conquier an entire continent"; 1106 for (int destCountry = 0; 1107 destCountry < m_world->getCountries().size(); 1108 destCountry++) 1109 { 1110 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1111 if ( (RISK_GetContinentOfCountry(destCountry) == continent) 1112 && (iEnemy != this)) 1113 { 1114 int i = 0; 1115 while ((i < 6) && (RISK_GetAdjCountryOfCountry(destCountry, i) != -1)) 1116 { 1117 int iCountry = RISK_GetAdjCountryOfCountry(destCountry, i); 1118 if (RISK_GetOwnerOfCountry(iCountry) == this 1119 && (RISK_GetNumArmiesOfCountry(iCountry) < (1.5*RISK_GetNumArmiesOfCountry(destCountry))+3) 1120 ) 1121 { 1122 AI_Place (iCountry, 1); 1123 return true; 1124 } 1125 i++; 1126 } 1127 } 1128 } 1129 1130 /* Try to defend an entire continent */ 1131 qCDebug(KSIRK_LOG) << "5. Try to defend an entire continent"; 1132 if ( (nbCountriesWithAdjacentEnemies > 0) 1133 && (RISK_GetNumArmiesOfPlayer(this) > 0) ) 1134 { 1135 int min = 0; 1136 bool boool = false; 1137 int destCountry = -1; 1138 for (int iCountry = 0; 1139 iCountry < m_world->getCountries().size(); 1140 iCountry++) 1141 { 1142 if ( (RISK_GetOwnerOfCountry(iCountry) == this) 1143 && (RISK_GetContinentOfCountry(iCountry) == continent) 1144 && GAME_IsEnemyAdjacent(iCountry)) 1145 { 1146 int nb = NbToAverageEnemyAdjacent(m_world->getCountries().at(iCountry)); 1147 if (nb < min) 1148 { 1149 min = nb ; 1150 destCountry = iCountry; 1151 boool = true; 1152 } 1153 } 1154 } 1155 if (boool) 1156 { 1157 AI_Place (destCountry, 1); 1158 return true; 1159 } 1160 } 1161 1162 qCDebug(KSIRK_LOG) << "6. Try to conquier an entire continent, attack enemy"; 1163 continent = getContinentToConquier(&nbCountriesWithAdjacentEnemies); 1164 /* Try to conquier an entire continent, attack enemy */ 1165 for (int iCountry = 0; 1166 iCountry < m_world->getCountries().size(); 1167 iCountry++) 1168 { 1169 if ((RISK_GetOwnerOfCountry(iCountry) == this) && 1170 (RISK_GetContinentOfCountry(iCountry) == continent) && 1171 GAME_IsEnemyAdjacent(iCountry)) 1172 { 1173 int i = 0; 1174 while ((i < 6) && (RISK_GetAdjCountryOfCountry(iCountry, i) != -1)) 1175 { 1176 int destCountry = RISK_GetAdjCountryOfCountry(iCountry, i); 1177 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1178 if ( (iEnemy != this) && isEnemyPlayer(iEnemy) 1179 && (RISK_GetContinentOfCountry(destCountry) == continent) 1180 && (RISK_GetNumArmiesOfCountry(iCountry) < (1.5*RISK_GetNumArmiesOfCountry(destCountry))+3) 1181 ) 1182 { 1183 qCDebug(KSIRK_LOG) << "iCountry " << RISK_GetNumArmiesOfCountry(iCountry) 1184 << " ; destCountry " 1185 << RISK_GetNumArmiesOfCountry(destCountry); 1186 AI_Place (iCountry, 1); 1187 return true; 1188 } 1189 i++; 1190 } 1191 } 1192 } 1193 1194 qCDebug(KSIRK_LOG) << "7. Try to conquier an entire continent"; 1195 /* Try to conquier an entire continent */ 1196 for (int iCountry = 0; 1197 iCountry < m_world->getCountries().size(); 1198 ++iCountry) 1199 { 1200 if ((RISK_GetOwnerOfCountry(iCountry) == this) && 1201 (RISK_GetContinentOfCountry(iCountry) == continent) && 1202 GAME_IsEnemyAdjacent(iCountry)) 1203 { 1204 int i = 0; 1205 while ((i < 6) && (RISK_GetAdjCountryOfCountry(iCountry, i) != -1)) 1206 { 1207 int destCountry = RISK_GetAdjCountryOfCountry(iCountry, i); 1208 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1209 if ( (iEnemy != this) 1210 && (RISK_GetContinentOfCountry(destCountry) == continent) 1211 && (RISK_GetNumArmiesOfCountry(iCountry) < (1.5*RISK_GetNumArmiesOfCountry(destCountry))+3) 1212 ) 1213 { 1214 AI_Place (iCountry, 1); 1215 return true; 1216 } 1217 i++; 1218 } 1219 } 1220 } 1221 1222 qCDebug(KSIRK_LOG) << "8. Try to defend an entire continent"; 1223 /* Try to defend an entire continent */ 1224 if (nbCountriesWithAdjacentEnemies > 0) 1225 { 1226 int min = 2; // a la place de 1000 1227 bool boool = false; 1228 int destCountry = -1; 1229 for (int iCountry = 0; 1230 iCountry < m_world->getCountries().size(); 1231 iCountry++) 1232 { 1233 if ( (RISK_GetOwnerOfCountry(iCountry) == this) 1234 && (RISK_GetContinentOfCountry(iCountry) == continent) 1235 && GAME_IsEnemyAdjacent(iCountry)) 1236 { 1237 int nb = NbToAverageEnemyAdjacent(m_world->getCountries().at(iCountry)); 1238 if (nb < min) 1239 { 1240 // min = RISK_GetNumArmiesOfCountry(iCountry); 1241 min = nb; 1242 destCountry = iCountry; 1243 boool = true; 1244 } 1245 } 1246 } 1247 if (boool) 1248 { 1249 AI_Place (destCountry, 1); 1250 return true; 1251 } 1252 } 1253 1254 qCDebug(KSIRK_LOG) << "9. Try to prepare an enemy attack, find a lowest defence"; 1255 /* Try to prepare an enemy attack, find a lowest defence */ 1256 int selected = 0; 1257 int myDefenceDelta = std::numeric_limits<int>::max(); 1258 bool boool9 = false; 1259 for (int iCountry = 0; 1260 iCountry < m_world->getCountries().size(); 1261 iCountry++) 1262 { 1263 if ( (RISK_GetOwnerOfCountry(iCountry) == this) 1264 && GAME_IsEnemyAdjacent(iCountry)) 1265 { 1266 int i = 0; 1267 while ((i < 6) && (RISK_GetAdjCountryOfCountry(iCountry, i) != -1)) 1268 { 1269 int destCountry = RISK_GetAdjCountryOfCountry(iCountry, i); 1270 int delta = RISK_GetNumArmiesOfCountry(iCountry) - RISK_GetNumArmiesOfCountry(destCountry); 1271 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1272 if ( (RISK_GetContinentOfCountry(destCountry) == continent) 1273 && (iEnemy != this) && isEnemyPlayer(iEnemy) 1274 && ( ( RISK_GetNumArmiesOfCountry(iCountry) < 1275 (1.5*RISK_GetNumArmiesOfCountry(destCountry))+3 ) 1276 || (RISK_GetNumArmiesOfCountry(iCountry)==1) ) 1277 && (delta < myDefenceDelta ) ) 1278 { 1279 selected = iCountry; 1280 myDefenceDelta = delta; 1281 boool9 = true; 1282 } 1283 i++; 1284 } 1285 } 1286 } 1287 if (boool9) 1288 { 1289 AI_Place (selected, 1); 1290 return true; 1291 } 1292 1293 qCDebug(KSIRK_LOG) << "10. Try to prepare an enemy attack"; 1294 /* Try to prepare an enemy attack */ 1295 bool boool10 = false; 1296 myDefenceDelta = std::numeric_limits<int>::max(); 1297 for (int iCountry = 0; 1298 iCountry < m_world->getCountries().size(); 1299 iCountry++) 1300 { 1301 // qCDebug(KSIRK_LOG) << " looking at iCountry " << iCountry; 1302 // qCDebug(KSIRK_LOG) << " owner " << RISK_GetOwnerOfCountry(iCountry); 1303 if ( (RISK_GetOwnerOfCountry(iCountry) == this) 1304 && GAME_IsEnemyAdjacent(iCountry)) 1305 { 1306 int i = 0; 1307 while ((i < 6) && (RISK_GetAdjCountryOfCountry(iCountry, i) != -1)) 1308 { 1309 int destCountry = RISK_GetAdjCountryOfCountry(iCountry, i); 1310 int delta = RISK_GetNumArmiesOfCountry(iCountry) - RISK_GetNumArmiesOfCountry(destCountry); 1311 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1312 // qCDebug(KSIRK_LOG) << " looking at destCountry " << destCountry; 1313 // qCDebug(KSIRK_LOG) << " iEnemy " << RISK_GetOwnerOfCountry(destCountry); 1314 // qCDebug(KSIRK_LOG) << " isEnemyPlayer? " << isEnemyPlayer(iEnemy); 1315 // qCDebug(KSIRK_LOG) << " delta / myDefenceDelta " << delta << " / " << myDefenceDelta; 1316 if ((iEnemy != this) && isEnemyPlayer(iEnemy) 1317 && (delta < myDefenceDelta ) ) 1318 { 1319 // qCDebug(KSIRK_LOG) << " GOT IT " << iCountry; 1320 myDefenceDelta = delta; 1321 boool10 = true; 1322 selected = iCountry; 1323 } 1324 i++; 1325 } 1326 } 1327 } 1328 if (boool10) 1329 { 1330 AI_Place (selected, 1); 1331 //AI_Place (iCountry, RISK_GetNumArmiesOfPlayer(this)); 1332 return true; 1333 } 1334 1335 // cannot reach this line ??? 1336 // assert(false); 1337 1338 qCDebug(KSIRK_LOG) << "11. Try to prepare an attack"; 1339 /* Try to prepare an attack */ 1340 for (int iCountry = 0; 1341 iCountry < m_world->getCountries().size(); 1342 iCountry++) 1343 { 1344 if ( (RISK_GetOwnerOfCountry(iCountry) == this) 1345 && GAME_IsEnemyAdjacent(iCountry)) 1346 { 1347 AI_Place (iCountry, 1); 1348 return true; 1349 } 1350 } 1351 1352 qCDebug(KSIRK_LOG) << "12. Try to place"; 1353 /* Try to place */ 1354 for (int iCountry = 0; 1355 iCountry < m_world->getCountries().size(); 1356 iCountry++) 1357 { 1358 if (RISK_GetOwnerOfCountry(iCountry) == this) 1359 { 1360 AI_Place (iCountry, 1); 1361 return true; 1362 } 1363 } 1364 return false; 1365 } 1366 1367 /** @return KsirK change: true if an attack have been tempted; false otherwise */ 1368 bool AIColsonPlayer::AttackEnemy() 1369 { 1370 qCDebug(KSIRK_LOG); 1371 1372 int nbCountriesWithAdjacentEnemies; 1373 const Continent* continent = GetContinentToFortify(&nbCountriesWithAdjacentEnemies); 1374 1375 if (Attack_SrcCountry!=-1 && Attack_DestCountry != -1 1376 && (RISK_GetOwnerOfCountry(Attack_SrcCountry)==this) 1377 && (RISK_GetOwnerOfCountry(Attack_DestCountry)!=this) 1378 && ComputerAttack (Attack_DestCountry, true, 1379 (RISK_GetNumArmiesOfCountry(Attack_DestCountry) < 5)?1: 1380 ((nbCountriesWithAdjacentEnemies > 4)?RISK_GetNumArmiesOfCountry(Attack_DestCountry):3))) 1381 { 1382 qCDebug(KSIRK_LOG) << "Attack tempted again."; 1383 return true; 1384 } 1385 1386 1387 qCDebug(KSIRK_LOG) << "1 Try to conquier an entire continent, attack player of other species "; 1388 /* Try to conquier an entire continent, attack player of other species */ 1389 for ( int destCountry = 0; 1390 destCountry < m_world->getCountries().size(); 1391 destCountry++) 1392 { 1393 // qCDebug(KSIRK_LOG) << "destCountry=" << destCountry << " / m_world->getCountries().size()=" << m_world->getCountries().size(); 1394 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1395 if ( (RISK_GetContinentOfCountry(destCountry) == continent) 1396 && (iEnemy != this) && isEnemyPlayer(iEnemy)) 1397 { 1398 if (ComputerAttack (destCountry, true, 1399 (RISK_GetNumArmiesOfCountry(destCountry) < 5)?1: 1400 ((nbCountriesWithAdjacentEnemies > 4)?RISK_GetNumArmiesOfCountry(destCountry):3))) 1401 { 1402 destCountry = 0; 1403 qCDebug(KSIRK_LOG) << "Attack tempted."; 1404 return true; 1405 } 1406 } 1407 } 1408 1409 qCDebug(KSIRK_LOG) << "2 Try to conquier an entire continent: " << continent; 1410 /* Try to conquier an entire continent */ 1411 1412 for (int destCountry = 0; destCountry < m_world->getCountries().size(); destCountry++) 1413 { 1414 if ( (RISK_GetContinentOfCountry(destCountry) == continent) 1415 && (RISK_GetOwnerOfCountry(destCountry) != this)) 1416 { 1417 if (ComputerAttack (destCountry, true, 1418 (RISK_GetNumArmiesOfCountry(destCountry) < 3)?1:50)) 1419 { 1420 destCountry = 0; 1421 qCDebug(KSIRK_LOG) << "Attack tempted."; 1422 return true; 1423 } 1424 } 1425 } 1426 1427 qCDebug(KSIRK_LOG) << "should abandon ?"; 1428 if ( !isContinentOfPlayer(continent, this) 1429 && (m_numTurn[this] <= 2) 1430 && (allPlayers.count() > m_world->getContinents().size()/2)) 1431 { 1432 qCDebug(KSIRK_LOG) << "No attack tried"; 1433 Attack_SrcCountry = -1; 1434 Attack_DestCountry = -1; 1435 return false; 1436 } 1437 1438 qCDebug(KSIRK_LOG) << "3 Try to destroy a human player"; 1439 /* Try to destroy a human player */ 1440 continent = getContinentToConquier(&nbCountriesWithAdjacentEnemies); 1441 1442 1443 for (int destCountry = 0; 1444 destCountry < m_world->getCountries().size(); 1445 destCountry++) 1446 { 1447 if ( (RISK_GetOwnerOfCountry(destCountry) != this) 1448 && (!RISK_GetOwnerOfCountry(destCountry)->isAI()) 1449 && (RISK_GetNumCountriesOfPlayer(RISK_GetOwnerOfCountry(destCountry)) == 1)) 1450 { 1451 if (ComputerAttack (destCountry, true, 1452 (nbCountriesWithAdjacentEnemies > 2)?10:2)) 1453 { 1454 qCDebug(KSIRK_LOG) << "Attack tempted."; 1455 return true; 1456 } 1457 } 1458 } 1459 1460 qCDebug(KSIRK_LOG) << "4 Try to destroy a enemy player"; 1461 /* Try to destroy a enemy player */ 1462 for (int destCountry = 0; 1463 destCountry < m_world->getCountries().size(); 1464 destCountry++) 1465 { 1466 if ( isEnemyPlayer(RISK_GetOwnerOfCountry(destCountry)) 1467 && (RISK_GetNumCountriesOfPlayer(RISK_GetOwnerOfCountry(destCountry)) == 1)) 1468 { 1469 if (ComputerAttack (destCountry, true, 1470 (nbCountriesWithAdjacentEnemies > 2)?20:2)) 1471 { 1472 qCDebug(KSIRK_LOG) << "Attack tempted."; 1473 return true; 1474 } 1475 } 1476 } 1477 1478 qCDebug(KSIRK_LOG) << "Try to destroy a player"; 1479 /* Try to destroy a player */ 1480 for (int destCountry = 0; 1481 destCountry < m_world->getCountries().size(); 1482 destCountry++) 1483 { 1484 if ( (RISK_GetOwnerOfCountry(destCountry) != this) 1485 && (RISK_GetNumCountriesOfPlayer(RISK_GetOwnerOfCountry(destCountry)) == 1)) 1486 { 1487 if (ComputerAttack (destCountry, true, 1488 (nbCountriesWithAdjacentEnemies> 2)?20:2)) 1489 { 1490 qCDebug(KSIRK_LOG) << "Attack tempted."; 1491 return true; 1492 } 1493 } 1494 } 1495 1496 qCDebug(KSIRK_LOG) << "5 Try to conquier an entire continent, attack player of other species"; 1497 /* Try to conquier an entire continent, attack player of other species */ 1498 for (int destCountry = 0; 1499 destCountry < m_world->getCountries().size(); 1500 destCountry++) 1501 { 1502 if ( (RISK_GetContinentOfCountry(destCountry) == continent) 1503 && (RISK_GetOwnerOfCountry(destCountry) != this) 1504 && isEnemyPlayer(RISK_GetOwnerOfCountry(destCountry))) 1505 { 1506 if (ComputerAttack (destCountry, true, 1507 (RISK_GetNumArmiesOfCountry(destCountry) < 5)?1: 1508 ((nbCountriesWithAdjacentEnemies > 4)?RISK_GetNumArmiesOfCountry(destCountry):3))) 1509 { 1510 destCountry = 0; 1511 qCDebug(KSIRK_LOG) << "Attack tempted."; 1512 return true; 1513 } 1514 } 1515 } 1516 1517 qCDebug(KSIRK_LOG) << "6 Try to conquier an entire continent"; 1518 /* Try to conquier an entire continent */ 1519 for (int destCountry = 0; 1520 destCountry < m_world->getCountries().size(); 1521 destCountry++) 1522 { 1523 if ( (RISK_GetContinentOfCountry(destCountry) == continent) 1524 && (RISK_GetOwnerOfCountry(destCountry) != this)) 1525 { 1526 if (ComputerAttack (destCountry, true, 1527 (RISK_GetNumArmiesOfCountry(destCountry) < 3)?1:50)) 1528 { 1529 destCountry = 0; 1530 qCDebug(KSIRK_LOG) << "Attack tempted."; 1531 return true; 1532 } 1533 } 1534 } 1535 1536 qCDebug(KSIRK_LOG) << "7 Try to attack a stronger human player for a card"; 1537 /* Try to attack a stronger human player for a card */ 1538 for (int destCountry = 0; 1539 destCountry < m_world->getCountries().size(); 1540 destCountry++) 1541 { 1542 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1543 if ( (iEnemy != this) && isEnemyPlayer(iEnemy) 1544 && (!iEnemy->isAI()) 1545 && isStrongerPlayer(RISK_GetOwnerOfCountry(destCountry))) 1546 { 1547 if (ComputerAttack (destCountry, false, 1548 (RISK_GetNumArmiesOfCountry(destCountry) < 3)?1:((nbCountriesWithAdjacentEnemies > 2)?10:2))) 1549 { 1550 qCDebug(KSIRK_LOG) << "Attack tempted."; 1551 return true; 1552 } 1553 } 1554 } 1555 1556 qCDebug(KSIRK_LOG) << "8 Try to attack an human player for a card"; 1557 /* Try to attack an human player for a card */ 1558 for (int destCountry = 0; 1559 destCountry < m_world->getCountries().size(); 1560 destCountry++) 1561 { 1562 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1563 if ( (iEnemy != this) && isEnemyPlayer(iEnemy) 1564 && (!iEnemy->isAI())) 1565 { 1566 if (ComputerAttack (destCountry, false, 1567 (RISK_GetNumArmiesOfCountry(destCountry) < 3)?1:((nbCountriesWithAdjacentEnemies > 2)?10:2))) 1568 { 1569 qCDebug(KSIRK_LOG) << "Attack tempted."; 1570 return true; 1571 } 1572 } 1573 } 1574 1575 qCDebug(KSIRK_LOG) << "9 Try to attack enemy player for a card"; 1576 /* Try to attack enemy player for a card */ 1577 for (int destCountry = 0; 1578 destCountry < m_world->getCountries().size(); 1579 destCountry++) 1580 { 1581 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1582 if ( (iEnemy != this) && isEnemyPlayer(iEnemy)) 1583 if (ComputerAttack (destCountry, false, 1584 (RISK_GetNumArmiesOfCountry(destCountry) < 3)?1:((nbCountriesWithAdjacentEnemies > 2)?10:2))) 1585 { 1586 { 1587 qCDebug(KSIRK_LOG) << "Attack tempted."; 1588 return true; 1589 } 1590 } 1591 } 1592 1593 qCDebug(KSIRK_LOG) << "10 Try to attack for a card, attack a stronger player"; 1594 /* Try to attack for a card, attack a stronger player */ 1595 for (int destCountry = 0; 1596 destCountry < m_world->getCountries().size(); 1597 destCountry++) 1598 { 1599 Player* iEnemy = RISK_GetOwnerOfCountry(destCountry); 1600 if ( (iEnemy != this) 1601 && isStrongerPlayer(iEnemy)) 1602 { 1603 if (ComputerAttack (destCountry, false, 1604 (RISK_GetNumArmiesOfCountry(destCountry) < 2)?1:100)) 1605 { 1606 qCDebug(KSIRK_LOG) << "Attack tempted."; 1607 return true; 1608 } 1609 } 1610 } 1611 1612 qCDebug(KSIRK_LOG) << "11 Try to attack for a card"; 1613 /* Try to attack for a card */ 1614 for (int destCountry = 0; 1615 destCountry < m_world->getCountries().size(); 1616 destCountry++) 1617 { 1618 if (RISK_GetOwnerOfCountry(destCountry) != this) 1619 { 1620 if (ComputerAttack (destCountry, false, 1621 RISK_GetNumArmiesOfCountry(destCountry) 1622 // (RISK_GetNumArmiesOfCountry(destCountry) < 2)?1:100 1623 )) 1624 { 1625 qCDebug(KSIRK_LOG) << "Attack tempted."; 1626 return true; 1627 } 1628 } 1629 } 1630 1631 qCDebug(KSIRK_LOG) << "No attack tried"; 1632 // No attack tried 1633 Attack_SrcCountry = -1; 1634 Attack_DestCountry = -1; 1635 return false; 1636 } 1637 1638 bool AIColsonPlayer::Attack() 1639 { 1640 qCDebug(KSIRK_LOG); 1641 int enemyAlive; 1642 1643 // if (RISK_GetAttackModeOfPlayer (player) != ACTION_DOORDIE) 1644 // RISK_SetAttackModeOfPlayer (player, ACTION_DOORDIE); 1645 // if (RISK_GetDiceModeOfPlayer (player) != ATTACK_AUTO) 1646 // RISK_SetDiceModeOfPlayer (player, ATTACK_AUTO); 1647 1648 enemyAlive = getNumEnemy(); 1649 while ((enemyAlive == 0) && (m_levelEnemy >0)) 1650 { 1651 m_levelEnemy--; 1652 enemyAlive = getNumEnemy(); 1653 } 1654 1655 return AttackEnemy(); 1656 } 1657 1658 void AIColsonPlayer::HowManyArmiesToMove(int *nb) 1659 { 1660 if ((Attack_SrcCountry == -1) || (Attack_DestCountry == -1)) 1661 return; 1662 1663 if (!GAME_IsEnemyAdjacent(Attack_SrcCountry)) 1664 *nb = 0; 1665 else if (!GAME_IsEnemyAdjacent(Attack_DestCountry)) 1666 *nb = *nb; 1667 else 1668 *nb = *nb/2; 1669 Attack_SrcCountry = -1; 1670 Attack_DestCountry = -1; 1671 } 1672 1673 int AIColsonPlayer::FindEnemyAdjacent(int iCountry, int distance) 1674 { 1675 if (m_enemyAdjacent.find(std::make_pair(iCountry,distance))!=m_enemyAdjacent.end()) 1676 { 1677 return m_enemyAdjacent[std::make_pair(iCountry,distance)]; 1678 } 1679 qCDebug(KSIRK_LOG) << iCountry << distance; 1680 int i, min, res, dest; 1681 1682 Player* iPlayer = RISK_GetOwnerOfCountry(iCountry); 1683 min = 100000; 1684 for (i=0; i!=6 && RISK_GetAdjCountryOfCountry(iCountry, i)!=-1; i++) 1685 { 1686 dest = RISK_GetAdjCountryOfCountry(iCountry, i); 1687 if (RISK_GetOwnerOfCountry(dest) == iPlayer) 1688 { 1689 if (distance <= 3) 1690 { 1691 res = FindEnemyAdjacent(dest, distance + 1); 1692 m_enemyAdjacent.insert(std::make_pair(std::make_pair(dest,distance+1),res)); 1693 1694 if (res < min) 1695 min = res; 1696 } 1697 } 1698 else 1699 { 1700 min = 0; 1701 } 1702 } 1703 1704 return (min + 1); 1705 } 1706 1707 int AIColsonPlayer::GAME_FindEnemyAdjacent(int iCountry) 1708 { 1709 qCDebug(KSIRK_LOG) << iCountry; 1710 m_enemyAdjacent.clear(); 1711 int i, min, res, dest, destCountry; 1712 Player* iPlayer = RISK_GetOwnerOfCountry(iCountry); 1713 destCountry = -1; 1714 min = 100000; 1715 for (i=0; i!=6 && RISK_GetAdjCountryOfCountry(iCountry, i)!=-1; i++) 1716 { 1717 qCDebug(KSIRK_LOG) << " i = " << i; 1718 dest = RISK_GetAdjCountryOfCountry(iCountry, i); 1719 if (RISK_GetOwnerOfCountry(dest) == iPlayer) 1720 { 1721 res = FindEnemyAdjacent(dest, 0); 1722 m_enemyAdjacent.insert(std::make_pair(std::make_pair(dest,0),res)); 1723 if (res < min) 1724 { 1725 min = res; 1726 destCountry = dest; 1727 } 1728 } 1729 else 1730 { 1731 min = 0; 1732 } 1733 } 1734 1735 return (destCountry); 1736 } 1737 1738 1739 bool AIColsonPlayer::Move() 1740 { 1741 qCDebug(KSIRK_LOG); 1742 1743 /* Try to move an unused max army in a frontier */ 1744 int iCountry = -1; 1745 int max = 1; 1746 for (int i=0; i < m_world->getCountries().size();i++) 1747 { 1748 qCDebug(KSIRK_LOG) << "1: " << i; 1749 if ( (RISK_GetOwnerOfCountry(i) == this) 1750 && (RISK_GetNumArmiesOfCountry(i) > max) 1751 && !GAME_IsEnemyAdjacent(i)) 1752 { 1753 max = RISK_GetNumArmiesOfCountry(i); 1754 qCDebug(KSIRK_LOG) << "country " << i << ", num armies:" << max; 1755 iCountry = i; 1756 } 1757 } 1758 qCDebug(KSIRK_LOG) << "1p iCountry=" << iCountry << "; max=" << max; 1759 if (iCountry>=0) 1760 { 1761 int destCountry = GAME_FindEnemyAdjacent(iCountry); 1762 qCDebug(KSIRK_LOG) << " found adjacent enemy " << destCountry; 1763 if (destCountry >= 0) 1764 { 1765 AI_Move (iCountry, destCountry, 1766 RISK_GetNumArmiesOfCountry(iCountry)-1); 1767 qCDebug(KSIRK_LOG) << " Moved " << RISK_GetNumArmiesOfCountry(iCountry)-1; 1768 return true; 1769 } 1770 } 1771 1772 qCDebug(KSIRK_LOG) << "2"; 1773 /* Try to move an unused army in a country witch have a frontier */ 1774 for (int iCountry = 0;iCountry < m_world->getCountries().size();iCountry++) 1775 { 1776 if ( (RISK_GetOwnerOfCountry(iCountry) == this) 1777 && (RISK_GetNumArmiesOfCountry(iCountry) > 2) 1778 && !GAME_IsEnemyAdjacent(iCountry)) 1779 { 1780 int destCountry = GAME_FindEnemyAdjacent(iCountry); 1781 if (destCountry >= 0) 1782 { 1783 AI_Move (iCountry, destCountry, 1784 RISK_GetNumArmiesOfCountry(iCountry)-1); 1785 qCDebug(KSIRK_LOG) << " Moved " << RISK_GetNumArmiesOfCountry(iCountry)-1; 1786 return true; 1787 } 1788 } 1789 } 1790 1791 qCDebug(KSIRK_LOG) << "3"; 1792 for (int iCountry = 0;(iCountry < m_world->getCountries().size()); iCountry++) 1793 { 1794 if ( (RISK_GetOwnerOfCountry(iCountry) == this) 1795 && (RISK_GetNumArmiesOfCountry(iCountry) > 2) 1796 && !GAME_IsEnemyAdjacent(iCountry)) 1797 { 1798 for (int i = 0; (i < 6) && (RISK_GetAdjCountryOfCountry(iCountry, i) != -1);i++) 1799 { 1800 int destCountry = RISK_GetAdjCountryOfCountry(iCountry, i); 1801 if (RISK_GetNumArmiesOfCountry(destCountry) == 1) 1802 { 1803 AI_Move (iCountry, destCountry, 1804 RISK_GetNumArmiesOfCountry(iCountry)/2); 1805 qCDebug(KSIRK_LOG) << " Moved " << RISK_GetNumArmiesOfCountry(iCountry)/2; 1806 return true; 1807 } 1808 } 1809 } 1810 } 1811 qCDebug(KSIRK_LOG) << " Nothing Moved "; 1812 1813 return false; 1814 } 1815 1816 // void AIColsonPlayer::ExchangeCards(const Player* player) 1817 // { 1818 // int i, this, nb, typ, piCards[4], nbCards[4], piCardValues[MAX_CARDS]; 1819 // bool fOptimal, fStronger, fSmaller; 1820 // 1821 // fStronger = isStrongerPlayer(player); 1822 // fSmaller = isSmallerPlayer(player); 1823 // nb = RISK_GetNumCardsOfPlayer(player); 1824 // do 1825 // { 1826 // piCards[0]=piCards[1]=piCards[2]=piCards[3]=-1; 1827 // nbCards[0]=nbCards[1]=nbCards[2]=nbCards[3]=0; 1828 // fOptimal = false; 1829 // for (i=0; i<nb; i++) 1830 // { 1831 // piCardValues[i] = RISK_GetCardOfPlayer(player, i); 1832 // /* Set the type of the card */ 1833 // if (piCardValues[i]<m_world->getCountries().size()) 1834 // { 1835 // typ = piCardValues[i] % 3; 1836 // nbCards[typ]++; 1837 // if (RISK_GetOwnerOfCountry(piCardValues[i]) == player) 1838 // piCards[typ] = i; 1839 // else if (piCards[typ] == -1) 1840 // piCards[typ] = i; 1841 // } 1842 // else /* Joker */ 1843 // { 1844 // piCards[3] = i; 1845 // nbCards[3]++; 1846 // } 1847 // } 1848 // if ((nbCards[0]>0)&&(nbCards[1]>0)&&(nbCards[2]>0)) 1849 // { 1850 // AI_ExchangeCards(piCards); 1851 // fOptimal = true; 1852 // } 1853 // else if ((nbCards[3]>=2)&&((nbCards[0]>0)||(nbCards[1]>0)||(nbCards[2]>0))) 1854 // { 1855 // if (nbCards[2]>1) 1856 // { 1857 // piCards[1] = piCards[3]; 1858 // j = 0; 1859 // } 1860 // else if (nbCards[1]>1) 1861 // { 1862 // piCards[0] = piCards[3]; 1863 // j = 2; 1864 // } 1865 // else if (nbCards[0]>1) 1866 // { 1867 // piCards[2] = piCards[3]; 1868 // j = 1; 1869 // } 1870 // else if (nbCards[2]>0) 1871 // { 1872 // piCards[1] = piCards[3]; 1873 // j = 0; 1874 // } 1875 // else if (nbCards[1]>0) 1876 // { 1877 // piCards[0] = piCards[3]; 1878 // j = 2; 1879 // } 1880 // else 1881 // { 1882 // piCards[2] = piCards[3]; 1883 // j = 1; 1884 // } 1885 // i = 0; 1886 // while (i<nb) 1887 // { 1888 // if (piCardValues[i] >= m_world->getCountries().size()) 1889 // { 1890 // piCards[j]=i; 1891 // i = nb; 1892 // } 1893 // else 1894 // i++; 1895 // } 1896 // AI_ExchangeCards(piCards); 1897 // fOptimal = true; 1898 // } 1899 // else if (!fStronger && (nbCards[0]>=3)) 1900 // { 1901 // j = 0; 1902 // for (i=0; i<nb; i++) 1903 // if ((piCardValues[i] % 3) == 0) 1904 // piCards[j++]=i; 1905 // AI_ExchangeCards(piCards); 1906 // } 1907 // else if (fSmaller && (nbCards[1]>=3)) 1908 // { 1909 // j = 0; 1910 // for (i=0; i<nb; i++) 1911 // if ((piCardValues[i] % 3) == 1) 1912 // piCards[j++]=i; 1913 // AI_ExchangeCards(piCards); 1914 // } 1915 // else if (fSmaller && (nbCards[2]>=3)) 1916 // { 1917 // j = 0; 1918 // for (i=0; i<nb; i++) 1919 // if ((piCardValues[i] % 3) == 2) 1920 // piCards[j++]=i; 1921 // AI_ExchangeCards(piCards); 1922 // } 1923 // else if (nb >= 5) 1924 // { 1925 // if ((nbCards[0]>0)&&(nbCards[1]>0)&&(nbCards[3]>0)) 1926 // piCards[2] = piCards[3]; 1927 // else if ((nbCards[0]>0)&&(nbCards[3]>0)&&(nbCards[2]>0)) 1928 // piCards[1] = piCards[3]; 1929 // else if ((nbCards[3]>0)&&(nbCards[1]>0)&&(nbCards[2]>0)) 1930 // piCards[0] = piCards[3]; 1931 // else if (nbCards[0]>=3) 1932 // { 1933 // j = 0; 1934 // for (i=0; i<nb; i++) 1935 // if ((piCardValues[i] % 3) == 0) 1936 // piCards[j++]=i; 1937 // } 1938 // else if (nbCards[1]>=3) 1939 // { 1940 // j = 0; 1941 // for (i=0; i<nb; i++) 1942 // if ((piCardValues[i] % 3) == 1) 1943 // piCards[j++]=i; 1944 // } 1945 // else if (nbCards[2]>=3) 1946 // { 1947 // j = 0; 1948 // for (i=0; i<nb; i++) 1949 // if ((piCardValues[i] % 3) == 2) 1950 // piCards[j++]=i; 1951 // } 1952 // else 1953 // { 1954 // piCards[0] = 0; 1955 // piCards[1] = 1; 1956 // piCards[2] = 2; 1957 // } 1958 // AI_ExchangeCards(piCards); 1959 // } 1960 // nb = RISK_GetNumCardsOfPlayer(player); 1961 // } 1962 // while ((fOptimal && (nb >= 3)) || (nb >= 5)); 1963 // } 1964 1965 // void AIColsonPlayer::COLSON_Play(void *pData, int iCommand, void *pArgs) 1966 // { 1967 // switch(iCommand) 1968 // { 1969 // case AI_INIT_ONCE: 1970 // { 1971 // /* InitClient((int)pArgs); */ 1972 // } 1973 // break; 1974 // 1975 // case AI_INIT_TURN: 1976 // { 1977 // m_numTurn[m_game->currentPlayer()]++; 1978 // } 1979 // break; 1980 // 1981 // case AI_FORTIFY: 1982 // { 1983 // Fortify(); 1984 // } 1985 // break; 1986 // 1987 // case AI_PLACE: 1988 // { 1989 // Place(); 1990 // } 1991 // break; 1992 // 1993 // case AI_ATTACK: 1994 // { 1995 // Attack(); 1996 // } 1997 // break; 1998 // 1999 // case AI_MOVE_MANUAL: 2000 // { 2001 // HowManyArmiesToMove((int *)pArgs); 2002 // } 2003 // break; 2004 // 2005 // case AI_MOVE: 2006 // { 2007 // Move(); 2008 // } 2009 // break; 2010 // 2011 // case AI_EXCHANGE_CARDS: 2012 // { 2013 // // ExchangeCards(m_game->currentPlayer()); 2014 // } 2015 // break; 2016 // 2017 // case AI_SERVER_MESSAGE: 2018 // { 2019 // } 2020 // break; 2021 // 2022 // } 2023 // 2024 // // return pData; 2025 // } 2026 2027 void AIColsonPlayer::finalize() 2028 { 2029 qCDebug(KSIRK_LOG); 2030 2031 for (int i=0; i<m_game->playerList()->count(); i++) 2032 { 2033 m_isEnemyPlayer[(Player*)m_game->playerList()->at(i)] = 0; 2034 } 2035 PlayersArray::iterator it = m_game->playerList()->begin(); 2036 PlayersArray::iterator it_end = m_game->playerList()->end(); 2037 for (; it != it_end; it++) 2038 { 2039 Player* player = (Player*)*it; 2040 m_numTurn[player] = 0; 2041 if (dynamic_cast<AIColsonPlayer*>(player)!=nullptr) 2042 m_isEnemyPlayer[player] = 1; 2043 else if (player->author() == AUTHOR) 2044 m_isEnemyPlayer[player] = 2; 2045 else if (player->isAI()) 2046 m_isEnemyPlayer[player] = 3; 2047 else 2048 m_isEnemyPlayer[player] = 4; 2049 } 2050 m_levelEnemy = 3; 2051 computeChoiceOfContinent(); 2052 m_initialized = true; 2053 qCDebug(KSIRK_LOG) <<" init done."; 2054 } 2055 2056 int AIColsonPlayer::AI_Place(int iCountry, int iNumArmies) 2057 { 2058 qCDebug(KSIRK_LOG) << iNumArmies 2059 << " on country number " << iCountry; 2060 if (m_placeData != nullptr) 2061 { 2062 delete m_placeData; 2063 } 2064 m_placeData = new PlaceData(); 2065 m_placeData->dest = m_game->game()->theWorld()->getCountries()[iCountry]; 2066 m_placeData->nb = iNumArmies; 2067 return 0; 2068 } 2069 2070 int AIColsonPlayer::AI_Move(int iSrcCountry, int iDstCountry, int iNumArmies) 2071 { 2072 qCDebug(KSIRK_LOG) << iSrcCountry << ", " << iDstCountry << ", " << iNumArmies; 2073 m_src = m_game->game()->theWorld()->getCountries()[iSrcCountry]; 2074 m_dest = m_game->game()->theWorld()->getCountries()[iDstCountry]; 2075 m_toMove = iNumArmies; 2076 qCDebug(KSIRK_LOG) << iNumArmies << " armies from " 2077 << m_src->name() << " to " << m_dest->name(); 2078 2079 QByteArray buffer; 2080 QDataStream stream(&buffer, QIODevice::WriteOnly); 2081 stream << QString("actionLButtonDown") << m_src->centralPoint(); 2082 aiPlayerIO()->sendInput(stream,true); 2083 2084 QByteArray buffer2; 2085 QDataStream stream2(&buffer2, QIODevice::WriteOnly); 2086 stream2 << QString("actionLButtonUp") << m_dest->centralPoint(); 2087 aiPlayerIO()->sendInput(stream2,true); 2088 2089 Attack_SrcCountry = m_game->game()->theWorld()->getCountries().indexOf(const_cast<Country*>(m_src)); 2090 Attack_DestCountry = m_game->game()->theWorld()->getCountries().indexOf(const_cast<Country*>(m_dest)); 2091 2092 stop(); 2093 return 0; 2094 } 2095 2096 2097 ////////////////////////////////////////////////////////// 2098 // Tool functions reimplemented from other parts of XFrisk 2099 ////////////////////////////////////////////////////////// 2100 2101 Player* AIColsonPlayer::RISK_GetOwnerOfCountry(int i) 2102 { 2103 return m_world->getCountries().at(i)->owner(); 2104 } 2105 2106 Continent* AIColsonPlayer::RISK_GetContinentOfCountry(int i) 2107 { 2108 return m_world->getCountries().at(i)->continent(); 2109 } 2110 2111 2112 bool AIColsonPlayer::GAME_IsEnemyAdjacent(int i) 2113 { 2114 qCDebug(KSIRK_LOG) << i; 2115 return m_game->game()->theWorld()->getCountries()[i]->hasAdjacentEnemy(); 2116 } 2117 2118 int AIColsonPlayer::RISK_GetNumArmiesOfCountry(int i) 2119 { 2120 return m_world->getCountries().at(i)->nbArmies(); 2121 } 2122 2123 2124 /** Returns the position in the countries list of the ith adjacent country of country iCountry */ 2125 int AIColsonPlayer::RISK_GetAdjCountryOfCountry(int iCountry, int j) 2126 { 2127 Country* country = m_world->getCountries().at(iCountry); 2128 if (j >= country->neighbours().size()) 2129 { 2130 return -1; 2131 } 2132 Country* neighbour = country->neighbours()[j]; 2133 for (int i=0; i<m_world->getCountries().size(); i++) 2134 { 2135 if (m_world->getCountries().at(i) == neighbour) 2136 { 2137 return i; 2138 } 2139 } 2140 return -1; 2141 } 2142 2143 int AIColsonPlayer::RISK_GetNumArmiesOfPlayer(Player* player) 2144 { 2145 return player->getNbAvailArmies(); 2146 } 2147 2148 int AIColsonPlayer::RISK_GetNumCountriesOfPlayer(const Player* player) 2149 { 2150 return player->countries().size(); 2151 } 2152 2153 2154 } // closing namespace GameLogic 2155 2156 } // closing namespace Ksirk 2157