rgb.cpp 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102
  1. //[ RGB
  2. ///////////////////////////////////////////////////////////////////////////////
  3. // Copyright 2008 Eric Niebler. Distributed under the Boost
  4. // Software License, Version 1.0. (See accompanying file
  5. // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  6. //
  7. // This is a simple example of doing arbitrary type manipulations with proto
  8. // transforms. It takes some expression involving primary colors and combines
  9. // the colors according to arbitrary rules. It is a port of the RGB example
  10. // from PETE (http://www.codesourcery.com/pooma/download.html).
  11. #include <iostream>
  12. #include <boost/proto/core.hpp>
  13. #include <boost/proto/transform.hpp>
  14. namespace proto = boost::proto;
  15. struct RedTag
  16. {
  17. friend std::ostream &operator <<(std::ostream &sout, RedTag)
  18. {
  19. return sout << "This expression is red.";
  20. }
  21. };
  22. struct BlueTag
  23. {
  24. friend std::ostream &operator <<(std::ostream &sout, BlueTag)
  25. {
  26. return sout << "This expression is blue.";
  27. }
  28. };
  29. struct GreenTag
  30. {
  31. friend std::ostream &operator <<(std::ostream &sout, GreenTag)
  32. {
  33. return sout << "This expression is green.";
  34. }
  35. };
  36. typedef proto::terminal<RedTag>::type RedT;
  37. typedef proto::terminal<BlueTag>::type BlueT;
  38. typedef proto::terminal<GreenTag>::type GreenT;
  39. struct Red;
  40. struct Blue;
  41. struct Green;
  42. ///////////////////////////////////////////////////////////////////////////////
  43. // A transform that produces new colors according to some arbitrary rules:
  44. // red & green give blue, red & blue give green, blue and green give red.
  45. struct Red
  46. : proto::or_<
  47. proto::plus<Green, Blue>
  48. , proto::plus<Blue, Green>
  49. , proto::plus<Red, Red>
  50. , proto::terminal<RedTag>
  51. >
  52. {};
  53. struct Green
  54. : proto::or_<
  55. proto::plus<Red, Blue>
  56. , proto::plus<Blue, Red>
  57. , proto::plus<Green, Green>
  58. , proto::terminal<GreenTag>
  59. >
  60. {};
  61. struct Blue
  62. : proto::or_<
  63. proto::plus<Red, Green>
  64. , proto::plus<Green, Red>
  65. , proto::plus<Blue, Blue>
  66. , proto::terminal<BlueTag>
  67. >
  68. {};
  69. struct RGB
  70. : proto::or_<
  71. proto::when< Red, RedTag() >
  72. , proto::when< Blue, BlueTag() >
  73. , proto::when< Green, GreenTag() >
  74. >
  75. {};
  76. template<typename Expr>
  77. void printColor(Expr const & expr)
  78. {
  79. int i = 0; // dummy state and data parameter, not used
  80. std::cout << RGB()(expr, i, i) << std::endl;
  81. }
  82. int main()
  83. {
  84. printColor(RedT() + GreenT());
  85. printColor(RedT() + GreenT() + BlueT());
  86. printColor(RedT() + (GreenT() + BlueT()));
  87. return 0;
  88. }
  89. //]