Add more utilities to LayersMask

This commit is contained in:
Wojtek Figat
2021-02-25 15:46:10 +01:00
parent 5d2fe5908b
commit 26607c1d09
6 changed files with 220 additions and 15 deletions

View File

@@ -0,0 +1,162 @@
// Copyright (c) 2012-2021 Wojciech Figat. All rights reserved.
using System;
using System.Runtime.CompilerServices;
namespace FlaxEngine
{
partial struct LayersMask : IComparable, IComparable<LayersMask>
{
/// <summary>
/// Initializes a new instance of the <see cref="LayersMask"/> struct.
/// </summary>
/// <param name="mask">The bit mask.</param>
public LayersMask(int mask) => Mask = (uint)mask;
/// <summary>
/// Initializes a new instance of the <see cref="LayersMask"/> struct.
/// </summary>
/// <param name="mask">The bit mask.</param>
public LayersMask(uint mask) => Mask = mask;
/// <summary>
/// Determines whether the specified layer index is set in the mask.
/// </summary>
/// <param name="layerIndex">Index of the layer (zero-based).</param>
/// <returns><c>true</c> if the specified layer is set; otherwise, <c>false</c>.</returns>
public bool HasLayer(int layerIndex)
{
return (Mask & (1 << layerIndex)) != 0;
}
/// <summary>
/// Determines whether the specified layer is set in the mask.
/// </summary>
/// <param name="layerName">Name of the layer (from layers settings).</param>
/// <returns><c>true</c> if the specified layer is set; otherwise, <c>false</c>.</returns>
public bool HasLayer(string layerName)
{
return HasLayer(Level.GetLayerIndex(layerName));
}
/// <summary>
/// Adds two masks.
/// </summary>
/// <param name="left">The left mask.</param>
/// <param name="right">The right mask.</param>
/// <returns>The sum of the two masks.</returns>
public static LayersMask operator +(LayersMask left, LayersMask right) => new LayersMask(left.Mask | right.Mask);
/// <summary>
/// Removes one mask from another.
/// </summary>
/// <param name="left">The left mask.</param>
/// <param name="right">The right mask.</param>
/// <returns>The left mask without right mask.</returns>
public static LayersMask operator -(LayersMask left, LayersMask right) => new LayersMask(left.Mask & ~right.Mask);
/// <summary>
/// Performance bitwise OR of the masks.
/// </summary>
/// <param name="left">The left mask.</param>
/// <param name="right">The right mask.</param>
/// <returns>The sum of the two masks.</returns>
public static LayersMask operator |(LayersMask left, LayersMask right) => new LayersMask(left.Mask | right.Mask);
/// <summary>
/// Performance bitwise AND of the masks.
/// </summary>
/// <param name="left">The left mask.</param>
/// <param name="right">The right mask.</param>
/// <returns>The conjunction of the two masks.</returns>
public static LayersMask operator &(LayersMask left, LayersMask right) => new LayersMask(left.Mask & right.Mask);
/// <summary>
/// Performance bitwise XOR of the masks.
/// </summary>
/// <param name="left">The left mask.</param>
/// <param name="right">The right mask.</param>
/// <returns>The difference of the two masks.</returns>
public static LayersMask operator ^(LayersMask left, LayersMask right) => new LayersMask(left.Mask ^ right.Mask);
/// <summary>
/// Performance bitwise NOT of the mask.
/// </summary>
/// <param name="left">The mask.</param>
/// <returns>The negated mask.</returns>
public static LayersMask operator ~(LayersMask left) => new LayersMask(~left.Mask);
/// <summary>
/// Performs an implicit conversion from <see cref="LayersMask"/> to <see cref="System.UInt32"/>.
/// </summary>
/// <param name="mask">The mask.</param>
/// <returns>The mask value.</returns>
public static implicit operator uint(LayersMask mask) => mask.Mask;
/// <summary>
/// Tests for equality between two objects.
/// </summary>
/// <param name="left">The first value to compare.</param>
/// <param name="right">The second value to compare.</param>
/// <returns><c>true</c> if <paramref name="left" /> has the same value as <paramref name="right" />; otherwise, <c>false</c>.</returns>
[MethodImpl(MethodImplOptions.AggressiveInlining)]
public static bool operator ==(LayersMask left, LayersMask right)
{
return left.Mask == right.Mask;
}
/// <summary>
/// Tests for inequality between two objects.
/// </summary>
/// <param name="left">The first value to compare.</param>
/// <param name="right">The second value to compare.</param>
/// <returns><c>true</c> if <paramref name="left" /> has a different value than <paramref name="right" />; otherwise, <c>false</c>.</returns>
[MethodImpl(MethodImplOptions.AggressiveInlining)]
public static bool operator !=(LayersMask left, LayersMask right)
{
return left.Mask != right.Mask;
}
/// <inheritdoc />
public override int GetHashCode()
{
return Mask.GetHashCode();
}
/// <inheritdoc />
public override string ToString()
{
return Mask.ToString();
}
/// <summary>
/// Tests for equality between two objects.
/// </summary>
/// <param name="other">The other value to compare.</param>
/// <returns>True if both values are equal, otherwise false.</returns>
public bool Equals(LayersMask other)
{
return Mask == other.Mask;
}
/// <inheritdoc />
public override bool Equals(object obj)
{
return obj is LayersMask other && Equals(other);
}
/// <inheritdoc />
public int CompareTo(object obj)
{
if (obj is LayersMask other)
return Mask.CompareTo(other.Mask);
return 0;
}
/// <inheritdoc />
public int CompareTo(LayersMask other)
{
return Mask.CompareTo(other.Mask);
}
}
}

View File

@@ -17,6 +17,17 @@ DECLARE_SCRIPTING_TYPE_MINIMAL(LayersMask);
/// </summary>
API_FIELD() uint32 Mask = MAX_uint32;
public:
FORCE_INLINE LayersMask()
{
}
FORCE_INLINE LayersMask(uint32 mask)
: Mask(mask)
{
}
FORCE_INLINE bool HasLayer(int32 layerIndex) const
{
return (Mask & (1 << layerIndex)) != 0;
@@ -24,8 +35,50 @@ DECLARE_SCRIPTING_TYPE_MINIMAL(LayersMask);
bool HasLayer(const StringView& layerName) const;
bool operator==(const LayersMask& other) const;
bool operator!=(const LayersMask& other) const;
operator uint32() const
{
return Mask;
}
bool operator==(const LayersMask& other) const
{
return Mask == other.Mask;
}
bool operator!=(const LayersMask& other) const
{
return Mask != other.Mask;
}
LayersMask operator+(const LayersMask& other) const
{
return Mask | other.Mask;
}
LayersMask operator-(const LayersMask& other) const
{
return Mask & ~other.Mask;
}
LayersMask operator&(const LayersMask& other) const
{
return Mask && other.Mask;
}
LayersMask operator|(const LayersMask& other) const
{
return Mask | other.Mask;
}
LayersMask operator^(const LayersMask& other) const
{
return Mask ^ other.Mask;
}
LayersMask operator-() const
{
return ~Mask;
}
};
// @formatter:off

View File

@@ -5,7 +5,7 @@
#include "Engine/Core/Math/BoundingFrustum.h"
#include "Engine/Core/Math/Matrix.h"
#include "Engine/Core/Math/Vector3.h"
#include "Engine/Core/Config/LayersMask.h"
#include "Engine/Core/Types/LayersMask.h"
#include "Engine/Level/Types.h"
#include "Enums.h"

View File

@@ -7,7 +7,7 @@
#include "Engine/Core/Math/BoundingFrustum.h"
#include "Engine/Core/Math/Viewport.h"
#include "Engine/Core/Math/Ray.h"
#include "Engine/Core/Config/LayersMask.h"
#include "Engine/Core/Types/LayersMask.h"
#if USE_EDITOR
#include "Engine/Content/AssetReference.h"
#include "Engine/Graphics/Models/ModelInstanceEntry.h"

View File

@@ -42,16 +42,6 @@ bool LayersMask::HasLayer(const StringView& layerName) const
return HasLayer(Level::GetLayerIndex(layerName));
}
bool LayersMask::operator==(const LayersMask& other) const
{
return Mask == other.Mask;
}
bool LayersMask::operator!=(const LayersMask& other) const
{
return Mask != other.Mask;
}
enum class SceneEventType
{
OnSceneSaving = 0,

View File

@@ -462,7 +462,7 @@ public:
/// <summary>
/// Gets the zero-based index of the layer.
/// </summary>
static int32 GetLayerIndex(const StringView& layer);
API_FUNCTION() static int32 GetLayerIndex(const StringView& layer);
private: