color.d 3.8 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192
  1. // Written in the D programming language.
  2. /**
  3. Copyright: Copyright Felix 'Zoadian' Hufnagel 2014-.
  4. License: $(WEB http://www.gnu.org/licenses/lgpl.html, LGPLv3).
  5. Authors: $(WEB zoadian.de, Felix 'Zoadian' Hufnagel)
  6. */
  7. module three.primitives.color;
  8. import std.typecons;
  9. import std.typetuple;
  10. import std.conv;
  11. struct RedColorComponent(T) { T r; alias r this; this(T t){r=t;} }
  12. struct GreenColorComponent(T) { T g; alias g this; this(T t){g=t;} }
  13. struct BlueColorComponent(T) { T b; alias b this; this(T t){b=t;} }
  14. struct AlphaColorComponent(T) { T a; alias a this; this(T t){a=t;} }
  15. ///
  16. enum isRedColorComponent(T) = is(typeof(_isRedColorComponent(T.init)));
  17. private void _isRedColorComponent(T)(RedColorComponent!(T) t) {}
  18. ///
  19. enum isGreenColorComponent(T) = is(typeof(_isGreenColorComponent(T.init)));
  20. private void _isGreenColorComponent(T)(GreenColorComponent!(T) t) {}
  21. ///
  22. enum isBlueColorComponent(T) = is(typeof(_isBlueColorComponent(T.init)));
  23. private void _isBlueColorComponent(T)(BlueColorComponent!(T) t) {}
  24. ///
  25. enum isAlphaColorComponent(T) = is(typeof(_isAlphaColorComponent(T.init)));
  26. private void _isAlphaColorComponent(T)(AlphaColorComponent!(T) t) {}
  27. enum isRGBColorComponent(T) = isRedColorComponent!T || isGreenColorComponent!T || isBlueColorComponent!T;
  28. enum isRGBAColorComponent(T) = isRGBColorComponent!T || isAlphaColorComponent!T;
  29. enum hasRedColorComponent(T...) = anySatisfy!(isRedColorComponent, T);
  30. enum hasGreenColorComponent(T...) = anySatisfy!(isGreenColorComponent, T);
  31. enum hasBlueColorComponent(T...) = anySatisfy!(isBlueColorComponent, T);
  32. enum hasAlphaColorComponent(T...) = anySatisfy!(isAlphaColorComponent, T);
  33. enum isRGB(T...) = T.length == 3 && isRedColorComponent!(T[0]) && isGreenColorComponent!(T[1]) && isBlueColorComponent!(T[2]);
  34. enum isRGBA(T...) = T.length == 4 && isRGB!(T[0..3]) && isAlphaColorComponent!(T[3]);
  35. enum isARGB(T...) = T.length == 4 && isAlphaColorComponent!(T[3]) && isRGB!(T[0..3]);
  36. enum isBGR(T...) = T.length == 3 && isBlueColorComponent!(T[0]) && isGreenColorComponent!(T[1]) && isRedColorComponent!(T[2]);
  37. enum isBGRA(T...) = T.length == 4 && isBGR!(T[0..3]) && isAlphaColorComponent!(T[3]);
  38. enum isABGR(T...) = T.length == 4 && isAlphaColorComponent!(T[3]) && isBGR!(T[0..3]);
  39. alias RGBColorComponents(T) = TypeTuple!(RedColorComponent!T, GreenColorComponent!T, BlueColorComponent!T);
  40. alias RGBAColorComponents(T) = TypeTuple!(RGBColorComponents!T, AlphaColorComponent!T);
  41. alias ARGBColorComponents(T) = TypeTuple!(AlphaColorComponent!T, RGBColorComponents!T);
  42. alias BGRColorComponents(T) = TypeTuple!(BlueColorComponent!T, GreenColorComponent!T, RedColorComponent!T);
  43. alias BGRAColorComponents(T) = TypeTuple!(BGRColorComponents!T, AlphaColorComponent!T);
  44. alias ABGRColorComponents(T) = TypeTuple!(AlphaColorComponent!T, BGRColorComponents!T);
  45. enum isValidColorComponentDefinition(T...) = allSatisfy!(isRGBAColorComponent, T) && NoDuplicates!(T).length == T.length;
  46. static assert(isValidColorComponentDefinition!(RGBAColorComponents!float));
  47. private string _genMembers(size_t IDX, N...)() {
  48. string ret;
  49. foreach(K; N) {
  50. ret ~= "alias " ~ K ~ " = _components[" ~ to!string(IDX-1) ~ "];\n";
  51. }
  52. return ret;
  53. }
  54. private mixin template _GenAccessors(size_t IDX, T...) if(T.length > 0) {
  55. static if(T.length == 1) {
  56. mixin(_genMembers!(IDX, __traits(allMembers, T[0]))());
  57. }
  58. else {
  59. mixin _GenAccessors!(IDX+1, T[0]);
  60. mixin _GenAccessors!(IDX+1, T[1..$]);
  61. }
  62. }
  63. struct Color(COMPONENTS...) if(COMPONENTS.length > 0 && isValidColorComponentDefinition!COMPONENTS) {
  64. COMPONENTS _components;
  65. this(T...)(T t) {
  66. this._components[] = t[];
  67. }
  68. mixin _GenAccessors!(0, COMPONENTS);
  69. }
  70. alias RGBAf = Color!(RGBAColorComponents!float);
  71. alias RGBf = Color!(RGBAColorComponents!float);