private static void _Fill(Span <PointNode> nodes, ReadOnlySpan <VECTOR3> points, float diameter, bool closed)
            {
                System.Diagnostics.Debug.Assert(points.Length > 1);
                System.Diagnostics.Debug.Assert(points[0] != points[points.Length - 1]);

                var joinPoint = closed ? VECTOR3.Normalize(points[points.Length - 1] - points[0]) : VECTOR3.Zero;

                for (int i = 0; i < nodes.Length; i++)
                {
                    nodes[i].Point    = points[i];
                    nodes[i].Diameter = diameter;

                    var prevDir = i > 0 ? VECTOR3.Normalize(points[i - 1] - points[i]) : joinPoint;
                    var nextDir = i < points.Length - 1 ? VECTOR3.Normalize(points[i] - points[i + 1]) : joinPoint;

                    var angle = POINT3.AngleInRadians(prevDir, nextDir);
                    nodes[i].Angle     = float.IsNaN(angle) ? 0 : angle;
                    nodes[i].Direction = -VECTOR3.Normalize(prevDir + nextDir);
                    nodes[i].Axis      = VECTOR3.Normalize(VECTOR3.Cross(prevDir, nextDir));

                    if (float.IsNaN(nodes[i].Axis.X))
                    {
                        nodes[i].Axis = VECTOR3.Zero;
                    }
                }
            }
            private readonly void _FillSection(Span <POINT3> points, int divisions, VECTOR3 mainAxis)
            {
                var r = _AdjustNGonRadius(Diameter / 2, divisions);

                var nz = Direction;
                var ny = VECTOR3.Cross(nz, mainAxis);
                var nx = VECTOR3.Cross(ny, nz);

                nx = VECTOR3.Normalize(nx);
                ny = VECTOR3.Normalize(ny);

                var nt = this.GetScale(4);

                for (int i = 0; i < divisions; ++i)
                {
                    var angle = -PI * 2 * i / divisions;

                    #if NETSTANDARD2_1_OR_GREATER
                    var p = nx * MathF.Cos(angle) + ny * MathF.Sin(angle) * nt;
                    #else
                    var p = nx * (float)Math.Cos(angle) + ny * (float)Math.Sin(angle) * nt;
                    #endif

                    points[i] = Point + p * r;
                }

                POINT3.DebugAssertIsFinite(points);
            }
            private static VECTOR3 _GetMainAxis(ReadOnlySpan <PointNode> nodes)
            {
                if (nodes.Length < 2)
                {
                    return(VECTOR3.UnitX);
                }
                if (nodes.Length == 2)
                {
                    var d = new POINT3(nodes[1].Point - nodes[0].Point);

                    // calculate a vector perpendicular to D
                    var a = VECTOR3.Cross(d.XYZ, d.DominantAxis == 0 ? VECTOR3.UnitY : VECTOR3.UnitX);

                    System.Diagnostics.Debug.Assert(a != VECTOR3.Zero);

                    return(a);
                }

                var axis = VECTOR3.Zero;

                for (int i = 2; i < nodes.Length; i++)
                {
                    var ab = nodes[i - 2].Point - nodes[i - 1].Point;
                    var ac = nodes[i - 1].Point - nodes[i - 0].Point;
                    axis += VECTOR3.Cross(ab, ac);
                }

                return(VECTOR3.Normalize(axis));
            }
Beispiel #4
0
        public SimpleVertex(Vector3 position, Vector3 normal, Color4f color)
        {
            this.Color    = color;
            this.Normal   = Vector3.Normalize(normal);
            this.Position = position;

            this.__packing = 0f;
        }
Beispiel #5
0
        public static CameraView3D CreateLookingAt(Record3D scene, XYZ direction)
        {
            if (direction == XYZ.Zero)
            {
                direction = -XYZ.UnitZ;
            }

            direction = XYZ.Normalize(direction);

            throw new NotImplementedException();

            // var bounds = scene.SphereBounds;

            // return CreatePerspective(bounds.Center - direction * bounds.Radius * 2, bounds.Center);
        }
Beispiel #6
0
        public void GunCalibrationFinalize()
        {
            // Old way
            Vector3.Normalize(vectorPointedForward);
            Vector3.Normalize(vectorPointedDown);
            pitch_axis = Vector3.Cross(vectorPointedDown, vectorPointedForward);
            Vector3.Normalize(pitch_axis);
            var roll_axis_approx = Vector3.Add(vectorPointedForward, Vector3.Cross(pitch_axis, vectorPointedDown));

            Vector3.Normalize(roll_axis_approx);
            yaw_axis = Vector3.Cross(pitch_axis, roll_axis_approx);
            Vector3.Normalize(yaw_axis);
            roll_axis = Vector3.Cross(yaw_axis, pitch_axis); // No need to normalize this one.

            // New way
            //propRotation = ReferenceFrame.CalibratePropOrientation(orientationPointedForward, orientationPointedDown);
            SaveSpecifics();
        }
Beispiel #7
0
    public static Vector3 Normalize(Vector3 value)
    {
        var result = SysVector3.Normalize(value._value);

        return(new Vector3(result));
    }
Beispiel #8
0
        public override void Update(MouseState mouseState, KeyboardState keyboardState)
        {
            int deltaX     = mouseState.X - mMousePreviousX;
            int deltaY     = mouseState.Y - mMousePreviousY;
            int deltaWheel = mouseState.Wheel - mMousePreviousWheel;

            if (mouseState.LeftButton == ButtonState.Pressed && mPreviousLeftButton == ButtonState.Pressed)
            {
                mOrbitRotation.X -= deltaX * 0.18f;
                mOrbitRotation.Y -= deltaY * 0.18f;
                mOrbitRotation.Y  = MathHelper.Clamp(mOrbitRotation.Y, -89.9f, +89.9f);
            }

            float wheelSpeed =
                keyboardState.IsKeyDown(cSpeedUpKey) ? cWheelSpeedFast :
                keyboardState.IsKeyDown(cSlowDownKey) ? cWheelSpeedSlow : cWheelSpeed;

            mOrbitDistance = MathHelper.Clamp(mOrbitDistance - (wheelSpeed * deltaWheel), mOrbitDistanceMin,
                                              mOrbitDistanceMax);

            var frontDirection = mInterest - mViewPoint;

            frontDirection.Y = 0.0f;
            frontDirection   = Vector3.Normalize(frontDirection);

            float speed =
                keyboardState.IsKeyDown(cSpeedUpKey) ? cSpeedFast :
                keyboardState.IsKeyDown(cSlowDownKey) ? cSpeedSlow : cSpeed;

            bool front = keyboardState.IsKeyDown(Key.W);
            bool back  = keyboardState.IsKeyDown(Key.S);
            bool left  = keyboardState.IsKeyDown(Key.A);
            bool right = keyboardState.IsKeyDown(Key.D);
            bool up    = keyboardState.IsKeyDown(Key.Space);
            bool down  = keyboardState.IsKeyDown(Key.ControlLeft);

            if (front && !back)
            {
                mInterest += frontDirection * speed;
            }

            else if (back && !front)
            {
                mInterest -= frontDirection * speed;
            }

            if (left && !right)
            {
                mInterest -= Vector3.Normalize(Vector3.Cross(frontDirection, Vector3.UnitY)) * speed;
            }

            else if (right && !left)
            {
                mInterest += Vector3.Normalize(Vector3.Cross(frontDirection, Vector3.UnitY)) * speed;
            }

            if (up && !down)
            {
                mInterest += Vector3.UnitY * speed / 2;
            }

            else if (!up && down)
            {
                mInterest -= Vector3.UnitY * speed / 2;
            }

            mViewPoint = mInterest + CalculateCameraOrbitPosition();

            mPreviousLeftButton = mouseState.LeftButton;
            mMousePreviousX     = mouseState.X;
            mMousePreviousY     = mouseState.Y;
            mMousePreviousWheel = mouseState.Wheel;
        }
Beispiel #9
0
        public GLMesh(Mesh mesh, Matrix4x4 modelMatrix, List <Bone> bones, List <GLNode> nodes, Dictionary <string, GLMaterial> materials)
        {
            Mesh = mesh;

            var vertices = mesh.Vertices;
            var normals  = mesh.Normals;

            if (mesh.VertexWeights != null)
            {
                vertices = new Vector3[mesh.VertexCount];
                normals  = null;

                if (mesh.Normals != null)
                {
                    normals = new Vector3[mesh.VertexCount];
                }

                Matrix4x4.Invert(modelMatrix, out var modelMatrixInv);

                for (int i = 0; i < mesh.VertexCount; i++)
                {
                    var position = mesh.Vertices[i];
                    var normal   = mesh.Normals?[i] ?? Vector3.Zero;

                    var newPosition = Vector3.Zero;
                    var newNormal   = Vector3.Zero;

                    for (int j = 0; j < 4; j++)
                    {
                        var weight = mesh.VertexWeights[i].Weights[j];
                        if (weight == 0)
                        {
                            continue;
                        }

                        var boneIndex = mesh.VertexWeights[i].Indices[j];
                        TransformVertex(bones, nodes, position, normal, ref newPosition, ref newNormal, weight, boneIndex);
                    }

                    vertices[i] = Vector3.Transform(newPosition, modelMatrixInv);

                    if (normals != null)
                    {
                        normals[i] =
                            Vector3.Normalize(Vector3.TransformNormal(newNormal, modelMatrixInv));
                    }
                }
            }

            var indices = new uint[mesh.Triangles.Length * 3];

            for (int i = 0; i < mesh.Triangles.Length; i++)
            {
                indices[(i * 3) + 0] = mesh.Triangles[i].A;
                indices[(i * 3) + 1] = mesh.Triangles[i].B;
                indices[(i * 3) + 2] = mesh.Triangles[i].C;
            }

            VertexArray = new GLVertexArray(vertices, normals, mesh.TexCoordsChannel0, indices, PrimitiveType.Triangles);

            // material
            if (mesh.MaterialName != null && materials != null)
            {
                if (materials.TryGetValue(mesh.MaterialName, out var material))
                {
                    Material = material;
                }
                else
                {
                    Trace.TraceError($"Mesh referenced material \"{mesh.MaterialName}\" which does not exist in the model");
                    Material = new GLMaterial();
                }
            }
            else
            {
                Material = new GLMaterial();
            }

            IsVisible = true;
        }
Beispiel #10
0
        /**
         * Split an individual face
         *
         * @param facePos face position on the array of faces
         * @param segment1 segment representing the intersection of the face with the plane
         * of another face
         * @return segment2 segment representing the intersection of other face with the
         * plane of the current face plane
         */
        private void splitFace(int facePos, Segment segment1, Segment segment2)
        {
            Vertex  startPosVertex, endPosVertex;
            Point3d startPos, endPos;
            int     startType, endType, middleType;
            double  startDist, endDist;

            Face   face        = getFace(facePos);
            Vertex startVertex = segment1.getStartVertex();
            Vertex endVertex   = segment1.getEndVertex();

            //starting point: deeper starting point
            if (segment2.getStartDistance() > segment1.getStartDistance() + TOL)
            {
                startDist = segment2.getStartDistance();
                startType = segment1.getIntermediateType();
                startPos  = segment2.getStartPosition();
            }
            else
            {
                startDist = segment1.getStartDistance();
                startType = segment1.getStartType();
                startPos  = segment1.getStartPosition();
            }

            //ending point: deepest ending point
            if (segment2.getEndDistance() < segment1.getEndDistance() - TOL)
            {
                endDist = segment2.getEndDistance();
                endType = segment1.getIntermediateType();
                endPos  = segment2.getEndPosition();
            }
            else
            {
                endDist = segment1.getEndDistance();
                endType = segment1.getEndType();
                endPos  = segment1.getEndPosition();
            }
            middleType = segment1.getIntermediateType();

            //set vertex to BOUNDARY if it is start type
            if (startType == Segment.VERTEX)
            {
                startVertex.setStatus(Vertex.BOUNDARY);
            }

            //set vertex to BOUNDARY if it is end type
            if (endType == Segment.VERTEX)
            {
                endVertex.setStatus(Vertex.BOUNDARY);
            }

            //VERTEX-_______-VERTEX
            if (startType == Segment.VERTEX && endType == Segment.VERTEX)
            {
                return;
            }

            //______-EDGE-______
            else if (middleType == Segment.EDGE)
            {
                //gets the edge
                int splitEdge;
                if ((startVertex == face.v1 && endVertex == face.v2) || (startVertex == face.v2 && endVertex == face.v1))
                {
                    splitEdge = 1;
                }
                else if ((startVertex == face.v2 && endVertex == face.v3) || (startVertex == face.v3 && endVertex == face.v2))
                {
                    splitEdge = 2;
                }
                else
                {
                    splitEdge = 3;
                }

                //VERTEX-EDGE-EDGE
                if (startType == Segment.VERTEX)
                {
                    breakFaceInTwo(facePos, endPos, splitEdge);
                    return;
                }

                //EDGE-EDGE-VERTEX
                else if (endType == Segment.VERTEX)
                {
                    breakFaceInTwo(facePos, startPos, splitEdge);
                    return;
                }

                // EDGE-EDGE-EDGE
                else if (startDist == endDist)
                {
                    breakFaceInTwo(facePos, endPos, splitEdge);
                }
                else
                {
                    if ((startVertex == face.v1 && endVertex == face.v2) || (startVertex == face.v2 && endVertex == face.v3) || (startVertex == face.v3 && endVertex == face.v1))
                    {
                        breakFaceInThree(facePos, startPos, endPos, splitEdge);
                    }
                    else
                    {
                        breakFaceInThree(facePos, endPos, startPos, splitEdge);
                    }
                }
                return;
            }

            //______-FACE-______

            //VERTEX-FACE-EDGE
            else if (startType == Segment.VERTEX && endType == Segment.EDGE)
            {
                breakFaceInTwo(facePos, endPos, endVertex);
            }
            //EDGE-FACE-VERTEX
            else if (startType == Segment.EDGE && endType == Segment.VERTEX)
            {
                breakFaceInTwo(facePos, startPos, startVertex);
            }
            //VERTEX-FACE-FACE
            else if (startType == Segment.VERTEX && endType == Segment.FACE)
            {
                breakFaceInThree(facePos, endPos, startVertex);
            }
            //FACE-FACE-VERTEX
            else if (startType == Segment.FACE && endType == Segment.VERTEX)
            {
                breakFaceInThree(facePos, startPos, endVertex);
            }
            //EDGE-FACE-EDGE
            else if (startType == Segment.EDGE && endType == Segment.EDGE)
            {
                breakFaceInThree(facePos, startPos, endPos, startVertex, endVertex);
            }
            //EDGE-FACE-FACE
            else if (startType == Segment.EDGE && endType == Segment.FACE)
            {
                breakFaceInFour(facePos, startPos, endPos, startVertex);
            }
            //FACE-FACE-EDGE
            else if (startType == Segment.FACE && endType == Segment.EDGE)
            {
                breakFaceInFour(facePos, endPos, startPos, endVertex);
            }
            //FACE-FACE-FACE
            else if (startType == Segment.FACE && endType == Segment.FACE)
            {
                Vector3d segmentVector = new Vector3d(startPos.X - endPos.X, startPos.Y - endPos.Y, startPos.Z - endPos.Z);

                //if the intersection segment is a point only...
                if (Math.Abs(segmentVector.X) < TOL && Math.Abs(segmentVector.Y) < TOL && Math.Abs(segmentVector.Z) < TOL)
                {
                    breakFaceInThree(facePos, startPos);
                    return;
                }

                //gets the vertex more lined with the intersection segment
                int      linedVertex;
                Point3d  linedVertexPos;
                Vector3d vertexVector = Vector3d.Normalize(new Vector3d(endPos.X - face.v1.X, endPos.Y - face.v1.Y, endPos.Z - face.v1.Z));

                double dot1 = Math.Abs(Vector3d.Dot(segmentVector, vertexVector));
                vertexVector = Vector3d.Normalize(new Vector3d(endPos.X - face.v2.X, endPos.Y - face.v2.Y, endPos.Z - face.v2.Z));

                double dot2 = Math.Abs(Vector3d.Dot(segmentVector, vertexVector));
                vertexVector = Vector3d.Normalize(new Vector3d(endPos.X - face.v3.X, endPos.Y - face.v3.Y, endPos.Z - face.v3.Z));

                double dot3 = Math.Abs(Vector3d.Dot(segmentVector, vertexVector));
                if (dot1 > dot2 && dot1 > dot3)
                {
                    linedVertex    = 1;
                    linedVertexPos = face.v1.getPosition();
                }
                else if (dot2 > dot3 && dot2 > dot1)
                {
                    linedVertex    = 2;
                    linedVertexPos = face.v2.getPosition();
                }
                else
                {
                    linedVertex    = 3;
                    linedVertexPos = face.v3.getPosition();
                }

                // Now find which of the intersection endpoints is nearest to that vertex.
                //if (linedVertexPos.distance(startPos) > linedVertexPos.distance(endPos)) {
                if (Vector3d.DistanceSquared(linedVertexPos, startPos) > Vector3d.DistanceSquared(linedVertexPos, endPos))
                {
                    breakFaceInFive(facePos, startPos, endPos, linedVertex);
                }
                else
                {
                    breakFaceInFive(facePos, endPos, startPos, linedVertex);
                }
            }
        }