mirror of https://github.com/SixLabors/ImageSharp
8 changed files with 266 additions and 120 deletions
@ -0,0 +1,40 @@ |
|||
// Copyright (c) Six Labors and contributors.
|
|||
// Licensed under the Apache License, Version 2.0.
|
|||
|
|||
using System; |
|||
using System.Runtime.CompilerServices; |
|||
|
|||
namespace SixLabors |
|||
{ |
|||
/// <summary>
|
|||
/// Provides common mathematical methods.
|
|||
/// </summary>
|
|||
internal static class MathFExtensions |
|||
{ |
|||
/// <summary>
|
|||
/// Converts a degree (360-periodic) angle to a radian (2*Pi-periodic) angle.
|
|||
/// </summary>
|
|||
/// <param name="degree">The angle in degrees.</param>
|
|||
/// <returns>
|
|||
/// The <see cref="float"/> representing the degree as radians.
|
|||
/// </returns>
|
|||
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|||
public static float DegreeToRadian(float degree) |
|||
{ |
|||
return degree * (MathF.PI / 180F); |
|||
} |
|||
|
|||
/// <summary>
|
|||
/// Converts a radian (2*Pi-periodic) angle to a degree (360-periodic) angle.
|
|||
/// </summary>
|
|||
/// <param name="radian">The angle in radians.</param>
|
|||
/// <returns>
|
|||
/// The <see cref="float"/> representing the degree as radians.
|
|||
/// </returns>
|
|||
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|||
public static float RadianToDegree(float radian) |
|||
{ |
|||
return radian / (MathF.PI / 180F); |
|||
} |
|||
} |
|||
} |
|||
@ -1,49 +1,50 @@ |
|||
<Project Sdk="Microsoft.NET.Sdk"> |
|||
|
|||
<PropertyGroup> |
|||
<Description>Low level primitives for use across Six Labors projects..</Description> |
|||
<VersionPrefix Condition="$(packageversion) != ''">$(packageversion)</VersionPrefix> |
|||
<VersionPrefix Condition="$(packageversion) == ''">0.1.0-alpha2</VersionPrefix> |
|||
<Authors>Six Labors</Authors> |
|||
<TargetFramework>netstandard1.1</TargetFramework> |
|||
<AllowUnsafeBlocks>true</AllowUnsafeBlocks> |
|||
<GenerateDocumentationFile>true</GenerateDocumentationFile> |
|||
<AssemblyName>SixLabors.Core</AssemblyName> |
|||
<PackageId>SixLabors.Core</PackageId> |
|||
<PackageTags>rectangle;point;size,primitives</PackageTags> |
|||
<PackageIconUrl>https://raw.githubusercontent.com/SixLabors/Home/master/logo.png</PackageIconUrl> |
|||
<PackageProjectUrl>https://github.com/SixLabors/Core</PackageProjectUrl> |
|||
<PackageLicenseUrl>http://www.apache.org/licenses/LICENSE-2.0</PackageLicenseUrl> |
|||
<RepositoryType>git</RepositoryType> |
|||
<RepositoryUrl>https://github.com/SixLabors/Core</RepositoryUrl> |
|||
<GenerateAssemblyDescriptionAttribute>false</GenerateAssemblyDescriptionAttribute> |
|||
<GenerateAssemblyConfigurationAttribute>false</GenerateAssemblyConfigurationAttribute> |
|||
<GenerateAssemblyCompanyAttribute>false</GenerateAssemblyCompanyAttribute> |
|||
<GenerateAssemblyProductAttribute>false</GenerateAssemblyProductAttribute> |
|||
<GenerateAssemblyCopyrightAttribute>false</GenerateAssemblyCopyrightAttribute> |
|||
<GenerateNeutralResourcesLanguageAttribute>false</GenerateNeutralResourcesLanguageAttribute> |
|||
<GenerateAssemblyVersionAttribute>false</GenerateAssemblyVersionAttribute> |
|||
<GenerateAssemblyFileVersionAttribute>false</GenerateAssemblyFileVersionAttribute> |
|||
<GenerateAssemblyInformationalVersionAttribute>false</GenerateAssemblyInformationalVersionAttribute> |
|||
<GenerateAssemblyTitleAttribute>false</GenerateAssemblyTitleAttribute> |
|||
<DebugType Condition="$(codecov) == 'true'">full</DebugType> |
|||
<RootNamespace>SixLabors</RootNamespace> |
|||
</PropertyGroup> |
|||
<PropertyGroup> |
|||
<Description>Low level primitives for use across Six Labors projects..</Description> |
|||
<VersionPrefix Condition="$(packageversion) != ''">$(packageversion)</VersionPrefix> |
|||
<VersionPrefix Condition="$(packageversion) == ''">0.1.0-alpha2</VersionPrefix> |
|||
<Authors>Six Labors</Authors> |
|||
<TargetFrameworks>netstandard1.1;netcoreapp2.0;</TargetFrameworks> |
|||
<AllowUnsafeBlocks>true</AllowUnsafeBlocks> |
|||
<GenerateDocumentationFile>true</GenerateDocumentationFile> |
|||
<AssemblyName>SixLabors.Core</AssemblyName> |
|||
<PackageId>SixLabors.Core</PackageId> |
|||
<PackageTags>rectangle;point;size,primitives</PackageTags> |
|||
<PackageIconUrl>https://raw.githubusercontent.com/SixLabors/Home/master/logo.png</PackageIconUrl> |
|||
<PackageProjectUrl>https://github.com/SixLabors/Core</PackageProjectUrl> |
|||
<PackageLicenseUrl>http://www.apache.org/licenses/LICENSE-2.0</PackageLicenseUrl> |
|||
<RepositoryType>git</RepositoryType> |
|||
<RepositoryUrl>https://github.com/SixLabors/Core</RepositoryUrl> |
|||
<GenerateAssemblyDescriptionAttribute>false</GenerateAssemblyDescriptionAttribute> |
|||
<GenerateAssemblyConfigurationAttribute>false</GenerateAssemblyConfigurationAttribute> |
|||
<GenerateAssemblyCompanyAttribute>false</GenerateAssemblyCompanyAttribute> |
|||
<GenerateAssemblyProductAttribute>false</GenerateAssemblyProductAttribute> |
|||
<GenerateAssemblyCopyrightAttribute>false</GenerateAssemblyCopyrightAttribute> |
|||
<GenerateNeutralResourcesLanguageAttribute>false</GenerateNeutralResourcesLanguageAttribute> |
|||
<GenerateAssemblyVersionAttribute>false</GenerateAssemblyVersionAttribute> |
|||
<GenerateAssemblyFileVersionAttribute>false</GenerateAssemblyFileVersionAttribute> |
|||
<GenerateAssemblyInformationalVersionAttribute>false</GenerateAssemblyInformationalVersionAttribute> |
|||
<GenerateAssemblyTitleAttribute>false</GenerateAssemblyTitleAttribute> |
|||
<DebugType Condition="$(codecov) == 'true'">full</DebugType> |
|||
<RootNamespace>SixLabors</RootNamespace> |
|||
</PropertyGroup> |
|||
|
|||
<PropertyGroup> |
|||
<CodeAnalysisRuleSet>..\SixLabors.ruleset</CodeAnalysisRuleSet> |
|||
</PropertyGroup> |
|||
<PropertyGroup> |
|||
<CodeAnalysisRuleSet>..\SixLabors.ruleset</CodeAnalysisRuleSet> |
|||
</PropertyGroup> |
|||
|
|||
<ItemGroup> |
|||
<AdditionalFiles Include="..\..\stylecop.json" /> |
|||
<Content Include="..\..\stylecop.json" Link="stylecop.json" /> |
|||
</ItemGroup> |
|||
|
|||
<ItemGroup> |
|||
<PackageReference Include="StyleCop.Analyzers" Version="1.1.0-beta004"> |
|||
<PrivateAssets>All</PrivateAssets> |
|||
</PackageReference> |
|||
<PackageReference Include="System.Numerics.Vectors" Version="4.4.0" /> |
|||
</ItemGroup> |
|||
<ItemGroup> |
|||
<AdditionalFiles Include="..\..\stylecop.json" /> |
|||
<Content Include="..\..\stylecop.json" Link="stylecop.json" /> |
|||
</ItemGroup> |
|||
|
|||
<ItemGroup> |
|||
<PackageReference Include="StyleCop.Analyzers" Version="1.1.0-beta004"> |
|||
<PrivateAssets>All</PrivateAssets> |
|||
</PackageReference> |
|||
</ItemGroup> |
|||
<ItemGroup Condition=" '$(TargetFramework)' == 'netstandard1.1'"> |
|||
<PackageReference Include="System.Numerics.Vectors" Version="4.4.0" /> |
|||
</ItemGroup> |
|||
</Project> |
|||
@ -0,0 +1,59 @@ |
|||
// Copyright (c) Six Labors and contributors.
|
|||
// Licensed under the Apache License, Version 2.0.
|
|||
|
|||
using System; |
|||
using System.Collections.Generic; |
|||
using System.Numerics; |
|||
|
|||
namespace SixLabors.Tests.Helpers |
|||
{ |
|||
/// <summary>
|
|||
/// Allows the comparison of single-precision floating point values by precision.
|
|||
/// </summary>
|
|||
public struct FloatRoundingComparer : IEqualityComparer<float>, IEqualityComparer<Vector4> |
|||
{ |
|||
/// <summary>
|
|||
/// Initializes a new instance of the <see cref="FloatRoundingComparer"/> struct.
|
|||
/// </summary>
|
|||
/// <param name="precision">The number of decimal places (valid values: 0-7)</param>
|
|||
public FloatRoundingComparer(int precision) |
|||
{ |
|||
Guard.MustBeBetweenOrEqualTo(precision, 0, 7, nameof(precision)); |
|||
this.Precision = precision; |
|||
} |
|||
|
|||
/// <summary>
|
|||
/// Gets the number of decimal places (valid values: 0-7)
|
|||
/// </summary>
|
|||
public int Precision { get; } |
|||
|
|||
/// <inheritdoc />
|
|||
public bool Equals(float x, float y) |
|||
{ |
|||
float xp = (float)Math.Round(x, this.Precision, MidpointRounding.AwayFromZero); |
|||
float yp = (float)Math.Round(y, this.Precision, MidpointRounding.AwayFromZero); |
|||
|
|||
return Comparer<float>.Default.Compare(xp, yp) == 0; |
|||
} |
|||
|
|||
/// <inheritdoc />
|
|||
public bool Equals(Vector4 x, Vector4 y) |
|||
{ |
|||
return this.Equals(x.X, y.X) && this.Equals(x.Y, y.Y) && this.Equals(x.Z, y.Z) && this.Equals(x.W, y.W); |
|||
} |
|||
|
|||
/// <inheritdoc />
|
|||
public int GetHashCode(float obj) |
|||
{ |
|||
unchecked |
|||
{ |
|||
int hashCode = obj.GetHashCode(); |
|||
hashCode = (hashCode * 397) ^ this.Precision.GetHashCode(); |
|||
return hashCode; |
|||
} |
|||
} |
|||
|
|||
/// <inheritdoc />
|
|||
public int GetHashCode(Vector4 obj) => HashHelpers.Combine(obj.GetHashCode(), this.Precision.GetHashCode()); |
|||
} |
|||
} |
|||
@ -0,0 +1,107 @@ |
|||
// Copyright (c) Six Labors and contributors.
|
|||
// Licensed under the Apache License, Version 2.0.
|
|||
|
|||
using System; |
|||
using Xunit; |
|||
|
|||
namespace SixLabors.Tests.Helpers |
|||
{ |
|||
public class MathFTests |
|||
{ |
|||
[Fact] |
|||
public void MathF_PI_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.PI, (float)Math.PI); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Ceililng_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Ceiling(0.3333F), (float)Math.Ceiling(0.3333F)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Cos_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Cos(0.3333F), (float)Math.Cos(0.3333F)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Abs_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Abs(-0.3333F), (float)Math.Abs(-0.3333F)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Atan2_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Atan2(1.2345F, 1.2345F), (float)Math.Atan2(1.2345F, 1.2345F)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Exp_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Exp(1.2345F), (float)Math.Exp(1.2345F)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Floor_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Floor(1.2345F), (float)Math.Floor(1.2345F)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Min_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Min(1.2345F, 5.4321F), (float)Math.Min(1.2345F, 5.4321F)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Max_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Max(1.2345F, 5.4321F), (float)Math.Max(1.2345F, 5.4321F)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Pow_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Pow(1.2345F, 5.4321F), (float)Math.Pow(1.2345F, 5.4321F)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Round_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Round(1.2345F), (float)Math.Round(1.2345F)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Round_With_Midpoint_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Round(1.2345F, MidpointRounding.AwayFromZero), (float)Math.Round(1.2345F, MidpointRounding.AwayFromZero)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Sin_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Sin(1.2345F), (float)Math.Sin(1.2345F)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void MathF_Sqrt_Is_Equal() |
|||
{ |
|||
Assert.Equal(MathF.Sqrt(2F), (float)Math.Sqrt(2F)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void Convert_Degree_To_Radian() |
|||
{ |
|||
Assert.Equal((float)(Math.PI / 2D), MathFExtensions.DegreeToRadian(90F), new FloatRoundingComparer(6)); |
|||
} |
|||
|
|||
[Fact] |
|||
public void Convert_Radian_To_Degree() |
|||
{ |
|||
Assert.Equal(60F, MathFExtensions.RadianToDegree((float)(Math.PI / 3D)), new FloatRoundingComparer(5)); |
|||
} |
|||
} |
|||
} |
|||
Loading…
Reference in new issue