예제 #1
0
void setVisibleObjects(Player::Ptr player) {
   ObjectManager *om = Game::getGame()->getObjectManager();
   
   IGObject::Ptr universe = om->getObject(0);
   PlayerView::Ptr pv = player->getPlayerView();
   set<uint32_t> ownedObjects = pv->getOwnedObjects();

   // add universe and star systems
   ObjectView::Ptr obv = pv->getObjectView(universe->getID());
   if(!obv){
      pv->addVisibleObject( universe->getID(), true );
   }
   
   uint32_t fleettype = Game::getGame()->getObjectTypeManager()->getObjectTypeByName("Fleet");
   set<uint32_t> containedObjects = universe->getContainedObjects();
   for(set<uint32_t>::const_iterator i = containedObjects.begin(); i != containedObjects.end(); ++i){
     IGObject::Ptr object = om->getObject(*i);
     obv = pv->getObjectView(*i);
     if(object->getType() != fleettype){
      if(!obv){
          pv->addVisibleObject(*i, true );
      }
     }else{
       if(obv && !obv->isGone()){
         obv->setGone(true);
         pv->updateObjectView(*i);
       }
     }
     om->doneWithObject(*i);
   }

   for(set<uint32_t>::const_iterator i = ownedObjects.begin(); i != ownedObjects.end(); ++i)
   {
      IGObject::Ptr obj = om->getObject(*i);
      if(obj->getType() != fleettype || obj->getParent() != 0){
        exploreStarSys(obj);
      }
      om->doneWithObject(*i);
   }
   
   set<uint32_t> visobjects = pv->getVisibleObjects();
   for(set<uint32_t>::const_iterator i = visobjects.begin(); i != visobjects.end(); ++i)
   {
      IGObject::Ptr obj = om->getObject(*i);
      obv = pv->getObjectView(*i);
      if(!obj){
        if(!obv->isGone()){
          obv->setGone(true);
          pv->updateObjectView(*i);
        }
      }else if((!obv->isGone()) && obv->isCompletelyVisible() && obj->getModTime() > obv->getModTime()){
        obv->setModTime(obj->getModTime());
        pv->updateObjectView(*i);
      }
      if(obj != NULL){
        om->doneWithObject(*i);
      }
   }
   
}
예제 #2
0
//Sends a fleet back to it's home planet
void TaeTurn::sendHome(uint32_t fleet) {
    Game* game = Game::getGame();
    ObjectManager* obm = game->getObjectManager();
    ObjectTypeManager* obtm = game->getObjectTypeManager();
    PlayerManager::Ptr pm = game->getPlayerManager();

    IGObject::Ptr fleetobj = obm->getObject(fleet);
    //Check to make sure it is really a fleet
    if(fleetobj->getType() != obtm->getObjectTypeByName("Fleet")) {
        return;
    }

    //Get all the required objects
    Fleet* f = (Fleet*) fleetobj->getObjectBehaviour();
    Player::Ptr p = pm->getPlayer(f->getOwner());
    IGObject::Ptr sys = obm->getObject(fleetobj->getParent());
    StarSystem* sysData = (StarSystem*) sys->getObjectBehaviour();

    //Remove fleet from system
    sysData->setRegion(0);
    fleetobj->removeFromParent();

    //Find it's home planet
    std::set<uint32_t> objects = obm->getAllIds();
    std::set<uint32_t>::iterator itcurr;
    for(itcurr = objects.begin(); itcurr != objects.end(); ++itcurr) {
        IGObject::Ptr ob = obm->getObject(*itcurr);
        if(ob->getName().compare(string(p->getName() + "'s Home Planet")) == 0) {
            Planet* p = (Planet*) ob->getObjectBehaviour();
            f->setPosition(p->getPosition());
            fleetobj->addToParent(ob->getID());
        }
    }
}
예제 #3
0
map<uint32_t, pair<string, uint32_t> > Colonize::generateListOptions() {
   map<uint32_t, pair<string,uint32_t> > options;
   Game* game = Game::getGame();
   ObjectManager* om = game->getObjectManager();

   IGObject::Ptr selectedObj = game->getObjectManager()->getObject(
      game->getOrderManager()->getOrderQueue(orderqueueid)->getObjectId());
   Planet* planet = dynamic_cast<Planet*>(selectedObj->getObjectBehaviour());
   assert(planet);
   om->doneWithObject(selectedObj->getID());

   set<uint32_t> allObjs = om->getAllIds();

   uint32_t availibleUnits = planet->getResource("Army").first + planet->getResource("Army").second - 1;

   /* This for loop will iterate over every adjacent planet. 
   This is where the majority of the work occurs, and we populate our list.
   You see here we select an item of the map, in my case (*i)->getID(), and
   for that item we create a pair.
      If its a little hard to read, here is what I am doing:
            options[#] = pair<string,uint32_t>( "title", max# );

   For my pair I set the title as the adjacent planet to move to, and set the
   max to availible units. */
   for(set<uint32_t>::iterator i = allObjs.begin(); i != allObjs.end(); i++) {
      IGObject::Ptr currObj = om->getObject((*i));
      Planet* owned = dynamic_cast<Planet*>(currObj->getObjectBehaviour());
      if ( owned != NULL && owned->getOwner() == 0) {   
         options[owned->getID()] = pair<string,uint32_t>(
            owned->getName(), availibleUnits );
      }
   }   

   return options;
}
예제 #4
0
void Build::createFrame(OutputFrame::Ptr f, int pos)
{
  IGObject::Ptr planet = Game::getGame()->getObjectManager()->getObject(Game::getGame()->getOrderManager()->getOrderQueue(orderqueueid)->getObjectId());
  
  // number of turns
  std::map<uint32_t, std::pair<uint32_t, uint32_t> > presources = static_cast<Planet*>(planet->getObjectBehaviour())->getResources();
  Game::getGame()->getObjectManager()->doneWithObject(planet->getID());
  uint32_t res_current;
  if(presources.find(1) != presources.end()){
    res_current = presources.find(1)->second.first;
  }else{
    res_current = 0;
  }
  uint32_t usedshipres = resources[1];
  if(pos != 0 || usedshipres == 0){
      turns = usedshipres;
  }else{
    if(usedshipres <= res_current){
      turns = 1;
    }else{
      turns = usedshipres - res_current;
    }
  }
  
  
  Order::createFrame(f, pos);

}
예제 #5
0
void BuildFleet::createFrame(OutputFrame::Ptr f, int pos)
{
  Logger::getLogger()->debug("Enter: BuildFleet::createFrame()");
  // set it to the high end of the production cost... this is a best case scenario where it gets all the factories
  IGObject::Ptr planet = Game::getGame()->getObjectManager()->getObject(Game::getGame()->getOrderManager()->getOrderQueue(orderqueueid)->getObjectId());
  
  // number of turns
  std::map<uint32_t, std::pair<uint32_t, uint32_t> > presources = static_cast<Planet*>(planet->getObjectBehaviour())->getResources();
  Game::getGame()->getObjectManager()->doneWithObject(planet->getID());
  uint32_t res_current;
  if(presources.find(1) != presources.end()){
    res_current = presources.find(1)->second.first;
  }else{
    res_current = 0;
  }
  uint32_t usedshipres = resources[1];
  if(pos != 0 || usedshipres == 0){
      turns = usedshipres;
  }else{
    if(usedshipres <= res_current){
      turns = 1;
    }else{
      turns = usedshipres - res_current;
    }
  }
  
  
  Order::createFrame(f, pos);
  Logger::getLogger()->debug("Exit: BuildFleet::createFrame()");

}
예제 #6
0
void TaeTurn::doTurn() {
    //check to make sure the game is still ging and this is not a combat turn
    if(isGameOver) {
        gameOver();
        return;
    } else if(combat) {
        doCombatTurn();
        return;
    }

    std::set<uint32_t>::iterator itcurr;

    Game* game = Game::getGame();
    OrderManager* ordermanager = game->getOrderManager();
    ObjectManager* objectmanager = game->getObjectManager();
    ObjectTypeManager* obtm = game->getObjectTypeManager();
    PlayerManager::Ptr playermanager = game->getPlayerManager();

    //build map for storing orders
    std::map<uint32_t, std::list<IGObject::Ptr > > playerOrders;

    containerids.clear();
    //separate orders by player
    std::set<uint32_t> objects = objectmanager->getAllIds();
    for(itcurr = objects.begin(); itcurr != objects.end(); ++itcurr) {
        IGObject::Ptr ob = objectmanager->getObject(*itcurr);
        if(ob->getType() == planettype || ob->getType() == fleettype) {
            OrderQueueObjectParam* oqop = dynamic_cast<OrderQueueObjectParam*>(ob->getParameterByType(obpT_Order_Queue));
            if(oqop != NULL) {
                OrderQueue::Ptr orderqueue = ordermanager->getOrderQueue(oqop->getQueueId());
                if(orderqueue != NULL) {
                    Order * currOrder = orderqueue->getFirstOrder();
                    if(currOrder != NULL) {
                        uint32_t owner = ((OwnedObject*)(ob->getObjectBehaviour()))->getOwner();
                        std::list<IGObject::Ptr >::iterator i = playerOrders[owner].end();
                        playerOrders[owner].insert(i, ob);
                    }
                }
            }
        }
    }

    //Do orders for players in the correct order
    //The order in which orders are processed is rotated each turn
    std::set<uint32_t> players = playermanager->getAllIds();
    itcurr = players.begin();
    for(int i = 0; i < playerTurn; i++) {
        itcurr++;
    }
    for(uint32_t it = 0; it < players.size(); it++) {
        if(itcurr == players.end()) {
            itcurr = players.begin();
        }
        if(playerOrders[*itcurr].size() > 0) {
            for(std::list<IGObject::Ptr >::iterator i = playerOrders[*itcurr].begin(); i != playerOrders[*itcurr].end(); i++) {
                OrderQueue::Ptr orderqueue = ordermanager->getOrderQueue(((OrderQueueObjectParam*)((*i)->getParameterByType(obpT_Order_Queue)))->getQueueId());
                Order* currOrder = orderqueue->getFirstOrder();
                if(currOrder!= NULL) {
                    if(currOrder->doOrder(*i)) {
                        orderqueue->removeFirstOrder();
                    } else {
                        orderqueue->updateFirstOrder();
                    }
                }
                if((*i)->getContainerType() >= 1) {
                    containerids.insert((*i)->getID());
                }
                objectmanager->doneWithObject((*i)->getID());
            }
        }
        itcurr++;
    }

    awardArtifacts();
    //Check for end game condition of less than 3 artifacts remaining
    objects = objectmanager->getAllIds();
    int numArtifacts = 0;
    for(itcurr = objects.begin(); itcurr != objects.end(); itcurr++) {
        IGObject::Ptr ob = objectmanager->getObject(*itcurr);
        if(ob->getType() == obtm->getObjectTypeByName("Planet")) {
            Planet* p = (Planet*) ob->getObjectBehaviour();
            if(p->getResource(3) > 0) {
                numArtifacts++;
            }
        }
    }
    if(numArtifacts < 3) {
        isGameOver = true;
        gameOver();
        return;
    }

    //Update which player's turn it is
    playerTurn = (playerTurn + 1) % playermanager->getNumPlayers();

    objectmanager->clearRemovedObjects();


    // to once a turn
    for(itcurr = objects.begin(); itcurr != objects.end(); ++itcurr) {
        IGObject::Ptr ob = objectmanager->getObject(*itcurr);
        if(ob->isAlive()) {
            ob->getObjectBehaviour()->doOnceATurn();
        }
        objectmanager->doneWithObject(ob->getID());
    }

    // find the objects that are visible to each player
    std::set<uint32_t> vis = objectmanager->getAllIds();
    for(std::set<uint32_t>::iterator itplayer = players.begin(); itplayer != players.end(); ++itplayer) {
        Player::Ptr player = playermanager->getPlayer(*itplayer);
        PlayerView::Ptr playerview = player->getPlayerView();

        for(std::set<uint32_t>::iterator itob = vis.begin(); itob != vis.end(); ++itob) {
            ObjectView::Ptr obv = playerview->getObjectView(*itob);
            if(obv == NULL) {
                if(objectmanager->getObject(*itob)->isAlive()) {
                    playerview->addVisibleObject( *itob, true );
                }
                objectmanager->doneWithObject(*itob);
            } else {
                IGObject::Ptr ro = objectmanager->getObject(*itob);
                uint64_t obmt = ro->getModTime();
                objectmanager->doneWithObject(*itob);
                if(obmt > obv->getModTime()) {
                    obv->setModTime(obmt);
                    playerview->updateObjectView(*itob);
                }
            }
        }

        // remove dead objects
        std::set<uint32_t> goneobjects;
        std::set<uint32_t> knownobjects = playerview->getVisibleObjects();
        set_difference(knownobjects.begin(), knownobjects.end(), vis.begin(), vis.end(), inserter(goneobjects, goneobjects.begin()));

        for(std::set<uint32_t>::iterator itob = goneobjects.begin(); itob != goneobjects.end(); ++itob) {
            ObjectView::Ptr obv = playerview->getObjectView(*itob);
            if(!obv->isGone()) {
                obv->setGone(true);
                playerview->updateObjectView(*itob);
            }
        }

        //Replace colonist fleets
        int fleets = 0;
        IGObject::Ptr homePlanet;
        for(std::set<uint32_t>::iterator itob = objects.begin(); itob != objects.end(); ++itob) {
            IGObject::Ptr ob = objectmanager->getObject(*itob);
            if(ob->getName().compare("Colonist Fleet") == 0) {
                uint32_t owner = ((OwnedObject*)(ob->getObjectBehaviour()))->getOwner();
                if(owner == *itplayer) {
                    fleets++;
                }
            }
            if(ob->getName().compare(string(player->getName() + "'s Home Planet")) == 0) {
                homePlanet = ob;
            }
        }

        for(int i = fleets; i < 6; i++) {
            IGObject::Ptr fleet = fleetBuilder->createFleet(FleetBuilder::PASSENGER_FLEET, FleetBuilder::RANDOM_SHIP, player, homePlanet, "Colonist Fleet");
            game->getObjectManager()->addObject(fleet);
            player->getPlayerView()->addVisibleObject(fleet->getID(), true);
        }

        //Send end of turn message to each player
        Message::Ptr msg( new Message() );
        msg->setSubject("Turn complete");
        stringstream out;
        out << "Your Current Score: \n";
        out << "Money: " << player->getScore(1) << "\n";
        out << "Technology: " << player->getScore(2) << "\n";
        out << "People: " << player->getScore(3) << "\n";
        out << "Raw Materials: " << player->getScore(4) << "\n";
        out << "Alien Artifacts: " << player->getScore(5);
        msg->setBody(out.str());
        player->postToBoard(msg);

        //Alert players to the turn order for next round
        msg.reset( new Message() );
        msg->setSubject("Turn Order");
        string body = "The order for the next turn is: ";
        itcurr = players.begin();
        for(int i = 0; i < playerTurn; i++) {
            itcurr++;
        }
        for(uint32_t it = 0; it < players.size(); it++) {
            if(itcurr == players.end()) {
                itcurr = players.begin();
            }
            body += playermanager->getPlayer(*itcurr)->getName();
            body += " ";
            itcurr++;
        }
        msg->setBody(body);
        player->postToBoard(msg);
    }

    //Initialize combat if the next turn is a combat turn
    if(combat) {
        initCombat();
    }

    playermanager->updateAll();

}
예제 #7
0
void TaeTurn::doCombatTurn() {
    std::set<uint32_t>::iterator itcurr;

    Game* game = Game::getGame();
    OrderManager* ordermanager = game->getOrderManager();
    ObjectManager* objectmanager = game->getObjectManager();
    ObjectTypeManager* obtm = game->getObjectTypeManager();
    PlayerManager::Ptr playermanager = game->getPlayerManager();

    containerids.clear();

    // Do orders
    std::set<uint32_t> objects = objectmanager->getAllIds();
    for(itcurr = objects.begin(); itcurr != objects.end(); ++itcurr) {
        IGObject::Ptr ob = objectmanager->getObject(*itcurr);
        if(ob->getType() == planettype || ob->getType() == fleettype) {
            OrderQueueObjectParam* oqop = dynamic_cast<OrderQueueObjectParam*>(ob->getParameterByType(obpT_Order_Queue));
            if(oqop != NULL) {
                OrderQueue::Ptr orderqueue = ordermanager->getOrderQueue(oqop->getQueueId());
                if(orderqueue != NULL) {
                    Order * currOrder = orderqueue->getFirstOrder();
                    if(currOrder != NULL) {
                        if(currOrder->doOrder(ob)) {
                            orderqueue->removeFirstOrder();
                        } else {
                            orderqueue->updateFirstOrder();
                        }
                    }
                    if(ob->getContainerType() >= 1) {
                        containerids.insert(ob->getID());
                    }
                    objectmanager->doneWithObject((ob)->getID());
                }
            }
        }
    }


    //Determine winner
    uint32_t winner = 0;
    uint32_t loser = 0;
    for(map<uint32_t, int>::iterator i = strength.begin(); i != strength.end(); ++i) {
        if(winner == 0) {
            winner = i->first;
        } else {
            if(strength[winner] < i->second) {
                winner = i->first;
            } else {
                loser = i->first;
            }
        }
    }

    //Remove losing combatants
    uint32_t losingRegion;
    uint32_t winningRegion;
    set<uint32_t> removedSystems;
    if(isInternal) {
        //Internal combat removes losing leader and awards one point to the winner
        for(map<uint32_t, uint32_t>::iterator i = combatants.begin(); i != combatants.end(); ++i) {
            IGObject::Ptr ob = objectmanager->getObject(i->first);
            Fleet* f = (Fleet*) ob->getObjectBehaviour();
            if(f->getOwner() != winner) {
                sendHome(i->first);
                Player::Ptr p = playermanager->getPlayer(winner);
                p->setScore(2, p->getScore(2) + 1);
                losingRegion = i->second;
                winningRegion = losingRegion;
            }
        }
        objects = objectmanager->getAllIds();
        for(itcurr = objects.begin(); itcurr!= objects.end(); ++itcurr) {
            IGObject::Ptr ob = objectmanager->getObject(*itcurr);
            if(ob->getType() == obtm->getObjectTypeByName("Star System")) {
                StarSystem* sysData = (StarSystem*) ob->getObjectBehaviour();
                if(sysData->getRegion() == losingRegion) {
                    sysData->setRegion(0);
                    removedSystems.insert(*itcurr);
                }
            }
        }
    } else {
        //External combat removes the losing leader and losing colonies.
        //1 point is awarded for the leader and each colony removed
        string shipType;
        //set shiptype, losing/winning regions, and send home the losing leader
        for(map<uint32_t, uint32_t>::iterator i = combatants.begin(); i != combatants.end(); ++i) {
            IGObject::Ptr ob = objectmanager->getObject(i->first);
            Fleet* f = (Fleet*) ob->getObjectBehaviour();
            if(f->getOwner() != winner) {
                losingRegion = i->second;
                shipType = ob->getName();
                sendHome(i->first);
            } else {
                winningRegion = i->second;
            }
        }

        //set the correct resource type
        int resourceType;
        if(shipType.compare("Merchant Leader") == 0) {
            resourceType = 4;
        } else if(shipType.compare("Scientist Leader") == 0) {
            resourceType = 5;
        } else if(shipType.compare("Settler Leader") == 0) {
            resourceType = 6;
        } else {
            resourceType = 7;
        }

        //add 1 to the winner for removing the leader
        Player::Ptr player = playermanager->getPlayer(winner);
        player->setScore(resourceType - 3, player->getScore(resourceType-3) + 1);

        //remove all losing colonies
        objects = objectmanager->getAllIds();
        for(itcurr = objects.begin(); itcurr!= objects.end(); ++itcurr) {
            IGObject::Ptr ob = objectmanager->getObject(*itcurr);
            if(ob->getType() == obtm->getObjectTypeByName("Planet")) {
                IGObject::Ptr sys = objectmanager->getObject(ob->getParent());
                StarSystem* sysData = (StarSystem*) sys->getObjectBehaviour();
                if(sysData->getRegion() == losingRegion) {
                    Planet* p = (Planet*) ob->getObjectBehaviour();
                    sysData->setRegion(0);
                    if(p->getResource(resourceType) > 0) {
                        p->removeResource(resourceType, 1);
                        player->setScore(resourceType - 3, player->getScore(resourceType-3) + 1);
                    } else {
                        removedSystems.insert(sys->getID());
                    }
                } else if(sysData->getRegion() == winningRegion) {
                    sysData->setRegion(0);
                    removedSystems.insert(sys->getID());
                }
            }
        }
    }

    //rebuild region
    for(itcurr = removedSystems.begin(); itcurr!= removedSystems.end(); ++itcurr) {
        rebuildRegion(*itcurr);
    }

    //Check for combat
    combat = false;
    while(!combatQueue.empty() && !combat) {
        pair<bool, map<uint32_t, uint32_t> > temp = combatQueue.front();
        combatQueue.pop();
        isInternal = temp.first;
        combatants = temp.second;
        combat = true;
        uint32_t region = 0;
        for(map<uint32_t, uint32_t>::iterator i = combatants.begin(); i != combatants.end() && combat; i++) {
            IGObject::Ptr ob = objectmanager->getObject(i->first);
            IGObject::Ptr sys = objectmanager->getObject(ob->getParent());
            StarSystem* sysData = (StarSystem*) sys->getObjectBehaviour();
            i->second = sysData->getRegion();
            if(region == 0) {
                region = sysData->getRegion();
            } else if(region != sysData->getRegion()) {
                combat = false;
            }
        }
    }

    //Cleanup and Set visibility
    objects = objectmanager->getAllIds();
    set<uint32_t> views;
    for(itcurr = objects.begin(); itcurr != objects.end(); ++itcurr) {
        IGObject::Ptr ob = objectmanager->getObject(*itcurr);
        if(ob->getType() == obtm->getObjectTypeByName("Fleet") && !combat) {
            Fleet* f = (Fleet*) ob->getObjectBehaviour();
            f->toggleCombat();
            f->setCombatant(false);
        }
        //Set visibility
        views.insert(ob->getID());
    }

    std::set<uint32_t> players = playermanager->getAllIds();
    std::set<uint32_t> vis = objectmanager->getAllIds();

    //clear the removed objecs
    objectmanager->clearRemovedObjects();
    objects = objectmanager->getAllIds();
    for(itcurr = objects.begin(); itcurr != objects.end(); ++itcurr) {
        IGObject::Ptr ob = objectmanager->getObject(*itcurr);
        if(ob->isAlive()) {
            ob->getObjectBehaviour()->doOnceATurn();
        }
        objectmanager->doneWithObject(ob->getID());
    }

    for(std::set<uint32_t>::iterator itplayer = players.begin(); itplayer != players.end(); ++itplayer) {
        Player::Ptr player = playermanager->getPlayer(*itplayer);
        PlayerView::Ptr playerview = player->getPlayerView();

        //Update visibility
        playerview->addVisibleObjects(views);

        for(std::set<uint32_t>::iterator itob = vis.begin(); itob != vis.end(); ++itob) {
            ObjectView::Ptr obv = playerview->getObjectView(*itob);
            if(obv == NULL) {
                if(objectmanager->getObject(*itob)->isAlive()) {
                    playerview->addVisibleObject(*itob, true);
                }
                objectmanager->doneWithObject(*itob);
            } else {
                IGObject::Ptr ro = objectmanager->getObject(*itob);
                uint64_t obmt = ro->getModTime();
                objectmanager->doneWithObject(*itob);
                if(obmt > obv->getModTime()) {
                    obv->setModTime(obmt);
                    playerview->updateObjectView(*itob);
                }
            }
        }

        // remove dead objects
        std::set<uint32_t> goneobjects;
        std::set<uint32_t> knownobjects = playerview->getVisibleObjects();
        set_difference(knownobjects.begin(), knownobjects.end(), vis.begin(), vis.end(), inserter(goneobjects, goneobjects.begin()));

        for(std::set<uint32_t>::iterator itob = goneobjects.begin(); itob != goneobjects.end(); ++itob) {
            ObjectView::Ptr obv = playerview->getObjectView(*itob);
            if(!obv->isGone()) {
                obv->setGone(true);
                playerview->updateObjectView(*itob);
            }
        }

        //Replace colonist fleets
        int fleets = 0;
        IGObject::Ptr homePlanet;
        for(std::set<uint32_t>::iterator itob = objects.begin(); itob != objects.end(); ++itob) {
            IGObject::Ptr ob = objectmanager->getObject(*itob);
            if(ob->getName().compare("Colonist Fleet") == 0) {
                uint32_t owner = ((OwnedObject*)(ob->getObjectBehaviour()))->getOwner();
                if(owner == *itplayer) {
                    fleets++;
                }
            }
            if(ob->getName().compare(string(player->getName() + "'s Home Planet")) == 0) {
                homePlanet = ob;
            }
        }

        for(int i = fleets; i < 6; i++) {
            IGObject::Ptr fleet = fleetBuilder->createFleet(FleetBuilder::PASSENGER_FLEET, FleetBuilder::RANDOM_SHIP, player, homePlanet, "Colonist Fleet");
            game->getObjectManager()->addObject(fleet);
            player->getPlayerView()->addVisibleObject(fleet->getID(), true);
        }

        //Send end of turn message to each player
        Message::Ptr msg( new Message() );
        msg->setSubject("Combat Complete!");
        stringstream out;
        Player::Ptr win = playermanager->getPlayer(winner);
        out << win->getName() << " has won the battle with a strength of ";
        out << strength[winner] << "!";
        msg->setBody(out.str());
        player->postToBoard(msg);

        msg.reset( new Message() );
        msg->setSubject("Turn complete");
        stringstream out2;
        out2 << "Your Current Score: \n";
        out2 << "Money: " << player->getScore(1) << "\n";
        out2 << "Technology: " << player->getScore(2) << "\n";
        out2 << "People: " << player->getScore(3) << "\n";
        out2 << "Raw Materials: " << player->getScore(4) << "\n";
        out2 << "Alien Artifacts: " << player->getScore(5);
        msg->setBody(out2.str());
        player->postToBoard(msg);

    }

    if(combat) {
        initCombat();
    }

    playermanager->updateAll();

}
예제 #8
0
//Setup the next turn to be ready for combat
void TaeTurn::initCombat() {
    std::set<uint32_t>::iterator itcurr;

    Game* game = Game::getGame();
    ObjectManager* objectmanager = game->getObjectManager();
    PlayerManager::Ptr playermanager = game->getPlayerManager();
    ObjectTypeManager* obtm = game->getObjectTypeManager();
    DesignStore::Ptr ds = game->getDesignStore();

    //Pop the combat queue and set the combatants
    pair<bool, map<uint32_t, uint32_t> > temp;
    temp = combatQueue.front();
    combatQueue.pop();
    isInternal = temp.first;
    combatants = temp.second;
    strength.clear();
    for(map<uint32_t, uint32_t>::iterator i = combatants.begin(); i != combatants.end(); ++i) {
        IGObject::Ptr ob = Game::getGame()->getObjectManager()->getObject(i->first);
        Fleet* f = (Fleet*) ob->getObjectBehaviour();
        strength[f->getOwner()] = 0;
    }

    set<uint32_t> owners;
    set<uint32_t> regions;
    string shipType;
    for(map<uint32_t, uint32_t>::iterator i = combatants.begin(); i != combatants.end(); ++i) {
        IGObject::Ptr ob = objectmanager->getObject(i->first);
        Fleet* leader = (Fleet*) (ob)->getObjectBehaviour();
        //look for the shiptype which this combat is associated with
        if(shipType.empty()) {
            if(isInternal) {
                shipType = "ScientistShip";
            } else {
                //Set shiptype to the type corresponding to the leader
                uint32_t ship = leader->getShips().begin()->first;
                shipType = ds->getDesign(ship)->getName();
                size_t pos = shipType.find("Leader");
                if(pos != shipType.npos) {
                    shipType.erase(pos, 6);
                }
            }
        }
        owners.insert(leader->getOwner());

        //Set which regions are involved in combat
        if(regions.count(i->second) <= 0) {
            regions.insert(i->second);
        }

        //Set initial internal combat strength
        if(isInternal) {
            IGObject::Ptr starSys = objectmanager->getObject(ob->getParent());
            StarSystem* starSysData = (StarSystem*)(starSys->getObjectBehaviour());
            Vector3d pos = starSysData->getPosition();
            //Search for bordering science colonies
            //east-west neighbors
            for(int i = -1; i < 2; i+=2) {
                set<uint32_t> ids = objectmanager->getObjectsByPos(pos+Vector3d(80000*i,0,0), 1);
                for(set<uint32_t>::iterator j=ids.begin(); j != ids.end(); j++) {
                    IGObject::Ptr tempObj = objectmanager->getObject(*j);
                    if(tempObj->getType() == obtm->getObjectTypeByName("Planet")) {
                        Planet* p = (Planet*)(tempObj->getObjectBehaviour());
                        if(p->getResource(5) > 0) {
                            addReinforcement(leader->getOwner());
                        }
                    }
                }
            }
            //north-south neighbors
            for(int i = -1; i < 2; i+=2) {
                set<uint32_t> ids = objectmanager->getObjectsByPos(pos+Vector3d(0,80000*i,0), 1);
                for(set<uint32_t>::iterator j=ids.begin(); j != ids.end(); j++) {
                    IGObject::Ptr tempObj = objectmanager->getObject(*j);
                    if(tempObj->getType() == obtm->getObjectTypeByName("Planet")) {
                        Planet* p = (Planet*)(tempObj->getObjectBehaviour());
                        if(p->getResource(5) > 0) {
                            addReinforcement(leader->getOwner());
                        }
                    }
                }
            }
        }
    }

    //Set which resource will be awarded
    int resourceType;
    if(shipType.compare("MerchantShip") == 0) {
        resourceType = 4;
    } else if(shipType.compare("ScientistShip") == 0) {
        resourceType = 5;
    } else if(shipType.compare("SettlerShip") == 0) {
        resourceType = 6;
    } else {
        resourceType = 7;
    }

    //Set all fleets to combat mode. Flag the fleets whose owners are
    //directly involved in combat.
    std::set<uint32_t> views;
    std::set<uint32_t> objects = objectmanager->getAllIds();
    for(itcurr = objects.begin(); itcurr != objects.end(); ++itcurr) {
        IGObject::Ptr ob = objectmanager->getObject(*itcurr);
        if(ob->getType() == obtm->getObjectTypeByName("Fleet")) {
            Fleet* f = (Fleet*) ob->getObjectBehaviour();
            f->toggleCombat();
            //check to see if this fleet is a combatant
            if(owners.count(f->getOwner()) > 0) {
                uint32_t ship = f->getShips().begin()->first;
                string name = ds->getDesign(ship)->getName();
                if(name.compare(shipType) == 0) {
                    f->setCombatant(true);
                }
            }

            //Set visibility
            views.insert(ob->getID());
        }
        //Set initial external combat strength
        else if(ob->getType() == obtm->getObjectTypeByName("Planet") && !isInternal) {
            Planet* p = (Planet*) ob->getObjectBehaviour();
            StarSystem* sys = (StarSystem*) objectmanager->getObject(ob->getParent())->getObjectBehaviour();
            if(regions.count(sys->getRegion()) > 0) {
                if(p->getResource(resourceType) > 0) {
                    for(map<uint32_t, uint32_t>::iterator i = combatants.begin(); i != combatants.end(); ++i) {
                        if(i->second == sys->getRegion()) {
                            Fleet* leader = (Fleet*) (objectmanager->getObject(i->first))->getObjectBehaviour();
                            addReinforcement(leader->getOwner());
                        }
                    }
                }
            }
        }
    }

    //Send message to players letting them know about combat
    Message::Ptr msg( new Message() );
    msg->setSubject("COMBAT!");
    stringstream out;
    out << "The next turn is an ";
    if(isInternal) {
        out << "INTERNAL ";
    } else {
        out << "EXTERNAL ";
    }
    out << "combat turn! Combatants are:  ";
    out << playermanager->getPlayer(*owners.begin())->getName();
    out << " with an initial strength of ";
    out << strength[*owners.begin()] << " and ";
    out << playermanager->getPlayer(*owners.end())->getName();
    out << " with an initial strength of ";
    out << strength[*owners.end()];
    msg->setBody(out.str());

    std::set<uint32_t> players = playermanager->getAllIds();
    for(itcurr = players.begin(); itcurr != players.end(); ++itcurr) {
        Player::Ptr player = playermanager->getPlayer(*itcurr);
        player->postToBoard(Message::Ptr( new Message(*msg)));
        player->getPlayerView()->addVisibleObjects( views );
    }
}
예제 #9
0
bool Colonise::doOrder(IGObject::Ptr ob){
  //if not close, move
  IGObject::Ptr target = Game::getGame()->getObjectManager()->getObject(ob->getParent());
  if(target == NULL || target->getType() != Game::getGame()->getObjectTypeManager()->getObjectTypeByName("Planet")){
    
    Logger::getLogger()->debug("Object(%d)->Colonise->doOrder(): Target was not valid.", ob->getID());
    Game::getGame()->getObjectManager()->doneWithObject(ob->getParent());
    Message::Ptr msg( new Message() );
    msg->setSubject("Colonise order canceled");
    msg->setBody("Not at a planet, colonisation canceled");
    msg->addReference(rst_Action_Order, rsorav_Canceled);
    msg->addReference(rst_Object, ob->getID());
    Game::getGame()->getPlayerManager()->getPlayer(((Fleet*)(ob->getObjectBehaviour()))->getOwner())->postToBoard(msg);

    return true;
  }
  
  Fleet* fleet = (Fleet*)(ob->getObjectBehaviour());
  Planet* planet = (Planet*)(target->getObjectBehaviour());
  
    Message::Ptr msg( new Message() );
  msg->addReference(rst_Object, ob->getID());
  msg->addReference(rst_Object, target->getID());

  if(planet->getOwner() != fleet->getOwner()){

    if(planet->getOwner() != 0){
      Logger::getLogger()->debug("Object(%d)->Colonise->doOrder(): Planet already owned.", 
        ob->getID());
    
      msg->setSubject("Colonisation failed");
      msg->setBody("The planet you tried to colonise, is already owned by someone else.");
      msg->addReference(rst_Action_Order, rsorav_Canceled);
    }else{

      DesignStore::Ptr ds = Game::getGame()->getDesignStore();
      int shiptype = 0;
      int shiphp = 2000000;
      IdMap ships = fleet->getShips();
      uint32_t colonisePropID = ds->getPropertyByName( "Colonise");
      uint32_t armorPropID = ds->getPropertyByName( "Armour");
      for(IdMap::iterator itcurr = ships.begin();
	  itcurr != ships.end(); ++itcurr){
        Design::Ptr design = ds->getDesign(itcurr->first);
	if(design->getPropertyValue(colonisePropID) != 0.0 && shiphp > (int)design->getPropertyValue(armorPropID)){
	  shiptype = itcurr->first;
	  shiphp = (int)design->getPropertyValue(armorPropID);
	}
      }

      Logger::getLogger()->debug("Object(%d)->Colonise->doOrder(): shiptype %d", 
          ob->getID(), shiptype);
      if(shiptype != 0){
        uint32_t oldowner = planet->getOwner();
        planet->setOwner(fleet->getOwner());
        Game::getGame()->getPlayerManager()->getPlayer(fleet->getOwner())->getPlayerView()->addOwnedObject(target->getID());
        uint32_t queueid = static_cast<OrderQueueObjectParam*>(target->getParameterByType(obpT_Order_Queue))->getQueueId();
        OrderQueue::Ptr queue = Game::getGame()->getOrderManager()->getOrderQueue(queueid);
        queue->removeOwner(oldowner);
        queue->addOwner(fleet->getOwner());

        fleet->removeShips(shiptype, 1);

        msg->setSubject("Colonised planet");
        msg->setBody("You have colonised a planet!");
        msg->addReference(rst_Action_Order, rsorav_Completion);

      }else{
        msg->setSubject("Colonisation failed");
        msg->setBody("Your fleet did not have a frigate to colonise the planet");
        msg->addReference(rst_Action_Order, rsorav_Invalid);
      }

      if(fleet->totalShips() == 0){
        Game::getGame()->getObjectManager()->scheduleRemoveObject(ob->getID());
        Game::getGame()->getPlayerManager()->getPlayer(fleet->getOwner())->getPlayerView()->removeOwnedObject(ob->getID());
      }
      
    }
  }else{
    Logger::getLogger()->debug("Object(%d)->Colonise->doOrder(): Was already owned by the player!", 
      ob->getID());

    msg->setSubject("Colonisation failed");
    msg->setBody("You already own the planet you tried to colonise");
    msg->addReference(rst_Action_Order, rsorav_Canceled);
  }
  
  Game::getGame()->getPlayerManager()->getPlayer(fleet->getOwner())->postToBoard(msg);
  Game::getGame()->getObjectManager()->doneWithObject(target->getID());
  return true;
  
}
예제 #10
0
bool BuildFleet::doOrder(IGObject::Ptr ob)
{
  Logger::getLogger()->debug("Entering BuildFleet::doOrder");

  Planet* planet = static_cast<Planet*>(ob->getObjectBehaviour());

  Game* game = Game::getGame();
  ResourceManager::Ptr resman = game->getResourceManager();
  const uint32_t resType = resman->getResourceDescription("Factories")->getResourceType();
  const uint32_t resValue = planet->getResourceSurfaceValue(resType);

  int ownerid = planet->getOwner();
  if(ownerid == 0){
      Logger::getLogger()->debug("Exiting BuildFleet::doOrder ownerid == 0");
      //currently not owned by anyone, just forget about it
      return true;
  }

  uint32_t runningTotal = resources[1];
  if (resValue == 0) {
    Message::Ptr msg(new Message());
    msg->setSubject("Build Fleet order error");
    msg->setBody(std::string("The construction of your  new fleet \"") + fleetname->getString() + "\" has been delayed, you do not have any production points this turn.");
    Game::getGame()->getPlayerManager()->getPlayer(ownerid)->postToBoard(msg);
    return false;
  } else if(runningTotal > resValue) {
    if (planet->removeResource(resType, resValue)) {
      removeResource(1, resValue);
      runningTotal = resources[1];
      uint32_t planetFactories = planet->getFactoriesPerTurn();
      turns = static_cast<uint32_t>(ceil(runningTotal / planetFactories));
      Message::Ptr msg(new Message());
      msg->setSubject("Build Fleet order slowed");
      msg->setBody(std::string("The construction of your new fleet \"") + fleetname->getString() + "\" has been delayed.");
      Game::getGame()->getPlayerManager()->getPlayer(ownerid)->postToBoard(msg);
      return false;
    }
  } else if(runningTotal <= resValue && planet->removeResource(resType, runningTotal)){
    //create fleet

    //this is probably unnecessary
    resources[1] = 0;
    Game* game = Game::getGame();
    
    
    IGObject::Ptr fleet = game->getObjectManager()->createNewObject();
    game->getObjectTypeManager()->setupObject(fleet, game->getObjectTypeManager()->getObjectTypeByName("Fleet"));

    //add fleet to container
    fleet->addToParent(ob->getID());

    fleet->setName(fleetname->getString().c_str());

    Fleet * thefleet = dynamic_cast<Fleet*>(fleet->getObjectBehaviour());

    thefleet->setSize(2);
    thefleet->setOwner(ownerid); // set ownerid
    thefleet->setPosition(planet->getPosition());
    thefleet->setVelocity(Vector3d(0LL, 0ll, 0ll));
    
    uint32_t queueid = Game::getGame()->getOrderManager()->addOrderQueue(fleet->getID(), ownerid);
    OrderQueueObjectParam* oqop = static_cast<OrderQueueObjectParam*>(fleet->getParameterByType(obpT_Order_Queue));
    oqop->setQueueId(queueid);
    thefleet->setDefaultOrderTypes();

    //set ship type
    IdMap fleettype = fleetlist->getList();
    for(IdMap::iterator itcurr = fleettype.begin(); itcurr != fleettype.end(); ++itcurr){
      thefleet->addShips(itcurr->first, itcurr->second);
      Design::Ptr design = Game::getGame()->getDesignStore()->getDesign(itcurr->first);
        design->addComplete(itcurr->second);
        Game::getGame()->getDesignStore()->designCountsUpdated(design);
    }
    //add fleet to universe
    Game::getGame()->getObjectManager()->addObject(fleet);
    Game::getGame()->getPlayerManager()->getPlayer(ownerid)->getPlayerView()->addOwnedObject(fleet->getID());

    Message::Ptr msg( new Message() );
    msg->setSubject("Build Fleet order complete");
    msg->setBody(std::string("The construction of your new fleet \"") + fleetname->getString() + "\" is complete.");
    msg->addReference(rst_Action_Order, rsorav_Completion);
    msg->addReference(rst_Object, fleet->getID());
    msg->addReference(rst_Object, ob->getID());
 
    Game::getGame()->getPlayerManager()->getPlayer(ownerid)->postToBoard(msg);
    Logger::getLogger()->debug("Exiting BuildFleet::doOrder on Success");

    return true;
  }
  Logger::getLogger()->debug("Exiting BuildFleet::doOrder on failure");

  return false;
}
예제 #11
0
void RftsTurn::doTurn() {

   Game* game = Game::getGame();
   OrderManager* ordermanager = game->getOrderManager();
   ObjectManager* objectmanager = game->getObjectManager();
   PlayerManager::Ptr pm = game->getPlayerManager();

   set<uint32_t> objectsIds = objectmanager->getAllIds();

   // currently just go through each obj and do each order
   // will be prioritized/sorted soon TODO

   for(set<uint32_t>::iterator i = objectsIds.begin();
         i != objectsIds.end(); ++i)
   {
      IGObject::Ptr currObj = objectmanager->getObject(*i);

      OrderQueueObjectParam* oqop = dynamic_cast<OrderQueueObjectParam*>(currObj->getParameterByType(obpT_Order_Queue));
      OrderQueue::Ptr oq;
      if(oqop != NULL && 
         (oq = ordermanager->getOrderQueue(oqop->getQueueId())) != NULL)
      {
         for(uint32_t j = 0; j < oq->getNumberOrders(); j++)
         {
            OwnedObject *orderedObj = dynamic_cast<OwnedObject*>(currObj->getObjectBehaviour());
            assert(orderedObj);

            Order* order = oq->getOrder(j, orderedObj->getOwner());
            if(order->doOrder(currObj))
            {
               oq->removeOrder(j, orderedObj->getOwner());
               j--; // list has been reordered
            }
            else
               oq->updateFirstOrder(); // CHECK
         }
         currObj->touchModTime();
      }
      objectmanager->doneWithObject(currObj->getID());
          
   }
   
   objectmanager->clearRemovedObjects();

   // re-explore new area
   setPlayerVisibleObjects();

   // to once a turn (right at the end)
   objectsIds = objectmanager->getAllIds();
   for(std::set<uint32_t>::iterator i = objectsIds.begin(); 
       i != objectsIds.end(); ++i)
   {
      IGObject::Ptr obj = objectmanager->getObject(*i);
      obj->getObjectBehaviour()->doOnceATurn();
      objectmanager->doneWithObject(obj->getID());
   }

   objectmanager->clearRemovedObjects();
   
   // update in case fleets were destroyed in combat
   setPlayerVisibleObjects();

   set<uint32_t> players = pm->getAllIds();
   for(set<uint32_t>::iterator i = players.begin(); i != players.end(); ++i)
      PlayerInfo::getPlayerInfo(*i).clearPdbUpgrade();

   Player::Ptr winner = getWinner();
   if(winner != NULL)
   {
      string body;
      Message::Ptr gameOver( new Message() );
      gameOver->setSubject("Game over!");
      
      if( game->getTurnNumber() ==
            static_cast<unsigned>(strtol(Settings::getSettings()->get("game_length").c_str(), NULL, 10)) )
         body = "Game length elapsed, winner is: ";
      else
         body = "Overwhelming victory by: ";
         
      body += winner->getName();
      gameOver->setBody(PlayerInfo::appAllVictoryPoints(body));

      for(set<uint32_t>::iterator i = players.begin(); i != players.end(); ++i)
         pm->getPlayer(*i)->postToBoard( Message::Ptr( new Message(*gameOver) ));
   }
   
   int turn = game->getTurnNumber() % 3;
   if(turn == 0){
       game->setTurnName("Production, Construction, Movement");
   }else if(turn == 1){
       game->setTurnName("Construction, Movement");
   }else{
       game->setTurnName("Movement");
   }
}
예제 #12
0
void RSPCombat::doCombat(std::map<uint32_t, IdSet> sides) {
    Game* game = Game::getGame();
    PlayerManager::Ptr playermanager = game->getPlayerManager();
    ObjectManager* objectmanager = game->getObjectManager();
    DesignStore::Ptr ds = game->getDesignStore();

    const char * const rsp[] = {"rock", "scissors", "paper"};

    IdSet listallobids;
    IdSet listallplayerids;

    std::map<uint32_t, std::vector<Combatant*> > fleetcache;

    battlelogger.reset(new BattleXML::BattleLogger());
    msgstrings.clear();

    for(std::map<uint32_t, IdSet>::iterator itmap = sides.begin(); itmap != sides.end(); ++itmap) {
        std::vector<Combatant*> pcombatant;
        Player::Ptr player = playermanager->getPlayer(itmap->first);
        battlelogger->startSide(player->getName());
        IdSet theset = itmap->second;
        for(IdSet::iterator itset = theset.begin(); itset != theset.end(); ++itset) {
            listallobids.insert(*itset);
            IGObject::Ptr obj = objectmanager->getObject (*itset);
            objectcache[*itset] = obj;
            if(obj->getType() == obT_Fleet) {
                Fleet* f2 = (Fleet*)(obj->getObjectBehaviour());
                IdMap shiplist = f2->getShips();
                uint32_t damage = f2->getDamage();
                for(IdMap::reverse_iterator itship = shiplist.rbegin(); itship != shiplist.rend(); ++itship) {
                    for(uint32_t i = 0; i < itship->second; i++) {
                        Combatant* f1 = new Combatant();
                        f1->setOwner(itmap->first);
                        f1->setObject(obj->getID());
                        f1->setShipType(itship->first);
                        uint32_t mydamage = damage / std::max(1U, (unsigned int)(shiplist.size() - i));
                        f1->setDamage(mydamage);
                        damage -= mydamage;
                        std::string type = ds->getDesign(itship->first)->getName();
                        f1->setBattleXmlType(type);
                        f1->setBattleXmlId(str(boost::format("%1%-%2%-%3%") % type % obj->getID() % i));
                        f1->setBattleXmlName(str(boost::format("%1%'s %2%, %3% %4%") % player->getName() % obj->getName() % type % i));
                        battlelogger->addCombatant(f1);
                        pcombatant.push_back(f1);
                    }
                }
            } else {
                int shipcount = 2;
                int homeplanetid = game->getResourceManager()->getResourceDescription("Home Planet")->getResourceType();
                if(((Planet*)(obj->getObjectBehaviour()))->getResource(homeplanetid) == 1) {
                    //three more for home planets
                    shipcount += 3;
                }
                for(int i = 0; i < shipcount; i++) {
                    Combatant* f1 = new Combatant();
                    f1->setOwner(itmap->first);
                    f1->setObject(obj->getID());
                    f1->setShipType(0);
                    f1->setBattleXmlType("planet");
                    f1->setBattleXmlId(str(boost::format("planet-%1%-%2%") % obj->getID() % i));
                    f1->setBattleXmlName(str(boost::format("%1%'s colony on %2%, Defense battery %3%") % player->getName() % obj->getName() % i));
                    battlelogger->addCombatant(f1);
                    pcombatant.push_back(f1);
                }
            }
        }
        listallplayerids.insert(itmap->first);
        battlelogger->endSide();
        //sort combatant list by ship type, descending
        sort(pcombatant.begin(), pcombatant.end(), CombatantSorter());
        fleetcache[itmap->first] = pcombatant;
    }

    for(std::set<uint32_t>::iterator itplayer = listallplayerids.begin(); itplayer != listallplayerids.end(); ++itplayer) {
        msgstrings[*itplayer] = "";
    }



    Random* random = Game::getGame()->getRandom();

    Logger::getLogger()->debug("Combat start");

    while(fleetcache.size() >= 2) {
        battlelogger->startRound();
        uint32_t pos1, pos2;
        if(fleetcache.size() == 2) {
            pos1 = 0;
            pos2 = 1;
        } else {
            pos1 = pos2 = random->getInRange(0U, ((uint32_t)(fleetcache.size() - 1)));
            while(pos2 == pos1) {
                pos2 = random->getInRange(0U, ((uint32_t)(fleetcache.size() - 1)));
            }
        }

        std::map<uint32_t, std::vector<Combatant*> >::iterator itpa = fleetcache.begin();
        advance(itpa, pos1);
        std::map<uint32_t, std::vector<Combatant*> >::iterator itpb = fleetcache.begin();
        advance(itpb, pos2);

        std::vector<Combatant*> f1 = itpa->second;
        std::vector<Combatant*> f2 = itpb->second;

        uint32_t ownerid1 = f1[0]->getOwner();
        uint32_t ownerid2 = f2[0]->getOwner();

        std::string p1name = playermanager->getPlayer(ownerid1)->getName();
        std::string p2name = playermanager->getPlayer(ownerid2)->getName();

        int32_t r1 = random->getInRange((int32_t)0, (int32_t)2);
        int32_t r2 = random->getInRange((int32_t)0, (int32_t)2);

        std::map<Combatant*, uint32_t> d1, d2;

        battlelogger->log(str(boost::format("%1%'s fleet chooses %2%.") % p1name % rsp[r2]));
        battlelogger->log(str(boost::format("%1%'s fleet chooses %2%.") % p2name % rsp[(r2 + r1) % 3]));

        if(r1 == 0) {
            //draw
            battlelogger->log("It's a draw");
            d1 = buildShotList(f1, true);
            d2 = buildShotList(f2, true);

            if(d1.size() != 0)
                doDamage(d1, f2);
            if(d2.size() != 0)
                doDamage(d2, f1);
        } else {

            if(r1 == 1) {
                //pa win
                battlelogger->log(str(boost::format("%1% wins.") % p1name));

                d1 = buildShotList(f1);
                if(d1.size() == 0) {
                    battlelogger->log(str(boost::format("%1%'s forces escape") % p1name));
                    msgstrings[ownerid1] += "Your Fleet escaped. ";
                    for(std::map<uint32_t, std::string>::iterator msgit = msgstrings.begin();
                            msgit != msgstrings.end(); ++msgit) {
                        if(msgit->first == ownerid1)
                            continue;
                        msgit->second += str(boost::format("%1%'s fleet of escaped. ") % p1name);
                    }
                    resolveCombatantsToObjects(f1);
                    for(std::vector<Combatant*>::iterator itcombatant = f1.begin(); itcombatant != f1.end();
                            ++itcombatant) {
                        delete *itcombatant;
                    }
                    fleetcache.erase(itpa);
                    battlelogger->endRound();
                    continue;
                }
                doDamage(d1, f2);
            } else {
                //pb win
                battlelogger->log(str(boost::format("%1% wins.") % p2name));
                d2 = buildShotList(f2);
                if(d2.size() == 0) {
                    battlelogger->log(str(boost::format("%1%'s forces escape") % p2name));
                    msgstrings[ownerid2] += "Your Fleet escaped. ";
                    for(std::map<uint32_t, std::string>::iterator msgit = msgstrings.begin();
                            msgit != msgstrings.end(); ++msgit) {
                        if(msgit->first == ownerid2)
                            continue;
                        msgit->second += str(boost::format("%1%'s fleet of escaped. ") % p2name);
                    }
                    resolveCombatantsToObjects(f2);
                    for(std::vector<Combatant*>::iterator itcombatant = f2.begin(); itcombatant != f2.end();
                            ++itcombatant) {
                        delete *itcombatant;
                    }
                    fleetcache.erase(itpb);
                    battlelogger->endRound();
                    continue;
                }
                doDamage(d2, f1);
            }

        }

        if(isAllDead(f1)) {
            msgstrings[ownerid1] += str(boost::format("Your fleet was destroyed by %1%'s fleet. ") % p2name);
            msgstrings[ownerid2] += str(boost::format("You destroyed %1%'s fleet. ") % p1name);
            std::string deathmsg = str(boost::format("%1%'s fleet destroyed %2%'s fleet. ") % p1name % p2name);
            for(std::map<uint32_t, std::string>::iterator msgit = msgstrings.begin();
                    msgit != msgstrings.end(); ++msgit) {
                if(msgit->first == ownerid1 || msgit->first == ownerid2)
                    continue;
                msgit->second += deathmsg;
            }
            resolveCombatantsToObjects(f1);
            for(std::vector<Combatant*>::iterator itcombatant = f1.begin(); itcombatant != f1.end();
                    ++itcombatant) {
                delete *itcombatant;
            }
            fleetcache.erase(itpa);
        }
        if(isAllDead(f2)) {
            msgstrings[ownerid2] += str(boost::format("Your fleet was destroyed by %1%'s fleet. ") % p1name);
            msgstrings[ownerid1] += str(boost::format("You destroyed %1%'s fleet. ") % p2name);
            std::string deathmsg = str(boost::format("%1%'s fleet destroyed %2%'s fleet. ") % p2name % p1name);
            for(std::map<uint32_t, std::string>::iterator msgit = msgstrings.begin();
                    msgit != msgstrings.end(); ++msgit) {
                if(msgit->first == ownerid1 || msgit->first == ownerid2)
                    continue;
                msgit->second += deathmsg;
            }
            resolveCombatantsToObjects(f2);
            for(std::vector<Combatant*>::iterator itcombatant = f2.begin(); itcombatant != f2.end();
                    ++itcombatant) {
                delete *itcombatant;
            }
            fleetcache.erase(itpb);
        }

        battlelogger->endRound();

    }

    std::string file = battlelogger->save();

    if(!fleetcache.empty()) {
        std::vector<Combatant*> flast = fleetcache.begin()->second;
        resolveCombatantsToObjects(flast);
        msgstrings[flast[0]->getOwner()] += "Your Fleet survived combat.";
        for(std::vector<Combatant*>::iterator itcombatant = flast.begin(); itcombatant != flast.end();
                ++itcombatant) {
            delete *itcombatant;
        }
        fleetcache.erase(fleetcache.begin());
        if(!fleetcache.empty()) {
            Logger::getLogger()->warning("fleetcache not empty at end of combat");
        }
    }
    for(std::map<uint32_t, std::string>::iterator msgit = msgstrings.begin();
            msgit != msgstrings.end(); ++msgit) {
        Message::Ptr msg( new Message() );
        msg->setSubject("Combat");
        for(std::set<uint32_t>::iterator itob = listallobids.begin(); itob != listallobids.end();
                ++itob) {
            msg->addReference(rst_Object, *itob);
        }
        for(std::set<uint32_t>::iterator itpl = listallplayerids.begin();
                itpl != listallplayerids.end(); ++itpl) {
            msg->addReference(rst_Player, *itpl);
        }

        msg->setBody(msgit->second);

        Game::getGame()->getPlayerManager()->getPlayer(msgit->first)->postToBoard(msg);
    }

    for(std::map<uint32_t, IGObject::Ptr>::iterator itob = objectcache.begin();
            itob != objectcache.end(); ++itob) {
        Game::getGame()->getObjectManager()->doneWithObject(itob->first);
    }
    objectcache.clear();

}
예제 #13
0
void RSPCombat::resolveCombatantsToObjects(std::vector<Combatant*> combatants) {

    std::map<objectid_t, bool> colonydead;

    std::map<objectid_t, uint32_t> damagemap;

    for(std::vector<Combatant*>::iterator itcombat = combatants.begin(); itcombat != combatants.end(); ++itcombat) {
        Combatant* combatant = *itcombat;
        if(combatant->getShipType() == 0) {
            //special for planets
            std::map<objectid_t, bool>::iterator itplanet = colonydead.find(combatant->getObject());
            if(itplanet == colonydead.end()) {
                colonydead[combatant->getObject()] = combatant->isDead();
            } else {
                itplanet->second &= combatant->isDead();
            }
        } else if(combatant->isDead()) {
            IGObject::Ptr obj = objectcache[combatant->getObject()];
            Fleet* fleet = dynamic_cast<Fleet*>(obj->getObjectBehaviour());
            if(fleet != NULL) {
                fleet->removeShips(combatant->getShipType(), 1);
                if(fleet->totalShips() == 0) {
                    //the fleet dead
                    //message player
                    msgstrings[combatant->getOwner()] += str(boost::format("Your fleet %1% was destroyed. ") % obj->getName());
                    //remove object
                    uint32_t queueid = static_cast<OrderQueueObjectParam*>(obj->getParameterByType(obpT_Order_Queue))->getQueueId();
                    OrderQueue::Ptr queue = Game::getGame()->getOrderManager()->getOrderQueue(queueid);
                    queue->removeOwner(combatant->getOwner());
                    queue->removeAllOrders();
                    Game::getGame()->getObjectManager()->scheduleRemoveObject(obj->getID());
                    Game::getGame()->getPlayerManager()->getPlayer(fleet->getOwner())->getPlayerView()->removeOwnedObject(obj->getID());
                }
            }
        } else {
            if(damagemap.find(combatant->getObject()) == damagemap.end()) {
                damagemap[combatant->getObject()] = combatant->getDamage();
            } else {
                damagemap[combatant->getObject()] += combatant->getDamage();
            }
        }
    }

    for(std::map<objectid_t, uint32_t>::iterator itobj = damagemap.begin(); itobj != damagemap.end(); ++itobj) {
        IGObject::Ptr obj = objectcache[itobj->first];
        Fleet* fleet = dynamic_cast<Fleet*>(obj->getObjectBehaviour());
        if(fleet == NULL) {
            warningLog("Fleet was not a fleet");
            continue;
        }
        fleet->setDamage(itobj->second);
    }

    for(std::map<objectid_t, bool>::iterator itplanet = colonydead.begin(); itplanet != colonydead.end(); ++itplanet) {
        if(itplanet->second) {
            IGObject::Ptr obj = objectcache[itplanet->first];
            Planet* planet = dynamic_cast<Planet*>(obj->getObjectBehaviour());
            if(planet == NULL) {
                warningLog("Planet was not a planet");
                continue;
            }
            resourcetypeid_t homeplanetres = Game::getGame()->getResourceManager()->getResourceDescription("Home Planet")->getResourceType();
            bool ishomeplanet = (planet->getResource(homeplanetres) == 1);

            //planet has fallen
            if(ishomeplanet) {
                planet->removeResource(homeplanetres, 1);
            }
            uint32_t oldowner = planet->getOwner();
            planet->setOwner(0);
            uint32_t queueid = static_cast<OrderQueueObjectParam*>(obj->getParameterByType(obpT_Order_Queue))->getQueueId();
            OrderQueue::Ptr queue = Game::getGame()->getOrderManager()->getOrderQueue(queueid);
            queue->removeOwner(oldowner);
            queue->removeAllOrders();
            Game::getGame()->getPlayerManager()->getPlayer(oldowner)->getPlayerView()->removeOwnedObject(obj->getID());
        }
    }

}
예제 #14
0
bool MergeFleet::doOrder(IGObject::Ptr ob){
  IGObject::Ptr parent = Game::getGame()->getObjectManager()->getObject(ob->getParent());
  
  Fleet *myfleet = (Fleet*)(ob->getObjectBehaviour());
  //find fleet to merge with
  
  uint32_t targetid = 0;
  
  std::set<uint32_t> oblist = parent->getContainedObjects();
  for(std::set<uint32_t>::iterator itcurr = oblist.begin(); itcurr != oblist.end(); ++itcurr){
    if(*itcurr == ob->getID())
      continue;
    IGObject::Ptr ptarget = Game::getGame()->getObjectManager()->getObject(*itcurr);
    if(ptarget->getType() == ob->getType()){
      Fleet* pfleet = (Fleet*)(ptarget->getObjectBehaviour());
      if(pfleet->getOwner() == myfleet->getOwner()){
        if(pfleet->getSize() + myfleet->getSize() > pfleet->getPosition().getDistance(myfleet->getPosition())){
          targetid = *itcurr;
          Game::getGame()->getObjectManager()->doneWithObject(*itcurr);
          break;
        }
      }
    }
    Game::getGame()->getObjectManager()->doneWithObject(*itcurr);
  }

  if(targetid == 0){
    Message::Ptr msg( new Message() );
    msg->setSubject("Merge Fleet order canceled");
    msg->setBody("No target fleet at this location");
    msg->addReference(rst_Action_Order, rsorav_Canceled);
    msg->addReference(rst_Object, ob->getID());
    Game::getGame()->getPlayerManager()->getPlayer(((Fleet*)(ob->getObjectBehaviour()))->getOwner())->postToBoard(msg);
  }else{
  
    IGObject::Ptr target = Game::getGame()->getObjectManager()->getObject(targetid);

    Message::Ptr msg( new Message() );
    msg->setSubject("Merge Fleet order complete");
    msg->setBody("The two fleets have been merged");
    msg->addReference(rst_Action_Order, rsorav_Completion);
    msg->addReference(rst_Object, ob->getID());
    msg->addReference(rst_Object, target->getID());

    
    Fleet *tfleet = (Fleet*)(target->getObjectBehaviour());
      

    IdMap ships = myfleet->getShips();
    for(IdMap::iterator itcurr = ships.begin();
        itcurr != ships.end(); ++itcurr){
      tfleet->addShips(itcurr->first, itcurr->second);
    }

    //remove the fleet from the physical universe
    ob->removeFromParent();
    
    Game::getGame()->getObjectManager()->scheduleRemoveObject(ob->getID());
    Game::getGame()->getPlayerManager()->getPlayer(myfleet->getOwner())->getPlayerView()->removeOwnedObject(ob->getID());
	
    Game::getGame()->getObjectManager()->doneWithObject(target->getID());

    Game::getGame()->getPlayerManager()->getPlayer(myfleet->getOwner())->postToBoard(msg);
  }
  return true;
}
예제 #15
0
//Recurrsively rebuilds regions given a system.
//If the system already has a region or is not occupied or
//colonized, then this function returns.  Otherwise it
//sets the region based on its neighbors.
void TaeTurn::rebuildRegion(uint32_t system) {
    Game* game = Game::getGame();
    ObjectManager* obm = game->getObjectManager();
    ObjectTypeManager* obtm = game->getObjectTypeManager();
    set<uint32_t>::iterator itcurr;

    IGObject::Ptr sys = obm->getObject(system);
    StarSystem* sysData = (StarSystem*) sys->getObjectBehaviour();

    //Check to make sure the system doesnt already have a region
    if(sysData->getRegion() != 0) {
        return;
    }

    //Check to make sure it is colonized or occupied
    set<uint32_t> children = sys->getContainedObjects();
    for(itcurr = children.begin(); itcurr != children.end(); itcurr++) {
        IGObject::Ptr ob = obm->getObject(*itcurr);
        bool resource = true;
        bool occupied = false;
        if(ob->getType() == obtm->getObjectTypeByName("Planet")) {
            Planet* p = (Planet*) ob->getObjectBehaviour();
            if(p->getResource(4) == 0 && p->getResource(5) == 0 && p->getResource(6) == 0 && p->getResource(7) == 0) {
                resource = false;
            }
        } else if(ob->getType() == obtm->getObjectTypeByName("Fleet")) {
            if(!Move::isBorderingScienceColony(sysData)) {
                sendHome(*itcurr);
                occupied = false;
            } else {
                occupied = true;
            }
        }
        if(!(resource || occupied)) {
            return;
        }
    }

    //Check to make sure this isnt a home system
    if(sys->getName().find("'s System") != string::npos) {
        return;
    }

    //Get neighbors
    set<uint32_t> regions;
    set<uint32_t> emptyNeighbors;
    Vector3d pos = sysData->getPosition();
    //east-west neighbors
    for(int i = -1; i < 2; i+=2) {
        set<uint32_t> ids = obm->getObjectsByPos(pos+Vector3d(80000*i,0,0), 1);
        for(set<uint32_t>::iterator j=ids.begin(); j != ids.end(); j++) {
            IGObject::Ptr tempObj = obm->getObject(*j);
            if(tempObj->getType() == obtm->getObjectTypeByName("Star System")) {
                uint32_t r = ((StarSystem*)(tempObj->getObjectBehaviour()))->getRegion();
                if(r == 0) {
                    emptyNeighbors.insert(*j);
                } else if (regions.count(r) == 0) {
                    regions.insert(r);
                }
            }
        }
    }
    //north-south neighbors
    for(int i = -1; i < 2; i+=2) {
        set<uint32_t> ids = obm->getObjectsByPos(pos+Vector3d(0,80000*i,0), 1);
        for(set<uint32_t>::iterator j=ids.begin(); j != ids.end(); j++) {
            IGObject::Ptr tempObj = obm->getObject(*j);
            if(tempObj->getType() == obtm->getObjectTypeByName("Star System")) {
                uint32_t r = ((StarSystem*)(tempObj->getObjectBehaviour()))->getRegion();
                if(r == 0) {
                    emptyNeighbors.insert(*j);
                } else if (regions.count(r) == 0) {
                    regions.insert(r);
                }
            }
        }
    }

    //Set Region
    if(regions.size() == 0) {
        //If neighbors have no region, then create a new region
        sysData->setRegion(sys->getID());
        stringstream out;
        out << sysData->getRegion();
        Logger::getLogger()->debug(string("System " + sys->getName() + " added to region " + out.str()).c_str());
    } else if(regions.size() == 1) {
        //If it neighbors 1 region, then set as that region
        sysData->setRegion(*(regions.begin()));
        stringstream out;
        out << sysData->getRegion();
        Logger::getLogger()->debug(string("System " + sys->getName() + " added to region " + out.str()).c_str());
    } else {
        //It should never border more than one region.  If it reaches this point, then there is an error somewhere
        Logger::getLogger()->debug(string("** Unable to rebuild region! System, " + sys->getName() + " is bordering more than one region! ***").c_str());
    }

    //Recurse on neighbors
    for(itcurr = emptyNeighbors.begin(); itcurr != emptyNeighbors.end(); itcurr++) {
        rebuildRegion(*itcurr);
    }
}
예제 #16
0
bool Build::doOrder(IGObject::Ptr ob)
{
  
  Planet* planet = static_cast<Planet*>(ob->getObjectBehaviour());

  uint32_t usedshipres = resources[1];
  
  if(usedshipres == 0)
    return true;

  int ownerid = planet->getOwner();
  if(ownerid == 0){
      //currently not owned by anyone, just forget about it
      return true;
  }
  
  planet->addResource(1, 1);
    
  if(planet->removeResource(1, usedshipres)){
    //create fleet
    
    Game* game = Game::getGame();
    
    
    IGObject::Ptr fleet = game->getObjectManager()->createNewObject();
    game->getObjectTypeManager()->setupObject(fleet, game->getObjectTypeManager()->getObjectTypeByName("Fleet"));
    
    //add fleet to container
    fleet->addToParent(ob->getID());
    
    fleet->setName(fleetname->getString().c_str());
    
    Fleet * thefleet = ((Fleet*)(fleet->getObjectBehaviour()));
    
    thefleet->setSize(2);
    thefleet->setOwner(ownerid); // set ownerid
    thefleet->setPosition(planet->getPosition());
    thefleet->setVelocity(Vector3d(0LL, 0ll, 0ll));
    
    uint32_t queueid = Game::getGame()->getOrderManager()->addOrderQueue(fleet->getID(), ownerid);
    OrderQueueObjectParam* oqop = static_cast<OrderQueueObjectParam*>(fleet->getParameterByType(obpT_Order_Queue));
    oqop->setQueueId(queueid);
    thefleet->setDefaultOrderTypes();
    thefleet->setIcon("common/object-icons/ship");
    thefleet->setMedia("common-2d/foreign/vegastrike/ship-small/" + ((MiniSec*)(game->getRuleset()))->getFleetMediaNames()->getName());
    
    //set ship type
    IdMap fleettype = fleetlist->getList();
    for(IdMap::iterator itcurr = fleettype.begin(); itcurr != fleettype.end(); ++itcurr){
      thefleet->addShips(itcurr->first, itcurr->second);
      Design::Ptr design = Game::getGame()->getDesignStore()->getDesign(itcurr->first);
        design->addComplete(itcurr->second);
        Game::getGame()->getDesignStore()->designCountsUpdated(design);
    }
    //add fleet to universe
    Game::getGame()->getObjectManager()->addObject(fleet);
    Game::getGame()->getPlayerManager()->getPlayer(ownerid)->getPlayerView()->addOwnedObject(fleet->getID());

    Message::Ptr msg( new Message() );
    msg->setSubject("Build Fleet order complete");
    msg->setBody(std::string("The construction of your new fleet \"") + fleetname->getString() + "\" is complete.");
    msg->addReference(rst_Action_Order, rsorav_Completion);
    msg->addReference(rst_Object, fleet->getID());
    msg->addReference(rst_Object, ob->getID());
 
    Game::getGame()->getPlayerManager()->getPlayer(ownerid)->postToBoard(msg);

    return true;
  }
  return false;
}
예제 #17
0
//This function gets the top bid for the given object
pair<IGObject::Ptr ,uint32_t> Colonize::getTopPlayerAndBid(IGObject::Ptr obj) {
   pair<IGObject::Ptr ,uint32_t> result;
   result.second = 0;
   
   Planet* origin = dynamic_cast<Planet*>(obj->getObjectBehaviour());
   assert(origin);

   Logger::getLogger()->debug("\tCollecting all bids on object %s",origin->getName().c_str());

   Game* game = Game::getGame();
   OrderManager* ordM = game->getOrderManager();
   ObjectManager* objM = game->getObjectManager();
   
   //Construct the map to be used, the identifier is the planet, the value is the bid
   map<IGObject::Ptr ,uint32_t> bids;
      
   //Get all objects from object manager
   set<uint32_t> objectsIds = objM->getAllIds();
   
   //Iterate over every object
   for(set<uint32_t>::iterator i = objectsIds.begin(); i != objectsIds.end(); ++i)
   {
      //Get current object
      IGObject::Ptr currObj = objM->getObject(*i);
      
      //Print out current planet
      Planet* bidder = dynamic_cast<Planet*>(currObj->getObjectBehaviour());
      if (bidder != NULL) {
         Logger::getLogger()->debug("\t\tLooking at orders on object %s",bidder->getName().c_str());
      }
      
      //Get order queue from object
      OrderQueueObjectParam* oqop = dynamic_cast<OrderQueueObjectParam*>(currObj->getParameterByType(obpT_Order_Queue));
      OrderQueue::Ptr oq;

      //Validate that the oq exists
      if(oqop != NULL && (oq = ordM->getOrderQueue(oqop->getQueueId())) != NULL)
      {
         //Iterate over all orders
         for (uint32_t j = 0; j < oq->getNumberOrders(); j++)
         {
            OwnedObject *orderedObj = dynamic_cast<OwnedObject*>(currObj->getObjectBehaviour());
            Order* order = NULL;
            if ( orderedObj != NULL ) {
               order = oq->getOrder(j, orderedObj->getOwner());
            }
            
            Logger::getLogger()->debug("\t\tThere exists a %s order on %s", order->getName().c_str(), bidder->getName().c_str());
            //if order is a colonize order
            if( order != NULL && order->getName() == "Colonize")
            {
               Colonize* colonize = dynamic_cast<Colonize*>(order);
               assert(colonize);

               //Get the list of planetIDs and the # of units to move
               IdMap list = colonize->getTargetList()->getList();
               
               //Iterate over all suborders
               for(IdMap::iterator i = list.begin(); i != list.end(); ++i) {
                  uint32_t planetID = i->first;
                  uint32_t numUnits = i->second;
                  
                  format debug("\t\t\tEncountered suborder to Colonize %1% with %2% units");
                  debug % planetID; debug % numUnits; 
                  Logger::getLogger()->debug(debug.str().c_str());
                  
                  IGObject::Ptr target = Game::getGame()->getObjectManager()->getObject(planetID);
                  if ( target == obj ) {
                     bids[currObj] += numUnits;                     
                  }
               }
            }
            else if ( order->getName() != "Colonize")
            {
               j = oq->getNumberOrders() + 1;   //force the loop to exit, we have "left" the frontal Colonize orders
            }
         }
         currObj->touchModTime();
      }
      objM->doneWithObject(currObj->getID());
   }
   

   //Iterate over all bids and restrict them to the maximum armies availible on that planet
   for(map<IGObject::Ptr ,uint32_t>::iterator i = bids.begin(); i != bids.end(); ++i) {
      Logger::getLogger()->debug("Iterating over all bids to pick the highest legal bid.");
      //FIXME: Somewhere in this "for" the server crashes when a single bid is created for 1 unit when planet only has 1 unit left

      //Restrict players bid to 1 less than their current reinforcements
      Planet* planet = dynamic_cast<Planet*>(i->first->getObjectBehaviour());
      assert(planet);

      result.first = i->first;      
      uint32_t numUnits = i->second;
      uint32_t maxUnits = planet->getResource("Army").first;
      
      //If there is overflow of numUnits, check for maxUnits over 0 insures we don't set unsigned to < 0
      if ( numUnits >= maxUnits && maxUnits > 0) {
         if ( maxUnits > 0)
            numUnits = maxUnits - 1;
         else
            numUnits = 0;
      }
      i->second = numUnits;
      result.second = i->second;
   }

   sendPlayerMessages(obj, bids,result);
   
   if (result.first == NULL)
   {
   }
   format debugMsg("Found highest bidder to be from planet #%1% with %2% units");
   debugMsg % result.first->getName(); debugMsg % result.second;
   Logger::getLogger()->debug(debugMsg.str().c_str());
   
   return result;
}
예제 #18
0
//The colonize order checks to make sure the system is valid, then adds a resource to the planet, checks for
//external combat, and awards one point to the player with the leader in the region of the new colony.
bool Colonize::doOrder(IGObject::Ptr obj) {
    ObjectManager* obm = Game::getGame()->getObjectManager();
    ObjectTypeManager* obtm = Game::getGame()->getObjectTypeManager();
    Fleet* fleetData = (Fleet*)(obj->getObjectBehaviour());
    Player::Ptr player = Game::getGame()->getPlayerManager()->getPlayer(fleetData->getOwner());

    IGObject::Ptr newStarSys = obm->getObject(starSys->getObjectId());

    //Perform last minute checks to make sure the system can be colonized
    if(newStarSys->getType() != obtm->getObjectTypeByName("Star System")) {
        //Not a star system
        Logger::getLogger()->debug("Trying to colonize to an object which is not a star system");
        Message::Ptr msg( new Message() );
        msg->setSubject("Colonize order failed");
        msg->setBody(string("You're fleet, \"" + obj->getName() + "\" tried to colonize an object which is not a star system!"));
        msg->addReference(rst_Object, obj->getID());
        player->postToBoard(msg);
        return false;
    }
    if(!((StarSystem*)(newStarSys->getObjectBehaviour()))->canBeColonized(isMining)) {
        //Not colonizable
        Logger::getLogger()->debug("Player tried to colonize a system which cannot be colonized.");
        Message::Ptr msg( new Message() );
        msg->setSubject("Colonize order failed");
        msg->setBody(string("You're fleet, \"" + obj->getName() + "\" tried to colonize a fleet which cannot be colonized!"));
        msg->addReference(rst_Object, obj->getID());
        player->postToBoard(msg);
        return false;
    }   

    //Find the star system's planet
    set<uint32_t> children = newStarSys->getContainedObjects();
    uint32_t pid;
    bool planetFound = false;
    for(set<uint32_t>::iterator i=children.begin(); i != children.end(); i++) {
        if(obm->getObject(*i)->getType() == obtm->getObjectTypeByName("Planet")) {
            pid = *i;
            planetFound = true;
        }
    }
    if(!planetFound) {
        Logger::getLogger()->debug("Colonize Order: No planet found in target star system");
        return false;
    }

    //Add resource to planet
    Planet* planet = (Planet*)(obm->getObject(pid)->getObjectBehaviour());
    Design::Ptr ship = Game::getGame()->getDesignStore()->getDesign(fleetData->getShips().begin()->first);
    uint32_t scoreType = 0;
    string leaderName;
    if(ship->getName().compare("MerchantShip") == 0) {
        planet->addResource(4, 1);
        scoreType = 1;
        leaderName = "MerchantLeaderShip";
    } else if(ship->getName().compare("ScientistShip") == 0) {
        planet->addResource(5, 1);
        scoreType = 2;
        leaderName = "ScientistLeaderShip";
    } else if(ship->getName().compare("SettlerShip") == 0) {
        planet->addResource(6, 1);
        scoreType = 3;
        leaderName = "SettlerLeaderShip";
    } else if(ship->getName().compare("MiningShip") == 0) {
        planet->addResource(7, 1);
        scoreType = 4;
        leaderName = "MiningLeaderShip";
    }

    //Get bordering star systems' regions
    StarSystem* starSysData = (StarSystem*)(newStarSys->getObjectBehaviour());
    set<uint32_t> regions = getBorderingRegions();
    
    //Put the newly colonized ship into the proper region
    //If it does not border any regions, then set it to a new one with a unique id
    if(regions.size() == 0) {
        starSysData->setRegion(starSys->getObjectId());
        stringstream out;
        out << starSysData->getRegion();
        Logger::getLogger()->debug(string("System " + newStarSys->getName() + " added to region " + out.str()).c_str());
    } else if(regions.size() == 1) {
        // Add +1 to the resource score of the player with the correct leader 
        // in this region
        
        int leaderID = getLeaderInRegion(*(regions.begin()), leaderName);
        if(leaderID < 0 && leaderName.compare("SettlerLeaderShip") != 0) {
            leaderID = getLeaderInRegion(*(regions.begin()), "SettlerLeaderShip");
        }
        if(leaderID >= 0) {
            Fleet* leader = (Fleet*) ((obm->getObject((uint32_t) leaderID))->getObjectBehaviour());
            Player::Ptr owner = Game::getGame()->getPlayerManager()->getPlayer(leader->getOwner());
            owner->setScore(scoreType, owner->getScore(scoreType) + 1);
        }    

        //Add the newly colonized system to the region
        starSysData->setRegion(*(regions.begin()));
        stringstream out;
        out << starSysData->getRegion();
        Logger::getLogger()->debug(string("System " + newStarSys->getName() + " added to region " + out.str()).c_str());
    } else {
        // This means that 2 regions are being connected. Perform check
        // for external combat
        map<uint32_t, uint32_t> settlers;
        map<uint32_t, uint32_t> scientists;
        map<uint32_t, uint32_t> merchants;
        map<uint32_t, uint32_t> miners;
        for(set<uint32_t>::iterator i = regions.begin(); i != regions.end(); i++) {
            int temp = getLeaderInRegion(*i, "SettlerLeaderShip");
            if(temp != -1) {
                settlers[temp] = *i;
            }
            temp = getLeaderInRegion(*i, "ScientistLeaderShip");
            if(temp != -1) {
                scientists[temp] = *i;
            }
            temp = getLeaderInRegion(*i, "MerchantLeaderShip");
            if(temp != -1) {
                merchants[temp] = *i;
            }
            temp = getLeaderInRegion(*i, "MiningLeaderShip");
            if(temp != -1) {
                miners[temp] = *i;
            }
        }

        TaeTurn* turn = (TaeTurn*) Game::getGame()->getTurnProcess();
        bool conflict = false;
        if(settlers.size() > 1) {
            //Settler Conflict!
            turn->queueCombatTurn(false, settlers);
            conflict = true;
        }
        if(scientists.size() > 1) {
            //Scientist Conflict!
            turn->queueCombatTurn(false, scientists);
            conflict = true;
        }
        if(merchants.size() > 1) {
            //Merchant Conflict!
            turn->queueCombatTurn(false, merchants);
            conflict = true;
        }
        if(miners.size() > 1) {
            //Miner Conflict!
            turn->queueCombatTurn(false, miners);
            conflict = true;
        }
        
        if(!conflict) {
            uint32_t region = *(regions.begin());
            set<uint32_t> objects = obm->getAllIds();
            for(set<uint32_t>::iterator i = objects.begin(); i != objects.end(); i++) {
                IGObject::Ptr ob = obm->getObject(*i);
                if(ob->getType() == obtm->getObjectTypeByName("Star System")) {
                    StarSystem* sys = (StarSystem*) ob->getObjectBehaviour();
                    uint32_t r = sys->getRegion();
                    if(r != region && regions.count(r) > 0) {
                        sys->setRegion(region);
                    }
                }
            }
        }
    }

    obm->doneWithObject(newStarSys->getID());
   
 
    // post completion message
    Message::Ptr msg( new Message() );
    msg->setSubject("Colonize fleet order complete");
    msg->setBody(string("You're fleet, \"" + obj->getName() + "\" has colonized ")
            + newStarSys->getName() + ".");
    msg->addReference(rst_Action_Order, rsorav_Completion);
    msg->addReference(rst_Object, starSys->getObjectId());
    msg->addReference(rst_Object, obj->getID());

    player->postToBoard(msg);

    //Remove fleet
    obj->removeFromParent();
    obm->scheduleRemoveObject(obj->getID());

    return true;
}
예제 #19
0
void MinisecTurn::doTurn(){
  std::set<uint32_t>::iterator itcurr;
  
  Game* game = Game::getGame();
  OrderManager* ordermanager = game->getOrderManager();
  ObjectManager* objectmanager = game->getObjectManager();
  RSPCombat* combatstrategy = new RSPCombat();
  PlayerManager::Ptr playermanager = game->getPlayerManager();
 
  //sort by order type
  std::set<uint32_t> movers;
  std::set<uint32_t> otherorders;
  std::set<uint32_t> interceptors; 
  
  containerids.clear();
  std::set<uint32_t> possiblecombatants;
  
  std::set<uint32_t> objects = objectmanager->getAllIds();
  for(itcurr = objects.begin(); itcurr != objects.end(); ++itcurr) {
    IGObject::Ptr ob = objectmanager->getObject(*itcurr);
    if(ob->getType() == planettype || ob->getType() == fleettype){
      possiblecombatants.insert(ob->getID());
      OrderQueueObjectParam* oqop = dynamic_cast<OrderQueueObjectParam*>(ob->getParameterByType(obpT_Order_Queue));
      if(oqop != NULL){
        OrderQueue::Ptr orderqueue = ordermanager->getOrderQueue(oqop->getQueueId());
        if(orderqueue != NULL){
          Order * currOrder = orderqueue->getFirstOrder();
          if(currOrder != NULL){
            if(currOrder->getType() == ordermanager->getOrderTypeByName("Move")){
              movers.insert(ob->getID());
            } else if (currOrder->getType() == ordermanager->getOrderTypeByName("Intercept")){
              interceptors.insert(ob->getID());
            }else{
              otherorders.insert(ob->getID());
            }
          }
        }
      }
    }
    if(ob->getContainerType() >= 1){
      containerids.insert(ob->getID());
    }
    objectmanager->doneWithObject(ob->getID());
  }
  
  // do move
  for(itcurr = movers.begin(); itcurr != movers.end(); ++itcurr) {
    IGObject::Ptr ob = objectmanager->getObject(*itcurr);
    
    OrderQueueObjectParam* oqop = dynamic_cast<OrderQueueObjectParam*>(ob->getParameterByType(obpT_Order_Queue));
    OrderQueue::Ptr orderqueue = ordermanager->getOrderQueue(oqop->getQueueId());
    Order * currOrder = orderqueue->getFirstOrder();
    if(currOrder->doOrder(ob)){
      orderqueue->removeFirstOrder();
    }else{
      orderqueue->updateFirstOrder();
    }
    
    objectmanager->doneWithObject(ob->getID());
  }

  // do interceptions

  for(itcurr = interceptors.begin(); itcurr != interceptors.end(); ++itcurr) {
    IGObject::Ptr ob = objectmanager->getObject(*itcurr);
    
    OrderQueueObjectParam* oqop = dynamic_cast<OrderQueueObjectParam*>(ob->getParameterByType(obpT_Order_Queue));
    OrderQueue::Ptr orderqueue = ordermanager->getOrderQueue(oqop->getQueueId());
    Order * currOrder = orderqueue->getFirstOrder();
    if(currOrder->doOrder(ob)){
      orderqueue->removeFirstOrder();
    }else{
      orderqueue->updateFirstOrder();
    }
    
    objectmanager->doneWithObject(ob->getID());
  }
 
  // do combat
  
  std::list<std::map<uint32_t, std::set<uint32_t> > > combats;
  
  for(itcurr = possiblecombatants.begin(); itcurr != possiblecombatants.end(); ++itcurr) {
    IGObject::Ptr ob = objectmanager->getObject(*itcurr);
    uint32_t playerid1;
    Vector3d pos1;
    uint32_t size1;
    if(ob->getType() == planettype){
      Planet* planet = (Planet*)(ob->getObjectBehaviour());
      playerid1 = planet->getOwner();
      pos1 = planet->getPosition();
      size1 = planet->getSize();
    }else{
      Fleet* fleet = (Fleet*)(ob->getObjectBehaviour());
      playerid1 = fleet->getOwner();
      pos1 = fleet->getPosition();
      size1 = fleet->getSize();
    }
    
    if(playerid1 == 0){
      objectmanager->doneWithObject(ob->getID());
      continue;
    }
    
    bool placed = false;
    
    for(std::list<std::map<uint32_t, std::set<uint32_t> > >::iterator itlist = combats.begin();
        itlist != combats.end(); ++itlist){
      std::map<uint32_t, std::set<uint32_t> > themap = *itlist;
      for(std::map<uint32_t, std::set<uint32_t> >::iterator itmap = themap.begin();
          itmap != themap.end(); ++itmap){
        std::set<uint32_t> theset = itmap->second;
        for(std::set<uint32_t>::iterator itset = theset.begin(); itset != theset.end(); ++itset){
          IGObject::Ptr itbobj = objectmanager->getObject(*itset);
          uint32_t playerid2;
          Vector3d pos2;
          uint32_t size2;
          if(itbobj->getType() == planettype){
            Planet* planet = (Planet*)(itbobj->getObjectBehaviour());
            playerid2 = planet->getOwner();
            pos2 = planet->getPosition();
            size2 = planet->getSize();
          }else{
            Fleet* fleet = (Fleet*)(itbobj->getObjectBehaviour());
            playerid2 = fleet->getOwner();
            pos2 = fleet->getPosition();
            size2 = fleet->getSize();
          }
        
          if(playerid2 == 0){
            objectmanager->doneWithObject(itbobj->getID());
            continue;
          }
          uint64_t diff = pos1.getDistance(pos2);
          if(diff <= size1 / 2 + size2 / 2){
            themap[playerid1].insert(ob->getID());
            *itlist = themap;
            placed = true;
            objectmanager->doneWithObject(itbobj->getID());
            break;
          }
          objectmanager->doneWithObject(itbobj->getID());
        }
        if(placed)
          break;
      }
      if(placed)
        break;
    }
    if(!placed){
      std::map<uint32_t, std::set<uint32_t> > themap;
      std::set<uint32_t> theset;
      theset.insert(ob->getID());
      themap[playerid1] = theset;
      combats.push_back(themap);
    }
    objectmanager->doneWithObject(ob->getID());
  }
  
  for(std::list<std::map<uint32_t, std::set<uint32_t> > >::iterator itlist = combats.begin();
        itlist != combats.end(); ++itlist){
    std::map<uint32_t, std::set<uint32_t> > themap = *itlist;
    if(themap.size() >= 2){
      combatstrategy->doCombat(themap);
    }
  }
  

  objectmanager->clearRemovedObjects();
  
  // do other orders (nop, buildfleet, colonise)
  
  for(itcurr = otherorders.begin(); itcurr != otherorders.end(); ++itcurr) {
    IGObject::Ptr ob = objectmanager->getObject(*itcurr);
    if(ob != NULL){
      if(ob->getType() == planettype || ob->getType() == fleettype){
        OrderQueueObjectParam* oqop = dynamic_cast<OrderQueueObjectParam*>(ob->getParameterByType(obpT_Order_Queue));
        if(oqop != NULL){
          OrderQueue::Ptr orderqueue = ordermanager->getOrderQueue(oqop->getQueueId());
          if(orderqueue != NULL){
            Order * currOrder = orderqueue->getFirstOrder();
            if(currOrder != NULL){
              if(currOrder->doOrder(ob)){
                orderqueue->removeFirstOrder();
              }else{
                orderqueue->updateFirstOrder();
              }
            }
          }
        }
      }
      objectmanager->doneWithObject(ob->getID());
    }
  }

  objectmanager->clearRemovedObjects();
  
  // to once a turn (right at the end)
  objects = objectmanager->getAllIds();
  for(itcurr = objects.begin(); itcurr != objects.end(); ++itcurr) {
    IGObject::Ptr ob = objectmanager->getObject(*itcurr);
    if(ob->isAlive()){
      ob->getObjectBehaviour()->doOnceATurn();
    }
    objectmanager->doneWithObject(ob->getID());
  }

  // find the objects that are visible to each player
  std::set<uint32_t> vis = objectmanager->getAllIds();
  std::set<uint32_t> players = playermanager->getAllIds();
  uint32_t numaliveplayers = 0;
  uint32_t numdeadplayers = 0;
  for(std::set<uint32_t>::iterator itplayer = players.begin(); itplayer != players.end(); ++itplayer){
    Player::Ptr player = playermanager->getPlayer(*itplayer);
    PlayerView::Ptr playerview = player->getPlayerView();
    
    for(std::set<uint32_t>::iterator itob = vis.begin(); itob != vis.end(); ++itob){
      ObjectView::Ptr obv = playerview->getObjectView(*itob);
      if(!obv){
        if(objectmanager->getObject(*itob)->isAlive()){
          playerview->addVisibleObject( *itob, true );
        }
        objectmanager->doneWithObject(*itob);
      }else{
        IGObject::Ptr ro = objectmanager->getObject(*itob);
        uint64_t obmt = ro->getModTime();
        objectmanager->doneWithObject(*itob);
        if(obmt > obv->getModTime()){
          obv->setModTime(obmt);
          playerview->updateObjectView(*itob);
        }
      }
    }
    
    // remove dead objects
    std::set<uint32_t> goneobjects;
    std::set<uint32_t> knownobjects = playerview->getVisibleObjects();
    set_difference(knownobjects.begin(), knownobjects.end(), vis.begin(), vis.end(), inserter(goneobjects, goneobjects.begin()));
    
    for(std::set<uint32_t>::iterator itob = goneobjects.begin(); itob != goneobjects.end(); ++itob){
      ObjectView::Ptr obv = playerview->getObjectView(*itob);
        if(!obv->isGone()){
            obv->setGone(true);
            playerview->updateObjectView(*itob);
        }
    }

    
    if(!player->isAlive() || playerview->getNumberOwnedObjects() == 0){
      if(player->isAlive()){
        Message::Ptr msg( new Message() );
        msg->setSubject("You lost");
        msg->setBody("You do not own any objects, therefore you game has finished.");
        msg->addReference(rst_Action_Player, rspav_Eliminated);
        player->postToBoard(msg);
        player->setIsAlive(false);
      }
      numdeadplayers++;
    }else{
      numaliveplayers++;
    }
  }
  
  if(numaliveplayers == 1){
    //find alive player
    Player::Ptr player;
    for(std::set<uint32_t>::iterator itplayer = players.begin(); itplayer != players.end(); ++itplayer){
      player = playermanager->getPlayer(*itplayer);
      if(player->isAlive())
        break;
    }
    if(player->getScore(0) != numdeadplayers - 1){
      Message::Ptr msg( new Message() );
      msg->setSubject("You won!");
      msg->setBody("You have eliminated all the competing players. Congratulations!");
      player->postToBoard(msg);
      player->setScore(0, numdeadplayers - 1);
    }
  }
  
  playermanager->updateAll();
  
  delete combatstrategy;
}