Sample Code Battle Tactics
|
|
|
A* Algorithm
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
public class Astar : MonoBehaviour
{
Nodes s;
public List AstarPathfinding(Nodes start, Nodes goal, List playerGraph)
{
s = start;
List closedset = new List(); // The set of nodes already evaluated.
List openset = new List(); openset.Add(start); // The set of tentative nodes to be evaluated, initially containing the start node
List path = new List();
start.m_gScore = 0;
start.m_hScore = Distance(start.m_position , goal.m_position);
while(openset.Count != 0)
{
//Debug.Log("AStar::openset.Count != 0");
Nodes currentCordinate = openset[0]; //= the node in openset having the lowest f_score[] value
//Opeset doesnt have a beigin
openset.Remove(openset[0]);
if( currentCordinate == goal)
{
path = reconstruct_path(goal);
return path;
}
closedset.Add(currentCordinate);
// for each neighbor in neighbor_nodes(current)
for(int i = 0; i < currentCordinate.m_neighbor.Count; i++ )
{
// if neighbor in closedset
Nodes neighbor = currentCordinate.m_neighbor[i];
if(neighbor.m_active == false)
continue;
if(neighbor.m_inUse == true)
continue;
if(Find(neighbor,closedset))
{
continue;
}
//tentative_g_score := g_score[current] + dist_between(current,neighbor)
float tempG = currentCordinate.m_gScore + Distance(currentCordinate.m_position , neighbor.m_position);
// if neighbor not in openset or tentative_g_score <= g_score[neighbor]
bool neighborInOpenSet = Find(neighbor,openset);
if( !neighborInOpenSet || tempG <= neighbor.m_gScore)
{
neighbor.m_prevNode = currentCordinate; //came_from[neighbor] := current
neighbor.m_gScore = tempG; // g_score[neighbor] := tentative_g_score
neighbor.m_fScore = tempG + Distance(neighbor.m_position, goal.m_position ); //f_score[neighbor] := g_score[neighbor] + heuristic_cost_estimate(neighbor, goal)
if(!neighborInOpenSet) //if neighbor not in openset
{
//Debug.Log("AStar::Adding to openSet");
openset.Add(neighbor); // add neighbor to openset
}
}
}
//end adj
//sort openset based on smallest f value
Sort(openset);
} // end while
return null;
}
List reconstruct_path(Nodes goal)
{
List temp = new List();
while(goal != null)//|| temp.Count < 5)
{
//Debug.Log("Reconstruct Path:: goal != null");
temp.Add(goal);
if(goal.m_prevNode != null)
{
if(goal.m_prevNode == s)
{
temp.Reverse();
return temp;
}
else
{
goal = goal.m_prevNode; // needs work
}
}
else
{
//Debug.Log("Reconstruct Path:: goal == null");
goal = null;
}
}
temp.Reverse();
return temp; //reverse
}
float Distance(Vector3 point1, Vector3 point2)
{
return Vector3.Distance(point1, point2);
}
bool Find(Nodes index, List list )
{
for(int i = 0; i < list.Count; i++ )
{
if(index == list[i])
{
return true;
}
}
return false;
}
void Sort(List list)
{
if(list.Count <= 0)
return;
float minFscore = list[0].m_fScore;
int minCordinate = 0;
for(int i = 1; i < list.Count ; i ++ )
{
if(minFscore > list[i].m_fScore)
{
minFscore = list[i].m_fScore;
minCordinate = i;
}
}
//No built in Swap Functio
if(minCordinate > 0)
Swap(minCordinate, list);
}
void Swap(int to, List list)
{
Nodes temp = list[to];
list[to] = list[0];
list[0] = temp;
}
}
Nodes
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
public class Nodes : MonoBehaviour
{
static Transform s_parent;
public Vector2 m_nodeCoordinate;
public Nodes m_prevNode;
public Vector3 m_position;
public float m_gScore;
public float m_hScore;
public float m_fScore;
public bool m_walkable;
public bool m_isCenter;
public bool m_active;
public bool m_inUse;
public List m_neighbor;
public void Init(Vector3 pos, Vector2 myNum, float width, float depth, bool walkable)
{
s_parent = transform.parent;
m_nodeCoordinate = myNum;
m_neighbor = new List();
m_position = pos;
m_active = false;
m_inUse = false;
}
public void AddNeighbor(Nodes node)
{
m_neighbor.Add(node);
}
static public Nodes MakeNode(Nodes toCopy)
{
GameObject FUCKYOUUNITY = (GameObject)Instantiate(toCopy.gameObject, toCopy.m_position, toCopy.transform.rotation);
Nodes toReturn = FUCKYOUUNITY.GetComponent();
toReturn.m_fScore = toCopy.m_fScore;
toReturn.m_prevNode = toCopy.m_prevNode;
toReturn.m_position = toCopy.m_position;
toReturn.m_gScore = toCopy.m_gScore;
toReturn.m_hScore = toCopy.m_hScore;
toReturn.m_walkable = toCopy.m_walkable;
toReturn.m_neighbor = toCopy.m_neighbor;
return toReturn;
}
static public void ResetNeighbors(List playerNodes)
{
for(int i = 0; i < playerNodes.Count; ++i)
{
for(int j = 0; j < playerNodes[i].m_neighbor.Count; ++j)
{
playerNodes[i].m_neighbor[j].m_active = Find(playerNodes, playerNodes[i].m_neighbor[j]);
}
}
}
public static bool Find(List list, Nodes needle)
{
if(!needle)
return false;
foreach(Nodes node in list)
{
if(node.m_nodeCoordinate == needle.m_nodeCoordinate)
{
return true;
}
}
return false;
}
public static void Show(List toShow)
{
foreach(Nodes node in toShow)
{
if(node.m_isCenter)
continue;
node.renderer.enabled = true;
node.collider.enabled = true;
}
}
public static void Hide(List toHide)
{
foreach(Nodes node in toHide)
{
if(node.m_isCenter)
node.m_isCenter = false;
node.renderer.enabled = false;
node.collider.enabled = false;
node.m_active = false;
}
}
public static Nodes FindCenter(List list)
{
foreach(Nodes node in list)
{
if(node.m_isCenter)
return node;
}
return null;
}
public void ResetParent()
{
transform.parent = s_parent.transform;
}
}
Graph
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
public class Graph : MonoBehaviour
{
public Nodes[ , ] m_nodes;
public static Nodes[ , ] s_nodes;
public float m_tileSize = 1;
public float m_levelWidth = 10;
public float m_levelHeight = 10;
//public float s_levelWidth;
public float s_levelHeight;
public int xMin, zMin;
void Awake()
{
f_CreateGraph();
}
private void f_CreateGraph()
{
xMin = (int)(-gameObject.collider.bounds.extents.x + 0.5f);
zMin = (int)(-gameObject.collider.bounds.extents.z + 0.5f);
m_levelWidth *= m_tileSize ;
m_levelHeight *= m_tileSize ;
IntializeNodes();
s_nodes = m_nodes;
s_levelHeight = 10;
}
void IntializeNodes()
{
GameObject graphNodes = new GameObject();
graphNodes.name = "Graph Nodes";
graphNodes.tag = "MasterNode";
m_nodes = new Nodes[(int)(m_levelWidth + 1), (int)(m_levelHeight + 1)];
int maxNumOfNeighibors = 4;
int xIdx, zIdx;
xIdx = 0;
zIdx = 0;
//Apply the nodes
int nodeNum = 0;
for (int x = xMin; x <(int)( m_levelWidth/2 + 1); x++)
{
for (int z = zMin; z < (int)( m_levelHeight/2 + 1); z++)
{
//GameObject sphere = GameObject.CreatePrimitive(PrimitiveType.Sphere);//
GameObject sphere;// = new GameObject("Sphere");
sphere = (GameObject)Instantiate(Resources.Load("NodesObj"));
sphere.AddComponent();
sphere.transform.parent = graphNodes.transform;
sphere.renderer.enabled = false;
sphere.collider.enabled = false;
sphere.name = string.Format("Node:{0:00}", nodeNum++);
//print ("X: " + xIdx + " Z: " + zIdx);
m_nodes[xIdx,zIdx]= sphere.GetComponent();
sphere.transform.position = new Vector3(x * m_tileSize - 0.5f,0 , z * m_tileSize - 0.5f);
m_nodes[xIdx,zIdx].Init(sphere.transform.position, new Vector2(x , z), m_levelWidth, m_levelHeight, true );
zIdx++;
}
zIdx = 0;
xIdx++;
}
//Apply the Neighbors
for (int x = 0; x < (int)(m_levelWidth); x++)
{
for (int z = 0; z < (int)(m_levelHeight); z++)
{
Nodes[] neighbors = new Nodes[maxNumOfNeighibors];
//top neighbor
if(z < (int)m_levelHeight - 1)
neighbors[0] = m_nodes[x, z + 1];
//bottom neighbor
if(z > 0)
neighbors[1] = m_nodes[x, z - 1];
//right neighbor
if(x < (int)m_levelWidth - 1)
neighbors[2] = m_nodes[x + 1, z];
//left neighbor
if(x > 0)
neighbors[3] = m_nodes[x - 1, z];
//Add the neigbors that are not null
for (int k = 0; k < maxNumOfNeighibors; k++)
{
if (neighbors[k] == null )
continue;
m_nodes[x, z].AddNeighbor(neighbors[k]);
}
}
}
}
public void SetPlayerGrid(PlayerControl player)
{
Vector3 startingPos = player.transform.position;
startingPos.z += player.AP;
float startingX = startingPos.x;
int maxObjThisItor = 1;
bool invert = false;
for(int i = 0; i >= 0; )
{
for(int j = 0; j < maxObjThisItor; ++j)
{
Nodes STUPIDUNITY = FindCoord(startingPos);
if(!STUPIDUNITY)
continue;
ChangeNodeColor(Color.green, STUPIDUNITY);
player.m_nodes.Add(STUPIDUNITY);
STUPIDUNITY.m_active = true;
if(startingPos == player.transform.position)
{
STUPIDUNITY.m_isCenter = true;
}
startingPos.x += 1;
}
if(i >= player.AP)
invert = true;
if(!invert)
{
++i;
maxObjThisItor += 2;
startingPos.x = startingX - 1;
startingX = startingPos.x;
}
else
{
--i;
maxObjThisItor -= 2;
startingPos.x = startingX + 1;
startingX = startingPos.x;
}
startingPos.z -= 1;
}
}
public void HideGrid(PlayerControl player)
{
foreach(Nodes node in player.m_nodes)
{
node.m_active = false;
}
}
void ChangeNodeColor(Color color, Nodes node)
{
//node.renderer.enabled = true;
//node.collider.enabled = true;
node.renderer.material.color = color;
}
public Nodes FindCoord(Vector2 coord)
{
for(int x = 0; x < m_levelWidth; ++x)
for(int y = 0; y < m_levelHeight; ++y)
if(m_nodes[x,y].m_nodeCoordinate == coord)
return m_nodes[x,y];
return null;
}
public Nodes FindCoord(Vector3 pos)
{
for(int x = 0; x < m_levelWidth; ++x)
for(int y = 0; y < m_levelHeight; ++y)
if(Vector3.Distance(m_nodes[x,y].m_position, pos) <= .75f)
return m_nodes[x,y];
return null;
}
void OnDrawGizmos()
{
//loop throgh
//Gizmos.color = Color.red;
//Gizmos.DrawSphere(ADPosition, 0.5f)
}
}