private void AddShallowBump(Point2I point, fieldT currFld, LinkedList <bumpT> steepBumps, LinkedList <bumpT> shallowBumps) { // First, the far point of shallow is set to the new point. currFld.m_Shallow.m_Far = point; // Second, we need to add the new bump to the shallow bump list for // future steep bump handling. shallowBumps.AddLast(new bumpT()); shallowBumps.Last.Value.m_Location = point; shallowBumps.Last.Value.m_Parent = currFld.m_ShallowBump; currFld.m_ShallowBump = shallowBumps.Last.Value; // Now we have too look through the list of steep bumps and see if // any of them are below the line. // If there are, we need to replace near point too. bumpT currentBump = currFld.m_SteepBump; while (currentBump != null) { if (currFld.m_Shallow.IsAbove(currentBump.m_Location)) { currFld.m_Shallow.m_Near = currentBump.m_Location; } currentBump = currentBump.m_Parent; } }
public fieldT(fieldT f) { m_Steep = new Line2I(new Point2I(f.m_Steep.m_Near.m_X, f.m_Steep.m_Near.m_Y), new Point2I(f.m_Steep.m_Far.m_X, f.m_Steep.m_Far.m_Y)); m_Shallow = new Line2I( new Point2I(f.m_Shallow.m_Near.m_X, f.m_Shallow.m_Near.m_Y), new Point2I(f.m_Shallow.m_Far.m_X, f.m_Shallow.m_Far.m_Y)); m_SteepBump = f.m_SteepBump; m_ShallowBump = f.m_ShallowBump; }
private bool CheckField(CLikeIterator <fieldT> currentField) { // If the two slopes are colinear, and if they pass through either // extremity, remove the field of view. fieldT currFld = currentField.GetCurrent(); bool ret = false; if (currFld.m_Shallow.DoesContain(currFld.m_Steep.m_Near) && currFld.m_Shallow.DoesContain(currFld.m_Steep.m_Far) && (currFld.m_Shallow.DoesContain(new Point2I(0, 1)) || currFld.m_Shallow .DoesContain(new Point2I(1, 0)))) { currentField.RemoveCurrent(); ret = true; } return(ret); }
private void AddSteepBump(Point2I point, fieldT currFld, LinkedList <bumpT> steepBumps, LinkedList <bumpT> shallowBumps) { currFld.m_Steep.m_Far = point; steepBumps.AddLast(new bumpT()); steepBumps.Last.Value.m_Location = point; steepBumps.Last.Value.m_Parent = currFld.m_SteepBump; currFld.m_SteepBump = steepBumps.Last.Value; // Now look through the list of shallow bumps and see if any of them // are below the line. bumpT currentBump = currFld.m_ShallowBump; while (currentBump != null) { if (currFld.m_Steep.IsBelow(currentBump.m_Location)) { currFld.m_Steep.m_Near = currentBump.m_Location; } currentBump = currentBump.m_Parent; } }
private void VisitSquare(fovStateT state, Point2I dest, CLikeIterator <fieldT> currentField, LinkedList <bumpT> steepBumps, LinkedList <bumpT> shallowBumps, LinkedList <fieldT> activeFields) { // The top-left and bottom-right corners of the destination square. Point2I topLeft = new Point2I(dest.m_X, dest.m_Y + 1); Point2I bottomRight = new Point2I(dest.m_X + 1, dest.m_Y); while (!currentField.IsAtEnd() && currentField.GetCurrent().m_Steep .IsBelowOrContains(bottomRight)) { // case ABOVE // The square is in case 'above'. This means that it is ignored // for the currentField. But the steeper fields might need it. currentField.GotoNext(); } if (currentField.IsAtEnd()) { // The square was in case 'above' for all fields. This means that // we no longer care about it or any squares in its diagonal rank. return; } // Now we check for other cases. if (currentField.GetCurrent().m_Shallow.IsAboveOrContains(topLeft)) { // case BELOW // The shallow line is above the extremity of the square, so that // square is ignored. return; } // The square is between the lines in some way. This means that we // need to visit it and determine whether it is blocked. bool isBlocked = ActIsBlocked(state, dest); if (!isBlocked) { // We don't care what case might be left, because this square does // not obstruct. return; } if (currentField.GetCurrent().m_Shallow.IsAbove(bottomRight) && currentField.GetCurrent().m_Steep.IsBelow(topLeft)) { // case BLOCKING // Both lines intersect the square. This current field has ended. currentField.RemoveCurrent(); } else if (currentField.GetCurrent().m_Shallow.IsAbove(bottomRight)) { // case SHALLOW BUMP // The square intersects only the shallow line. AddShallowBump(topLeft, currentField.GetCurrent(), steepBumps, shallowBumps); CheckField(currentField); } else if (currentField.GetCurrent().m_Steep.IsBelow(topLeft)) { // case STEEP BUMP // The square intersects only the steep line. AddSteepBump(bottomRight, currentField.GetCurrent(), steepBumps, shallowBumps); CheckField(currentField); } else { // case BETWEEN // The square intersects neither line. We need to split into two // fields. fieldT steeperField = currentField.GetCurrent(); fieldT shallowerField = new fieldT(currentField.GetCurrent()); currentField.InsertBeforeCurrent(shallowerField); AddSteepBump(bottomRight, shallowerField, steepBumps, shallowBumps); currentField.GotoPrevious(); if (!CheckField(currentField)) // did not remove { currentField.GotoNext(); // point to the original element } AddShallowBump(topLeft, steeperField, steepBumps, shallowBumps); CheckField(currentField); } }