< Summary

Class:GDX.Vector3Extensions
Assembly:GDX
File(s):./Packages/com.dotbunny.gdx/GDX/Vector3Extensions.cs
Covered lines:68
Uncovered lines:0
Coverable lines:68
Total lines:196
Line coverage:100% (68 of 68)
Covered branches:0
Total branches:0
Covered methods:7
Total methods:7
Method coverage:100% (7 of 7)

Coverage History

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity NPath complexity Sequence coverage
Approximately(...)0%330100%
DistanceSqr(...)0%110100%
HorizontalDistance(...)0%110100%
DistanceToRay(...)0%110100%
Midpoint(...)0%110100%
NearestIndex(...)0%6.046090%
TryParseVector3(...)0%10.056051.72%

File(s)

./Packages/com.dotbunny.gdx/GDX/Vector3Extensions.cs

#LineLine coverage
 1// Copyright (c) 2020-2024 dotBunny Inc.
 2// dotBunny licenses this file to you under the BSL-1.0 license.
 3// See the LICENSE file in the project root for more information.
 4
 5#if !UNITY_DOTSRUNTIME
 6
 7using System.Runtime.CompilerServices;
 8using Unity.Mathematics;
 9using UnityEngine;
 10
 11namespace GDX
 12{
 13    /// <summary>
 14    ///     <see cref="Vector3" /> Based Extension Methods
 15    /// </summary>
 16    /// <exception cref="UnsupportedRuntimeException">Not supported on DOTS Runtime.</exception>
 17    [VisualScriptingCompatible(2)]
 18    public static class Vector3Extensions
 19    {
 20        /// <summary>
 21        ///     Is one <see cref="Vector3" /> approximately similar to another <see cref="Vector3" />?
 22        /// </summary>
 23        /// <remarks>Includes optimized Unity.Mathematics approach.</remarks>
 24        /// <param name="targetVector3">Point A</param>
 25        /// <param name="otherVector3">Point B</param>
 26        /// <returns>Are the two <see cref="Vector3" /> approximately the same?</returns>
 27        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 28        public static bool Approximately(this Vector3 targetVector3, Vector3 otherVector3)
 829        {
 830            float moddedEpsilon = Mathf.Epsilon * 8f;
 31            const float k_BaseMultiplier = 1E-06f;
 832            return math.abs(otherVector3.x - targetVector3.x) < math.max(
 33                       k_BaseMultiplier * math.max(math.abs(targetVector3.x), math.abs(otherVector3.x)),
 34                       moddedEpsilon) &&
 35                   math.abs(otherVector3.y - targetVector3.y) < math.max(
 36                       k_BaseMultiplier * math.max(math.abs(targetVector3.y), math.abs(otherVector3.y)),
 37                       moddedEpsilon) &&
 38                   math.abs(otherVector3.z - targetVector3.z) < math.max(
 39                       k_BaseMultiplier * math.max(math.abs(targetVector3.z), math.abs(otherVector3.z)),
 40                       moddedEpsilon);
 841        }
 42
 43        /// <summary>
 44        ///     Calculate the squared distance between two <see cref="Vector3" />.
 45        /// </summary>
 46        /// <remarks>
 47        ///     <para>Based on https://en.wikipedia.org/wiki/Euclidean_distance#Squared_Euclidean_distance.</para>
 48        /// </remarks>
 49        /// <param name="targetVector3">Point A</param>
 50        /// <param name="otherVector3">Point B</param>
 51        /// <returns>The squared distance.</returns>
 52        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 53        public static float DistanceSqr(this Vector3 targetVector3, Vector3 otherVector3)
 154        {
 155            float x = targetVector3.x - otherVector3.x;
 156            float y = targetVector3.y - otherVector3.y;
 157            float z = targetVector3.z - otherVector3.z;
 158            return x * x + y * y + z * z;
 159        }
 60
 61        /// <summary>
 62        ///     Get the horizontal distance between two <see cref="Vector3" /> points.
 63        /// </summary>
 64        /// <remarks>Ignores the Y-axis completely.</remarks>
 65        /// <param name="targetVector3">Point A</param>
 66        /// <param name="otherVector3">Point B</param>
 67        /// <returns>The horizontal distance.</returns>
 68        public static float HorizontalDistance(this Vector3 targetVector3, Vector3 otherVector3)
 169        {
 170            float num1 = targetVector3.x - otherVector3.x;
 171            float num2 = targetVector3.z - otherVector3.z;
 172            return (float)math.sqrt(num1 * (double)num1 + num2 * (double)num2);
 173        }
 74
 75        /// <summary>
 76        ///     Calculate the distance from a <see cref="Vector3" /> to a <see cref="Ray" />.
 77        /// </summary>
 78        /// <param name="targetVector3">The position.</param>
 79        /// <param name="targetRay">The line.</param>
 80        /// <returns>The distance.</returns>
 81        public static float DistanceToRay(this Vector3 targetVector3, Ray targetRay)
 182        {
 183            return Vector3.Cross(targetRay.direction, targetVector3 - targetRay.origin).magnitude;
 184        }
 85
 86        /// <summary>
 87        ///     Get the midpoint between two <see cref="Vector3" />s.
 88        /// </summary>
 89        /// <param name="targetVector3">Point A</param>
 90        /// <param name="otherVector3">Point B</param>
 91        /// <returns>The midpoint between <paramref name="targetVector3" /> and <paramref name="otherVector3" />.</retur
 92        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 93        public static Vector3 Midpoint(this Vector3 targetVector3, Vector3 otherVector3)
 194        {
 195            return new Vector3(
 96                targetVector3.x + (otherVector3.x - targetVector3.x) * 0.5f,
 97                targetVector3.y + (otherVector3.y - targetVector3.y) * 0.5f,
 98                targetVector3.z + (otherVector3.z - targetVector3.z) * 0.5f
 99            );
 1100        }
 101
 102        /// <summary>
 103        ///     Find the index of the <see cref="Vector3" /> in <paramref name="otherVector3" /> that is nearest to the
 104        ///     <paramref name="targetVector3" />.
 105        /// </summary>
 106        /// <param name="targetVector3">The <see cref="Vector3" /> to use as the point of reference.</param>
 107        /// <param name="otherVector3">An array of <see cref="Vector3" /> positions to evaluate for which one is nearest
 108        /// <returns>
 109        ///     The index of the nearest <paramref name="otherVector3" /> element to <paramref name="targetVector3" />.
 110        ///     Returning -1 if the the <paramref name="otherVector3" /> has no elements or is null.
 111        /// </returns>
 112        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 113        public static int NearestIndex(this Vector3 targetVector3, Vector3[] otherVector3)
 2114        {
 115            // We found nothing to compare against
 2116            if (otherVector3 == null || otherVector3.Length == 0)
 1117            {
 1118                return -1;
 119            }
 120
 1121            float closestSquareMagnitude = float.PositiveInfinity;
 1122            int closestIndex = -1;
 1123            int otherVector3Length = otherVector3.Length;
 124
 125            // Loop through the provided points and figure out what is closest (close enough).
 12126            for (int i = 0; i < otherVector3Length; i++)
 5127            {
 5128                float squareDistance = (otherVector3[i] - targetVector3).sqrMagnitude;
 5129                if (float.IsNaN(squareDistance) || !(squareDistance < closestSquareMagnitude))
 3130                {
 3131                    continue;
 132                }
 133
 2134                closestSquareMagnitude = squareDistance;
 2135                closestIndex = i;
 2136            }
 137
 1138            return closestIndex;
 2139        }
 140
 141        /// <summary>
 142        ///     Attempt to parse a <see cref="string" /> into a <see cref="Vector3" />.
 143        /// </summary>
 144        /// <remarks>This isn't great for runtime performance, it should be used predominantly when reconstructing data.
 145        /// <param name="targetString">The <see cref="string" /> to convert into a <see cref="Vector3" /> if possible.</
 146        /// <param name="outputVector3">The outputted <see cref="Vector3" />.</param>
 147        /// <returns>true/false if the conversion was successful.</returns>
 148        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 149        public static bool TryParseVector3(this string targetString, out Vector3 outputVector3)
 7150        {
 151            // Find split points
 7152            int firstSplit = targetString.IndexOf(',', 0);
 7153            if (firstSplit == -1)
 1154            {
 1155                outputVector3 = Vector3.zero;
 1156                return false;
 157            }
 158
 6159            int secondSplit = targetString.IndexOf(',', firstSplit + 1);
 6160            if (secondSplit == -1)
 1161            {
 1162                outputVector3 = Vector3.zero;
 1163                return false;
 164            }
 165
 166            // Get source parts
 5167            string sourceX = targetString.Substring(0, firstSplit);
 5168            string sourceY = targetString.Substring(firstSplit + 1, secondSplit - (firstSplit + 1));
 5169            string sourceZ = targetString.Substring(secondSplit + 1);
 170
 171            // Parse components
 5172            if (!float.TryParse(sourceX, out float parsedX))
 1173            {
 1174                outputVector3 = Vector3.zero;
 1175                return false;
 176            }
 177
 4178            if (!float.TryParse(sourceY, out float parsedY))
 1179            {
 1180                outputVector3 = Vector3.zero;
 1181                return false;
 182            }
 183
 3184            if (!float.TryParse(sourceZ, out float parsedZ))
 1185            {
 1186                outputVector3 = Vector3.zero;
 1187                return false;
 188            }
 189
 190            // Everything looks good, assign the values
 2191            outputVector3 = new Vector3(parsedX, parsedY, parsedZ);
 2192            return true;
 7193        }
 194    }
 195}
 196#endif // !UNITY_DOTSRUNTIME

Coverage by test methods






















Methods/Properties

Approximately(UnityEngine.Vector3, UnityEngine.Vector3)
DistanceSqr(UnityEngine.Vector3, UnityEngine.Vector3)
HorizontalDistance(UnityEngine.Vector3, UnityEngine.Vector3)
DistanceToRay(UnityEngine.Vector3, UnityEngine.Ray)
Midpoint(UnityEngine.Vector3, UnityEngine.Vector3)
NearestIndex(UnityEngine.Vector3, UnityEngine.Vector3[])
TryParseVector3(System.String, UnityEngine.Vector3&)