void DrawFieldOfView() { int stepCount = Mathf.RoundToInt(viewAngle * meshResolution); float stepAngleSize = viewAngle / stepCount; List<Vector3> viewPoints = new List<Vector3>(); ViewCastInfo oldViewCast = new ViewCastInfo(); for (int i = 0; i <= stepCount; i++) { float angle = transform.eulerAngles.y - viewAngle / 2 + stepAngleSize * i; ViewCastInfo newViewCast = ViewCast(angle); if (i > 0) { bool edgeDstThresholdExceeded = Mathf.Abs(oldViewCast.dst - newViewCast.dst) > edgeDstThreshold; if (oldViewCast.hit != newViewCast.hit || (oldViewCast.hit && newViewCast.hit && edgeDstThresholdExceeded)) { EdgeInfo edge = FindEdge(oldViewCast, newViewCast); if (edge.pointA != Vector3.zero) { viewPoints.Add(edge.pointA); } if (edge.pointB != Vector3.zero) { viewPoints.Add(edge.pointB); } } } viewPoints.Add(newViewCast.point); oldViewCast = newViewCast; } int vertexCount = viewPoints.Count + 1; Vector3[] vertices = new Vector3[vertexCount]; int[] triangles = new int[(vertexCount - 2) * 3]; vertices[0] = Vector3.zero; for (int i = 0; i < vertexCount - 1; i++) { vertices[i + 1] = transform.InverseTransformPoint(viewPoints[i]); if (i < vertexCount - 2) { triangles[i * 3] = 0; triangles[i * 3 + 1] = i + 1; triangles[i * 3 + 2] = i + 2; } } viewMesh.Clear(); viewMesh.vertices = vertices; viewMesh.triangles = triangles; viewMesh.RecalculateNormals(); viewMesh.RecalculateBounds(); }
EdgeInfo FindEdge(ViewCastInfo minViewCast, ViewCastInfo maxViewCast) { float minAngle = minViewCast.angle; float maxAngle = maxViewCast.angle; Vector3 minPoint = Vector3.zero; Vector3 maxPoint = Vector3.zero; for (int i = 0; i < edgeResolveIterations; i++) { float angle = (minAngle + maxAngle) / 2; ViewCastInfo newViewCast = ViewCast (angle); bool edgeDstThresholdExceeded = Mathf.Abs (minViewCast.dst - newViewCast.dst) > edgeDstThreshold; if (newViewCast.hit == minViewCast.hit && !edgeDstThresholdExceeded) { minAngle = angle; minPoint = newViewCast.point; } else { maxAngle = angle; maxPoint = newViewCast.point; } } return new EdgeInfo (minPoint, maxPoint); }
/// <summary> /// Draw visualization cone /// </summary> void DrawFieldOfView() { int stepCount = Mathf.RoundToInt(ViewAngle * MeshResolution); // Number of rays float stepAngleSize = ViewAngle / stepCount; // Degrees per ray List <Vector3> viewPoints = new List <Vector3>(); // Vertexes points used to draw mesh ViewCastInfo oldViewCast = new ViewCastInfo(); // Previous cast, used to check if there is a collide difference to find edge // Cast rays for (int i = 0; i < stepCount; ++i) { float angle = transform.eulerAngles.y - ViewAngle / 2 + stepAngleSize * i; ViewCastInfo newViewCast = ViewCast(angle); // Check if edge between old cast and new one if (i > 0) { //if (oldViewCast.Hit != newViewCast.Hit) bool tooFar = Mathf.Abs(oldViewCast.Distance - newViewCast.Distance) > EdgeDistanceThreshold; if (oldViewCast.Hit != newViewCast.Hit || (oldViewCast.Hit && newViewCast.Hit && tooFar)) { EdgeInfo edge = FindEdge(oldViewCast, newViewCast); if (edge.pointA != Vector3.zero) { viewPoints.Add(edge.pointA); } if (edge.pointB != Vector3.zero) { viewPoints.Add(edge.pointB); } if (drawGizmo) { Debug.DrawLine(transform.position, viewPoints.Last(), Color.yellow); } } } viewPoints.Add(newViewCast.Point); oldViewCast = newViewCast; if (drawGizmo) { Debug.DrawLine(transform.position, newViewCast.Point); } } // Initialize mesh int vertexCount = viewPoints.Count + 1; Vector3[] vertices = new Vector3[vertexCount]; int[] triangles = new int[(vertexCount - 2) * 3]; // Create mesh data vertices[0] = Vector3.zero; for (int i = 0; i < vertexCount - 1; ++i) { vertices[i + 1] = transform.InverseTransformPoint(viewPoints[i]); if (i < vertexCount - 2) { triangles[i * 3] = 0; triangles[i * 3 + 1] = i + 1; triangles[i * 3 + 2] = i + 2; } } }
void DrawFieldOfView() { //number of rays to cast per degree int stepCount = Mathf.RoundToInt(viewAngle * meshResolution); //how many degrees in each steps float stepAngles = viewAngle / stepCount; //List of all the points the viewcast hits to construct mesh List <Vector3> viewPoints = new List <Vector3>(); //Edge: if previews viewcast hit obstacle ViewCastInfo oldViewCast = new ViewCastInfo(); for (int i = 0; i <= stepCount; i++) { //rotate curront rotation back to the left most angle, then rotate stepwise clockwise to right moust viewangle float angle = transform.eulerAngles.y - viewAngle / 2 + stepAngles * i; ViewCastInfo newViewCast = ViewCast(angle); //first iteration the oldviewcast is not set if (i > 0) { //value between two hits bool edgeDstThresholdExceeded = Mathf.Abs(oldViewCast.dst - newViewCast.dst) > edgeDistanceThreshold; //oldviewcast and the new one didnt or the old one didnt and the new one did if (oldViewCast.hit != newViewCast.hit || (oldViewCast.hit && newViewCast.hit && edgeDstThresholdExceeded)) { //find the edge EdgeInfo edge = FindEdge(oldViewCast, newViewCast); //if the dont have the default value if (edge.pointA != Vector3.zero) { viewPoints.Add(edge.pointA); } if (edge.pointB != Vector3.zero) { viewPoints.Add(edge.pointB); } } } viewPoints.Add(newViewCast.point); oldViewCast = newViewCast; Debug.DrawLine(transform.position, transform.position + DirFromAngle(angle, true) * viewRadius, Color.green); } //length of array is vertices - 2 * 3, vertices for all viewpoints + transform and 3 to generate a triangle from each corner int vertexCount = viewPoints.Count + 1; //unity generates of each 3 pair position in the array a trianglemesh Vector3[] vertices = new Vector3[vertexCount]; int[] triangles = new int[(vertexCount - 2) * 3]; //viewmesh is child of character obj, so all positions of vertices need to be localspace(relative to character) //first vertex = transform position = localspace = vector3.zero vertices[0] = Vector3.zero; for (int i = 0; i < vertexCount - 1; i++) { //so it wont go out of bounds if (i < vertexCount - 2) { //always go back to sourcepoint, convert viewpoints to localspace vertices[i + 1] = transform.InverseTransformPoint(viewPoints[i]); //triangle array, first vertex of each triangle triangles[i * 3] = 0; //next vertex of the triangle triangles[i * 3 + 1] = i + 1; //last vertex of the triangle triangles[i * 3 + 2] = i + 2; } } ViewMesh.Clear(); ViewMesh.vertices = vertices; ViewMesh.triangles = triangles; ViewMesh.RecalculateNormals(); }
void DrawFieldOfView() { //number of rays int stepCount = Mathf.RoundToInt(viewAngle * meshResolution); //for example if we want look at 3 degrees (viewAngle) and we rays 2 times at one degree (meshResolution) //we have 6 of all steps=rays (stepCount) and 1/2 rays for degree (stepAngleSize) float stepAngleSize = viewAngle / stepCount; List <Vector2> viewPoints = new List <Vector2> (); //to find edge we need to have 2 rays at same moment ViewCastInfo oldViewCast = new ViewCastInfo(); //iterations for all steps for (int i = 0; i <= stepCount; i++) { //ray at angle float angle = transform.eulerAngles.z - viewAngle / 2 + stepAngleSize * i; ViewCastInfo newViewCast = ViewCast(angle); if (i > 0) { //secures when there is more than one edge //for example two rays one after one hit different obstacle bool edgeDistanceThresholdExceeded = Mathf.Abs(oldViewCast.distance - newViewCast.distance) > edgeDistanceThreshold; //checking if ray is an edge (first ray in row which hits smth or last) if (oldViewCast.hit != newViewCast.hit || (oldViewCast.hit && newViewCast.hit && edgeDistanceThresholdExceeded)) { //finding more accurate edge (deep iteration) EdgeInfo edge = FindEdge(oldViewCast, newViewCast); if (edge.pointA != Vector2.zero) { viewPoints.Add(edge.pointA); } if (edge.pointB != Vector2.zero) { viewPoints.Add(edge.pointB); } } } viewPoints.Add(newViewCast.point); oldViewCast = newViewCast; } //truly drawing part of fun //it draws triangles which go from one end of ray to source, next to end of second ray and back to end of first ray //init of vertex and triangles int vertexCount = viewPoints.Count + 1; Vector3[] vertices = new Vector3[vertexCount]; int [] triangles = new int[(vertexCount - 2) * 3]; vertices [0] = Vector3.zero; for (int i = 0; i < vertexCount - 1; i++) { vertices [i + 1] = transform.InverseTransformPoint(viewPoints [i]); //setting vertexes for each triangle if (i < vertexCount - 2) { triangles [i * 3] = 0; triangles [i * 3 + 1] = i + 1; triangles [i * 3 + 2] = i + 2; } } //setting mesh which will be drawn viewMesh.Clear(); viewMesh.vertices = vertices; viewMesh.triangles = triangles; viewMesh.RecalculateNormals(); }
void DrawFieldOfView() { int stepCount = Mathf.RoundToInt(viewAngle * meshResolution); float stepAngleSize = viewAngle / stepCount; List <Vector3> viewPoints = new List <Vector3> (); ViewCastInfo oldViewCast = new ViewCastInfo(); for (int i = 0; i <= stepCount; i++) { float angle = transform.eulerAngles.y - viewAngle / 2 + stepAngleSize * i; ViewCastInfo newViewCast = ViewCast(angle); if (i > 0) { bool edgeDstThresholdExceeded = Mathf.Abs(oldViewCast.dst - newViewCast.dst) > edgeDstThreshold; if (oldViewCast.hit != newViewCast.hit || (oldViewCast.hit && newViewCast.hit && edgeDstThresholdExceeded)) { EdgeInfo edge = FindEdge(oldViewCast, newViewCast); if (edge.pointA != Vector3.zero) { viewPoints.Add(edge.pointA); } if (edge.pointB != Vector3.zero) { viewPoints.Add(edge.pointB); } } } viewPoints.Add(newViewCast.point); oldViewCast = newViewCast; } int vertexCount = viewPoints.Count + 1; Vector3[] vertices = new Vector3[vertexCount]; int[] triangles = new int[(vertexCount - 2) * 3]; Vector2[] uvs = new Vector2[vertexCount]; vertices [0] = Vector3.zero; uvs[0] = Vector2.one * alphaShift; for (int i = 0; i < vertexCount - 1; i++) { vertices [i + 1] = transform.InverseTransformPoint(viewPoints [i]) + Vector3.forward * maskCutawayDst; uvs[i + 1] = (Vector2.one * vertices[i + 1].magnitude / viewRadius) + Vector2.one * alphaShift; if (i < vertexCount - 2) { triangles [i * 3] = 0; triangles [i * 3 + 1] = i + 1; triangles [i * 3 + 2] = i + 2; } } viewMesh.Clear(); viewMesh.vertices = vertices; viewMesh.triangles = triangles; viewMesh.uv = uvs; viewMesh.RecalculateNormals(); }
void LateUpdate() {//draw field of view Vector2 direction; //Direction Set up if (agent == null) { direction = (Vector2)(Quaternion.Euler(0, 0, transform.eulerAngles.z) * Vector2.down); //Debug.Log(transform.eulerAngles.z); direction_tmp = direction; } else { if ((Vector2)agent.velocity.normalized == Vector2.zero) { //direction_tmp = Vector2.up; direction_tmp = transform.GetComponent <GuardIAController>().stationaryDirection; direction = direction_tmp; } else { direction = agent.velocity.normalized; direction_tmp = direction; } } int stepCount = Mathf.RoundToInt(viewAngle * meshResolution); float stepAngleSize = viewAngle / stepCount; viewPoints.Clear(); ViewCastInfo oldViewCast = new ViewCastInfo(); for (int i = 0; i <= stepCount; i++) { //float angle = -transform.eulerAngles.z - viewAngle / 2 + stepAngleSize * i; float angle; if (direction.x < 0) { angle = -Vector2.Angle(Vector2.up, direction) - viewAngle / 2 + stepAngleSize * i; } else { angle = Vector2.Angle(Vector2.up, direction) - viewAngle / 2 + stepAngleSize * i; } ViewCastInfo newViewCast = ViewCast(angle); if (i > 0) { bool edgeDstThresholdExceeded = Mathf.Abs(oldViewCast.dst - newViewCast.dst) > edgeDstThreshold; if (oldViewCast.hit != newViewCast.hit || (oldViewCast.hit && newViewCast.hit && edgeDstThresholdExceeded)) { FindEdge(oldViewCast, newViewCast, out edgeMinPoint, out edgeMaxPoint); if (edgeMinPoint != Vector3.zero) { viewPoints.Add(edgeMinPoint); } if (edgeMaxPoint != Vector3.zero) { viewPoints.Add(edgeMaxPoint); } } } viewPoints.Add(newViewCast.point); oldViewCast = newViewCast; } int vertexCount = viewPoints.Count + 1; Vector3[] vertices = new Vector3[vertexCount]; int[] triangles = new int[(vertexCount - 2) * 3]; vertices[0] = Vector3.zero; for (int i = 0; i < vertexCount - 1; i++) { vertices[i + 1] = transform.InverseTransformPoint(viewPoints[i]) + Vector3.up * maskCutawayDst; if (i < vertexCount - 2) { triangles[i * 3] = 0; triangles[i * 3 + 1] = i + 1; triangles[i * 3 + 2] = i + 2; } } viewMesh.Clear(); viewMesh.vertices = vertices; viewMesh.triangles = triangles; viewMesh.RecalculateNormals(); FindVisiblePlayer(); }
private void DrawFieldOfView() { if (viewMesh == null) { return; } int stepCount = (int)(viewAngle * meshResolution); float stepAngleSize = viewAngle / stepCount; List <Vector3> viewPoints = new List <Vector3>(); ViewCastInfo oldViewCast = new ViewCastInfo(); for (int i = 0; i <= stepCount; i++) { float angle = transform.eulerAngles.y - viewAngle / 2 + stepAngleSize * i; ViewCastInfo newViewCast = ViewCast(angle); if (i > 0) { bool edgeDistanceThresholdExceeded = Mathf.Abs(oldViewCast.distance - newViewCast.distance) > edgeDistanceThreshold; if (oldViewCast.hit != newViewCast.hit || (oldViewCast.hit && newViewCast.hit && edgeDistanceThresholdExceeded)) { EdgeInfo edge = FindEdge(oldViewCast, newViewCast); if (edge.pointA != Vector3.zero) { viewPoints.Add(edge.pointA); } if (edge.pointB != Vector3.zero) { viewPoints.Add(edge.pointB); } } } viewPoints.Add(newViewCast.point); oldViewCast = newViewCast; } int vertexCount = viewPoints.Count + 1; Vector3[] verticies = new Vector3[vertexCount]; int[] triangles = new int[(vertexCount - 2) * 3]; verticies[0] = Vector3.zero; for (int i = 0; i < vertexCount - 1; i++) { Vector3 direction = (viewPoints[i] - transform.position).normalized; verticies[i + 1] = transform.InverseTransformPoint(viewPoints[i]) + direction * maskCutawayDistance; if (i < vertexCount - 2) { triangles[i * 3] = 0; triangles[i * 3 + 1] = i + 1; triangles[i * 3 + 2] = i + 2; } } viewMesh.Clear(); viewMesh.vertices = verticies; viewMesh.triangles = triangles; viewMesh.RecalculateNormals(); }
internal void DrawFieldOfView() { int stepCount = Mathf.RoundToInt(viewAngle * meshResolution); float stepAngleSize = viewAngle / stepCount; List <ViewCastInfo> viewPoints = new List <ViewCastInfo> (); ViewCastInfo oldViewCast = new ViewCastInfo(); for (int i = 0; i <= stepCount; i++) { float angle = transform.eulerAngles.z - viewAngle / 2 + stepAngleSize * i; //Debug.DrawLine(transform.position, transform.position + DirFromAngle(angle, true) * viewRadius, Color.red); ViewCastInfo newViewCast = ViewCast(angle); if (i > 0) { bool edgeDstThresholdExceeded = Mathf.Abs(oldViewCast.dst - newViewCast.dst) > edgeDstThreshold; if (oldViewCast.hit != newViewCast.hit || (oldViewCast.hit && newViewCast.hit && edgeDstThresholdExceeded)) { EdgeInfo edge = FindEdge(oldViewCast, newViewCast); if (edge.pointA.point != Vector3.zero) { viewPoints.Add(edge.pointA); } if (edge.pointB.point != Vector3.zero) { viewPoints.Add(edge.pointB); } } } viewPoints.Add(newViewCast); oldViewCast = newViewCast; } int vertexCount = viewPoints.Count + 1; Vector3[] vertices = new Vector3[vertexCount]; int[] triangles = new int[(vertexCount - 2) * 3]; vertices [0] = Vector3.zero; for (int i = 0; i < vertexCount - 1; i++) { vertices[i + 1] = transform.InverseTransformPoint(viewPoints[i].point); //Debug.DrawLine(viewPoints[i].point, viewPoints[i].normal); if (vertices[i + 1].y <= eyesHeight && viewPoints[i].normal.y > 0) { vertices[i + 1] += Vector3.down * edgeRevealDst; } if (viewPoints[i].normal.x != 0) { //Debug.Log(Vector3.Angle(vertices[i + 1], viewPoints[i].normal)); //vertices[i + 1] -= (Vector3)viewPoints[i].normal * Mathf.Lerp(edgeRevealDst, 0f, Vector3.Angle(viewPoints[i].normal, -vertices[i + 1]) / 90); vertices[i + 1] -= Vector3.right * viewPoints[i].normal.x * edgeRevealDst; } //vertices[i + 1] = transform.InverseTransformPoint(viewPoints[i]); if (i < vertexCount - 2) { triangles [i * 3] = 0; triangles [i * 3 + 1] = i + 1; triangles [i * 3 + 2] = i + 2; } } viewMesh.Clear(); viewMesh.vertices = vertices; viewMesh.triangles = triangles; viewMesh.RecalculateNormals(); }
void DrawFieldOfView() { int stepCount = Mathf.RoundToInt(ViewAngle * MeshResolution); float stepAngleSize = ViewAngle / stepCount; ViewCastInfo oldViewCast = new ViewCastInfo(); for (int i = 0; i <= stepCount; i++) { float angle = transform.eulerAngles.z - ViewAngle / 2 + stepAngleSize * i; ViewCastInfo newViewCast = ViewCast(angle); if (i > 0) { bool edgeDstThreshholdExceeded = Mathf.Abs(oldViewCast.dst - newViewCast.dst) > EdgeDistanceThreshhold; if (oldViewCast.hit != newViewCast.hit || (oldViewCast.hit && edgeDstThreshholdExceeded)) { EdgeInfo edge = FindEdge(oldViewCast, newViewCast); if (edge.pointA != Vector3.zero) { viewPoints.Add(edge.pointA); } if (edge.pointB != Vector3.zero) { viewPoints.Add(edge.pointB); } } } viewPoints.Add(newViewCast.point); oldViewCast = newViewCast; } int pointCount = viewPoints.Count + 1; if (pointCount > mMeshBuffer.bufferSize) { mMeshBuffer.bufferSize = pointCount; } // Fill. mMeshBuffer.vertices[0] = Vector3.zero; for (int index = 0; index < mMeshBuffer.vertices.Length - 1; index++) { if (index < viewPoints.Count) { mMeshBuffer.vertices[index + 1] = transform.InverseTransformPoint(viewPoints[index]); // + Vector3.up * maskCutawayDst; } else { mMeshBuffer.vertices[index + 1] = Vector3.zero; } } mMeshBuffer.Update(); viewPoints.Clear(); }
void DrawFOV() { int numRays = Mathf.RoundToInt(viewAngle * raysPerDegree); float angleBetweenRays = viewAngle / numRays; List <Vector3> viewPoints = new List <Vector3>(); ViewCastInfo oldViewCast = new ViewCastInfo(); // Angle along the left edge of the FOV. float angleStart = transform.eulerAngles.y - viewAngle / 2; for (int i = 0; i < numRays; i++) { float angle = angleStart + angleBetweenRays * i; ViewCastInfo newViewCast = ViewCast(angle); if (i > 0) { bool isEdgeDistanceThresholdExceeded = Mathf.Abs(oldViewCast.length - newViewCast.length) > edgeDistanceThreshold; if (oldViewCast.isHit != newViewCast.isHit || (oldViewCast.isHit && newViewCast.isHit && isEdgeDistanceThresholdExceeded)) { EdgeInfo edge = FindEdge(oldViewCast, newViewCast); if (edge.pointA != Vector3.zero) { viewPoints.Add(edge.pointA); } if (edge.pointB != Vector3.zero) { viewPoints.Add(edge.pointB); } } } viewPoints.Add(newViewCast.endPoint); //Debug.DrawLine(transform.position, transform.position + DirectionFromAngle(angle, true) * viewRadius, Color.red); oldViewCast = newViewCast; } // The viewPoints array sould likely just double as the vertex array, by first inserting the origin point. int vertexCount = viewPoints.Count + 1; Vector3[] vertices = new Vector3[vertexCount]; int[] triangles = new int[(vertexCount - 2) * 3]; vertices[0] = Vector3.zero; for (int i = 0; i < vertexCount - 1; i++) { vertices[i + 1] = transform.InverseTransformPoint(viewPoints[i]); if (i < vertexCount - 2) { triangles[i * 3] = 0; triangles[i * 3 + 1] = i + 1; triangles[i * 3 + 2] = i + 2; } else { break; } } meshFOV.Clear(); meshFOV.vertices = vertices; meshFOV.triangles = triangles; meshFOV.RecalculateNormals(); }
void drawFieldOfView() { int rayCount = Mathf.RoundToInt(viewAngle * meshResolution); float stepAngleSize = viewAngle / rayCount; List <Vector3> viewPoints = new List <Vector3>(); // List to hold all the points that ViewCast hit so we can draw it ViewCastInfo oldViewCast = new ViewCastInfo(); for (int i = 0; i <= rayCount; i++) { float angle = transform.eulerAngles.y - viewAngle / 2 + stepAngleSize * i; // Debug.DrawLine(transform.position, transform.position + directionFromAngle(angle, true) * viewRadius, Color.red); ViewCastInfo newViewCast = ViewCast(angle); if (i > 0) // Edge Detection { bool edgeDstThresholdExceeded = Mathf.Abs(oldViewCast.dst - newViewCast.dst) > edgeDstThreshold; if (oldViewCast.hit != newViewCast.hit || (oldViewCast.hit && newViewCast.hit && edgeDstThresholdExceeded)) { EdgeInfo edge = FindEdge(oldViewCast, newViewCast); if (edge.pointA != Vector3.zero) { viewPoints.Add(edge.pointA); } if (edge.pointB != Vector3.zero) { viewPoints.Add(edge.pointB); } } } viewPoints.Add(newViewCast.point); oldViewCast = newViewCast; } // Creating a Mesh via script int vertexCount = viewPoints.Count + 1; Vector3[] vertices = new Vector3[vertexCount]; int[] triangles = new int[(vertexCount - 2) * 3]; vertices[0] = Vector3.zero; // Set vertices to viewPointList for (int i = 0; i < vertexCount - 1; i++) { // Convert global points into local points vertices [i + 1] = transform.InverseTransformPoint(viewPoints [i]); // Setting the triangles array x 3 - Each triangle starts at the origin vertex 0 if (i < vertexCount - 2) // OutOfBounds array check { triangles[i * 3] = 0; triangles[i * 3 + 1] = i + 1; triangles[i * 3 + 2] = i + 2; } } viewMesh.Clear(); viewMesh.vertices = vertices; viewMesh.triangles = triangles; viewMesh.RecalculateNormals(); }
// ---------------------------- Logic ---------------------------- // method for drawing area we can see public void DrawField(Transform parent) { int stepCount = Mathf.RoundToInt(viewAngle * meshResolution); float angleStep = viewAngle / stepCount; List <Vector3> pointsHit = new List <Vector3>(); // for all steps ViewCastInfo oldViewCast = new ViewCastInfo(); for (int i = 0; i <= stepCount; i++) { // get ray !rotate! angle // rotate angle + left edge of field + step // start from left and go right float rayAngle = parent.transform.eulerAngles.y - viewAngle / 2 + angleStep * i; ViewCastInfo castInfo = ViewCast(rayAngle, viewRadius, parent); //Debug.DrawLine(parent.transform.position, castInfo.point); if (i > 0) { // check if our rays collide different walls // check by watch distance of two rays, on different walls distance will be big bool edgeDistanceThreshHolll = Mathf.Abs(oldViewCast.dst - castInfo.dst) > edgeDistanceThresh; // check if (right hit and left not) or (right not hit and left hit) if (oldViewCast.hit != castInfo.hit || (oldViewCast.hit && oldViewCast.hit && edgeDistanceThreshHolll)) { // then when we have this situation, we nead find where is obstical edge EdgeInfo edge = FindObsticalEdge(oldViewCast, castInfo, parent); // if parametrs not steal zero if (edge.pointA != Vector3.zero) { pointsHit.Add(edge.pointA); } if (edge.pointB != Vector3.zero) { pointsHit.Add(edge.pointB); } } } //add poin we hit in list pointsHit.Add(castInfo.point); oldViewCast = castInfo; } //create array of triangls we need to paint //count of vertex int vertexCount = pointsHit.Count + 1; // array for all vertexes // for example {0,1,2,3} Vector3[] verteces = new Vector3[vertexCount]; //array for triangls vertexes // for example {0,1,2, 0,2,3} two triangls int[] trianglArray = new int[(vertexCount - 2) * 3]; //start point on zero verteces[0] = Vector3.zero; //add vertexes to triangle array for (int i = 0; i < vertexCount - 1; i++) { //full vertices array with points we have verteces[i + 1] = parent.transform.InverseTransformPoint(pointsHit[i]) + Vector3.forward * fieldObjectsOverlap; if (i < vertexCount - 2) { //full triangl array with index of points of triangls trianglArray[i * 3] = 0; trianglArray[i * 3 + 1] = i + 1; trianglArray[i * 3 + 2] = i + 2; } } // when we have all info we need (vetrices, triangles) // paint triangls fieldMesh.Clear(); fieldMesh.vertices = verteces; fieldMesh.triangles = trianglArray; fieldMesh.RecalculateNormals(); }
void DrawFieldOfView() { int stepCount = Mathf.RoundToInt(viewAngle * meshResolution); float stepAngleSize = viewAngle / stepCount; List <Vector3> viewPoints = new List <Vector3>(); ViewCastInfo oldViewCast = new ViewCastInfo(); for (int i = 0; i <= stepCount; i++) { float angle = target_transform.eulerAngles.y - (viewAngle + (view_direction / 2)) / 2 + stepAngleSize * i; ViewCastInfo newViewCast = ViewCast(angle); if (i > 0) { bool edgeDstThresholdExceeded = Mathf.Abs(oldViewCast.dst - newViewCast.dst) > edgeDstThreshold; if (oldViewCast.hit != newViewCast.hit || (oldViewCast.hit && newViewCast.hit && edgeDstThresholdExceeded)) { EdgeInfo edge = FindEdge(oldViewCast, newViewCast); if (edge.pointA != Vector3.zero) { viewPoints.Add(edge.pointA); } if (edge.pointB != Vector3.zero) { viewPoints.Add(edge.pointB); } } } viewPoints.Add(newViewCast.point); oldViewCast = newViewCast; } int vertexCount = viewPoints.Count + 1; Vector3[] vertices = new Vector3[vertexCount]; int[] triangles = new int[(vertexCount - 2) * 3]; vertices[0] = Vector3.zero; for (int i = 0; i < vertexCount - 1; i++) { Transform temp_trans = target_transform; Quaternion rotation_holder = target_transform.rotation; Vector3 scale_holder = target_transform.localScale; temp_trans.localRotation = new Quaternion(); temp_trans.localScale = new Vector3(1.0f, 1.0f, 1.0f); vertices[i + 1] = temp_trans.InverseTransformPoint(viewPoints[i]) + Vector3.forward * maskCutawayDst; target_transform.rotation = rotation_holder; target_transform.localScale = scale_holder; if (i < vertexCount - 2) { triangles[i * 3] = 0; triangles[i * 3 + 1] = i + 1; triangles[i * 3 + 2] = i + 2; } } viewMesh.Clear(); viewMesh.vertices = vertices; viewMesh.triangles = triangles; viewMesh.RecalculateNormals(); }
private bool ExceededEdgeDistanceThreshold(ViewCastInfo oldViewCast, ViewCastInfo newViewCast) { return(Mathf.Abs(oldViewCast.distance - newViewCast.distance) > edgeDistanceThreshold); }
void DrawFieldOfView() { float orientation = sprite_orient.eulerAngles.z; fade_view.transform.rotation = Quaternion.Euler(0, 0, orientation); float FOV = body.viewAngle; if (reverse) { orientation -= 180; FOV = 360 - FOV; } int stepCount = Mathf.RoundToInt(FOV * meshResolution); float stepAngleSize = FOV / stepCount; List <Vector3> viewPoints = new List <Vector3>(); ViewCastInfo oldViewCast = new ViewCastInfo(); //Casting rays to detect corners int shadow_fins_count = 0; for (int i = 0; i <= stepCount; i++) { float angle; if (fullview) { angle = 180 - stepAngleSize * i; } else { angle = orientation + FOV / 2 - stepAngleSize * i; } //Debug.DrawLine(transform.position, transform.position + DirFromAngle(angle, true) * viewRadius, Color.red); ViewCastInfo newViewCast = ViewCast(angle); if (i > 0) { //bool edgeDsThresholdExceeded = Mathf.Abs(oldViewCast.dst - newViewCast.dst) > edgeDstThreshold; float edge_dist = Mathf.Abs(oldViewCast.dst - newViewCast.dst); if (oldViewCast.hit != newViewCast.hit || (oldViewCast.hit && newViewCast.hit && edge_dist > edgeDstThreshold)) { EdgeInfo edge = FindEdge(oldViewCast, newViewCast); if (edge.pointA != Vector3.zero) { viewPoints.Add(edge.pointA); //vec_shadow = edge.pointA; } if (edge.pointB != Vector3.zero) { viewPoints.Add(edge.pointB); //vec_clear = edge.pointB; } if (QualitySettings.GetQualityLevel() > 2 && edge_dist > CONSTANTS.SHADOW_FIN_THREDSHOLD) { bool fade_in = true;//This boolean is gonna be very confusing Vector3 vec_shadow = newViewCast.point; Vector3 vec_clear = oldViewCast.point; if (oldViewCast.dst < newViewCast.dst) { fade_in = false; vec_shadow = oldViewCast.point; vec_clear = newViewCast.point; } //Shadow fin GameObject fin; if (shadow_fins_count >= shadow_fin_pool.Count) { fin = Instantiate(shadow_fin_template, vec_shadow, Quaternion.identity); shadow_fin_pool.Add(fin); } else { fin = shadow_fin_pool[shadow_fins_count]; fin.SetActive(true); } shadow_fins_count++; Vector2 base_vec = vec_shadow - transform.position; float base_vec_dist = base_vec.magnitude; float base_angle = Mathf.Atan2(base_vec.y, base_vec.x) * 180 / 3.14f - 90; //Extend the soft side of the shadow float offset = Mathf.Atan2(body.size, base_vec_dist) * 180 / 3.14f; float soft_angle = 0; if (fade_in) { soft_angle = base_angle - offset; } else { soft_angle = base_angle + offset; } /* * if (fade_left) * { * base_angle += offset; * } * else * { * base_angle -= offset; * } */ // vec_shadow.z = CONSTANTS.SHADOW_FIN_Z; fin.transform.position = vec_shadow; fin.transform.rotation = Quaternion.Euler(0, 0, base_angle); //bool face_left = fin.transform.localScale.x >= 0; Vector3 flip = fin.transform.localScale; flip.y = Mathf.Max(edge_dist, body.viewRadius - base_vec_dist) * 1.2f; flip.x = (body.viewRadius - base_vec_dist) * (body.size / base_vec_dist) * 1.2f; if (!fade_in) { flip.x *= -1; } fin.transform.localScale = flip; } } } // viewPoints.Add(newViewCast.point); oldViewCast = newViewCast; } //Debug.DrawLine(transform.position, transform.position + DirFromAngle(transform.eulerAngles.z, true) * viewRadius, Color.blue); //Clean redundant fins for (int j = shadow_fins_count; j < shadow_fin_pool.Count; j++) { shadow_fin_pool[j].SetActive(false); } int vertexCount = viewPoints.Count + 1; Vector3[] vertices = new Vector3[vertexCount]; int[] triangles = new int[(vertexCount - 2) * 3]; vertices[0] = Vector3.zero; //Analyzing points for (int i = 0; i < vertexCount - 1; i++) { vertices[i + 1] = transform.InverseTransformPoint(viewPoints[i]) + Vector3.right * maskCutAwayDst; if (i < vertexCount - 2) { triangles[i * 3] = 0; triangles[i * 3 + 1] = i + 1; triangles[i * 3 + 2] = i + 2; } } viewMesh.Clear(); viewMesh.vertices = vertices; viewMesh.triangles = triangles; viewMesh.RecalculateNormals(); }
public EdgeInfo(ViewCastInfo _pointA, ViewCastInfo _pointB) { pointA = _pointA; pointB = _pointB; }