int CProgAndPlay::execPendingCommands(){ //log("ProgAndPLay::execPendingCommands begin"); int nbCmd = 0; PP_PendingCmds* pendingCommands = PP_GetPendingCommands(); if (pendingCommands == NULL) return -1; else{ nbCmd = pendingCommands->size; for (int i = 0 ; i < pendingCommands->size ; i++){ PP_PendingCmd pc = pendingCommands->pendingCommand[i]; // Check for affecting group if (pc.group != -2){ // Check if unit exists CUnit* tmp = uh->GetUnit(pc.unitId); if (tmp != NULL){ if (tmp->team == gu->myTeam){ // Check the grouphandlers for my team if (grouphandlers[gu->myTeam]){ // Check if it's a command to withdraw unit from its current group if (pc.group == -1){ // suppression de l'unité de sons groupe tmp->SetGroup(NULL); } else{ // Check if the number of groups is being enough while (pc.group >= grouphandlers[gu->myTeam]->groups.size()){ // add a new group grouphandlers[gu->myTeam]->CreateNewGroup(); } // Check if the group exists if (!grouphandlers[gu->myTeam]->groups[pc.group]){ // recreate all groups until recreate this group CGroup * gTmp; do { // création d'un groupe intermédiaire manquant gTmp = grouphandlers[gu->myTeam]->CreateNewGroup(); } while (gTmp->id != pc.group); } if (pc.group >= 0){ // devote the unit to this group tmp->SetGroup(grouphandlers[gu->myTeam]->groups[pc.group]); } } } } } } // Check if a command must be executed bool ok = true, found = false; switch (pc.commandType){ case -1 : // the command is invalid => do not execute this command ok = false; break; case 0 : // the command target a position // indicates the y value pc.command.param[1] = ground->GetHeight(pc.command.param[0], pc.command.param[2]); break; case 1 : // the command targets a unit // Find targeted unit for (int t = 0 ; t < teamHandler->ActiveTeams() && !found ; t++){ CUnit* tmp = uh->GetUnit((int)pc.command.param[0]); if (tmp != NULL){ if (tmp->team == t){ // check if this unit is visible by the player if (!loshandler->InLos(tmp, gu->myAllyTeam)) ok = false; found = true; } } } break; case 2 : // the command is untargeted // nothing to do break; default : PP_SetError("Spring : commandType unknown"); PP_FreePendingCommands(pendingCommands); return -1; } // send command if (ok){ if (pc.command.code == -7658){ // This code is a Prog&Play reserved code defined in constantList files // Clear CommandQueue of factory CUnit* fact = uh->GetUnit(pc.unitId); if (fact){ CFactoryCAI* facAI = dynamic_cast<CFactoryCAI*>(fact->commandAI); if (facAI) { Command c; c.options = RIGHT_MOUSE_KEY; // Set RIGHT_MOUSE_KEY option in order to decrement building order CCommandQueue& buildCommands = facAI->commandQue; CCommandQueue::iterator it; std::vector<Command> clearCommands; clearCommands.reserve(buildCommands.size()); for (it = buildCommands.begin(); it != buildCommands.end(); ++it) { c.id = it->id; clearCommands.push_back(c); } for (int i = 0; i < (int)clearCommands.size(); i++) { facAI->GiveCommand(clearCommands[i]); } } } } else{ // Copy pc.command.param in a vector to pass it at SendAICommand std::vector<float> stdParam; for (int j = 0 ; j < pc.command.nbParam ; j++) stdParam.push_back(pc.command.param[j]); net->Send(CBaseNetProtocol::Get().SendAICommand(gu->myPlayerNum, pc.unitId, pc.command.code, 0, stdParam)); /* // Permet de gérer les commandes plus correctement mais produit des // erreurs de synchronisation (à utiliser en SYNCED_MODE) CUnitSet *tmp = &(gs->Team(gu->myTeam)->units); CUnitSetConstIterator it = tmp->find(pc.unitId); if (it != tmp->end() && (*it)->commandAI){ Command cTmp; cTmp.id = pc.command.code; cTmp.params = stdParam; (*it)->commandAI->GiveCommand(cTmp); }*/ } } } } PP_FreePendingCommands(pendingCommands); //log("ProgAndPLay::execPendingCommands end"); return nbCmd; }
void CUnit::ChangeTeamReset() { Command c; // clear the commands (newUnitCommands for factories) c.id = CMD_STOP; commandAI->GiveCommand(c); // clear the build commands for factories CFactoryCAI* facAI = dynamic_cast<CFactoryCAI*>(commandAI); if (facAI) { c.options = RIGHT_MOUSE_KEY; // clear option CCommandQueue& buildCommands = facAI->commandQue; CCommandQueue::iterator it; std::vector<Command> clearCommands; for (it = buildCommands.begin(); it != buildCommands.end(); ++it) { c.id = it->id; clearCommands.push_back(c); } for (int i = 0; i < (int)clearCommands.size(); i++) { facAI->GiveCommand(clearCommands[i]); } } // deactivate to prevent the old give metal maker trick c.id = CMD_ONOFF; c.params.push_back(0); // always off commandAI->GiveCommand(c); c.params.clear(); // reset repeat state c.id = CMD_REPEAT; c.params.push_back(0); commandAI->GiveCommand(c); c.params.clear(); // reset cloak state if (unitDef->canCloak) { c.id = CMD_CLOAK; c.params.push_back(0); // always off commandAI->GiveCommand(c); c.params.clear(); } // reset move state if (unitDef->canmove || unitDef->builder) { c.id = CMD_MOVE_STATE; c.params.push_back(1); commandAI->GiveCommand(c); c.params.clear(); } // reset fire state if (!unitDef->noAutoFire && (!unitDef->weapons.empty() || (unitDef->type == "Factory"))) { c.id = CMD_FIRE_STATE; c.params.push_back(2); commandAI->GiveCommand(c); c.params.clear(); } // reset trajectory state if (unitDef->highTrajectoryType > 1) { c.id = CMD_TRAJECTORY; c.params.push_back(0); commandAI->GiveCommand(c); c.params.clear(); } }