예제 #1
0
        public void SnapSelectedVertices(bool isAbsoluteGrid)
        {
            // So we know which polygons need to have their normals recalculated
            List <Polygon> affectedPolygons = new List <Polygon>();

            foreach (PrimitiveBrush brush in targetBrushes)
            {
                Polygon[] polygons = brush.GetPolygons();

                for (int i = 0; i < polygons.Length; i++)
                {
                    Polygon polygon = polygons[i];

                    int vertexCount = polygon.Vertices.Length;

                    Vector3[] newPositions = new Vector3[vertexCount];
                    Vector2[] newUV        = new Vector2[vertexCount];

                    for (int j = 0; j < vertexCount; j++)
                    {
                        newPositions[j] = polygon.Vertices[j].Position;
                        newUV[j]        = polygon.Vertices[j].UV;
                    }

                    bool polygonAffected = false;
                    for (int j = 0; j < vertexCount; j++)
                    {
                        Vertex vertex = polygon.Vertices[j];
                        if (selectedVertices.ContainsKey(vertex))
                        {
                            Vector3 newPosition = vertex.Position;

                            float snapDistance = CurrentSettings.PositionSnapDistance;
                            if (isAbsoluteGrid)
                            {
                                newPosition = brush.transform.TransformPoint(newPosition);
                            }
                            newPosition = MathHelper.RoundVector3(newPosition, snapDistance);
                            if (isAbsoluteGrid)
                            {
                                newPosition = brush.transform.InverseTransformPoint(newPosition);
                            }

                            newPositions[j] = newPosition;

                            newUV[j] = GeometryHelper.GetUVForPosition(polygon, newPosition);

                            polygonAffected = true;
                        }
                    }

                    if (polygonAffected)
                    {
                        affectedPolygons.Add(polygon);
                    }

                    // Apply all the changes to the polygon
                    for (int j = 0; j < vertexCount; j++)
                    {
                        Vertex vertex = polygon.Vertices[j];
                        vertex.Position = newPositions[j];
                        vertex.UV       = newUV[j];
                    }

                    polygon.CalculatePlane();
                }
            }

            if (affectedPolygons.Count > 0)
            {
                for (int i = 0; i < affectedPolygons.Count; i++)
                {
                    affectedPolygons[i].ResetVertexNormals();
                }

                foreach (PrimitiveBrush brush in targetBrushes)
                {
                    brush.Invalidate(true);

                    brush.BreakTypeRelation();
                }
            }
        }
예제 #2
0
        /// <summary>
        /// Translates the specified vertices by a position delta (local to the brush) and updates the UVs
        /// </summary>
        /// <param name="brush">Brush from which the vertices belong.</param>
        /// <param name="specifiedVertices">Specified vertices to be translated.</param>
        /// <param name="localDelta">Local positional delta.</param>
        public static void TranslateSpecifiedVertices(Brush brush, List <Vertex> specifiedVertices, Vector3 localDelta)
        {
            Polygon.Vector3ComparerEpsilon positionComparer = new Polygon.Vector3ComparerEpsilon();

            // Cache the positions as the position of vertices will change while in the for loop
            List <Vector3> specifiedPositions = specifiedVertices.Select(item => item.Position).ToList();

            // So we know which polygons need to have their normals recalculated
            List <Polygon> affectedPolygons = new List <Polygon>();

            Polygon[] polygons = brush.GetPolygons();

            for (int i = 0; i < polygons.Length; i++)
            {
                Polygon polygon = polygons[i];

                int vertexCount = polygon.Vertices.Length;

                Vector3[] newPositions = new Vector3[vertexCount];
                Vector2[] newUV        = new Vector2[vertexCount];

                for (int j = 0; j < vertexCount; j++)
                {
                    newPositions[j] = polygon.Vertices[j].Position;
                    newUV[j]        = polygon.Vertices[j].UV;
                }

                bool polygonAffected = false;

                for (int j = 0; j < vertexCount; j++)
                {
                    Vertex vertex = polygon.Vertices[j];
                    if (specifiedPositions.Contains(vertex.Position, positionComparer))
                    {
                        Vector3 newPosition = vertex.Position + localDelta;

                        newPositions[j] = newPosition;

                        newUV[j] = GeometryHelper.GetUVForPosition(polygon, newPosition);

                        polygonAffected = true;
                    }
                }

                if (polygonAffected)
                {
                    affectedPolygons.Add(polygon);
                }

                // Apply all the changes to the polygon
                for (int j = 0; j < vertexCount; j++)
                {
                    Vertex vertex = polygon.Vertices[j];
                    vertex.Position = newPositions[j];
                    vertex.UV       = newUV[j];
                }

                polygon.CalculatePlane();
            }

            if (affectedPolygons.Count > 0)
            {
                for (int i = 0; i < affectedPolygons.Count; i++)
                {
                    affectedPolygons[i].ResetVertexNormals();
                }
            }
        }
예제 #3
0
        public void TranslateSelectedVertices(Vector3 worldDelta)
        {
            // So we know which polygons need to have their normals recalculated
            List <Polygon> affectedPolygons = new List <Polygon>();

            foreach (PrimitiveBrush brush in targetBrushes)
            {
                Polygon[] polygons   = brush.GetPolygons();
                Vector3   localDelta = brush.transform.InverseTransformDirection(worldDelta);

                for (int i = 0; i < polygons.Length; i++)
                {
                    Polygon polygon = polygons[i];

                    int vertexCount = polygon.Vertices.Length;

                    Vector3[] newPositions = new Vector3[vertexCount];
                    Vector2[] newUV        = new Vector2[vertexCount];

                    for (int j = 0; j < vertexCount; j++)
                    {
                        newPositions[j] = polygon.Vertices[j].Position;
                        newUV[j]        = polygon.Vertices[j].UV;
                    }

                    bool polygonAffected = false;

                    for (int j = 0; j < vertexCount; j++)
                    {
                        Vertex vertex = polygon.Vertices[j];
                        if (selectedVertices.ContainsKey(vertex))
                        {
                            Vector3 startPosition = startPositions[vertex];
                            Vector3 newPosition   = vertex.Position + localDelta;

                            Vector3 accumulatedDelta = newPosition - startPosition;

                            if (CurrentSettings.PositionSnappingEnabled)
                            {
                                float snapDistance = CurrentSettings.PositionSnapDistance;
                                //							newPosition = targetBrush.transform.TransformPoint(newPosition);
                                accumulatedDelta = MathHelper.RoundVector3(accumulatedDelta, snapDistance);
                                //							newPosition = targetBrush.transform.InverseTransformPoint(newPosition);
                            }

                            if (accumulatedDelta != Vector3.zero)
                            {
                                newPosition = startPosition + accumulatedDelta;

                                newPositions[j] = newPosition;

                                newUV[j] = GeometryHelper.GetUVForPosition(polygon, newPosition);

                                polygonAffected = true;
                            }
                        }
                    }

                    if (polygonAffected)
                    {
                        affectedPolygons.Add(polygon);
                    }

                    // Apply all the changes to the polygon
                    for (int j = 0; j < vertexCount; j++)
                    {
                        Vertex vertex = polygon.Vertices[j];
                        vertex.Position = newPositions[j];
                        vertex.UV       = newUV[j];
                    }

                    polygon.CalculatePlane();
                }
            }

            if (affectedPolygons.Count > 0)
            {
                for (int i = 0; i < affectedPolygons.Count; i++)
                {
                    affectedPolygons[i].ResetVertexNormals();
                }

                foreach (PrimitiveBrush brush in targetBrushes)
                {
                    brush.Invalidate(true);

                    brush.BreakTypeRelation();
                }
            }
        }
예제 #4
0
        public void TranslateSelectedVertices(Vector3 worldDelta)
        {
            foreach (PrimitiveBrush brush in targetBrushes)
            {
                bool anyAffected = false;

                Polygon[] polygons   = brush.GetPolygons();
                Vector3   localDelta = brush.transform.InverseTransformDirection(worldDelta);

                for (int i = 0; i < polygons.Length; i++)
                {
                    Polygon polygon = polygons[i];

                    polygon.CalculatePlane();
                    Vector3 previousPlaneNormal = polygons[i].Plane.normal;

                    int vertexCount = polygon.Vertices.Length;

                    Vector3[] newPositions = new Vector3[vertexCount];
                    Vector2[] newUV        = new Vector2[vertexCount];

                    for (int j = 0; j < vertexCount; j++)
                    {
                        newPositions[j] = polygon.Vertices[j].Position;
                        newUV[j]        = polygon.Vertices[j].UV;
                    }

                    bool polygonAffected = false;

                    for (int j = 0; j < vertexCount; j++)
                    {
                        Vertex vertex = polygon.Vertices[j];
                        if (selectedVertices.ContainsKey(vertex))
                        {
                            Vector3 startPosition = startPositions[vertex];
                            Vector3 newPosition   = vertex.Position + localDelta;

                            Vector3 accumulatedDelta = newPosition - startPosition;

                            if (CurrentSettings.PositionSnappingEnabled)
                            {
                                float snapDistance = CurrentSettings.PositionSnapDistance;
                                //							newPosition = targetBrush.transform.TransformPoint(newPosition);
                                accumulatedDelta = MathHelper.RoundVector3(accumulatedDelta, snapDistance);
                                //							newPosition = targetBrush.transform.InverseTransformPoint(newPosition);
                            }

                            if (accumulatedDelta != Vector3.zero)
                            {
                                newPosition = startPosition + accumulatedDelta;

                                newPositions[j] = newPosition;

                                newUV[j] = GeometryHelper.GetUVForPosition(polygon, newPosition);

                                polygonAffected = true;
                                anyAffected     = true;
                            }
                        }
                    }

                    // Apply all the changes to the polygon
                    for (int j = 0; j < vertexCount; j++)
                    {
                        Vertex vertex = polygon.Vertices[j];
                        vertex.Position = newPositions[j];
                        vertex.UV       = newUV[j];
                    }

                    if (polygonAffected)
                    {
                        // Polygon geometry has changed, inform the polygon that it needs to recalculate its cached plane
                        polygons[i].CalculatePlane();

                        Vector3 newPlaneNormal = polygons[i].Plane.normal;

                        // Find the rotation from the original polygon plane to the new polygon plane
                        Quaternion normalRotation = Quaternion.FromToRotation(previousPlaneNormal, newPlaneNormal);

                        // Update the affected normals so they are rotated by the rotational difference of the polygon from translation
                        for (int j = 0; j < vertexCount; j++)
                        {
                            Vertex vertex = polygon.Vertices[j];
                            vertex.Normal = normalRotation * vertex.Normal;
                        }
                    }
                }

                if (anyAffected)                // If any polygons have changed
                {
                    // Mark the polygons and brush as having changed
                    brush.Invalidate(true);

                    // Assume that the brush no longer resembles it's base shape, this has false positives but that's not a big issue
                    brush.BreakTypeRelation();
                }
            }
        }