public override bool Action(GoapPlan _currentPlan, GoapWorldstate _worldState) { GameObject goalNode = null; //if the path has not already been made if (_currentPlan.plannedPath.Value == null || _currentPlan.plannedPath.Key != actionName) { KeyValuePair<string, List<GameObject>> tempPath = new KeyValuePair<string, List<GameObject>>(actionName, _currentPlan.plannedPath.Value); _currentPlan.plannedPath = tempPath; TruncOct enemyTroct= core.actor.targetEnemy.currentTrOct.GetComponent<TruncOct>(); List<TruncOct> inLineTrocts = new List<TruncOct>(); //List all trocts leading from enemy location //loop through all faces of the troct for (int i = 0; i < enemyTroct.Faces.Count; i++) { //if the current face has no connection, continue to the next face. if (enemyTroct.connections[i] != TruncOct.connectionState.Connected) { continue; } else //else it it connected and should be pushed as far as it can go outwards { //get the next troct TruncOct newTroct = _worldState.topology[enemyTroct.connectionObjects[i]].GetComponent<TruncOct>(); List<TruncOct> direction = new List<TruncOct>(); direction.Add(newTroct); inLineTrocts.AddRange (TroctsInDirection(direction, i, newTroct, _worldState)); } } //find the closest one that is avaliable float closestDistance = float.MaxValue; TruncOct closestTroct; for (int i = 0; i < inLineTrocts.Count; i++) { float tempDist = Vector3.Distance(core.actor.currentTrOct.transform.position, inLineTrocts[i].transform.position); if (tempDist < closestDistance) { closestDistance = tempDist; closestTroct = inLineTrocts[i]; goalNode = closestTroct.gameObject; } } //now plot a route to A* pathfind to _currentPlan.plotRoute(core.actor, core.actor.currentTrOct, goalNode); } //try to follow the A* path return ProceedAlongPath(_currentPlan); }
public override bool Action(GoapPlan _currentPlan, GoapWorldstate _worldState) { GameObject goalNode = null; //if there is not currently a path, plot a course towards a random undiscovered area if (_currentPlan.plannedPath.Value == null) { //compile a list of all trocts concealed by the fow List<GameObject> undiscoveredTrocts = new List<GameObject>(); foreach (GameObject _trOctObj in _worldState.topology) { if (_trOctObj.GetComponent<TruncOct>().inFow) { undiscoveredTrocts.Add(_trOctObj); } } //find the one with the largest combined distance from all allies float biggestDistance = 0f; GameObject furthestTroct; for (int i = 0; i < undiscoveredTrocts.Count; i++) { float totalDistance = 0f; for (int j = 0; j < _worldState.allies.Count; j++) { totalDistance += Vector3.Distance(undiscoveredTrocts[i].transform.position, _worldState.allies[j].currentTrOct.transform.position); } if (totalDistance > biggestDistance) { furthestTroct = undiscoveredTrocts[i]; biggestDistance = totalDistance; //this will be the goal TrOct goalNode = furthestTroct; } } //plot a route using the central A* plotter through the current plan _currentPlan.plotRoute(core.actor, core.actor.currentTrOct, goalNode); } // attempt to follow the path that was either preexisting or was just generated return ProceedAlongPath(_currentPlan); }
/// <summary> /// Carry out the GOAP action, in this case, move to a safer area. /// </summary> /// <param name="_currentPlan">Current plan.</param> /// <param name="_worldState">World state.</param> public override bool Action(GoapPlan _currentPlan, GoapWorldstate _worldState) { GameObject goalNode = null; //if the path has not already been made if (_currentPlan.plannedPath.Value == null || _currentPlan.plannedPath.Key != actionName) { KeyValuePair<string, List<GameObject>> tempPath = new KeyValuePair<string, List<GameObject>>(actionName, _currentPlan.plannedPath.Value); _currentPlan.plannedPath = tempPath; List<TruncOct> inLineTrocts = new List<TruncOct>(); //compile a list of trocts from all visible enemies for (int i = 0; i < _worldState.enemyData.Count; i++) { TruncOct enemyTroct = _worldState.enemyData[i].enemyLocation; //List all trocts leading from enemy location //loop through all faces of the troct for (int j = 0; j < enemyTroct.Faces.Count; j++) { //if the current face has no connection, continue to the next face. if (enemyTroct.connections[j] != TruncOct.connectionState.Connected) { continue; } else //else it it connected and should be pushed as far as it can go outwards { //get the next troct TruncOct newTroct = _worldState.topology[enemyTroct.connectionObjects[j]].GetComponent<TruncOct>(); List<TruncOct> direction = new List<TruncOct>(); direction.Add(newTroct); inLineTrocts.AddRange (TroctsInDirection(direction, j, newTroct, _worldState)); } } } //find the closest troct in line that is not in line with the enemy List<TruncOct> inLineSelf = new List<TruncOct>(); TruncOct thisTroct = core.actor.currentTrOct.GetComponent<TruncOct>(); //loop through all faces of the troct for (int i = 0; i < thisTroct.Faces.Count; i++) { //if the current face has no connection, continue to the next face. if (thisTroct.connections[i] != TruncOct.connectionState.Connected) { continue; } else //else it it connected and should be pushed as far as it can go outwards { //get the next troct TruncOct newTroct = _worldState.topology[thisTroct.connectionObjects[i]].GetComponent<TruncOct>(); List<TruncOct> direction = new List<TruncOct>(); direction.Add(newTroct); inLineSelf.AddRange (TroctsInDirection(direction, i, newTroct, _worldState)); } } TruncOct targetTroct = null; //compare to find a troct that is not inline with an enemy for (int i = 0; i < inLineSelf.Count; i++) { if (!inLineTrocts.Contains(inLineSelf[i])) { targetTroct = inLineSelf[i]; break; } } //if a new location still needs to be found if (targetTroct == null) { //else find a close troct that is not in line List<TruncOct> closeTrocts = new List<TruncOct>(); foreach(GameObject _tObject in GameManager.instance.allTrocts) { if (Vector3.Distance(core.actor.transform.position, _tObject.transform.position) <= (core.actor.viewDistance / 1.5f)) { if (!inLineTrocts.Contains(_tObject.GetComponent<TruncOct>())) { targetTroct = _tObject.GetComponent<TruncOct>(); } } } //if a close one cant be found, just generate a random one by force, we must move! while ((!inLineTrocts.Contains(targetTroct) && targetTroct == null) || targetTroct == null) { TruncOct rand = GameManager.instance.allTrocts[Random.Range(0, GameManager.instance.allTrocts.Count)].GetComponent<TruncOct>(); if (!inLineTrocts.Contains(rand)) { targetTroct = rand; break; } } } goalNode = targetTroct.gameObject; //now plot a route to A* pathfind to _currentPlan.plotRoute(core.actor, core.actor.currentTrOct, goalNode); } //try to follow the A* path return ProceedAlongPath(_currentPlan); }