예제 #1
0
        /// <summary>
        /// The Editing handles are used to manipulate and resize ProBuilderShapes
        /// These handles are used in 2 tools : EditShapeTool and DrawShapeTool. In this second tool,
        /// these handles allow to modified the last created shape.
        /// </summary>
        /// <param name="proBuilderShape">The Shape on which to attach the handles</param>
        /// <param name="updatePrefs">Parameter used to update the DrawShapeTool when needed</param>
        internal static void DoEditingHandles(ProBuilderShape proBuilderShape, bool updatePrefs = false)
        {
            if (proBuilderShape == null)
            {
                return;
            }

            var scale    = proBuilderShape.transform.lossyScale;
            var position = proBuilderShape.transform.position
                           + Vector3.Scale(proBuilderShape.transform.TransformDirection(proBuilderShape.shapeBox.center), scale);
            var matrix = Matrix4x4.TRS(position, proBuilderShape.transform.rotation, Vector3.one);

            using (new Handles.DrawingScope(matrix))
            {
                EditorShapeUtility.UpdateFaces(proBuilderShape.editionBounds, scale, faces);

                for (int i = 0; i < 4; ++i)
                {
                    k_OrientationControlIDs[i] = GUIUtility.GetControlID(FocusType.Passive);
                }
                for (int i = 0; i < faces.Length; ++i)
                {
                    s_FaceControlIDs[i] = GUIUtility.GetControlID(FocusType.Passive);
                }

                var absSize = Math.Abs(proBuilderShape.editionBounds.size);
                if (absSize.x > Mathf.Epsilon && absSize.y > Mathf.Epsilon && absSize.z > Mathf.Epsilon)
                {
                    DoOrientationHandles(proBuilderShape, updatePrefs);
                }

                DoSizeHandles(proBuilderShape, updatePrefs);
            }
        }
예제 #2
0
        static void DoSizeHandles(ProBuilderShape proBuilderShape, bool updatePrefs)
        {
            int faceCount = s_Faces.Length;

            var evt = Event.current;

            var is2D = proBuilderShape.shape is Plane || proBuilderShape.shape is Sprite;

            for (int i = 0; i < faceCount; i++)
            {
                var face = faces[i];
                if (is2D && !face.IsValid)
                {
                    continue;
                }

                if (Event.current.type == EventType.Repaint)
                {
                    Color color = k_BoundsHandleColor;
                    color.a *= face.IsVisible ? 1f : 0.5f;
                    using (new Handles.DrawingScope(color))
                    {
                        int pointsCount = face.Points.Length;
                        for (int k = 0; k < pointsCount; k++)
                        {
                            Handles.DrawLine(face.Points[k], face.Points[(k + 1) % pointsCount]);
                        }
                    }
                }

                if (DoFaceSizeHandle(face, s_FaceControlIDs[i]))
                {
                    if (!s_SizeManipulationInit)
                    {
                        s_StartCenter          = proBuilderShape.transform.position + proBuilderShape.transform.TransformVector(proBuilderShape.shapeBox.center);
                        s_StartScale           = proBuilderShape.transform.lossyScale;
                        s_StartScaleInverse    = new Vector3(1f / Mathf.Abs(s_StartScale.x), 1f / Mathf.Abs(s_StartScale.y), 1f / Mathf.Abs(s_StartScale.z));
                        s_StartPositionLocal   = face.CenterPosition;
                        s_StartPositionGlobal  = proBuilderShape.transform.TransformPoint(Vector3.Scale(face.CenterPosition, s_StartScale));
                        s_StartSize            = proBuilderShape.size;
                        s_SizeManipulationInit = true;
                        s_Scaling = Vector3.Scale(face.Normal, Math.Sign(s_StartSize));
                    }

                    var targetSize = s_StartSize;
                    if (Math.IsCardinalAxis(proBuilderShape.transform.up) &&
                        EditorSnapSettings.gridSnapEnabled &&
                        !EditorSnapSettings.incrementalSnapActive &&
                        !evt.alt)
                    {
                        var faceDelta    = (s_SizeDelta * s_Faces[i].Normal);
                        var facePosition = s_StartPositionGlobal + faceDelta;
                        facePosition = ProBuilderSnapping.Snap(facePosition, EditorSnapping.activeMoveSnapValue);
                        targetSize  += Vector3.Scale((facePosition - s_StartPositionGlobal), s_Scaling);
                    }
                    else
                    {
                        //Should we expand on the 2 sides?
                        var modifier = evt.alt ? 2f : 1f;
                        var delta    = modifier * (s_SizeDelta * s_Faces[i].Normal);
                        delta.Scale(s_Scaling);
                        delta.Scale(s_StartScaleInverse);

                        targetSize += delta;
                        var snap = EditorSnapSettings.incrementalSnapActive
                            ? Vector3.Scale(EditorSnapping.activeMoveSnapValue, Math.Abs(face.Normal))
                            : Vector3.zero;

                        targetSize = ProBuilderSnapping.Snap(targetSize, snap);
                    }

                    var center = Vector3.zero;
                    if (!evt.alt)
                    {
                        center = Vector3.Scale((targetSize - s_StartSize) / 2f, s_Scaling);
                        center = Vector3.Scale(center, Math.Sign(s_StartScale));
                        center = proBuilderShape.transform.TransformVector(center);
                    }

                    ApplyProperties(proBuilderShape, s_StartCenter + center, targetSize);

                    if (updatePrefs)
                    {
                        DrawShapeTool.SaveShapeParams(proBuilderShape);
                    }
                }
            }
        }