Merge branch 'feat/command-priority' into play

This commit is contained in:
pavanvo 2022-09-06 17:54:44 +04:00
commit edc9de3d15
No known key found for this signature in database
GPG Key ID: 34C1C36681B4AD84
12 changed files with 356 additions and 387 deletions

View File

@ -120,9 +120,11 @@ std::pair<CommandResult,string> Commander::tryGiveCommand(const Selection *selec
} }
if(useCommandtype != NULL) { if(useCommandtype != NULL) {
auto mct= unit->getCurrMorphCt();
int nextUnitTypeId= mct? mct->getMorphUnit()->getId(): -1;
NetworkCommand networkCommand(this->world,nctGiveCommand, unitId, NetworkCommand networkCommand(this->world,nctGiveCommand, unitId,
useCommandtype->getId(), usePos, unitType->getId(), useCommandtype->getId(), usePos, unitType->getId(), nextUnitTypeId,
(targetUnit != NULL ? targetUnit->getId() : -1), (targetUnit != NULL ? targetUnit->getId() : -1),
facing, tryQueue, commandStateType,commandStateValue, facing, tryQueue, commandStateType,commandStateValue,
unitCommandGroupId); unitCommandGroupId);
@ -162,8 +164,10 @@ std::pair<CommandResult,string> Commander::tryGiveCommand(const Unit* unit, cons
std::pair<CommandResult,string> result(crFailUndefined,""); std::pair<CommandResult,string> result(crFailUndefined,"");
bool canSubmitCommand=canSubmitCommandType(unit, commandType); bool canSubmitCommand=canSubmitCommandType(unit, commandType);
if(canSubmitCommand == true) { if(canSubmitCommand == true) {
auto mct= unit->getCurrMorphCt();
int nextUnitTypeId= mct? mct->getMorphUnit()->getId(): -1;
NetworkCommand networkCommand(this->world,nctGiveCommand, unit->getId(), NetworkCommand networkCommand(this->world,nctGiveCommand, unit->getId(),
commandType->getId(), pos, unitType->getId(), commandType->getId(), pos, unitType->getId(), nextUnitTypeId,
(targetUnit != NULL ? targetUnit->getId() : -1), (targetUnit != NULL ? targetUnit->getId() : -1),
facing, tryQueue,cst_None,-1,unitGroupCommandId); facing, tryQueue,cst_None,-1,unitGroupCommandId);
@ -210,8 +214,10 @@ std::pair<CommandResult,string> Commander::tryGiveCommand(const Selection *selec
int unitId= selection->getUnit(i)->getId(); int unitId= selection->getUnit(i)->getId();
Vec2i currPos= world->getMap()->computeDestPos(refPos, Vec2i currPos= world->getMap()->computeDestPos(refPos,
selection->getUnit(i)->getPosNotThreadSafe(), pos); selection->getUnit(i)->getPosNotThreadSafe(), pos);
auto mct= unit->getCurrMorphCt();
int nextUnitTypeId= mct? mct->getMorphUnit()->getId(): -1;
NetworkCommand networkCommand(this->world,nctGiveCommand, NetworkCommand networkCommand(this->world,nctGiveCommand,
unitId, ct->getId(), currPos, -1, targetId, -1, unitId, ct->getId(), currPos, -1, nextUnitTypeId, targetId, -1,
tryQueue,cst_None,-1,unitCommandGroupId); tryQueue,cst_None,-1,unitCommandGroupId);
//every unit is ordered to a different pos //every unit is ordered to a different pos
@ -263,8 +269,11 @@ std::pair<CommandResult,string> Commander::tryGiveCommand(const Selection *selec
int targetId= targetUnit==NULL? Unit::invalidId: targetUnit->getId(); int targetId= targetUnit==NULL? Unit::invalidId: targetUnit->getId();
int unitId= unit->getId(); int unitId= unit->getId();
Vec2i currPos= world->getMap()->computeDestPos(refPos, unit->getPosNotThreadSafe(), pos); Vec2i currPos= world->getMap()->computeDestPos(refPos, unit->getPosNotThreadSafe(), pos);
auto mct= unit->getCurrMorphCt();
int nextUnitTypeId= mct? mct->getMorphUnit()->getId(): -1;
NetworkCommand networkCommand(this->world,nctGiveCommand, unitId, NetworkCommand networkCommand(this->world,nctGiveCommand, unitId,
commandType->getId(), currPos, -1, targetId, -1, tryQueue, commandType->getId(), currPos, -1, nextUnitTypeId, targetId, -1, tryQueue,
cst_None, -1, unitCommandGroupId); cst_None, -1, unitCommandGroupId);
//every unit is ordered to a different position //every unit is ordered to a different position
@ -310,19 +319,22 @@ std::pair<CommandResult,string> Commander::tryGiveCommand(const Selection *selec
currPos= world->getMap()->computeDestPos(refPos, unit->getPosNotThreadSafe(), pos); currPos= world->getMap()->computeDestPos(refPos, unit->getPosNotThreadSafe(), pos);
//get command type //get command type
const CommandType *commandType= unit->computeCommandType(pos, targetUnit); auto mct= unit->getCurrMorphCt();
auto nextUnitType= mct? mct->getMorphUnit(): NULL;
const CommandType *commandType= unit->computeCommandType(pos, targetUnit, nextUnitType);
//give commands //give commands
if(commandType != NULL) { if(commandType != NULL) {
int targetId= targetUnit==NULL? Unit::invalidId: targetUnit->getId(); int targetId= targetUnit==NULL? Unit::invalidId: targetUnit->getId();
int unitId= unit->getId(); int unitId= unit->getId();
int nextUnitTypeId= nextUnitType? nextUnitType->getId(): -1;
std::pair<CommandResult,string> resultCur(crFailUndefined,""); std::pair<CommandResult,string> resultCur(crFailUndefined,"");
bool canSubmitCommand=canSubmitCommandType(unit, commandType); bool canSubmitCommand=canSubmitCommandType(unit, commandType);
if(canSubmitCommand == true) { if(canSubmitCommand == true) {
NetworkCommand networkCommand(this->world,nctGiveCommand, NetworkCommand networkCommand(this->world,nctGiveCommand,
unitId, commandType->getId(), currPos, -1, targetId, unitId, commandType->getId(), currPos, -1, nextUnitTypeId, targetId,
-1, tryQueue, cst_None, -1, unitCommandGroupId); -1, tryQueue, cst_None, -1, unitCommandGroupId);
resultCur= pushNetworkCommand(&networkCommand); resultCur= pushNetworkCommand(&networkCommand);
} }
@ -330,7 +342,7 @@ std::pair<CommandResult,string> Commander::tryGiveCommand(const Selection *selec
} }
else if(unit->isMeetingPointSettable() == true) { else if(unit->isMeetingPointSettable() == true) {
NetworkCommand command(this->world,nctSetMeetingPoint, NetworkCommand command(this->world,nctSetMeetingPoint,
unit->getId(), -1, currPos,-1,-1,-1,false, unit->getId(), -1, currPos,-1,-1,-1,-1,false,
cst_None,-1,unitCommandGroupId); cst_None,-1,unitCommandGroupId);
std::pair<CommandResult,string> resultCur= pushNetworkCommand(&command); std::pair<CommandResult,string> resultCur= pushNetworkCommand(&command);
@ -358,7 +370,7 @@ CommandResult Commander::tryCancelCommand(const Selection *selection) const {
for(int i = 0; i < selection->getCount(); ++i) { for(int i = 0; i < selection->getCount(); ++i) {
NetworkCommand command(this->world,nctCancelCommand, NetworkCommand command(this->world,nctCancelCommand,
selection->getUnit(i)->getId(),-1,Vec2i(0),-1,-1,-1,false, selection->getUnit(i)->getId(),-1,Vec2i(0),-1,-1,-1,-1,false,
cst_None,-1,unitCommandGroupId); cst_None,-1,unitCommandGroupId);
pushNetworkCommand(&command); pushNetworkCommand(&command);
} }
@ -950,7 +962,7 @@ Command* Commander::buildCommand(const NetworkCommand* networkCommand) const {
throw megaglest_runtime_error(szBuf); throw megaglest_runtime_error(szBuf);
} }
ct = unit->getType()->findCommandTypeById(networkCommand->getCommandTypeId()); ct = unit->getType()->findCommandTypeById(networkCommand->getCommandTypeId());
if(unit->getFaction()->getIndex() != networkCommand->getUnitFactionIndex()) { if(unit->getFaction()->getIndex() != networkCommand->getUnitFactionIndex()) {
@ -984,7 +996,13 @@ Command* Commander::buildCommand(const NetworkCommand* networkCommand) const {
throw megaglest_runtime_error(sError); throw megaglest_runtime_error(sError);
} }
const UnitType* unitType= world->findUnitTypeById(unit->getFaction()->getType(), networkCommand->getUnitTypeId()); const UnitType* unitType= world->findUnitTypeById(unit->getFaction()->getType(), networkCommand->getUnitTypeId());
if(networkCommand->getNextUnitTypeId() > -1 && networkCommand->getWantQueue()) { //Morph Queue
auto nextUnitType= world->findUnitTypeById(unit->getFaction()->getType(), networkCommand->getNextUnitTypeId());
auto mct = nextUnitType->findCommandTypeById(networkCommand->getCommandTypeId());
if(mct) ct = mct;
}
// debug test! // debug test!
//throw megaglest_runtime_error("Test missing command type!"); //throw megaglest_runtime_error("Test missing command type!");

View File

@ -5005,7 +5005,10 @@ void Game::keyUp(SDL_KeyboardEvent key) {
gameCamera.setMoveX(0); gameCamera.setMoveX(0);
camRightButtonDown= false; camRightButtonDown= false;
calcCameraMoveX(); calcCameraMoveX();
} else {
gui.hotKeyReleased(key);
} }
} }
} }
catch(const exception &ex) { catch(const exception &ex) {

View File

@ -460,6 +460,16 @@ void Gui::hotKey(SDL_KeyboardEvent key) {
break; break;
} }
} }
if(isKeyDown(queueCommandKey)) {
computeDisplay();
}
}
void Gui::hotKeyReleased(SDL_KeyboardEvent key) {
if(!isKeyDown(queueCommandKey)) {
computeDisplay();
}
} }
void Gui::switchToNextDisplayColor(){ void Gui::switchToNextDisplayColor(){
@ -567,7 +577,7 @@ void Gui::giveTwoClickOrders(int x, int y , bool prepared) {
else { else {
result= commander->tryGiveCommand(&selection, activeCommandClass, result= commander->tryGiveCommand(&selection, activeCommandClass,
targetPos, targetUnit,queueKeyDown); targetPos, targetUnit,queueKeyDown);
} }
} }
else { else {
//selecting building //selecting building
@ -697,6 +707,8 @@ void Gui::mouseDownDisplayUnitSkills(int posDisplay) {
if (activeCommandClass == ccAttack) { if (activeCommandClass == ccAttack) {
ct = selection.getUnitFromCC(ccAttack)->getType()->getFirstCtOfClass(activeCommandClass); ct = selection.getUnitFromCC(ccAttack)->getType()->getFirstCtOfClass(activeCommandClass);
} }
auto mct= unit->getCurrMorphCt();
if(mct && isKeyDown(queueCommandKey)) ct= mct->getMorphUnit()->getFirstCtOfClass(activeCommandClass);
if(activeCommandType!=NULL && activeCommandType->getClass()==ccBuild){ if(activeCommandType!=NULL && activeCommandType->getClass()==ccBuild){
assert(selection.isUniform()); assert(selection.isUniform());
@ -969,6 +981,10 @@ void Gui::computeDisplay(){
//uniform selection //uniform selection
if(u->isBuilt()){ if(u->isBuilt()){
//printf("u->isBuilt()\n"); //printf("u->isBuilt()\n");
auto mct = u->getCurrMorphCt();
if(mct && isKeyDown(queueCommandKey)) {//Morph Queue
ut=mct->getMorphUnit();
}//TODO on queueCommandKey presed disable stop cmd
int morphPos= CommandHelper::getRowPos(crMorphs); int morphPos= CommandHelper::getRowPos(crMorphs);
for(int i= 0; i < ut->getCommandTypeSortedCount(); ++i){ for(int i= 0; i < ut->getCommandTypeSortedCount(); ++i){
@ -993,7 +1009,7 @@ void Gui::computeDisplay(){
display.setCommandType(displayPos, ct); display.setCommandType(displayPos, ct);
display.setCommandClass(displayPos, ct->getClass()); display.setCommandClass(displayPos, ct->getClass());
bool reqOk=u->getFaction()->reqsOk(ct); bool reqOk=u->getFaction()->reqsOk(ct);
display.setDownLighted(displayPos,reqOk); display.setDownLighted(displayPos, reqOk && !(!ct->isQueueAppendable() && isKeyDown(queueCommandKey)));
if (reqOk && produced != NULL) { if (reqOk && produced != NULL) {
if (possibleAmount == 0) { if (possibleAmount == 0) {

View File

@ -197,6 +197,7 @@ public:
void mouseDoubleClickLeftGraphics(int x, int y); void mouseDoubleClickLeftGraphics(int x, int y);
void groupKey(int groupIndex); void groupKey(int groupIndex);
void hotKey(SDL_KeyboardEvent key); void hotKey(SDL_KeyboardEvent key);
void hotKeyReleased(SDL_KeyboardEvent key);
//misc //misc
void switchToNextDisplayColor(); void switchToNextDisplayColor();

View File

@ -28,12 +28,13 @@ namespace Glest{ namespace Game{
NetworkCommand::NetworkCommand(World *world, int networkCommandType, int unitId, NetworkCommand::NetworkCommand(World *world, int networkCommandType, int unitId,
int commandTypeId, const Vec2i &pos, int unitTypeId, int commandTypeId, const Vec2i &pos, int unitTypeId,
int targetId, int facing, bool wantQueue, int nextUnitTypeId, int targetId, int facing, bool wantQueue,
CommandStateType commandStateType, CommandStateType commandStateType,
int commandStateValue, int unitCommandGroupId) int commandStateValue, int unitCommandGroupId)
: networkCommandType(networkCommandType) : networkCommandType(networkCommandType)
, unitId(unitId) , unitId(unitId)
, unitTypeId(unitTypeId) , unitTypeId(unitTypeId)
, nextUnitTypeId(nextUnitTypeId)
, commandTypeId(commandTypeId) , commandTypeId(commandTypeId)
, positionX(pos.x) , positionX(pos.x)
, positionY(pos.y) , positionY(pos.y)
@ -48,43 +49,44 @@ NetworkCommand::NetworkCommand(World *world, int networkCommandType, int unitId,
this->targetId = targetId >= 0 ? targetId : facing; this->targetId = targetId >= 0 ? targetId : facing;
this->fromFactionIndex = world->getThisFactionIndex(); this->fromFactionIndex = world->getThisFactionIndex();
if(this->networkCommandType == nctGiveCommand) { if(this->networkCommandType == nctGiveCommand) {
const Unit *unit= world->findUnitById(this->unitId); const Unit *unit= world->findUnitById(this->unitId);
//validate unit //validate unit
if(unit != NULL) { if(unit != NULL) {
this->unitFactionIndex = unit->getFaction()->getIndex(); this->unitFactionIndex = unit->getFaction()->getIndex();
this->unitFactionUnitCount = unit->getFaction()->getUnitCount(); this->unitFactionUnitCount = unit->getFaction()->getUnitCount();
//const UnitType *unitType= world->findUnitTypeById(unit->getFaction()->getType(), this->unitTypeId); const CommandType *ct= unit->getType()->findCommandTypeById(this->commandTypeId);
const CommandType *ct = unit->getType()->findCommandTypeById(this->commandTypeId);
if(ct != NULL && ct->getClass() == ccBuild) { if(ct != NULL && ct->getClass() == ccBuild) {
if(SystemFlags::getSystemSettingType(SystemFlags::debugNetwork).enabled) SystemFlags::OutputDebug(SystemFlags::debugNetwork,"In [%s::%s Line: %d] %s\n",__FILE__,__FUNCTION__,__LINE__,toString().c_str()); if(SystemFlags::getSystemSettingType(SystemFlags::debugNetwork).enabled) SystemFlags::OutputDebug(SystemFlags::debugNetwork,"In [%s::%s Line: %d] %s\n",__FILE__,__FUNCTION__,__LINE__,toString().c_str());
CardinalDir::assertDirValid(facing); CardinalDir::assertDirValid(facing);
assert(targetId == -1); assert(targetId == -1);
} }
} }
} }
if(SystemFlags::getSystemSettingType(SystemFlags::debugNetwork).enabled) SystemFlags::OutputDebug(SystemFlags::debugNetwork,"In [%s::%s Line: %d] Created NetworkCommand as follows:\n%s\n",__FILE__,__FUNCTION__,__LINE__,toString().c_str()); if(SystemFlags::getSystemSettingType(SystemFlags::debugNetwork).enabled) SystemFlags::OutputDebug(SystemFlags::debugNetwork,"In [%s::%s Line: %d] Created NetworkCommand as follows:\n%s\n",__FILE__,__FUNCTION__,__LINE__,toString().c_str());
} }
void NetworkCommand::preprocessNetworkCommand(World *world) { void NetworkCommand::preprocessNetworkCommand(World *world) {
if(networkCommandType == nctGiveCommand) { if(networkCommandType == nctGiveCommand) {
const Unit *unit= world->findUnitById(unitId); const Unit *unit= world->findUnitById(unitId);
//validate unit //validate unit
if(unit != NULL) { if(unit != NULL) {
//const UnitType *unitType= world->findUnitTypeById(unit->getFaction()->getType(), unitTypeId);
const CommandType *ct = unit->getType()->findCommandTypeById(commandTypeId); const CommandType *ct= unit->getType()->findCommandTypeById(commandTypeId);
if(ct != NULL && ct->getClass() == ccBuild && targetId >= 0) {
if(ct != NULL && ct->getClass() == ccBuild && targetId >= 0) {
CardinalDir::assertDirValid(targetId); CardinalDir::assertDirValid(targetId);
} }
} }
else { else {
if(SystemFlags::getSystemSettingType(SystemFlags::debugNetwork).enabled) SystemFlags::OutputDebug(SystemFlags::debugNetwork,"In [%s::%s Line: %d] (unit == NULL) %s\n",__FILE__,__FUNCTION__,__LINE__,toString().c_str()); if(SystemFlags::getSystemSettingType(SystemFlags::debugNetwork).enabled) SystemFlags::OutputDebug(SystemFlags::debugNetwork,"In [%s::%s Line: %d] (unit == NULL) %s\n",__FILE__,__FUNCTION__,__LINE__,toString().c_str());
} }
} }
} }

View File

@ -94,6 +94,7 @@ public:
networkCommandType=0; networkCommandType=0;
unitId=0; unitId=0;
unitTypeId=0; unitTypeId=0;
nextUnitTypeId=0;
commandTypeId=0; commandTypeId=0;
positionX=0; positionX=0;
positionY=0; positionY=0;
@ -114,6 +115,7 @@ public:
int commandTypeId= -1, int commandTypeId= -1,
const Vec2i &pos= Vec2i(0), const Vec2i &pos= Vec2i(0),
int unitTypeId= -1, int unitTypeId= -1,
int nextUnitTypeId= -1,
int targetId= -1, int targetId= -1,
int facing= -1, int facing= -1,
bool wantQueue = false, bool wantQueue = false,
@ -124,6 +126,7 @@ public:
int16 networkCommandType; int16 networkCommandType;
int32 unitId; int32 unitId;
int16 unitTypeId; int16 unitTypeId;
int16 nextUnitTypeId;
int16 commandTypeId; int16 commandTypeId;
int16 positionX; int16 positionX;
int16 positionY; int16 positionY;
@ -141,6 +144,7 @@ public:
int getCommandTypeId() const {return commandTypeId;} int getCommandTypeId() const {return commandTypeId;}
Vec2i getPosition() const {return Vec2i(positionX, positionY);} Vec2i getPosition() const {return Vec2i(positionX, positionY);}
int getUnitTypeId() const {return unitTypeId;} int getUnitTypeId() const {return unitTypeId;}
int getNextUnitTypeId() const {return nextUnitTypeId;}
int getTargetId() const {return targetId;} int getTargetId() const {return targetId;}
int getWantQueue() const {return wantQueue;} int getWantQueue() const {return wantQueue;}
int getFromFactionIndex() const {return fromFactionIndex;} int getFromFactionIndex() const {return fromFactionIndex;}

View File

@ -76,12 +76,6 @@ Command::Command(const CommandType *ct, const Vec2i &pos, const UnitType *unitTy
//} //}
} }
int Command::getPriority(){
if(this->commandType->commandTypeClass==ccAttack && getUnit()==NULL){
return 5; // attacks to the ground have low priority
}
return this->commandType->getTypePriority();
}
// =============== set =============== // =============== set ===============
void Command::setCommandType(const CommandType *commandType) { void Command::setCommandType(const CommandType *commandType) {

View File

@ -71,9 +71,6 @@ public:
inline const UnitType* getUnitType() const {return unitType;} inline const UnitType* getUnitType() const {return unitType;}
inline CardinalDir getFacing() const {return facing;} inline CardinalDir getFacing() const {return facing;}
//Priority: commands of higher priority will cancel commands of lower priority
virtual int getPriority();
//set //set
void setCommandType(const CommandType *commandType); void setCommandType(const CommandType *commandType);
void setPos(const Vec2i &pos); void setPos(const Vec2i &pos);

View File

@ -745,6 +745,15 @@ void Unit::cleanupAllParticlesystems() {
} }
const MorphCommandType* Unit::getCurrMorphCt() const {
auto result = std::find_if(commands.rbegin(), commands.rend(),[](Command *i)
{ return i->getCommandType()->getClass() == ccMorph; });//TODO set CurrMorphCt on push comands instead of looping
if(result != commands.rend()) {
return static_cast<const MorphCommandType*>((*result)->getCommandType());
}
else return NULL;
}
ParticleSystem * Unit::getFire() const { ParticleSystem * Unit::getFire() const {
if(this->fire != NULL && if(this->fire != NULL &&
Renderer::getInstance().validateParticleSystemStillExists(this->fire,rsGame) == false) { Renderer::getInstance().validateParticleSystemStillExists(this->fire,rsGame) == false) {
@ -1828,8 +1837,6 @@ std::pair<CommandResult,string> Unit::giveCommand(Command *command, bool tryQueu
throw megaglest_runtime_error("command->getCommandType() == NULL"); throw megaglest_runtime_error("command->getCommandType() == NULL");
} }
const int command_priority = command->getPriority();
if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s] Line: %d took msecs: %lld\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,chrono.getMillis()); if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s] Line: %d took msecs: %lld\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,chrono.getMillis());
//printf("In [%s::%s] Line: %d unit [%d - %s] command [%s] tryQueue = %d command->getCommandType()->isQueuable(tryQueue) = %d\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,this->getId(),this->getType()->getName().c_str(), command->getCommandType()->getName().c_str(), tryQueue,command->getCommandType()->isQueuable(tryQueue)); //printf("In [%s::%s] Line: %d unit [%d - %s] command [%s] tryQueue = %d command->getCommandType()->isQueuable(tryQueue) = %d\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,this->getId(),this->getType()->getName().c_str(), command->getCommandType()->getName().c_str(), tryQueue,command->getCommandType()->isQueuable(tryQueue));
@ -1839,32 +1846,6 @@ std::pair<CommandResult,string> Unit::giveCommand(Command *command, bool tryQueu
if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s] Line: %d took msecs: %lld\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,chrono.getMillis()); if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s] Line: %d took msecs: %lld\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,chrono.getMillis());
if(SystemFlags::getSystemSettingType(SystemFlags::debugUnitCommands).enabled) SystemFlags::OutputDebug(SystemFlags::debugUnitCommands,"In [%s::%s Line: %d] Command is Queable\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__); if(SystemFlags::getSystemSettingType(SystemFlags::debugUnitCommands).enabled) SystemFlags::OutputDebug(SystemFlags::debugUnitCommands,"In [%s::%s Line: %d] Command is Queable\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__);
if(command->getCommandType()->isQueuable() == qAlways && tryQueue){
// Its a produce or upgrade command called without queued key
// in this case we must NOT delete lower priority commands!
// we just queue it!
}
else {
//Delete all lower-prioirty commands
for(list<Command*>::iterator i= commands.begin(); i != commands.end();){
if((*i)->getPriority() < command_priority){
if(SystemFlags::getSystemSettingType(SystemFlags::debugUnitCommands).enabled)
SystemFlags::OutputDebug(SystemFlags::debugUnitCommands,"In [%s::%s Line: %d] Deleting lower priority command [%s]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,(*i)->toString(false).c_str());
static string mutexOwnerId = string(__FILE__) + string("_") + intToStr(__LINE__);
MutexSafeWrapper safeMutex(mutexCommands,mutexOwnerId);
deleteQueuedCommand(*i);
i= commands.erase(i);
safeMutex.ReleaseLock();
}
else {
++i;
}
}
}
if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s] Line: %d took msecs: %lld\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,chrono.getMillis()); if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s] Line: %d took msecs: %lld\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,chrono.getMillis());
//cancel current command if it is not queuable //cancel current command if it is not queuable
@ -2183,8 +2164,9 @@ void Unit::resetHighlight(){
highlight= 1.f; highlight= 1.f;
} }
const CommandType *Unit::computeCommandType(const Vec2i &pos, const Unit *targetUnit) const{ const CommandType *Unit::computeCommandType(const Vec2i &pos, const Unit *targetUnit, const UnitType* unitType) const{
const CommandType *commandType= NULL; const CommandType *commandType= NULL;
unitType= unitType? unitType: type;
if(map->isInside(pos) == false || map->isInsideSurface(map->toSurfCoords(pos)) == false) { if(map->isInside(pos) == false || map->isInsideSurface(map->toSurfCoords(pos)) == false) {
throw megaglest_runtime_error("#6 Invalid path position = " + pos.getString()); throw megaglest_runtime_error("#6 Invalid path position = " + pos.getString());
@ -2192,22 +2174,21 @@ const CommandType *Unit::computeCommandType(const Vec2i &pos, const Unit *target
SurfaceCell *sc= map->getSurfaceCell(Map::toSurfCoords(pos)); SurfaceCell *sc= map->getSurfaceCell(Map::toSurfCoords(pos));
if(type == NULL) { if(unitType == NULL) {
char szBuf[8096]=""; char szBuf[8096]="";
snprintf(szBuf,8096,"In [%s::%s Line: %d] ERROR: type == NULL, Unit = [%s]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,this->toString().c_str()); snprintf(szBuf,8096,"In [%s::%s Line: %d] ERROR: unitType == NULL, Unit = [%s]\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,this->toString().c_str());
throw megaglest_runtime_error(szBuf); throw megaglest_runtime_error(szBuf);
} }
//printf("Line: %d Unit::computeCommandType pos [%s] targetUnit [%s]\n",__LINE__,pos.getString().c_str(),(targetUnit != NULL ? targetUnit->getType()->getName().c_str() : "(null)"));
if(targetUnit != NULL) { if(targetUnit != NULL) {
//attack enemies //attack enemies
if(isAlly(targetUnit) == false) { if(isAlly(targetUnit) == false) {
commandType= type->getFirstAttackCommand(targetUnit->getCurrField()); commandType= unitType->getFirstAttackCommand(targetUnit->getCurrField());
} }
//repair allies //repair allies
else { else {
if(targetUnit->isBuilt() == false || targetUnit->isDamaged() == true) { if(targetUnit->isBuilt() == false || targetUnit->isDamaged() == true) {
commandType= type->getFirstRepairCommand(targetUnit->getType()); commandType= unitType->getFirstRepairCommand(targetUnit->getType());
} }
//printf("Line: %d Unit::computeCommandType pos [%s] targetUnit [%s] commandType [%p]\n",__LINE__,pos.getString().c_str(),(targetUnit != NULL ? targetUnit->getType()->getName().c_str() : "(null)"),commandType); //printf("Line: %d Unit::computeCommandType pos [%s] targetUnit [%s] commandType [%p]\n",__LINE__,pos.getString().c_str(),(targetUnit != NULL ? targetUnit->getType()->getName().c_str() : "(null)"),commandType);
@ -2223,7 +2204,7 @@ const CommandType *Unit::computeCommandType(const Vec2i &pos, const Unit *target
targetUnit->getType() != NULL && targetUnit->getType() != NULL &&
targetUnit->getType()->getStore(this->getLoadType()) > 0) { targetUnit->getType()->getStore(this->getLoadType()) > 0) {
commandType = type->getFirstHarvestEmergencyReturnCommand(); commandType = unitType->getFirstHarvestEmergencyReturnCommand();
} }
} }
} }
@ -2232,7 +2213,7 @@ const CommandType *Unit::computeCommandType(const Vec2i &pos, const Unit *target
//check harvest command //check harvest command
Resource *resource= sc->getResource(); Resource *resource= sc->getResource();
if(resource != NULL) { if(resource != NULL) {
commandType= type->getFirstHarvestCommand(resource->getType(),this->getFaction()); commandType= unitType->getFirstHarvestCommand(resource->getType(),this->getFaction());
} }
} }
@ -2247,7 +2228,7 @@ const CommandType *Unit::computeCommandType(const Vec2i &pos, const Unit *target
(targetUnit->isBuilt() == false || targetUnit->isDamaged() == true)) { (targetUnit->isBuilt() == false || targetUnit->isDamaged() == true)) {
const RepairCommandType *rct= this->getType()->getFirstRepairCommand(targetUnit->getType()); const RepairCommandType *rct= this->getType()->getFirstRepairCommand(targetUnit->getType());
if(rct != NULL) { if(rct != NULL) {
commandType= type->getFirstRepairCommand(targetUnit->getType()); commandType= unitType->getFirstRepairCommand(targetUnit->getType());
//printf("************ Unit will repair building built = %d, repair = %d\n",targetUnit->isBuilt(),targetUnit->isDamaged()); //printf("************ Unit will repair building built = %d, repair = %d\n",targetUnit->isBuilt(),targetUnit->isDamaged());
} }
} }
@ -2257,7 +2238,7 @@ const CommandType *Unit::computeCommandType(const Vec2i &pos, const Unit *target
//default command is move command //default command is move command
if(commandType == NULL) { if(commandType == NULL) {
commandType= type->getFirstCtOfClass(ccMove); commandType= unitType->getFirstCtOfClass(ccMove);
} }
return commandType; return commandType;
@ -3848,12 +3829,16 @@ std::pair<CommandResult,string> Unit::checkCommand(Command *command) const {
(ignoreCheckCommand == false && this->getFaction()->reqsOk(command->getCommandType()) == false)) { (ignoreCheckCommand == false && this->getFaction()->reqsOk(command->getCommandType()) == false)) {
if(SystemFlags::getSystemSettingType(SystemFlags::debugLUA).enabled) SystemFlags::OutputDebug(SystemFlags::debugLUA,"In [%s::%s Line: %d] isOperative() = %d, command->getUnit() = %p, getType()->hasCommandType(command->getCommandType()) = %d, this->getFaction()->reqsOk(command->getCommandType()) = %d\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__, __LINE__,isOperative(),command->getUnit(),getType()->hasCommandType(command->getCommandType()),this->getFaction()->reqsOk(command->getCommandType())); if(SystemFlags::getSystemSettingType(SystemFlags::debugLUA).enabled) SystemFlags::OutputDebug(SystemFlags::debugLUA,"In [%s::%s Line: %d] isOperative() = %d, command->getUnit() = %p, getType()->hasCommandType(command->getCommandType()) = %d, this->getFaction()->reqsOk(command->getCommandType()) = %d\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__, __LINE__,isOperative(),command->getUnit(),getType()->hasCommandType(command->getCommandType()),this->getFaction()->reqsOk(command->getCommandType()));
auto mct = getCurrMorphCt();
// Allow self healing if able to heal own unit type // Allow self healing if able to heal own unit type
if( command->getUnit() == this && if( command->getUnit() == this &&
command->getCommandType()->getClass() == ccRepair && command->getCommandType()->getClass() == ccRepair &&
this->getType()->getFirstRepairCommand(this->getType()) != NULL) { this->getType()->getFirstRepairCommand(this->getType()) != NULL) {
} }
else if(mct && mct->getMorphUnit()->hasCommandType(command->getCommandType())) {
// Allow Current Morph Commands
}
else { else {
//printf("In [%s::%s Line: %d] command = %p\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,command); //printf("In [%s::%s Line: %d] command = %p\n",extractFileFromDirectoryPath(__FILE__).c_str(),__FUNCTION__,__LINE__,command);

View File

@ -653,6 +653,7 @@ public:
} }
return NULL; return NULL;
} }
const MorphCommandType* getCurrMorphCt() const;
void replaceCurrCommand(Command *cmd); void replaceCurrCommand(Command *cmd);
int getCountOfProducedUnitsPreExistence(const UnitType *ut) const; int getCountOfProducedUnitsPreExistence(const UnitType *ut) const;
unsigned int getCommandSize() const; unsigned int getCommandSize() const;
@ -673,7 +674,7 @@ public:
//other //other
void resetHighlight(); void resetHighlight();
const CommandType *computeCommandType(const Vec2i &pos, const Unit *targetUnit= NULL) const; const CommandType *computeCommandType(const Vec2i &pos, const Unit *targetUnit= NULL, const UnitType* unitType= NULL) const;
string getDesc(bool translatedValue) const; string getDesc(bool translatedValue) const;
string getDescExtension(bool translatedValue) const; string getDescExtension(bool translatedValue) const;
bool computeEp(); bool computeEp();

View File

@ -125,8 +125,6 @@ public:
Queueability q = isQueuable(); Queueability q = isQueuable();
return (q != qNever) && (q != qOnlyLast); return (q != qNever) && (q != qOnlyLast);
} }
//Priority: commands of higher priority will cancel commands of lower priority
virtual int getTypePriority() const {return 10;}
virtual bool usesPathfinder() const= 0; virtual bool usesPathfinder() const= 0;
//get //get
@ -156,7 +154,6 @@ public:
virtual string getDesc(const TotalUpgrade *totalUpgrade, bool translatedValue) const; virtual string getDesc(const TotalUpgrade *totalUpgrade, bool translatedValue) const;
virtual string toString(bool translatedValue) const; virtual string toString(bool translatedValue) const;
virtual Queueability isQueuable() const {return qNever;} virtual Queueability isQueuable() const {return qNever;}
virtual int getTypePriority() const {return 100000;}
//get //get
const StopSkillType *getStopSkillType() const {return stopSkillType;}; const StopSkillType *getStopSkillType() const {return stopSkillType;};
@ -230,6 +227,7 @@ public:
const TechTree *tt, const FactionType *ft, const UnitType &ut, const TechTree *tt, const FactionType *ft, const UnitType &ut,
std::map<string,vector<pair<string, string> > > &loadedFileList, string parentLoader); std::map<string,vector<pair<string, string> > > &loadedFileList, string parentLoader);
virtual string getDesc(const TotalUpgrade *totalUpgrade, bool translatedValue) const; virtual string getDesc(const TotalUpgrade *totalUpgrade, bool translatedValue) const;
virtual Queueability isQueuable() const {return qOnlyLast;}
virtual string toString(bool translatedValue) const; virtual string toString(bool translatedValue) const;
//get //get
@ -386,7 +384,6 @@ public:
virtual string toString(bool translatedValue) const; virtual string toString(bool translatedValue) const;
virtual const ProducibleType *getProduced() const; virtual const ProducibleType *getProduced() const;
virtual Queueability isQueuable() const {return qAlways;} virtual Queueability isQueuable() const {return qAlways;}
virtual int getTypePriority() const {return 15;}
//get //get
const ProduceSkillType *getProduceSkillType() const {return produceSkillType;} const ProduceSkillType *getProduceSkillType() const {return produceSkillType;}
@ -416,7 +413,6 @@ public:
virtual string getReqDesc(bool translatedValue) const; virtual string getReqDesc(bool translatedValue) const;
virtual const ProducibleType *getProduced() const; virtual const ProducibleType *getProduced() const;
virtual Queueability isQueuable() const {return qAlways;} virtual Queueability isQueuable() const {return qAlways;}
virtual int getTypePriority() const {return 15;}
//get //get
const UpgradeSkillType *getUpgradeSkillType() const {return upgradeSkillType;} const UpgradeSkillType *getUpgradeSkillType() const {return upgradeSkillType;}
@ -446,7 +442,7 @@ public:
virtual string toString(bool translatedValue) const; virtual string toString(bool translatedValue) const;
virtual string getReqDesc(bool translatedValue) const; virtual string getReqDesc(bool translatedValue) const;
virtual const ProducibleType *getProduced() const; virtual const ProducibleType *getProduced() const;
Queueability isQueuable() const {return qOnlyLast;} //After morph anything can happen Queueability isQueuable() const {return qAlways;} //After morph anything can happen
//get //get
const MorphSkillType *getMorphSkillType() const {return morphSkillType;} const MorphSkillType *getMorphSkillType() const {return morphSkillType;}

View File

@ -720,167 +720,137 @@ void UnitUpdater::updateAttack(Unit *unit, int frameIndex) {
if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s Line: %d] took msecs: %lld\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis()); if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s Line: %d] took msecs: %lld\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis());
if( (command->getUnit() == NULL || !(command->getUnit()->isAlive()) ) && unit->getCommandSize() > 1) {
if(attackableOnRange(unit, &target, act->getAttackSkillType(),(frameIndex >= 0))) {
if(frameIndex < 0) { if(frameIndex < 0) {
unit->finishCommand(); // all queued "ground attacks" are skipped if somthing else is queued after them. if(unit->getEp() >= act->getAttackSkillType()->getEpCost()) {
unit->setCurrSkill(act->getAttackSkillType());
unit->setTarget(target);
}
else {
unit->setCurrSkill(scStop);
}
if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex < 0) { if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex < 0) {
char szBuf[8096]=""; char szBuf[8096]="";
snprintf(szBuf,8096,"[updateAttack]"); snprintf(szBuf,8096,"[updateAttack]");
unit->logSynchData(extractFileFromDirectoryPath(__FILE__).c_str(),__LINE__,szBuf); unit->logSynchData(extractFileFromDirectoryPath(__FILE__).c_str(),__LINE__,szBuf);
} }
} }
return; if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s Line: %d] took msecs: %lld\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis());
} }
else {
//if found //compute target pos
//if(frameIndex < 0) { Vec2i pos;
{ if(command->getUnit() != NULL) {
if(attackableOnRange(unit, &target, act->getAttackSkillType(),(frameIndex >= 0))) { pos= command->getUnit()->getCenteredPos();
if(frameIndex < 0) { }
if(unit->getEp() >= act->getAttackSkillType()->getEpCost()) { else if(attackableOnSight(unit, &target, act->getAttackSkillType(), (frameIndex >= 0))) {
unit->setCurrSkill(act->getAttackSkillType()); pos= target->getPos();
unit->setTarget(target); }
} else {
else { pos= command->getPos();
unit->setCurrSkill(scStop); }
} if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex < 0) {
char szBuf[8096]="";
snprintf(szBuf,8096,"[updateAttack] pos [%s] unit->getPos() [%s]",pos.getString().c_str(),unit->getPos().getString().c_str());
unit->logSynchData(__FILE__,__LINE__,szBuf);
}
if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s Line: %d] took msecs: %lld\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis());
TravelState tsValue = tsImpossible;
//if(frameIndex < 0) {
{
//printf("In [%s::%s Line: %d] START pathfind for attacker [%d - %s]\n",__FILE__,__FUNCTION__,__LINE__,unit->getId(), unit->getType()->getName().c_str());
//fflush(stdout);
switch(this->game->getGameSettings()->getPathFinderType()) {
case pfBasic:
tsValue = pathFinder->findPath(unit, pos, NULL, frameIndex);
break;
default:
throw megaglest_runtime_error("detected unsupported pathfinder type!");
}
//printf("In [%s::%s Line: %d] END pathfind for attacker [%d - %s]\n",__FILE__,__FUNCTION__,__LINE__,unit->getId(), unit->getType()->getName().c_str());
//fflush(stdout);
}
if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s Line: %d] took msecs: %lld\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis());
if(frameIndex < 0) {
if(command->getUnit() != NULL && !command->getUnit()->isAlive() && unit->getCommandSize() > 1) {
// don't run over to dead body if there is still something to do in the queue
unit->finishCommand();
if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex < 0) { if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex < 0) {
char szBuf[8096]=""; char szBuf[8096]="";
snprintf(szBuf,8096,"[updateAttack]"); snprintf(szBuf,8096,"[updateAttack]");
unit->logSynchData(extractFileFromDirectoryPath(__FILE__).c_str(),__LINE__,szBuf); unit->logSynchData(extractFileFromDirectoryPath(__FILE__).c_str(),__LINE__,szBuf);
} }
}
if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s Line: %d] took msecs: %lld\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis());
}
else {
//compute target pos
Vec2i pos;
if(command->getUnit() != NULL) {
pos= command->getUnit()->getCenteredPos();
}
else if(attackableOnSight(unit, &target, act->getAttackSkillType(), (frameIndex >= 0))) {
pos= target->getPos();
} }
else { else {
pos= command->getPos(); //if unit arrives destPos order has ended
} if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex < 0 &&
SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynchMax).enabled == true) {
if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex < 0) { char szBuf[8096]="";
char szBuf[8096]=""; snprintf(szBuf,8096,"#1 [updateAttack] tsValue = %d",tsValue);
snprintf(szBuf,8096,"[updateAttack] pos [%s] unit->getPos() [%s]",pos.getString().c_str(),unit->getPos().getString().c_str()); unit->logSynchData(extractFileFromDirectoryPath(__FILE__).c_str(),__LINE__,szBuf);
unit->logSynchData(__FILE__,__LINE__,szBuf); }
} switch (tsValue) {
case tsMoving:
if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s Line: %d] took msecs: %lld\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis()); unit->setCurrSkill(act->getMoveSkillType());
break;
TravelState tsValue = tsImpossible; case tsBlocked:
//if(frameIndex < 0) { if(unit->getPath()->isBlocked()) {
{ unit->finishCommand();
//printf("In [%s::%s Line: %d] START pathfind for attacker [%d - %s]\n",__FILE__,__FUNCTION__,__LINE__,unit->getId(), unit->getType()->getName().c_str()); }
//fflush(stdout);
switch(this->game->getGameSettings()->getPathFinderType()) {
case pfBasic:
tsValue = pathFinder->findPath(unit, pos, NULL, frameIndex);
break; break;
default: default:
throw megaglest_runtime_error("detected unsupported pathfinder type!"); unit->finishCommand();
} break;
//printf("In [%s::%s Line: %d] END pathfind for attacker [%d - %s]\n",__FILE__,__FUNCTION__,__LINE__,unit->getId(), unit->getType()->getName().c_str());
//fflush(stdout);
}
if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s Line: %d] took msecs: %lld\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis());
if(frameIndex < 0) {
if(command->getUnit() != NULL && !command->getUnit()->isAlive() && unit->getCommandSize() > 1) {
// don't run over to dead body if there is still something to do in the queue
unit->finishCommand();
if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex < 0) {
char szBuf[8096]="";
snprintf(szBuf,8096,"[updateAttack]");
unit->logSynchData(extractFileFromDirectoryPath(__FILE__).c_str(),__LINE__,szBuf);
} }
}
else {
//if unit arrives destPos order has ended
if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex < 0 &&
SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynchMax).enabled == true) {
char szBuf[8096]="";
snprintf(szBuf,8096,"#1 [updateAttack] tsValue = %d",tsValue);
unit->logSynchData(extractFileFromDirectoryPath(__FILE__).c_str(),__LINE__,szBuf);
}
switch (tsValue) {
case tsMoving:
unit->setCurrSkill(act->getMoveSkillType());
break;
case tsBlocked:
if(unit->getPath()->isBlocked()) {
unit->finishCommand();
}
break;
default:
unit->finishCommand();
break;
}
/* /*
case tsMoving: case tsMoving:
unit->setCurrSkill(act->getMoveSkillType()); unit->setCurrSkill(act->getMoveSkillType());
{
{ std::pair<bool,Unit *> beingAttacked = unitBeingAttacked(unit);
std::pair<bool,Unit *> beingAttacked = unitBeingAttacked(unit); if(beingAttacked.first == true) {
if(beingAttacked.first == true) { Unit *enemy = beingAttacked.second;
Unit *enemy = beingAttacked.second; const AttackCommandType *act_forenemy = unit->getType()->getFirstAttackCommand(enemy->getCurrField());
const AttackCommandType *act_forenemy = unit->getType()->getFirstAttackCommand(enemy->getCurrField()); if(act_forenemy != NULL) {
if(act_forenemy != NULL) { if(unit->getEp() >= act_forenemy->getAttackSkillType()->getEpCost()) {
if(unit->getEp() >= act_forenemy->getAttackSkillType()->getEpCost()) { unit->setCurrSkill(act_forenemy->getAttackSkillType());
unit->setCurrSkill(act_forenemy->getAttackSkillType()); unit->setTarget(enemy);
unit->setTarget(enemy);
}
//aiInterface->giveCommand(i, act_forenemy, beingAttacked.second->getPos());
} }
else { //aiInterface->giveCommand(i, act_forenemy, beingAttacked.second->getPos());
const AttackStoppedCommandType *asct_forenemy = unit->getType()->getFirstAttackStoppedCommand(enemy->getCurrField()); }
if(asct_forenemy != NULL) { else {
//aiInterface->giveCommand(i, asct_forenemy, beingAttacked.second->getCenteredPos()); const AttackStoppedCommandType *asct_forenemy = unit->getType()->getFirstAttackStoppedCommand(enemy->getCurrField());
if(unit->getEp() >= asct_forenemy->getAttackSkillType()->getEpCost()) { if(asct_forenemy != NULL) {
unit->setCurrSkill(asct_forenemy->getAttackSkillType()); //aiInterface->giveCommand(i, asct_forenemy, beingAttacked.second->getCenteredPos());
unit->setTarget(enemy); if(unit->getEp() >= asct_forenemy->getAttackSkillType()->getEpCost()) {
} unit->setCurrSkill(asct_forenemy->getAttackSkillType());
unit->setTarget(enemy);
} }
} }
} }
} }
}
break; break;
case tsBlocked:
case tsBlocked: if(unit->getPath()->isBlocked()){
if(unit->getPath()->isBlocked()){
unit->finishCommand();
}
break;
default:
unit->finishCommand(); unit->finishCommand();
} }
break;
default:
unit->finishCommand();
}
*/ */
if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex < 0 &&
if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex < 0 && SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynchMax).enabled == true) {
SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynchMax).enabled == true) { char szBuf[8096]="";
char szBuf[8096]=""; snprintf(szBuf,8096,"#2 [updateAttack] tsValue = %d",tsValue);
snprintf(szBuf,8096,"#2 [updateAttack] tsValue = %d",tsValue); unit->logSynchData(extractFileFromDirectoryPath(__FILE__).c_str(),__LINE__,szBuf);
unit->logSynchData(extractFileFromDirectoryPath(__FILE__).c_str(),__LINE__,szBuf);
}
} }
} }
if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s Line: %d] took msecs: %lld\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis());
} }
} if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s Line: %d] took msecs: %lld\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis());
}
if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s] Line: %d took msecs: %lld --------------------------- [END OF METHOD] ---------------------------\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis()); if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled && chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s] Line: %d took msecs: %lld --------------------------- [END OF METHOD] ---------------------------\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis());
@ -1350,7 +1320,7 @@ void UnitUpdater::updateHarvestEmergencyReturn(Unit *unit, int frameIndex) {
if(previousHarvestCmd != NULL) { if(previousHarvestCmd != NULL) {
//printf("\n\n#1a return harvested resources\n\n"); //printf("\n\n#1a return harvested resources\n\n");
NetworkCommand networkCommand(this->world,nctGiveCommand, unit->getId(), previousHarvestCmd->getId(), unit->getLastHarvestedResourcePos(), NetworkCommand networkCommand(this->world,nctGiveCommand, unit->getId(), previousHarvestCmd->getId(), unit->getLastHarvestedResourcePos(),
-1, Unit::invalidId, -1, false, cst_None, -1, -1); -1, -1, Unit::invalidId, -1, false, cst_None, -1, -1);
if(SystemFlags::getSystemSettingType(SystemFlags::debugUnitCommands).enabled) SystemFlags::OutputDebug(SystemFlags::debugUnitCommands,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__); if(SystemFlags::getSystemSettingType(SystemFlags::debugUnitCommands).enabled) SystemFlags::OutputDebug(SystemFlags::debugUnitCommands,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__);
@ -2088,7 +2058,7 @@ void UnitUpdater::updateRepair(Unit *unit, int frameIndex) {
const CommandType *ctbuild = unit->getType()->getFirstCtOfClass(ccBuild); const CommandType *ctbuild = unit->getType()->getFirstCtOfClass(ccBuild);
NetworkCommand networkCommand(this->world,nctGiveCommand, unit->getId(), ctbuild->getId(), command->getPos(), NetworkCommand networkCommand(this->world,nctGiveCommand, unit->getId(), ctbuild->getId(), command->getPos(),
command->getUnitType()->getId(), -1, CardinalDir(CardinalDir::NORTH), true, command->getStateType(), command->getUnitType()->getId(), -1, -1, CardinalDir(CardinalDir::NORTH), true, command->getStateType(),
command->getStateValue()); command->getStateValue());
if(SystemFlags::getSystemSettingType(SystemFlags::debugUnitCommands).enabled) SystemFlags::OutputDebug(SystemFlags::debugUnitCommands,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__); if(SystemFlags::getSystemSettingType(SystemFlags::debugUnitCommands).enabled) SystemFlags::OutputDebug(SystemFlags::debugUnitCommands,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__);
@ -2918,97 +2888,86 @@ void UnitUpdater::findEnemiesForCell(const Vec2i pos, int size, int sightRange,
//if the unit has any enemy on range //if the unit has any enemy on range
bool UnitUpdater::unitOnRange(Unit *unit, int range, Unit **rangedPtr, bool UnitUpdater::unitOnRange(Unit *unit, int range, Unit **rangedPtr,
const AttackSkillType *ast,bool evalMode) { const AttackSkillType *ast,bool evalMode) {
bool result=false; bool result=false;
try { try {
vector<Unit*> enemies; vector<Unit*> enemies;
enemies.reserve(100); enemies.reserve(100);
//we check command target //we check command target
const Unit *commandTarget = NULL; const Unit *commandTarget = NULL;
if(unit->anyCommand() && unit->getCurrCommand() != NULL) { if(unit->anyCommand() && unit->getCurrCommand() != NULL) {
commandTarget = static_cast<const Unit*>(unit->getCurrCommand()->getUnit()); commandTarget = static_cast<const Unit*>(unit->getCurrCommand()->getUnit());
} }
if(commandTarget != NULL && commandTarget->isDead()) { if(commandTarget != NULL && commandTarget->isDead()) {
commandTarget = NULL; commandTarget = NULL;
} }
//aux vars //aux vars
int size = unit->getType()->getSize(); int size = unit->getType()->getSize();
Vec2i center = unit->getPos(); Vec2i center = unit->getPos();
Vec2f floatCenter = unit->getFloatCenteredPos(); Vec2f floatCenter = unit->getFloatCenteredPos();
//bool foundInCache = true; //bool foundInCache = true;
if(findCachedCellsEnemies(center,range,size,enemies,ast, if(findCachedCellsEnemies(center,range,size,enemies,ast,
unit,commandTarget) == false) { unit,commandTarget) == false) {
//foundInCache = false; //foundInCache = false;
//nearby cells //nearby cells
UnitRangeCellsLookupItem cacheItem; UnitRangeCellsLookupItem cacheItem;
for(int i = center.x - range; i < center.x + range + size; ++i) { for(int i = center.x - range; i < center.x + range + size; ++i) {
for(int j = center.y - range; j < center.y + range + size; ++j) { for(int j = center.y - range; j < center.y + range + size; ++j) {
//cells inside map and in range //cells inside map and in range
#ifdef USE_STREFLOP #ifdef USE_STREFLOP
if(map->isInside(i, j) && streflop::floor(static_cast<streflop::Simple>(floatCenter.dist(Vec2f((float)i, (float)j)))) <= (range+1)){ if(map->isInside(i, j) && streflop::floor(static_cast<streflop::Simple>(floatCenter.dist(Vec2f((float)i, (float)j)))) <= (range+1))
#else #else
if(map->isInside(i, j) && floor(floatCenter.dist(Vec2f((float)i, (float)j))) <= (range+1)){ if(map->isInside(i, j) && floor(floatCenter.dist(Vec2f((float)i, (float)j))) <= (range+1))
#endif #endif
Cell *cell = map->getCell(i,j); {
findEnemiesForCell(ast,cell,unit,commandTarget,enemies); Cell *cell = map->getCell(i,j);
findEnemiesForCell(ast,cell,unit,commandTarget,enemies);
cacheItem.rangeCellList.push_back(cell); cacheItem.rangeCellList.push_back(cell);
}
} }
} }
// Ok update our caches with the latest info
if(cacheItem.rangeCellList.empty() == false) {
MutexSafeWrapper safeMutex(mutexUnitRangeCellsLookupItemCache,string(__FILE__) + "_" + intToStr(__LINE__));
UnitRangeCellsLookupItemCache[center][size][range] = cacheItem;
}
} }
//attack enemies that can attack first
// Ok update our caches with the latest info float distToUnit= -1;
if(cacheItem.rangeCellList.empty() == false) { Unit* enemySeen= NULL;
MutexSafeWrapper safeMutex(mutexUnitRangeCellsLookupItemCache,string(__FILE__) + "_" + intToStr(__LINE__)); std::vector<Unit*> fightingEnemiesInRange;
std::vector<Unit*> damagedFightingEnemiesInRange;
UnitRangeCellsLookupItemCache[center][size][range] = cacheItem; Unit* myFightingEnemyInRange= NULL;
} float distToStandingUnit= -1;
} Unit* attackingEnemySeen= NULL;
ControlType controlType= unit->getFaction()->getControlType();
//attack enemies that can attack first bool isUltra= controlType == ctCpuUltra || controlType == ctNetworkCpuUltra;
float distToUnit= -1; bool isMega= controlType == ctCpuMega || controlType == ctNetworkCpuMega;
Unit* enemySeen= NULL; string randomInfoData = "enemies.size() = " + intToStr(enemies.size());
std::vector<Unit*> fightingEnemiesInRange; //printf("unit %d has control:%d\n",unit->getId(),controlType);
std::vector<Unit*> damagedFightingEnemiesInRange; for(int i = 0; i< (int)enemies.size(); ++i) {
Unit* myFightingEnemyInRange= NULL; Unit *enemy = enemies[i];
if(enemy != NULL && enemy->isAlive() == true) {
float distToStandingUnit= -1; // Here we default to first enemy if no attackers found
Unit* attackingEnemySeen= NULL; if(enemySeen == NULL) {
ControlType controlType= unit->getFaction()->getControlType(); *rangedPtr = enemy;
bool isUltra= controlType == ctCpuUltra || controlType == ctNetworkCpuUltra; enemySeen = enemy;
bool isMega= controlType == ctCpuMega || controlType == ctNetworkCpuMega; result = true;
}
//randomInfoData += " i = " + intToStr(i) + " alive = true result = " + intToStr(result);
string randomInfoData = "enemies.size() = " + intToStr(enemies.size()); // Attackers get first priority
if(enemy->getType()->hasSkillClass(scAttack) == true) {
//printf("unit %d has control:%d\n",unit->getId(),controlType); float currentDist = unit->getCenteredPos().dist(enemy->getCenteredPos());
for(int i = 0; i< (int)enemies.size(); ++i) { //randomInfoData += " currentDist = " + floatToStr(currentDist);
Unit *enemy = enemies[i];
if(enemy != NULL && enemy->isAlive() == true) {
// Here we default to first enemy if no attackers found
if(enemySeen == NULL) {
*rangedPtr = enemy;
enemySeen = enemy;
result = true;
}
//randomInfoData += " i = " + intToStr(i) + " alive = true result = " + intToStr(result);
// Attackers get first priority
if(enemy->getType()->hasSkillClass(scAttack) == true) {
float currentDist = unit->getCenteredPos().dist(enemy->getCenteredPos());
//randomInfoData += " currentDist = " + floatToStr(currentDist);
// Select closest attacking unit // Select closest attacking unit
if (distToUnit < 0 || currentDist < distToUnit) { if (distToUnit < 0 || currentDist < distToUnit) {
distToUnit = currentDist; distToUnit = currentDist;
@ -3041,10 +3000,9 @@ bool UnitUpdater::unitOnRange(Unit *unit, int range, Unit **rangedPtr,
} }
} }
} }
}
} }
} }
}
if (evalMode == false) { if (evalMode == false) {
bool doUltra = false; bool doUltra = false;
if (isMega) { if (isMega) {
@ -3062,7 +3020,6 @@ bool UnitUpdater::unitOnRange(Unit *unit, int range, Unit **rangedPtr,
unitList = &damagedFightingEnemiesInRange; unitList = &damagedFightingEnemiesInRange;
else else
unitList = &fightingEnemiesInRange; unitList = &fightingEnemiesInRange;
//printf("Choosing new one\n"); //printf("Choosing new one\n");
int myChoice = unit->getRandom()->randRange(1, unitList->size(), extractFileFromDirectoryPath(__FILE__) + intToStr(__LINE__)); int myChoice = unit->getRandom()->randRange(1, unitList->size(), extractFileFromDirectoryPath(__FILE__) + intToStr(__LINE__));
//printf("myChoice=%d\n", myChoice); //printf("myChoice=%d\n", myChoice);
@ -3085,95 +3042,90 @@ bool UnitUpdater::unitOnRange(Unit *unit, int range, Unit **rangedPtr,
} }
if(result == true) { if(result == true) {
//const Unit* teamUnit = NULL; //const Unit* teamUnit = NULL;
const Unit* enemyUnit = NULL; const Unit* enemyUnit = NULL;
bool onlyEnemyUnits = true; bool onlyEnemyUnits = true;
if(unit->getTeam() == world->getThisTeamIndex()) { if(unit->getTeam() == world->getThisTeamIndex()) {
//teamUnit = unit; //teamUnit = unit;
enemyUnit = enemySeen; enemyUnit = enemySeen;
onlyEnemyUnits = false; onlyEnemyUnits = false;
} }
else if(enemySeen->getTeam() == world->getThisTeamIndex()) { else if(enemySeen->getTeam() == world->getThisTeamIndex()) {
//teamUnit = enemySeen; //teamUnit = enemySeen;
enemyUnit = unit; enemyUnit = unit;
onlyEnemyUnits = false; onlyEnemyUnits = false;
} }
if(evalMode == false && onlyEnemyUnits == false && if(evalMode == false && onlyEnemyUnits == false &&
enemyUnit->getTeam() != world->getThisTeamIndex()) { enemyUnit->getTeam() != world->getThisTeamIndex()) {
Vec2f enemyFloatCenter = enemyUnit->getFloatCenteredPos(); Vec2f enemyFloatCenter = enemyUnit->getFloatCenteredPos();
// find nearest Attack and cleanup old dates // find nearest Attack and cleanup old dates
AttackWarningData *nearest = NULL; AttackWarningData *nearest = NULL;
float currentDistance = 0.f; float currentDistance = 0.f;
float nearestDistance = 0.f; float nearestDistance = 0.f;
MutexSafeWrapper safeMutex(mutexAttackWarnings,string(__FILE__) + "_" + intToStr(__LINE__)); MutexSafeWrapper safeMutex(mutexAttackWarnings,string(__FILE__) + "_" + intToStr(__LINE__));
for(int i = (int)attackWarnings.size() - 1; i >= 0; --i) { for(int i = (int)attackWarnings.size() - 1; i >= 0; --i) {
if(world->getFrameCount() - attackWarnings[i]->lastFrameCount > 200) { //after 200 frames attack break we warn again if(world->getFrameCount() - attackWarnings[i]->lastFrameCount > 200) { //after 200 frames attack break we warn again
AttackWarningData *toDelete =attackWarnings[i]; AttackWarningData *toDelete =attackWarnings[i];
attackWarnings.erase(attackWarnings.begin()+i); attackWarnings.erase(attackWarnings.begin()+i);
delete toDelete; // old one delete toDelete; // old one
}
else {
#ifdef USE_STREFLOP
currentDistance = streflop::floor(static_cast<streflop::Simple>(enemyFloatCenter.dist(attackWarnings[i]->attackPosition))); // no need for streflops here!
#else
currentDistance = floor(enemyFloatCenter.dist(attackWarnings[i]->attackPosition)); // no need for streflops here!
#endif
if(nearest == NULL) {
nearest = attackWarnings[i];
nearestDistance = currentDistance;
} }
else { else {
if(currentDistance < nearestDistance) { #ifdef USE_STREFLOP
currentDistance = streflop::floor(static_cast<streflop::Simple>(enemyFloatCenter.dist(attackWarnings[i]->attackPosition))); // no need for streflops here!
#else
currentDistance = floor(enemyFloatCenter.dist(attackWarnings[i]->attackPosition)); // no need for streflops here!
#endif
if(nearest == NULL) {
nearest = attackWarnings[i]; nearest = attackWarnings[i];
nearestDistance = currentDistance; nearestDistance = currentDistance;
} }
else {
if(currentDistance < nearestDistance) {
nearest = attackWarnings[i];
nearestDistance = currentDistance;
}
}
} }
} }
} if(nearest != NULL) {
// does it fit?
if(nearestDistance < attackWarnRange) {
// update entry with current values
nearest->lastFrameCount=world->getFrameCount();
nearest->attackPosition.x=enemyFloatCenter.x;
nearest->attackPosition.y=enemyFloatCenter.y;
}
else {
//Must be a different Attack!
nearest=NULL; //set to null to force a new entry in next step
}
}
// add new attack
if(nearest == NULL) {
// no else!
AttackWarningData* awd= new AttackWarningData();
awd->lastFrameCount=world->getFrameCount();
awd->attackPosition.x=enemyFloatCenter.x;
awd->attackPosition.y=enemyFloatCenter.y;
MutexSafeWrapper safeMutex(mutexAttackWarnings,string(__FILE__) + "_" + intToStr(__LINE__));
attackWarnings.push_back(awd);
if(nearest != NULL) { if(world->getAttackWarningsEnabled() == true) {
SoundRenderer::getInstance().playFx(CoreData::getInstance().getAttentionSound(),true);
// does it fit? world->addAttackEffects(enemyUnit);
if(nearestDistance < attackWarnRange) { }
// update entry with current values }
nearest->lastFrameCount=world->getFrameCount(); }
nearest->attackPosition.x=enemyFloatCenter.x;
nearest->attackPosition.y=enemyFloatCenter.y;
}
else {
//Must be a different Attack!
nearest=NULL; //set to null to force a new entry in next step
}
}
// add new attack
if(nearest == NULL) {
// no else!
AttackWarningData* awd= new AttackWarningData();
awd->lastFrameCount=world->getFrameCount();
awd->attackPosition.x=enemyFloatCenter.x;
awd->attackPosition.y=enemyFloatCenter.y;
MutexSafeWrapper safeMutex(mutexAttackWarnings,string(__FILE__) + "_" + intToStr(__LINE__));
attackWarnings.push_back(awd);
if(world->getAttackWarningsEnabled() == true) {
SoundRenderer::getInstance().playFx(CoreData::getInstance().getAttentionSound(),true);
world->addAttackEffects(enemyUnit);
}
}
} }
} }
}
catch(const exception &ex) { catch(const exception &ex) {
//setRunningStatus(false); //setRunningStatus(false);