public override void SearchingObjectivesToAttack() { //Comportamiento normal if (!amIBeingPossesed) { myCurrentObjective = null; myCurrentObjectiveTile = null; pathToObjective.Clear(); if (isDead || hasAttacked) { myCurrentEnemyState = enemyState.Ended; return; } if (!haveIBeenAlerted) { //Comprobar las unidades que hay en mi rango de acción unitsInRange = LM.TM.GetAllUnitsInRangeWithoutPathfinding(rangeOfAction, GetComponent <UnitBase>()); //Si hay personajes del jugador en mi rango de acción paso a attacking donde me alerto y hago mi accion for (int i = 0; i < unitsInRange.Count; i++) { if (unitsInRange[i].GetComponent <PlayerUnit>()) { myCurrentEnemyState = enemyState.Attacking; return; } } //Si llega hasta aqui significa que no había personajes en rango y termina myCurrentEnemyState = enemyState.Ended; } else { //Determinamos el enemigo más cercano. currentUnitsAvailableToAttack = LM.CheckEnemyPathfinding(GetComponent <EnemyUnit>()); //Si esta oculto lo quito de la lista de objetivos for (int i = 0; i < currentUnitsAvailableToAttack.Count; i++) { if (currentUnitsAvailableToAttack[i].isHidden) { currentUnitsAvailableToAttack.RemoveAt(i); i--; } } //Si no hay enemigos termina su turno if (currentUnitsAvailableToAttack.Count == 0) { myCurrentEnemyState = enemyState.Ended; return; } else if (currentUnitsAvailableToAttack.Count > 0) { if (currentUnitsAvailableToAttack.Count == 1) { base.SearchingObjectivesToAttack(); if (currentUnitsAvailableToAttack.Count == 1) { myCurrentObjective = currentUnitsAvailableToAttack[0]; myCurrentObjectiveTile = myCurrentObjective.myCurrentTile; } } //Si hay varios enemigos a la misma distancia, se queda con el que tenga más unidades adyacentes else if (currentUnitsAvailableToAttack.Count > 1) { //Ordeno la lista de posibles objetivos según el número de unidades dyacentes currentUnitsAvailableToAttack.Sort(delegate(UnitBase a, UnitBase b) { return((b.myCurrentTile.neighboursOcuppied).CompareTo(a.myCurrentTile.neighboursOcuppied)); }); //Elimino a todos los objetivos de la lista que no tengan el mayor número de enemigos adyacentes for (int i = currentUnitsAvailableToAttack.Count - 1; i > 0; i--) { if (currentUnitsAvailableToAttack[0].myCurrentTile.neighboursOcuppied > currentUnitsAvailableToAttack[i].myCurrentTile.neighboursOcuppied) { currentUnitsAvailableToAttack.RemoveAt(i); } } //Si sigue habiendo varios enemigos los ordeno segun la vida if (currentUnitsAvailableToAttack.Count > 1) { //Añado esto para eliminar a los personajes ocultos base.SearchingObjectivesToAttack(); //Ordeno la lista de posibles objetivos de menor a mayor vida actual currentUnitsAvailableToAttack.Sort(delegate(UnitBase a, UnitBase b) { return((a.currentHealth).CompareTo(b.currentHealth)); }); } myCurrentObjective = currentUnitsAvailableToAttack[0]; myCurrentObjectiveTile = myCurrentObjective.myCurrentTile; } //CAMBIAR ESTO (lm.tm) LM.TM.CalculatePathForMovementCost(myCurrentObjectiveTile.tileX, myCurrentObjectiveTile.tileZ, false); //No vale con igualar pathToObjective= LM.TM.currentPath porque entonces toma una referencia de la variable no de los valores. //Esto significa que si LM.TM.currentPath cambia de valor también lo hace pathToObjective for (int i = 0; i < LM.TM.currentPath.Count; i++) { pathToObjective.Add(LM.TM.currentPath[i]); } myCurrentEnemyState = enemyState.Attacking; } } } //Comportamiento del dark lord else { myCurrentObjective = null; myCurrentObjectiveTile = null; pathToObjective.Clear(); coneTiles.Clear(); tilesToCheck.Clear(); currentUnitsAvailableToAttack.Clear(); if (isDead || attackCountThisTurn >= 2) { myCurrentEnemyState = enemyState.Ended; return; } else { if (attackCountThisTurn >= 2) { if (!hasMoved) { myCurrentEnemyState = enemyState.Moving; return; } else { myCurrentEnemyState = enemyState.Ended; return; } } if (areaCharged) { //Explotar área Debug.Log("0.Area Explota"); DoAreaAttack(); areaCharged = false; attackCountThisTurn++; CallWaitCoroutine(); return; } //Como no puedo hacer traspaso, compruebo que ataques puedo hacer else { if (CheckCono()) { Debug.Log("1.Cono"); DoConeAttack(); coneUsed = true; attackCountThisTurn++; CallWaitCoroutine(); return; } //Si he usado el cono lo primero que compruebo es si puedo hacer el área if (coneUsed) { if (CheckArea()) { //Do area Debug.Log("1.5. Área"); DoAreaAttack(); attackCountThisTurn++; CallWaitCoroutine(); return; } } //No se puede poner else porque puede no usar el cono y el área o no if (CheckNormal()) { //Do físico Debug.Log("2. Físico"); DoNormalAttack(); normalAttackUsed = true; attackCountThisTurn++; CallWaitCoroutine(); return; } if (CheckArea()) { //Do Área Debug.Log("2.5 Area"); DoAreaAttack(); attackCountThisTurn++; CallWaitCoroutine(); return; } else if (normalAttackUsed) { //Do Stun Debug.Log("3. Stun"); DoStunAttack(); attackCountThisTurn++; CallWaitCoroutine(); return; } else if (!hasMoved) { Debug.Log("6. Movimiento"); currentUnitsAvailableToAttack.Clear(); //tilesToCheck.Clear(); //coneTiles.Clear(); ///Comprueba si se ha movido (si no, se mueve y repite todas las comprobaciones menos el traspaso) //Determinamos el enemigo más cercano. currentUnitsAvailableToAttack = LM.CheckEnemyPathfinding(GetComponent <EnemyUnit>()); //Si esta oculto lo quito de la lista de objetivos for (int i = 0; i < currentUnitsAvailableToAttack.Count; i++) { if (currentUnitsAvailableToAttack[i].isHidden) { currentUnitsAvailableToAttack.RemoveAt(i); i--; } } //Si no hay enemigos termina su turno if (currentUnitsAvailableToAttack.Count == 0) { myCurrentEnemyState = enemyState.Ended; return; } else if (currentUnitsAvailableToAttack.Count > 0) { if (currentUnitsAvailableToAttack.Count == 1) { base.SearchingObjectivesToAttack(); if (currentUnitsAvailableToAttack.Count == 1) { myCurrentObjective = currentUnitsAvailableToAttack[0]; myCurrentObjectiveTile = myCurrentObjective.myCurrentTile; } } //Si hay varios enemigos a la misma distancia, se queda con el que tenga más unidades adyacentes else if (currentUnitsAvailableToAttack.Count > 1) { //Ordeno la lista de posibles objetivos según el número de unidades dyacentes currentUnitsAvailableToAttack.Sort(delegate(UnitBase a, UnitBase b) { return((b.myCurrentTile.neighboursOcuppied).CompareTo(a.myCurrentTile.neighboursOcuppied)); }); //Elimino a todos los objetivos de la lista que no tengan el mayor número de enemigos adyacentes for (int i = currentUnitsAvailableToAttack.Count - 1; i > 0; i--) { if (currentUnitsAvailableToAttack[0].myCurrentTile.neighboursOcuppied > currentUnitsAvailableToAttack[i].myCurrentTile.neighboursOcuppied) { currentUnitsAvailableToAttack.RemoveAt(i); } } //Si sigue habiendo varios enemigos los ordeno segun la vida if (currentUnitsAvailableToAttack.Count > 1) { //Añado esto para eliminar a los personajes ocultos base.SearchingObjectivesToAttack(); //Ordeno la lista de posibles objetivos de menor a mayor vida actual currentUnitsAvailableToAttack.Sort(delegate(UnitBase a, UnitBase b) { return((a.currentHealth).CompareTo(b.currentHealth)); }); } myCurrentObjective = currentUnitsAvailableToAttack[0]; myCurrentObjectiveTile = myCurrentObjective.myCurrentTile; } //CAMBIAR ESTO (lm.tm) LM.TM.CalculatePathForMovementCost(myCurrentObjectiveTile.tileX, myCurrentObjectiveTile.tileZ, false); //No vale con igualar pathToObjective= LM.TM.currentPath porque entonces toma una referencia de la variable no de los valores. //Esto significa que si LM.TM.currentPath cambia de valor también lo hace pathToObjective for (int i = 0; i < LM.TM.currentPath.Count; i++) { pathToObjective.Add(LM.TM.currentPath[i]); } myCurrentEnemyState = enemyState.Moving; //myCurrentEnemyState = enemyState.Attacking; } } else { Debug.Log("Ended with: " + attackCountThisTurn + " attackCountThisTurn"); myCurrentEnemyState = enemyState.Ended; return; } } } } }
//Esta función sirve para que busque los objetivos a atacar pero sin que haga cambios en el turn state del enemigo public override void SearchingObjectivesToAttackShowActionPathFinding() { myCurrentObjective = null; myCurrentObjectiveTile = null; //Si no ha sido alertado compruebo si hay players al alcance que van a hacer que se despierte y se mueva if (!haveIBeenAlerted) { //Comprobar las unidades que hay en mi rango de acción unitsInRange = LM.TM.GetAllUnitsInRangeWithoutPathfinding(rangeOfAction, GetComponent <UnitBase>()); for (int i = 0; i < unitsInRange.Count; i++) { if (unitsInRange[i].GetComponent <PlayerUnit>()) { keepSearching = true; currentUnitsAvailableToAttack = LM.CheckEnemyPathfinding(GetComponent <EnemyUnit>()); break; } } } //Si ha sido alertado compruebo simplemente hacia donde se va a mover else { //Determinamos el enemigo más cercano. //currentUnitsAvailableToAttack = LM.TM.OnlyCheckClosestPathToPlayer(); currentUnitsAvailableToAttack = LM.CheckEnemyPathfinding(GetComponent <EnemyUnit>()); //Debug.Log("Line 435 " + currentUnitsAvailableToAttack.Count); keepSearching = true; } if (keepSearching) { if (currentUnitsAvailableToAttack.Count == 1) { myCurrentObjective = currentUnitsAvailableToAttack[0]; myCurrentObjectiveTile = myCurrentObjective.myCurrentTile; } //Si hay varios enemigos a la misma distancia, se queda con el que tenga más unidades adyacentes else if (currentUnitsAvailableToAttack.Count > 1) { //Ordeno la lista de posibles objetivos según el número de unidades dyacentes currentUnitsAvailableToAttack.Sort(delegate(UnitBase a, UnitBase b) { return((b.myCurrentTile.neighboursOcuppied).CompareTo(a.myCurrentTile.neighboursOcuppied)); }); //Elimino a todos los objetivos de la lista que no tengan el mayor número de enemigos adyacentes for (int i = currentUnitsAvailableToAttack.Count - 1; i > 0; i--) { if (currentUnitsAvailableToAttack[0].myCurrentTile.neighboursOcuppied > currentUnitsAvailableToAttack[i].myCurrentTile.neighboursOcuppied) { currentUnitsAvailableToAttack.RemoveAt(i); } } //Si sigue habiendo varios enemigos los ordeno segun la vida if (currentUnitsAvailableToAttack.Count > 1) { //Ordeno la lista de posibles objetivos de menor a mayor vida actual currentUnitsAvailableToAttack.Sort(delegate(UnitBase a, UnitBase b) { return((a.currentHealth).CompareTo(b.currentHealth)); }); } myCurrentObjective = currentUnitsAvailableToAttack[0]; myCurrentObjectiveTile = myCurrentObjective.myCurrentTile; } } keepSearching = false; }
public override void SearchingObjectivesToAttack() { myCurrentObjective = null; myCurrentObjectiveTile = null; pathToObjective.Clear(); if (isDead || hasAttacked) { myCurrentEnemyState = enemyState.Ended; return; } if (!personalHaveIBeenAlerted) { //Comprobar las unidades que hay en mi rango de acción unitsInRange = new List <UnitBase>(LM.TM.GetAllUnitsInRangeWithoutPathfinding(rangeOfAction, GetComponent <UnitBase>())); //Si esta oculto lo quito de la lista de objetivos for (int i = 0; i < unitsInRange.Count; i++) { if (unitsInRange[i].isHidden) { unitsInRange.RemoveAt(i); i--; } } //Si hay personajes del jugador en mi rango de acción paso a attacking donde me alerto y hago mi accion for (int i = 0; i < unitsInRange.Count; i++) { if (unitsInRange[i].GetComponent <PlayerUnit>()) { AlertEnemy(); myCurrentEnemyState = enemyState.Searching; return; } } //Si llega hasta aqui significa que no había personajes en rango y termina myCurrentEnemyState = enemyState.Attacking; } else if (hasMoved) { myCurrentEnemyState = enemyState.Attacking; } else { if (isCharging) { myCurrentEnemyState = enemyState.Attacking; } else { //Determinamos el enemigo más cercano. currentUnitsAvailableToAttack = new List <UnitBase>(LM.CheckEnemyPathfinding(GetComponent <EnemyUnit>())); //Si no hay enemigos termina su turno if (currentUnitsAvailableToAttack.Count == 0) { myCurrentEnemyState = enemyState.Ended; } else if (currentUnitsAvailableToAttack.Count > 0) { if (currentUnitsAvailableToAttack.Count == 1) { base.SearchingObjectivesToAttack(); if (currentUnitsAvailableToAttack.Count == 1) { myCurrentObjective = currentUnitsAvailableToAttack[0]; myCurrentObjectiveTile = myCurrentObjective.myCurrentTile; } } //Si hay varios enemigos a la misma distancia, se queda con el que tenga más unidades adyacentes else if (currentUnitsAvailableToAttack.Count > 1) { //Ordeno la lista de posibles objetivos según el número de unidades dyacentes currentUnitsAvailableToAttack.Sort(delegate(UnitBase a, UnitBase b) { return((b.myCurrentTile.neighboursOcuppied).CompareTo(a.myCurrentTile.neighboursOcuppied)); }); //Elimino a todos los objetivos de la lista que no tengan el mayor número de enemigos adyacentes for (int i = currentUnitsAvailableToAttack.Count - 1; i > 0; i--) { if (currentUnitsAvailableToAttack[0].myCurrentTile.neighboursOcuppied > currentUnitsAvailableToAttack[i].myCurrentTile.neighboursOcuppied) { currentUnitsAvailableToAttack.RemoveAt(i); } } //Si sigue habiendo varios enemigos los ordeno segun la vida if (currentUnitsAvailableToAttack.Count > 1) { //Añado esto para eliminar a los personajes ocultos base.SearchingObjectivesToAttack(); //Ordeno la lista de posibles objetivos de menor a mayor vida actual currentUnitsAvailableToAttack.Sort(delegate(UnitBase a, UnitBase b) { return((a.currentHealth).CompareTo(b.currentHealth)); }); } myCurrentObjective = currentUnitsAvailableToAttack[0]; myCurrentObjectiveTile = myCurrentObjective.myCurrentTile; } //CAMBIAR ESTO (lm.tm) LM.TM.CalculatePathForMovementCost(myCurrentObjectiveTile.tileX, myCurrentObjectiveTile.tileZ, false); //No vale con igualar pathToObjective= LM.TM.currentPath porque entonces toma una referencia de la variable no de los valores. //Esto significa que si LM.TM.currentPath cambia de valor también lo hace pathToObjective for (int i = 0; i < LM.TM.currentPath.Count; i++) { pathToObjective.Add(LM.TM.currentPath[i]); } myCurrentEnemyState = enemyState.Moving; } } } }
public override void MoveUnit() { #region EQUIVALENTE_AL_SEARCH currentUnitsAvailableToAttack.Clear(); //Determinamos el enemigo más cercano. currentUnitsAvailableToAttack = LM.CheckEnemyPathfinding(GetComponent <EnemyUnit>()); //Si no hay enemigos termina su turno if (currentUnitsAvailableToAttack.Count == 0) { myCurrentEnemyState = enemyState.Searching; hasMoved = true; return; } else if (currentUnitsAvailableToAttack.Count > 0) { if (currentUnitsAvailableToAttack.Count == 1) { myCurrentObjective = currentUnitsAvailableToAttack[0]; myCurrentObjectiveTile = myCurrentObjective.myCurrentTile; } //Si hay varios enemigos a la misma distancia else if (currentUnitsAvailableToAttack.Count > 1) { //Si sigue habiendo varios enemigos los ordeno segun la vida if (currentUnitsAvailableToAttack.Count > 1) { //Ordeno la lista de posibles objetivos de menor a mayor vida actual currentUnitsAvailableToAttack.Sort(delegate(UnitBase a, UnitBase b) { return((a.currentHealth).CompareTo(b.currentHealth)); }); } myCurrentObjective = currentUnitsAvailableToAttack[0]; myCurrentObjectiveTile = myCurrentObjective.myCurrentTile; } //CAMBIAR ESTO (lm.tm) LM.TM.CalculatePathForMovementCost(myCurrentObjectiveTile.tileX, myCurrentObjectiveTile.tileZ, false); //No vale con igualar pathToObjective= LM.TM.currentPath porque entonces toma una referencia de la variable no de los valores. //Esto significa que si LM.TM.currentPath cambia de valor también lo hace pathToObjective //ES -1 PORQUE EN EL CASO DEL DRAGÓN HAY QUE RESTAR UN TILE YA QUE ESTÁ OCUPADO POR EL PROPIO DRAGÓN!!!!!!!!!!!!!!!!!!!!!!!! for (int i = 0; i < LM.TM.currentPath.Count - offsetPathBecauseDragon; i++) { pathToObjective.Add(LM.TM.currentPath[i]); } lastTileInPathSurroundingTiles.Clear(); //Despúes de haber restado uno al path compruebo que en este último tile sigue sin estar el jugador. //En caso contrario resto otro tile al path for (int i = 0; i < LM.TM.GetSurroundingTiles(pathToObjective[pathToObjective.Count - 2], 1, true, false).Count; i++) { lastTileInPathSurroundingTiles.Add(LM.TM.GetSurroundingTiles(pathToObjective[pathToObjective.Count - 2], 1, true, false)[i]); } for (int i = 0; i < lastTileInPathSurroundingTiles.Count; i++) { if (lastTileInPathSurroundingTiles[i].unitOnTile != null && lastTileInPathSurroundingTiles[i].unitOnTile.GetComponent <PlayerUnit>()) { pathToObjective.RemoveAt(pathToObjective.Count - 2); break; } } } #endregion #region EQUIVALENTE_AL_MOVE limitantNumberOfTilesToMove = 0; movementParticle.SetActive(true); ShowActionPathFinding(false); //Como el path guarda el tile en el que esta el enemigo yel tile en el que esta el personaje del jugador resto 2. //Si esta resta se pasa del número de unidades que me puedo mover entonces solo voy a recorrer el número de tiles máximo que puedo llegar. if (pathToObjective.Count - 2 > movementUds) { limitantNumberOfTilesToMove = movementUds; } //Si esta resta por el contrario es menor o igual a movementUds significa que me voy mover el máximo o menos tiles. else { limitantNumberOfTilesToMove = pathToObjective.Count - 2; } //Compruebo la dirección en la que se mueve para girar a la unidad CheckTileDirection(pathToObjective[pathToObjective.Count - 1]); myCurrentEnemyState = enemyState.Waiting; //Actualizo info de los tiles UpdateInformationAfterMovement(pathToObjective[limitantNumberOfTilesToMove]); bossPortrait.FlipMovementToken(); StartCoroutine("MovingUnitAnimation"); #endregion }