예제 #1
0
    public Cone(Vector3 <TScalar> axis, TScalar radius, Vector3 <TScalar> position)
    {
        Axis     = axis;
        Position = position;
        Radius   = radius;

        Length = Vector3 <TScalar> .Length(axis);

        var two        = NumberValues.Two <TScalar>();
        var halfHeight = Length / two;
        var r2         = Radius * Radius;

        ContainingRadius = TScalar.Sqrt((halfHeight * halfHeight) + r2);

        var _halfPath = Vector3 <TScalar> .Normalize(axis) * halfHeight;

        _start = Position - _halfPath;
        _end   = _start + axis;

        var pl = Vector3 <TScalar> .Normalize(Axis);

        var pr = Vector3 <TScalar> .UnitY - (pl * Vector3 <TScalar> .Dot(Vector3 <TScalar> .UnitY, pl));
        var h  = Vector3 <TScalar> .Normalize(pr) * Radius;

        var endTop    = _end + h;
        var endBottom = _end - h;

        HighestPoint = endTop.Y >= _start.Y ? endTop : _start;
        LowestPoint  = endBottom.Y < _start.Y ? endBottom : _start;

        SmallestDimension = TScalar.Min(Length, Radius * two);

        Volume = TScalar.Pi * r2 * (Length / NumberValues.Three <TScalar>());
    }
예제 #2
0
    /// <summary>
    /// Initializes a new instance of cone with the given parameters.
    /// </summary>
    /// <param name="origin">The position of the apex of the cone.</param>
    /// <param name="orientation">The direction of the cone's axis, and its length.</param>
    /// <param name="angle">The angle of the cone.</param>
    public Cone(Vector3 <TScalar> origin, Vector3 <TScalar> orientation, TScalar angle)
    {
        Axis = orientation;

        _start = origin;
        _end   = origin + orientation;

        Length = Vector3 <TScalar> .Length(orientation);

        var two        = NumberValues.Two <TScalar>();
        var halfHeight = Length / two;

        var normalAxis = Vector3 <TScalar> .Normalize(orientation);

        Position = origin + (normalAxis * halfHeight);

        Radius = TScalar.Tan(angle / two) * Length;
        var r2 = Radius * Radius;

        ContainingRadius = TScalar.Sqrt((halfHeight * halfHeight) + r2);

        var pr = Vector3 <TScalar> .UnitY - (normalAxis * Vector3 <TScalar> .Dot(Vector3 <TScalar> .UnitY, normalAxis));
        var h  = Vector3 <TScalar> .Normalize(pr) * Radius;

        var endTop    = _end + h;
        var endBottom = _end - h;

        HighestPoint = endTop.Y >= _start.Y ? endTop : _start;
        LowestPoint  = endBottom.Y < _start.Y ? endBottom : _start;

        SmallestDimension = TScalar.Min(Length, Radius * two);

        Volume = TScalar.Pi * r2 * (Length / NumberValues.Three <TScalar>());
    }
예제 #3
0
    public Torus(TScalar majorRadius, TScalar minorRadius, Vector3 <TScalar> position, Quaternion <TScalar> rotation)
    {
        if (majorRadius < minorRadius)
        {
            throw new ArgumentException("majorRadius cannot be smaller than minorRadius", nameof(majorRadius));
        }
        MajorRadius = majorRadius;
        MinorRadius = minorRadius;
        Position    = position;
        Rotation    = rotation;

        ContainingRadius = MajorRadius + MinorRadius;

        var x = Vector3 <TScalar> .Transform(Vector3 <TScalar> .UnitX, Rotation);

        var z = Vector3 <TScalar> .Transform(Vector3 <TScalar> .UnitZ, Rotation);

        var pl = Vector3 <TScalar> .Normalize(Vector3 <TScalar> .Cross(x, z));

        var pr = Vector3 <TScalar> .UnitY - (pl * Vector3 <TScalar> .Dot(Vector3 <TScalar> .UnitY, pl));
        var h  = Vector3 <TScalar> .Normalize(pr) * MajorRadius;

        var y = Vector3 <TScalar> .UnitY * MinorRadius;

        HighestPoint = Position + h + y;
        LowestPoint  = Position - h - y;

        SmallestDimension = TScalar.Min(MajorRadius, MinorRadius);
        Volume            = NumberValues.TwoPiSquared <TScalar>() * MajorRadius * MinorRadius.Square();
    }
예제 #4
0
    public Sphere(TScalar radius, Vector3 <TScalar> position)
    {
        Position = position;
        Radius   = radius;

        HighestPoint = Position + (Vector3 <TScalar> .UnitY * radius);
        LowestPoint  = Position + (-Vector3 <TScalar> .UnitY * radius);
        Volume       = NumberValues.FourThirdsPi <TScalar>() * Radius.Cube();
    }
예제 #5
0
    public HollowSphere(TScalar innerRadius, TScalar outerRadius, Vector3 <TScalar> position)
    {
        InnerRadius = innerRadius;
        OuterRadius = outerRadius;
        Position    = position;

        HighestPoint = Position + (Vector3 <TScalar> .UnitY * outerRadius);
        LowestPoint  = Position + (-Vector3 <TScalar> .UnitY * outerRadius);
        var fourThirdsPi = NumberValues.FourThirdsPi <TScalar>();
        var three        = NumberValues.Three <TScalar>();

        Volume = (fourThirdsPi * TScalar.Pow(OuterRadius, three))
                 - (fourThirdsPi * TScalar.Pow(InnerRadius, three));
    }
예제 #6
0
    public Cuboid(TScalar axisX, TScalar axisY, TScalar axisZ, Vector3 <TScalar> position, Quaternion <TScalar> rotation)
    {
        AxisX    = axisX;
        AxisY    = axisY;
        AxisZ    = axisZ;
        Position = position;
        Rotation = rotation;

        var two = NumberValues.Two <TScalar>();

        ContainingRadius  = TScalar.Sqrt((AxisX * AxisX) + (AxisY * AxisY) + (AxisZ * AxisZ)) / two;
        SmallestDimension = TScalar.Min(AxisX, TScalar.Min(AxisY, AxisZ));
        Volume            = AxisX * AxisY * AxisZ;

        var x = Vector3 <TScalar> .Transform(Vector3 <TScalar> .UnitX *(AxisX / two), Rotation);

        var y = Vector3 <TScalar> .Transform(Vector3 <TScalar> .UnitY *(AxisY / two), Rotation);

        var z = Vector3 <TScalar> .Transform(Vector3 <TScalar> .UnitZ *(AxisZ / two), Rotation);

        Corners = new Vector3 <TScalar>[8]
        {
            Position + x + y + z,
            Position + x - y + z,
            Position + x - y - z,
            Position + x + y - z,
            Position - x + y - z,
            Position - x - y - z,
            Position - x - y + z,
            Position - x + y + z
        };

        HighestPoint = Corners[0];
        LowestPoint  = Corners[0];
        for (var i = 1; i < 8; i++)
        {
            if (Corners[i].Y > HighestPoint.Y)
            {
                HighestPoint = Corners[i];
            }
            if (Corners[i].Y < LowestPoint.Y)
            {
                LowestPoint = Corners[i];
            }
        }
    }
예제 #7
0
    public Ellipsoid(TScalar axisX, TScalar axisY, TScalar axisZ, Vector3 <TScalar> position, Quaternion <TScalar> rotation)
    {
        AxisX    = axisX;
        AxisY    = axisY;
        AxisZ    = axisZ;
        Position = position;
        Rotation = rotation;

        ContainingRadius = TScalar.Max(AxisX, TScalar.Max(AxisY, AxisZ));

        var x = Vector3 <TScalar> .Transform(Vector3 <TScalar> .UnitX *AxisX, Rotation);

        var y = Vector3 <TScalar> .Transform(Vector3 <TScalar> .UnitY *AxisY, Rotation);

        var z = Vector3 <TScalar> .Transform(Vector3 <TScalar> .UnitZ *AxisZ, Rotation);

        var points = new Vector3 <TScalar>[6]
        {
            Position + x,
            Position + y,
            Position + z,
            Position - x,
            Position - y,
            Position - z,
        };

        HighestPoint = points[0];
        LowestPoint  = points[0];
        for (var i = 0; i < 6; i++)
        {
            if (points[i].Y > HighestPoint.Y)
            {
                HighestPoint = points[i];
            }
            if (points[i].Y < LowestPoint.Y)
            {
                LowestPoint = points[i];
            }
        }

        SmallestDimension = TScalar.Min(AxisX, TScalar.Min(AxisY, AxisZ));
        Volume            = NumberValues.FourThirdsPi <TScalar>() * AxisX * AxisY * AxisZ;
    }
예제 #8
0
    private static bool Quadratic(TScalar a, TScalar b, TScalar c, out TScalar root1, out TScalar root2)
    {
        var q = (b * b) - (NumberValues.Four <TScalar>() * a * c);

        if (q >= TScalar.Zero)
        {
            var sq = TScalar.Sqrt(q);
            var d  = TScalar.One / (NumberValues.Two <TScalar>() * a);
            root1 = (-b + sq) * d;
            root2 = (-b - sq) * d;
            return(true);
        }
        else
        {
            root1 = TScalar.NaN;
            root2 = TScalar.NaN;
            return(false);
        }
    }
예제 #9
0
    public Capsule(Vector3 <TScalar> axis, TScalar radius, Vector3 <TScalar> position)
    {
        Axis     = axis;
        Position = position;
        Radius   = radius;

        var two = NumberValues.Two <TScalar>();

        _pathLength = Vector3 <TScalar> .Length(axis);

        var twoR = Radius * two;

        Length = _pathLength + twoR;

        var halfHeight = _pathLength / two;

        ContainingRadius = halfHeight + Radius;

        var _halfPath = Vector3 <TScalar> .Normalize(axis) * halfHeight;

        _start = Position - _halfPath;
        _end   = _start + axis;

        var y = Vector3 <TScalar> .UnitY * Radius;

        if (_end.Y >= _start.Y)
        {
            HighestPoint = _end + y;
            LowestPoint  = _start - y;
        }
        else
        {
            HighestPoint = _start + y;
            LowestPoint  = _end - y;
        }

        SmallestDimension = TScalar.Min(Length, twoR);

        Volume = (TScalar.Pi * Radius * Radius * _pathLength)
                 + (NumberValues.FourThirdsPi <TScalar>() * Radius.Cube());
    }
예제 #10
0
    public Cylinder(Vector3 <TScalar> axis, TScalar radius, Vector3 <TScalar> position)
    {
        Axis     = axis;
        Position = position;
        Radius   = radius;

        var two        = NumberValues.Two <TScalar>();
        var axisLength = Vector3 <TScalar> .Length(axis);

        var halfHeight = axisLength / two;
        var r2         = Radius * Radius;

        ContainingRadius = TScalar.Sqrt((halfHeight * halfHeight) + r2);

        var _halfPath = Vector3 <TScalar> .Normalize(axis) * halfHeight;

        _start = Position - _halfPath;
        _end   = _start + axis;

        var pl = Vector3 <TScalar> .Normalize(Axis);

        var pr = Vector3 <TScalar> .UnitY - (pl * Vector3 <TScalar> .Dot(Vector3 <TScalar> .UnitY, pl));
        var h  = Vector3 <TScalar> .Normalize(pr) * Radius;

        if (_end.Y >= _start.Y)
        {
            HighestPoint = _end + h;
            LowestPoint  = _start - h;
        }
        else
        {
            HighestPoint = _start + h;
            LowestPoint  = _end - h;
        }

        SmallestDimension = TScalar.Min(axisLength, Radius * two);

        Volume = TScalar.Pi * r2 * axisLength;
    }
예제 #11
0
        private static void Main(string[] args)
        {
            Verbose = false;
            // TODO: parse args

            var defaultCategoryValues = "Cn,L";

            // Create a 12:4:4 table for Unicode category
            // "Cn", Not assigned.  The value is 1 byte to indicate Unicode category
            // Make sure to put the default value into the slot 0 in $categoriesValueTable
            var categoriesIndexTable = new DataTable();
            // Create a 12:4:4 table for decimal digit value/digit value/numeric value
            var numericIndexTable = new DataTable();
            // Create a flat table for Unicode category and BiDi category
            var categoriesValueTable = new FlatDataTable(defaultCategoryValues, GetCategoriesValueBytes);
            // Create a flat table.
            // GetNumericValueBytes() is the callback used to generate the bytes of each item.
            var numericValueTable = new FlatDataTable("-1", GetNumericValueBytes);
            // Create a flat table for digit values
            // GetDigitValueBytes() is the callback used to generate the bytes of each item.
            var digitValueTable = new FlatDataTable("255,255", GetDigitValueBytes);

            // Add a default item into the category value table.  This will be the item 0 in the category value table.
            GetCategoryValueItem(categoriesValueTable, defaultCategoryValues);
            NumberValues.Add("-1,255,255", 0);
            numericValueTable.AddData(0, "-1");
            digitValueTable.AddData(0, "255,255");

            ReadSourceFile("UnicodeData.txt", categoriesIndexTable, categoriesValueTable, numericIndexTable, numericValueTable, digitValueTable);

            categoriesIndexTable.GenerateTable(nameof(categoriesIndexTable), 5, 4);
            //categoriesIndexTable.CalculateTableVariants();
            numericIndexTable.GenerateTable(nameof(numericIndexTable), 4, 4, cutOff: true);
            //numericIndexTable.CalculateTableVariants(cutOff: true);

            // generate the data C# source
            using (var file = File.CreateText(SOURCE_NAME))
            {
                file.Write("// Licensed to the .NET Foundation under one or more agreements.\n");
                file.Write("// The .NET Foundation licenses this file to you under the MIT license.\n");
                file.Write("// See the LICENSE file in the project root for more information.\n\n");

                file.Write("namespace System.Globalization\n");
                file.Write("{\n");
                file.Write("    public static partial class CharUnicodeInfo\n    {\n");

                file.Write("        // THE FOLLOWING DATA IS AUTO GENERATED BY GenUnicodeProp program UNDER THE TOOLS FOLDER\n");
                file.Write("        // PLEASE DON'T MODIFY BY HAND\n\n\n");

                file.Write("        // 11:5:4 index table of the Unicode category data.");
                PrintSourceIndexArray("CategoryLevel1Index", categoriesIndexTable, file);

                PrintValueArray("CategoriesValue", categoriesValueTable, file);

                file.Write("\n        // 12:4:4 index table of the Unicode numeric data.");
                PrintSourceIndexArray("NumericLevel1Index", numericIndexTable, file);

                file.Write("\n        // Every item contains the value for numeric value.");
                PrintValueArray("NumericValues", numericValueTable, file);

                PrintValueArray("DigitValues", digitValueTable, file);

                file.Write("\n    }\n}");
            }
        }
예제 #12
0
        /// <summary>
        /// This method allows the assignment and retrieval of the values of the enumeration
        /// </summary>
        /// <param name="numberValues">The value of the enum</param>
        public static int NumberValue(NumberValues numberValues)
        {
            int number = (int)numberValues;

            return(number);
        }
예제 #13
0
    public Frustum(
        TScalar aspectRatio,
        Vector3 <TScalar> axis,
        TScalar fieldOfViewAngle,
        TScalar nearPlaneDistance,
        Vector3 <TScalar> position,
        Quaternion <TScalar> rotation)
    {
        AspectRatio       = aspectRatio;
        Axis              = axis;
        FieldOfViewAngle  = fieldOfViewAngle;
        NearPlaneDistance = nearPlaneDistance;
        Position          = position;
        Rotation          = rotation;

        var farPlaneDistSq = Vector3 <TScalar> .LengthSquared(Axis);

        FarPlaneDistance = TScalar.Sqrt(farPlaneDistSq);

        var two    = NumberValues.Two <TScalar>();
        var tan    = TScalar.Tan(fieldOfViewAngle);
        var tanSq4 = tan.Square() * NumberValues.Four <TScalar>();
        var tanAR  = tan * aspectRatio;

        Volume = tanSq4
                 * aspectRatio
                 * ((farPlaneDistSq * FarPlaneDistance) - nearPlaneDistance.Cube())
                 / NumberValues.Three <TScalar>();

        SmallestDimension = aspectRatio <= TScalar.One
            ? two * tanAR * nearPlaneDistance
            : two * tan * nearPlaneDistance;

        ContainingRadius = TScalar.Sqrt(
            (FarPlaneDistance - nearPlaneDistance).Square()
            + (tanSq4 * farPlaneDistSq * (TScalar.One + aspectRatio.Square())))
                           / two;

        axis = position - (axis / two);
        var basis1 = Vector3 <TScalar> .Transform(Vector3 <TScalar> .Normalize(axis), rotation);

        Vector3 <TScalar> basis2, basis3;

        if (basis1.Z.IsNearlyEqualTo(TScalar.NegativeOne))
        {
            basis2 = new Vector3 <TScalar>(TScalar.Zero, TScalar.NegativeOne, TScalar.Zero);
            basis3 = new Vector3 <TScalar>(TScalar.NegativeOne, TScalar.Zero, TScalar.Zero);
        }
        else
        {
            var a = TScalar.One / (TScalar.One + basis1.Z);
            var b = -basis1.X * basis1.Y * a;
            basis2 = new Vector3 <TScalar>(TScalar.One - (basis1.X.Square() * a), b, -basis1.X);
            basis3 = new Vector3 <TScalar>(b, TScalar.One - (basis1.Y.Square() * a), -basis1.Y);
        }
        var farY  = basis2 * farPlaneDistSq * tanAR;
        var farZ  = basis3 * tan * FarPlaneDistance;
        var nearX = basis1 * nearPlaneDistance;
        var nearY = basis2 * nearPlaneDistance.Square() * tanAR;
        var nearZ = basis3 * tan * nearPlaneDistance;

        Corners = new Vector3 <TScalar>[8]
        {
            Position + axis - farY + farZ,
            Position + axis + farY + farZ,
            Position + axis - farY - farZ,
            Position + axis + farY - farZ,
            Position + nearX + nearY - nearZ,
            Position + nearX - nearY - nearZ,
            Position + nearX - nearY + nearZ,
            Position + nearX + nearY + nearZ
        };

        HighestPoint = Corners[0];
        LowestPoint  = Corners[0];
        for (var i = 1; i < 8; i++)
        {
            if (Corners[i].Y > HighestPoint.Y)
            {
                HighestPoint = Corners[i];
            }
            if (Corners[i].Y < LowestPoint.Y)
            {
                LowestPoint = Corners[i];
            }
        }

        Planes = new Plane <TScalar>[6]
        {
            Plane <TScalar> .CreateFromVertices(Corners[0], Corners[1], Corners[2]),
            Plane <TScalar> .CreateFromVertices(Corners[0], Corners[1], Corners[4]),
            Plane <TScalar> .CreateFromVertices(Corners[0], Corners[1], Corners[5]),
            Plane <TScalar> .CreateFromVertices(Corners[0], Corners[1], Corners[6]),
            Plane <TScalar> .CreateFromVertices(Corners[0], Corners[1], Corners[7]),
            Plane <TScalar> .CreateFromVertices(Corners[4], Corners[5], Corners[6]),
        };
    }