Nazara Engine  0.4
A fast, complete, cross-platform API designed for game development
Flags.hpp
1 // Copyright (C) 2017 Jérôme Leclercq
2 // This file is part of the "Nazara Engine - Core module"
3 // For conditions of distribution and use, see copyright notice in Config.hpp
4 
5 #pragma once
6 
7 #ifndef NAZARA_FLAGS_HPP
8 #define NAZARA_FLAGS_HPP
9 
10 #include <Nazara/Prerequesites.hpp>
11 #include <type_traits>
12 
13 namespace Nz
14 {
15  // From: https://www.justsoftwaresolutions.co.uk/cplusplus/using-enum-classes-as-bitfields.html
16  template<typename E>
17  struct EnumAsFlags
18  {
19  static constexpr bool value = false;
20  static constexpr int max = 0;
21  };
22 
23  template<typename E>
24  class Flags
25  {
26  static_assert(std::is_enum<E>::value, "Type must be an enumeration");
27  static_assert(EnumAsFlags<E>::value, "Enum has not been enabled as flags by an EnumAsFlags specialization");
28 
29  public:
30  using BitField = typename std::conditional<(EnumAsFlags<E>::max > 32), UInt64, UInt32>::type;
31 
32  constexpr Flags(BitField value = 0);
33  constexpr Flags(E enumVal);
34 
35  explicit constexpr operator bool() const;
36  explicit constexpr operator BitField() const;
37 
38  constexpr Flags operator~() const;
39  constexpr Flags operator&(const Flags& rhs) const;
40  constexpr Flags operator|(const Flags& rhs) const;
41  constexpr Flags operator^(const Flags& rhs) const;
42 
43  constexpr bool operator==(const Flags& rhs) const;
44  constexpr bool operator!=(const Flags& rhs) const;
45 
46  /*constexpr*/ Flags& operator|=(const Flags& rhs);
47  /*constexpr*/ Flags& operator&=(const Flags& rhs);
48  /*constexpr*/ Flags& operator^=(const Flags& rhs);
49 
50  static constexpr BitField GetFlagValue(E enumValue);
51 
52  static constexpr BitField ValueMask = ((BitField(1) << (EnumAsFlags<E>::max + 1)) - 1);
53 
54  private:
55  BitField m_value;
56  };
57 
58  // Little hack to have them in both Nz and global scope
59  namespace FlagsOperators
60  {
61  template<typename E> constexpr std::enable_if_t<EnumAsFlags<E>::value, Flags<E>> operator~(E lhs);
62  template<typename E> constexpr std::enable_if_t<EnumAsFlags<E>::value, Flags<E>> operator|(E lhs, E rhs);
63  template<typename E> constexpr std::enable_if_t<EnumAsFlags<E>::value, Flags<E>> operator&(E lhs, E rhs);
64  template<typename E> constexpr std::enable_if_t<EnumAsFlags<E>::value, Flags<E>> operator^(E lhs, E rhs);
65  }
66 
67  using namespace FlagsOperators;
68 }
69 
70 using namespace Nz::FlagsOperators;
71 
72 #include <Nazara/Core/Flags.inl>
73 
74 #endif // NAZARA_FLAGS_HPP
TODO: Inherit SoundEmitter from Node.
Definition: Algorithm.hpp:12
Definition: Flags.hpp:59
Bitset< Block, Allocator > operator^(const Bitset< Block, Allocator > &lhs, const Bitset< Block, Allocator > &rhs)
Performs the operator "XOR" between two bitsets.
Definition: Bitset.inl:1628
bool operator!=(const Bitset< Block, Allocator > &lhs, const Nz::Bitset< Block, Allocator > &rhs)
Compares two bitsets.
Definition: Bitset.inl:1503
Bitset< Block, Allocator > operator &(const Bitset< Block, Allocator > &lhs, const Bitset< Block, Allocator > &rhs)
Performs the operator "AND" between two bitsets.
Definition: Bitset.inl:1594
Core class used to combine enumeration values into flags bitfield.
Definition: Flags.hpp:24
Bitset< Block, Allocator > operator|(const Bitset< Block, Allocator > &lhs, const Bitset< Block, Allocator > &rhs)
Performs the operator "OR" between two bitsets.
Definition: Bitset.inl:1611
bool operator==(const Bitset< Block, Allocator > &lhs, const Nz::Bitset< Block, Allocator > &rhs)
Compares two bitsets.
Definition: Bitset.inl:1469