Ejemplo n.º 1
0
        public void CycleSpriteIndex()
        {
            ISelection selection = ShapeEditorCache.GetSelection();

            if (selection.single == -1)
            {
                return;
            }

            int   nextIndex       = SplineUtility.NextIndex(selection.single, m_Spline.GetPointCount());
            float angle           = SpriteShapeHandleUtility.PosToAngle(m_Spline.GetPosition(selection.single), m_Spline.GetPosition(nextIndex), 0f);
            int   angleRangeIndex = SpriteShapeEditorUtility.GetRangeIndexFromAngle(m_SpriteShape, angle);

            if (angleRangeIndex == -1)
            {
                return;
            }

            AngleRange angleRange = m_SpriteShape.angleRanges[angleRangeIndex];

            int spriteIndex = (m_Spline.GetSpriteIndex(selection.single) + 1) % angleRange.sprites.Count;

            Undo.RecordObject(m_CurrentEditor.target, "Edit Sprite Index");

            m_Spline.SetSpriteIndex(selection.single, spriteIndex);

            EditorUtility.SetDirty(m_CurrentEditor.target);
        }
Ejemplo n.º 2
0
        private void ResetTangents(int pointIndex)
        {
            Vector3 position     = GetPosition(pointIndex);
            Vector3 positionNext = GetPosition(SplineUtility.NextIndex(pointIndex, GetPointCount()));
            Vector3 positionPrev = GetPosition(SplineUtility.PreviousIndex(pointIndex, GetPointCount()));
            Vector3 forward      = Vector3.forward;

            if (SplineEditorCache.IsValid() && SplineEditorCache.GetTarget() != null)
            {
                forward = SplineEditorCache.GetTarget().transform.forward;
            }

            float scale = Mathf.Min((positionNext - position).magnitude, (positionPrev - position).magnitude) * 0.33f;

            Vector3 leftTangent  = (positionPrev - position).normalized * scale;
            Vector3 rightTangent = (positionNext - position).normalized * scale;

            if (GetTangentMode(pointIndex) == TangentMode.Continuous)
            {
                SplineUtility.CalculateTangents(position, positionPrev, positionNext, forward, scale, out rightTangent, out leftTangent);
            }

            SetLeftTangent(pointIndex, leftTangent);
            SetRightTangent(pointIndex, rightTangent);
        }
Ejemplo n.º 3
0
        public Vector2 GetEdgeWindowPosition(int edgeIndex)
        {
            int     nextIndex    = SplineUtility.NextIndex(edgeIndex, m_Points.Count);
            Vector2 start        = m_Points[edgeIndex].m_Position;
            Vector2 startTangent = (Vector2)m_Points[edgeIndex].m_RightTangent + start;
            Vector2 end          = m_Points[nextIndex].m_Position;
            Vector2 endTangent   = (Vector2)m_Points[nextIndex].m_LeftTangent + end;

            return(BezierUtility.BezierPoint(start, startTangent, endTangent, end, 0.5f) + Vector3.up * kWindowHeaderHeight);
        }
        private void LayoutEdges()
        {
            if (currentEvent.type != EventType.Layout)
            {
                return;
            }

            PrepareEdgePoints();

            int pointCount = GetPointCount();
            int edgeCount  = OpenEnded() ? pointCount - 1 : pointCount;

            float minDistance = float.MaxValue;

            for (int index = 0; index < edgeCount; ++index)
            {
                int id = GUIUtility.GetControlID("Edge".GetHashCode(), FocusType.Passive);

                if (currentEvent.type == EventType.Layout)
                {
                    int nextIndex = SplineUtility.NextIndex(index, pointCount);

                    Vector3 position0 = GetPosition(index);
                    Vector3 position1 = GetPosition(nextIndex);
                    Vector3 tangent0  = GetRightTangent(index) + position0;
                    Vector3 tangent1  = GetLeftTangent(nextIndex) + position1;

                    float   t;
                    Vector3 closestPoint = BezierUtility.ClosestPointOnCurve(ScreenToWorld(currentEvent.mousePosition), position0, position1, tangent0, tangent1, out t);

                    Vector2 guiPosition = HandleUtility.WorldToGUIPoint(closestPoint);

                    float distance = (currentEvent.mousePosition - guiPosition).magnitude;

                    if (m_HoveredPointIndex == -1)
                    {
                        HandleUtility.AddControl(id, distance);

                        if (HandleUtility.nearestControl == id)
                        {
                            m_HoveredEdgeIndex    = index;
                            m_HoveredPointIndex   = -1;
                            m_HoveredTangentPoint = -1;
                        }
                    }

                    if (distance < minDistance)
                    {
                        m_ClosestPoint  = closestPoint;
                        m_ClosestPointT = t;
                        minDistance     = distance;
                    }
                }
            }
        }
Ejemplo n.º 5
0
        private int GetAngleRangeLocal(int index)
        {
            var selection       = SplineEditorCache.GetSelection();
            var spriteShape     = SplineEditorCache.GetTarget().spriteShape;
            var nextIndex       = SplineUtility.NextIndex(selection.single, GetPointCount());
            var pos1            = GetLocalPosition(selection.single);
            var pos2            = GetLocalPosition(nextIndex);
            var angle           = SplineUtility.SlopeAngle(pos1, pos2) + 90;
            var angleRangeIndex = SpriteShapeEditorUtility.GetRangeIndexFromAngle(spriteShape, angle);

            return(angleRangeIndex);
        }
Ejemplo n.º 6
0
    // Start is called before the first frame update

    private void Smoothen(SpriteShapeController sc, int pointIndex)
    {
        Vector3 position     = sc.spline.GetPosition(pointIndex);
        Vector3 positionNext = sc.spline.GetPosition(SplineUtility.NextIndex(pointIndex, sc.spline.GetPointCount()));
        Vector3 positionPrev = sc.spline.GetPosition(SplineUtility.PreviousIndex(pointIndex, sc.spline.GetPointCount()));
        Vector3 forward      = gameObject.transform.forward;

        float scale = Mathf.Min((positionNext - position).magnitude, (positionPrev - position).magnitude) * 0.33f;

        Vector3 leftTangent  = (positionPrev - position).normalized * scale;
        Vector3 rightTangent = (positionNext - position).normalized * scale;

        sc.spline.SetTangentMode(pointIndex, ShapeTangentMode.Continuous);
        SplineUtility.CalculateTangents(position, positionPrev, positionNext, forward, scale, out rightTangent, out leftTangent);

        sc.spline.SetLeftTangent(pointIndex, leftTangent);
        sc.spline.SetRightTangent(pointIndex, rightTangent);
    }
Ejemplo n.º 7
0
        private void ResetTangents(int pointIndex)
        {
            Vector3 position     = m_Spline.GetPosition(pointIndex);
            Vector3 positionNext = m_Spline.GetPosition(SplineUtility.NextIndex(pointIndex, m_Spline.GetPointCount()));
            Vector3 positionPrev = m_Spline.GetPosition(SplineUtility.PreviousIndex(pointIndex, m_Spline.GetPointCount()));
            Vector3 forward      = (m_CurrentEditor.target as SpriteShapeController).transform.forward;
            float   scale        = Mathf.Min((positionNext - position).magnitude, (positionPrev - position).magnitude) * 0.33f;

            Vector3 leftTangent  = (positionPrev - position).normalized * scale;
            Vector3 rightTangent = (positionNext - position).normalized * scale;

            if (m_Spline.GetTangentMode(pointIndex) == ShapeTangentMode.Continuous)
            {
                SplineUtility.CalculateTangents(position, positionPrev, positionNext, forward, scale, out rightTangent, out leftTangent);
            }

            m_Spline.SetLeftTangent(pointIndex, leftTangent);
            m_Spline.SetRightTangent(pointIndex, rightTangent);
        }
Ejemplo n.º 8
0
        private void HandleDragEdge()
        {
            EventType eventType = currentEvent.GetTypeForControl(m_DragEdgeControlId);

            if ((m_HoveredEdgeIndex != -1 && GUIUtility.hotControl == 0 && EdgeDragModifiersActive()) ||
                GUIUtility.hotControl == m_DragEdgeControlId)
            {
                if (eventType == EventType.MouseDown && currentEvent.button == 0)
                {
                    m_ActiveEdgeIndex = m_HoveredEdgeIndex;
                    m_SliderPosition  = GetPosition(m_HoveredEdgeIndex);
                }

                if (eventType == EventType.MouseUp && currentEvent.button == 0)
                {
                    m_ActiveEdgeIndex = -1;
                }

                if (eventType == EventType.Layout && GUIUtility.hotControl == 0)
                {
                    HandleUtility.AddControl(m_DragEdgeControlId, 0f);
                }

                EditorGUI.BeginChangeCheck();

                var newPosition = DoSlider(m_DragEdgeControlId, m_SliderPosition, GetUpVector(), GetRightVector(), GetHandleSize(m_SliderPosition), (int cid, Vector3 p, Quaternion q, float s, EventType et) => { });

                if (EditorGUI.EndChangeCheck())
                {
                    RegisterUndoOnSliderChangedOnce();

                    var snappedDelta = Snap(newPosition) - m_SliderPosition;
                    var nextIndex    = SplineUtility.NextIndex(m_ActiveEdgeIndex, GetPointCount());

                    SetPosition(m_ActiveEdgeIndex, GetPosition(m_ActiveEdgeIndex) + snappedDelta);
                    SetPosition(nextIndex, GetPosition(nextIndex) + snappedDelta);

                    m_EdgePointsDirty = true;
                }

                m_SliderPosition = newPosition;
            }
        }
        private void PrepareEdgePoints()
        {
            int pointCount = GetPointCount();
            int edgeCount  = OpenEnded() ? pointCount - 1 : pointCount;

            if (m_EdgePoints.Count != edgeCount)
            {
                m_EdgePointsDirty = true;
            }

            if (!m_EdgePointsDirty)
            {
                return;
            }

            m_EdgePoints.Clear();

            for (int index = 0; index < edgeCount; ++index)
            {
                int nextIndex = SplineUtility.NextIndex(index, pointCount);

                Vector3 position0 = GetPosition(index);
                Vector3 position1 = GetPosition(nextIndex);

                if (GetTangentMode(index) == TangentMode.Linear && GetTangentMode(nextIndex) == TangentMode.Linear)
                {
                    m_EdgePoints.Add(new Vector3[] { position0, position1 });
                }
                else
                {
                    var tangent0 = GetRightTangent(index) + position0;
                    var tangent1 = GetLeftTangent(nextIndex) + position1;
                    m_EdgePoints.Add(Handles.MakeBezierPoints(position0, position1, tangent0, tangent1, kBezierPatch));
                }
            }

            m_EdgePointsDirty = false;
        }
        private void GenerateSegments(SpriteShapeController sc, List <ShapeAngleRange> angleRanges)
        {
            var          controlPointCount = sc.spline.GetPointCount();
            var          angleRangeIndices = new int[controlPointCount];
            ShapeSegment activeSegment     = new ShapeSegment()
            {
                start = -1, end = -1, angleRange = -1
            };

            m_ShapeSegments.Clear();

            for (int i = 0; i < controlPointCount; ++i)
            {
                var   actv = i;
                var   next = SplineUtility.NextIndex(actv, controlPointCount);
                var   pos1 = sc.spline.GetPosition(actv);
                var   pos2 = sc.spline.GetPosition(next);
                bool  continueStrip = (sc.spline.GetTangentMode(actv) == ShapeTangentMode.Continuous), edgeUpdated = false;
                float angle = 0;
                if (false == continueStrip || activeSegment.start == -1)
                {
                    angle = SplineUtility.SlopeAngle(pos1, pos2) + 90.0f;
                }

                next = (!sc.spline.isOpenEnded && next == 0) ? (actv + 1) : next;
                int mn = (actv < next) ? actv : next;
                int mx = (actv > next) ? actv : next;

                var anglerange = RangeFromAngle(angleRanges, angle);
                angleRangeIndices[actv] = anglerange;
                if (anglerange == -1)
                {
                    activeSegment = new ShapeSegment()
                    {
                        start = mn, end = mx, angleRange = anglerange
                    };
                    m_ShapeSegments.Add(activeSegment);
                    continue;
                }

                // Check for Segments. Also check if the Segment Start has been resolved. Otherwise simply start with the next one
                if (activeSegment.start != -1)
                {
                    continueStrip = continueStrip && (angleRangeIndices[activeSegment.start] != -1);
                }

                bool canContinue = (actv != (controlPointCount - 1)) || (!sc.spline.isOpenEnded && (actv == (controlPointCount - 1)));
                if (continueStrip && canContinue)
                {
                    for (int s = 0; s < m_ShapeSegments.Count; ++s)
                    {
                        activeSegment = m_ShapeSegments[s];
                        if (activeSegment.start - mn == 1)
                        {
                            edgeUpdated         = true;
                            activeSegment.start = mn;
                            m_ShapeSegments[s]  = activeSegment;
                            break;
                        }
                        if (mx - activeSegment.end == 1)
                        {
                            edgeUpdated        = true;
                            activeSegment.end  = mx;
                            m_ShapeSegments[s] = activeSegment;
                            break;
                        }
                    }
                }

                if (!edgeUpdated)
                {
                    activeSegment.start      = mn;
                    activeSegment.end        = mx;
                    activeSegment.angleRange = anglerange;
                    m_ShapeSegments.Add(activeSegment);
                }
            }
        }
        private void HandleInsertPointToEdge()
        {
            EventType eventType = currentEvent.GetTypeForControl(m_DragPointControlId);

            if (m_HoveredPointIndex == -1 && m_HoveredEdgeIndex != -1 && GUIUtility.hotControl == 0 && eventType == EventType.MouseDown && currentEvent.button == 0 && !currentEvent.shift)
            {
                RecordUndo();
                ClearSelection();

                int nextIndex = SplineUtility.NextIndex(m_HoveredEdgeIndex, GetPointCount());

                TangentMode leftTangentMode  = GetTangentMode(m_HoveredEdgeIndex);
                TangentMode rightTangentMode = GetTangentMode(nextIndex);

                Vector3 leftStartPosition;
                Vector3 leftEndPosition;
                Vector3 leftStartTangent;
                Vector3 leftEndTangent;

                Vector3 rightStartPosition;
                Vector3 rightEndPosition;
                Vector3 rightStartTangent;
                Vector3 rightEndTangent;

                Vector3 position0 = GetPosition(m_HoveredEdgeIndex);
                Vector3 position1 = GetPosition(nextIndex);
                Vector3 tangent0  = GetRightTangent(m_HoveredEdgeIndex) + position0;
                Vector3 tangent1  = GetLeftTangent(nextIndex) + position1;

                BezierUtility.SplitBezier(m_ClosestPointT, position0, position1, tangent0, tangent1,
                                          out leftStartPosition, out leftEndPosition, out leftStartTangent, out leftEndTangent,
                                          out rightStartPosition, out rightEndPosition, out rightStartTangent, out rightEndTangent);

                if (leftTangentMode != TangentMode.Linear)
                {
                    SetTangentMode(m_HoveredEdgeIndex, TangentMode.Broken);
                    SetRightTangent(m_HoveredEdgeIndex, leftStartTangent - leftStartPosition);
                }

                if (rightTangentMode != TangentMode.Linear)
                {
                    SetTangentMode(nextIndex, TangentMode.Broken);
                    SetLeftTangent(nextIndex, rightEndTangent - rightEndPosition);
                }

                InsertPointAt(nextIndex, m_ClosestPoint);

                if (leftTangentMode != TangentMode.Linear || rightTangentMode != TangentMode.Linear)
                {
                    SetTangentMode(nextIndex, TangentMode.Broken);

                    if (m_ClosestPointT == 0.5f)
                    {
                        SetTangentMode(nextIndex, TangentMode.Continuous);
                    }

                    SetLeftTangent(nextIndex, leftEndTangent - leftEndPosition);
                    SetRightTangent(nextIndex, rightStartTangent - rightStartPosition);
                }

                m_HoveredPointIndex = nextIndex;
                m_HoveredEdgeIndex  = -1;

                HandleUtility.nearestControl = m_DragPointControlId;
            }
        }
Ejemplo n.º 12
0
    public static void Bake(GameObject go, bool forced)
    {
        var sc = go.GetComponent <SpriteShapeController>();
        var lc = go.GetComponent <LegacyCollider>();

        if (sc != null)
        {
            List <IntPoint> path             = new List <IntPoint>();
            int             splinePointCount = sc.spline.GetPointCount();
            int             pathPointCount   = splinePointCount;

            ColliderCornerType cct = ColliderCornerType.Square;
            float co = 1.0f;

            if (lc != null)
            {
                int hashCode = sc.spline.GetHashCode() + lc.m_ColliderCornerType.GetHashCode() + lc.m_ColliderOffset.GetHashCode();
                if (lc.m_HashCode == hashCode && !forced)
                {
                    return;
                }

                lc.m_HashCode = hashCode;
                cct           = lc.m_ColliderCornerType;
                co            = lc.m_ColliderOffset;
            }

            if (sc.spline.isOpenEnded)
            {
                pathPointCount--;
            }

            for (int i = 0; i < pathPointCount; ++i)
            {
                int nextIndex = SplineUtility.NextIndex(i, splinePointCount);
                SampleCurve(sc.colliderDetail, sc.spline.GetPosition(i), sc.spline.GetRightTangent(i), sc.spline.GetPosition(nextIndex), sc.spline.GetLeftTangent(nextIndex), ref path);
            }

            if (co != 0f)
            {
                List <List <IntPoint> > solution   = new List <List <IntPoint> >();
                ClipperOffset           clipOffset = new ClipperOffset();

                EndType endType = EndType.etClosedPolygon;

                if (sc.spline.isOpenEnded)
                {
                    endType = EndType.etOpenSquare;

                    if (cct == ColliderCornerType.Round)
                    {
                        endType = EndType.etOpenRound;
                    }
                }

                clipOffset.ArcTolerance = 200f / sc.colliderDetail;
                clipOffset.AddPath(path, (ExtrasClipperLib.JoinType)cct, endType);
                clipOffset.Execute(ref solution, s_ClipperScale * co);

                if (solution.Count > 0)
                {
                    path = solution[0];
                }
            }

            List <Vector2> pathPoints = new List <Vector2>(path.Count);
            for (int i = 0; i < path.Count; ++i)
            {
                IntPoint ip = path[i];
                pathPoints.Add(new Vector2(ip.X / s_ClipperScale, ip.Y / s_ClipperScale));
            }

            var pc = go.GetComponent <PolygonCollider2D>();
            if (pc)
            {
                pc.pathCount = 0;
                pc.SetPath(0, pathPoints.ToArray());
            }

            var ec = go.GetComponent <EdgeCollider2D>();
            if (ec)
            {
                if (co > 0f || co < 0f && !sc.spline.isOpenEnded)
                {
                    pathPoints.Add(pathPoints[0]);
                }
                ec.points = pathPoints.ToArray();
            }
        }
    }