1 module des.stdx.bitflags;
2 
3 import std.algorithm : reduce;
4 import std.traits : isIntegral;
5 
6 import des.ts;
7 
8 /// pack array of values to bit value
9 auto packFlags(T)( in T[] list... )
10     if( isIntegral!T )
11 { return reduce!((a,b)=>a|=b)(T(0),list); }
12 
13 ///
14 unittest
15 {
16     assertEq( packFlags!uint(), 0 );
17     auto a = 0b01;
18     assertEq( packFlags(a), a );
19     auto b = 0b10;
20     auto c = 0b11;
21     assertEq( packFlags(a,b), c );
22 }
23 
24 /// remove flags from bit value
25 auto removeFlags(T)( in T bit_value, in T[] list... )
26     if( isIntegral!T )
27 { return reduce!((a,b)=>(a^=a&b))( bit_value, list ); }
28 
29 ///
30 unittest
31 {
32     auto a = 0b01;
33     auto b = 0b10;
34     auto c = 0b11;
35     assertEq( removeFlags(c,a), b );
36     assertEq( removeFlags(c,b), a );
37     assertEq( removeFlags(c,a,b), 0 );
38 }
39 
40 /// checks flag in bit value
41 bool hasFlag(T)( in T bit_value, in T flag )
42     if( isIntegral!T )
43 { return ( bit_value & flag ) == flag; }
44 
45 ///
46 unittest
47 {
48     auto a = 0b01;
49     auto b = 0b10;
50     auto c = 0b11;
51     assert( hasFlag(c,a) );
52     assert( hasFlag(c,b) );
53     assert( hasFlag(c,0) );
54 }
55 
56 /// checks flags in bit value
57 bool hasFlags(T)( in T bit_value, in T[] list... )
58     if( isIntegral!T )
59 { return hasFlag( bit_value, packFlags( list ) ); }
60 
61 ///
62 unittest
63 {
64     auto a = 0b001;
65     auto b = 0b010;
66     auto c = 0b100;
67     auto d = 0b111;
68     assert( hasFlags(d,a,b,c) );
69 }