public Vector2 GetOffset(List <Vector2> aSegment, int i, bool aClosed) { Ferr2DT_TerrainDirection prev = Ferr2D_Path.GetDirection(aSegment, i - 1, fill == Ferr2DT_FillMode.InvertedClosed, aClosed); Ferr2DT_TerrainDirection next = Ferr2D_Path.GetDirection(aSegment, i, fill == Ferr2DT_FillMode.InvertedClosed, aClosed); int prevID = (int)prev; int nextID = (int)next; Vector2 result = new Vector2(0, 0); if (prev == Ferr2DT_TerrainDirection.Left || prev == Ferr2DT_TerrainDirection.Right) { result.x += surfaceOffset[prevID]; } else if (next == Ferr2DT_TerrainDirection.Left || next == Ferr2DT_TerrainDirection.Right) { result.x += surfaceOffset[nextID]; } if (prev == Ferr2DT_TerrainDirection.Top || prev == Ferr2DT_TerrainDirection.Bottom) { result.y += surfaceOffset[prevID]; } else if (next == Ferr2DT_TerrainDirection.Top || next == Ferr2DT_TerrainDirection.Bottom) { result.y += surfaceOffset[nextID]; } return(result); }
/// <summary> /// This method will close a list of split segments, merging and adding points to the end chunks. /// </summary> /// <param name="aSegmentList">List of split segments that make up the path.</param> /// <param name="aCorners">If there are corners or not.</param> /// <returns>A closed loop of segments.</returns> public static bool CloseEnds(ref List <List <Vector2> > aSegmentList, bool aCorners) { Vector2 start = aSegmentList[0][0]; Vector2 startNext = aSegmentList[0][1]; Vector2 end = aSegmentList[aSegmentList.Count - 1][aSegmentList[aSegmentList.Count - 1].Count - 1]; Vector2 endPrev = aSegmentList[aSegmentList.Count - 1][aSegmentList[aSegmentList.Count - 1].Count - 2]; if (aCorners == false) { aSegmentList[0].Add(start); return(true); } bool endCorner = Ferr2D_Path.GetDirection(endPrev, end) != Ferr2D_Path.GetDirection(end, start); bool startCorner = Ferr2D_Path.GetDirection(end, start) != Ferr2D_Path.GetDirection(start, startNext); if (endCorner && startCorner) { List <Vector2> lastSeg = new List <Vector2>(); lastSeg.Add(end); lastSeg.Add(start); aSegmentList.Add(lastSeg); } else if (endCorner && !startCorner) { aSegmentList[0].Insert(0, end); } else if (!endCorner && startCorner) { aSegmentList[aSegmentList.Count - 1].Add(start); } else { aSegmentList[0].InsertRange(0, aSegmentList[aSegmentList.Count - 1]); aSegmentList.RemoveAt(aSegmentList.Count - 1); } return(true); }
bool ColliderNormValid(Ferr2DT_PathTerrain aSprite, Vector2 aOne, Vector2 aTwo) { Ferr2DT_TerrainDirection dir = Ferr2D_Path.GetDirection(aTwo, aOne); if (dir == Ferr2DT_TerrainDirection.Top && aSprite.collidersTop) { return(true); } if (dir == Ferr2DT_TerrainDirection.Left && aSprite.collidersLeft) { return(true); } if (dir == Ferr2DT_TerrainDirection.Right && aSprite.collidersRight) { return(true); } if (dir == Ferr2DT_TerrainDirection.Bottom && aSprite.collidersBottom) { return(true); } return(false); }
/// <summary> /// This method will close a list of split segments, merging and adding points to the end chunks. /// </summary> /// <param name="aSegmentList">List of split segments that make up the path.</param> /// <param name="aCorners">If there are corners or not.</param> /// <returns>A closed loop of segments.</returns> public static bool CloseEnds(List <Vector2> aPath, ref List <List <int> > aSegmentList, ref List <Ferr2DT_TerrainDirection> aSegmentDirections, bool aCorners, bool aInverted) { int startID = aSegmentList[0][0]; Vector2 start = aPath[startID]; Vector2 startNext = aPath[aSegmentList[0][1]]; int endID = aSegmentList[aSegmentList.Count - 1][aSegmentList[aSegmentList.Count - 1].Count - 1]; Vector2 end = aPath[endID]; Vector2 endPrev = aPath[aSegmentList[aSegmentList.Count - 1][aSegmentList[aSegmentList.Count - 1].Count - 2]]; if (aCorners == false) { aSegmentList[0].Add(startID); return(true); } bool endCorner = Ferr2D_Path.GetDirection(endPrev, end) != Ferr2D_Path.GetDirection(end, start); bool startCorner = Ferr2D_Path.GetDirection(end, start) != Ferr2D_Path.GetDirection(start, startNext); if (endCorner && startCorner) { List <int> lastSeg = new List <int>(); lastSeg.Add(endID); lastSeg.Add(startID); aSegmentList.Add(lastSeg); Ferr2DT_TerrainDirection dir = GetDirection(start, end); if (aInverted && dir == Ferr2DT_TerrainDirection.Top) { dir = Ferr2DT_TerrainDirection.Bottom; } if (aInverted && dir == Ferr2DT_TerrainDirection.Bottom) { dir = Ferr2DT_TerrainDirection.Top; } if (aInverted && dir == Ferr2DT_TerrainDirection.Right) { dir = Ferr2DT_TerrainDirection.Left; } if (aInverted && dir == Ferr2DT_TerrainDirection.Left) { dir = Ferr2DT_TerrainDirection.Right; } aSegmentDirections.Add(dir); } else if (endCorner && !startCorner) { aSegmentList[0].Insert(0, endID); } else if (!endCorner && startCorner) { aSegmentList[aSegmentList.Count - 1].Add(startID); } else { aSegmentList[0].InsertRange(0, aSegmentList[aSegmentList.Count - 1]); aSegmentList.RemoveAt(aSegmentList.Count - 1); aSegmentDirections.RemoveAt(aSegmentDirections.Count - 1); } return(true); }
private Ferr2DT_SegmentDescription GetDescription(List <Vector2> aSegment) { Ferr2DT_TerrainDirection dir = Ferr2D_Path.GetDirection(aSegment, 0, fill == Ferr2DT_FillMode.InvertedClosed); return(terrainMaterial.GetDescriptor(dir)); }
private void AddEdge() { // split the path into segments based on the split angle List <List <int> > segments = new List <List <int> >(); List <Ferr2DT_TerrainDirection> dirs = new List <Ferr2DT_TerrainDirection>(); List <int> order = new List <int>(); segments = GetSegments(Path.GetVertsRaw(), out dirs); if (dirs.Count < segments.Count) { dirs.Add(directionOverrides[directionOverrides.Count - 1]); } for (int i = 0; i < segments.Count; i++) { order.Add(i); } order.Sort( new Ferr.LambdaComparer <int>( (x, y) => { Ferr2DT_TerrainDirection dirx = dirs[x] == Ferr2DT_TerrainDirection.None ? Ferr2D_Path.GetDirection(Path.pathVerts, segments[x], 0, fill == Ferr2DT_FillMode.InvertedClosed) : dirs[x]; Ferr2DT_TerrainDirection diry = dirs[y] == Ferr2DT_TerrainDirection.None ? Ferr2D_Path.GetDirection(Path.pathVerts, segments[y], 0, fill == Ferr2DT_FillMode.InvertedClosed) : dirs[y]; return(terrainMaterial.GetDescriptor(diry).zOffset.CompareTo(terrainMaterial.GetDescriptor(dirx).zOffset)); } )); // process the segments into meshes for (int i = 0; i < order.Count; i++) { List <int> currSeg = segments[order[i]]; List <int> prevSeg = order[i] - 1 < 0 ? segments[segments.Count - 1] : segments[order[i] - 1]; List <int> nextSeg = segments[(order[i] + 1) % segments.Count]; int curr = currSeg[0]; int prev = prevSeg[prevSeg.Count - 2]; int next = currSeg[1]; Vector2 p1 = Path.pathVerts[prev] - Path.pathVerts[curr]; Vector2 p2 = Path.pathVerts[next] - Path.pathVerts[curr]; bool leftInner = Mathf.Atan2(p1.x * p2.y - p1.y * p2.x, Vector2.Dot(p1, p2)) < 0; curr = currSeg[currSeg.Count - 1]; prev = currSeg[currSeg.Count - 2]; next = nextSeg[1]; p1 = Path.pathVerts[prev] - Path.pathVerts[curr]; p2 = Path.pathVerts[next] - Path.pathVerts[curr]; bool rightInner = Mathf.Atan2(p1.x * p2.y - p1.y * p2.x, Vector2.Dot(p1, p2)) < 0; AddSegment(Ferr2D_Path.IndicesToPath(Path.pathVerts, segments[order[i]]), leftInner, rightInner, GetScalesFromIndices(segments[order[i]]), order.Count <= 1 && Path.closed, smoothPath, dirs[order[i]]); } }
public void LegacyUpgrade() { if (!IsLegacy) { return; } #if UNITY_EDITOR UnityEditor.Undo.RecordObject(gameObject, "Upgrade Ferr2D Terrain"); #endif Ferr2D_Path oldPath = GetComponent <Ferr2D_Path>(); MatchOverrides(); // upgrade the path pathData = new Ferr2DPath(); pathData.Closed = oldPath.closed; for (int i = 0; i < oldPath.pathVerts.Count; i++) { int next = Ferr.PathUtil.WrapIndex(i - 1, Path.Count, Path.closed); Ferr.PointType pointType = Ferr.PointType.Sharp; if (smoothPath) { Ferr2DT_TerrainDirection prevSegmentDirection = Ferr2D_Path.GetDirection(Path.pathVerts, next, fill == Ferr2DT_FillMode.InvertedClosed, Path.closed, directionOverrides); Ferr2DT_TerrainDirection nextSegmentDirection = Ferr2D_Path.GetDirection(Path.pathVerts, i, fill == Ferr2DT_FillMode.InvertedClosed, Path.closed, directionOverrides); if (prevSegmentDirection == nextSegmentDirection) { pointType = Ferr.PointType.Auto; } } Ferr2D_PointData data = new Ferr2D_PointData(); data.scale = vertScales[next]; data.directionOverride = (int)directionOverrides[next]; data.cutOverrides = cutOverrides[next].data; pathData.Add(oldPath.pathVerts[i], data, pointType); } pathData.ReverseSelf(); pathData.SetDirty(); // remove old path values directionOverrides = null; cutOverrides = null; vertScales = null; // upgrade collider settings if (createCollider) { if (useEdgeCollider) { colliderMode = Ferr2D_ColliderMode.Edge2D; } else if (create3DCollider) { colliderMode = Ferr2D_ColliderMode.Mesh3D; } else { colliderMode = Ferr2D_ColliderMode.Polygon2D; } } else { colliderMode = Ferr2D_ColliderMode.None; } // upgrade the fill settings switch (fill) { case Ferr2DT_FillMode.None: edgeMode = Ferr2D_SectionMode.Normal; fillMode = Ferr2D_SectionMode.None; break; case Ferr2DT_FillMode.Closed: edgeMode = Ferr2D_SectionMode.Normal; fillMode = Ferr2D_SectionMode.Normal; break; case Ferr2DT_FillMode.InvertedClosed: edgeMode = Ferr2D_SectionMode.Invert; fillMode = Ferr2D_SectionMode.Invert; break; case Ferr2DT_FillMode.FillOnlyClosed: edgeMode = Ferr2D_SectionMode.None; fillMode = Ferr2D_SectionMode.Normal; break; case Ferr2DT_FillMode.Skirt: edgeMode = Ferr2D_SectionMode.Normal; fillMode = Ferr2D_SectionMode.Normal; useSkirt = true; break; case Ferr2DT_FillMode.FillOnlySkirt: edgeMode = Ferr2D_SectionMode.None; fillMode = Ferr2D_SectionMode.Normal; useSkirt = true; break; } isLegacy = false; #if UNITY_EDITOR UnityEditor.Undo.DestroyObjectImmediate(oldPath); #else Destroy(oldPath); #endif Build(true); #if UNITY_EDITOR UnityEditor.SceneView.RepaintAll(); #endif }
public Ferr2DT_SegmentDescription GetDescription(List <int> aSegment) { Ferr2DT_TerrainDirection dir = Ferr2D_Path.GetDirection(Path.pathVerts, aSegment, 0, fill == Ferr2DT_FillMode.InvertedClosed); return(TerrainMaterial.GetDescriptor(dir)); }
private void AddEdge() { // split the path into segments based on the split angle List <List <int> > segments = new List <List <int> >(); List <Ferr2DT_TerrainDirection> dirs = new List <Ferr2DT_TerrainDirection>(); List <int> order = new List <int>(); segments = GetSegments(Path.GetVertsRaw(), out dirs); if (dirs.Count < segments.Count) { dirs.Add(directionOverrides[directionOverrides.Count - 1]); } for (int i = 0; i < segments.Count; i++) { order.Add(i); } order.Sort( new Ferr_LambdaComparer <int>( (x, y) => { Ferr2DT_TerrainDirection dirx = dirs[x] == Ferr2DT_TerrainDirection.None ? Ferr2D_Path.GetDirection(Path.pathVerts, segments[x], 0, fill == Ferr2DT_FillMode.InvertedClosed) : dirs[x]; Ferr2DT_TerrainDirection diry = dirs[y] == Ferr2DT_TerrainDirection.None ? Ferr2D_Path.GetDirection(Path.pathVerts, segments[y], 0, fill == Ferr2DT_FillMode.InvertedClosed) : dirs[y]; return(terrainMaterial.GetDescriptor(diry).zOffset.CompareTo(terrainMaterial.GetDescriptor(dirx).zOffset)); } )); // process the segments into meshes for (int i = 0; i < order.Count; i++) { AddSegment(Ferr2D_Path.IndicesToPath(Path.pathVerts, segments[order[i]]), GetScalesFromIndices(segments[order[i]]), order.Count <= 1 && Path.closed, smoothPath, dirs[order[i]]); } }