home *** CD-ROM | disk | FTP | other *** search
/ Hackers Magazine 57 / CdHackersMagazineNr57.iso / Software / Multimedia / k3d-setup-0.7.11.0.exe / include / k3d / k3dsdk / hints.h < prev    next >
Encoding:
C/C++ Source or Header  |  2009-02-09  |  8.0 KB  |  397 lines

  1. #ifndef K3DSDK_HINTS_H
  2. #define K3DSDK_HINTS_H
  3.  
  4. // K-3D
  5. // Copyright (c) 1995-2008, Timothy M. Shead
  6. //
  7. // Contact: tshead@k-3d.com
  8. //
  9. // This program is free software; you can redistribute it and/or
  10. // modify it under the terms of the GNU General Public
  11. // License as published by the Free Software Foundation; either
  12. // version 2 of the License, or (at your option) any later version.
  13. //
  14. // This program is distributed in the hope that it will be useful,
  15. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  16. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  17. // General Public License for more details.
  18. //
  19. // You should have received a copy of the GNU General Public
  20. // License along with this program; if not, write to the Free Software
  21. // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  22.  
  23. /** \file
  24.     \author Timothy M. Shead (tshead@k-3d.com)
  25. */
  26.  
  27. #include "algebra.h"
  28. #include "ihint.h"
  29. #include "mesh.h"
  30. #include "signal_system.h"
  31.  
  32. #include <boost/any.hpp>
  33.  
  34. #include <iosfwd>
  35.  
  36. namespace k3d
  37. {
  38.  
  39. /// Namespace reserved for "hints" that pass metadata about an upstream change to downstream nodes
  40. namespace hint
  41. {
  42.  
  43. //////////////////////////////////////////////////////////////////////////////
  44. // slot_t
  45.  
  46. /// iostream-compatible manipulator object that serializes information about a hint object
  47. class print
  48. {
  49. public:
  50.     print(ihint* Hint);
  51.  
  52.     ihint* const hint;
  53. };
  54.  
  55. /// Stream serialization
  56. std::ostream& operator<<(std::ostream& Stream, const print& RHS);
  57.  
  58. //////////////////////////////////////////////////////////////////////////////
  59. // slot_t
  60.  
  61. /// Defines a standard slot that receives a hint
  62. typedef sigc::slot<void, ihint*> slot_t;
  63.  
  64. //////////////////////////////////////////////////////////////////////////////
  65. // bitmap_dimensions_changed
  66.  
  67. /// Hint passed to downstream nodes to indicate that the pixel dimensions of a bitmap have changed (and thus its internal memory).
  68. class bitmap_dimensions_changed :
  69.     public ihint
  70. {
  71. public:
  72.     ihint* clone();
  73.     void print(std::ostream& Stream);
  74.  
  75.     static bitmap_dimensions_changed* instance();
  76. };
  77.  
  78. //////////////////////////////////////////////////////////////////////////////
  79. // bitmap_pixels_changed
  80.  
  81. /// Hint passed to downstream nodes to indicate that the pixel values of a bitmap have changed (i.e. one-or-more pixels have changed color).
  82. class bitmap_pixels_changed :
  83.     public ihint
  84. {
  85. public:
  86.     ihint* clone();
  87.     void print(std::ostream& Stream);
  88.  
  89.     static bitmap_pixels_changed* instance();
  90. };
  91.  
  92. //////////////////////////////////////////////////////////////////////////////
  93. // selection_changed
  94.  
  95. /// Hint object that indicates that an object's selection state has changed
  96. class selection_changed :
  97.     public ihint
  98. {
  99. public:
  100.     ihint* clone();
  101.     void print(std::ostream& Stream);
  102.  
  103.     static selection_changed* instance();
  104. };
  105.  
  106. //////////////////////////////////////////////////////////////////////////////
  107. // mesh_geometry_changed
  108.  
  109. /// Hint object that indicates that a mesh's geometry (the locations of its points) has changed
  110. class mesh_geometry_changed :
  111.     public ihint
  112. {
  113. public:
  114.     ihint* clone();
  115.     void print(std::ostream& Stream);
  116.  
  117.     static mesh_geometry_changed* instance();
  118.  
  119.     /// Indices of the points affected by the change
  120.     k3d::mesh::indices_t changed_points;
  121.     /// Transformation matrix used for the change
  122.     k3d::matrix4 transformation_matrix;
  123. };
  124.  
  125. //////////////////////////////////////////////////////////////////////////////
  126. // mesh_topology_changed
  127.  
  128. /// Hint object that indicates that a mesh's topology has changed
  129. class mesh_topology_changed :
  130.     public ihint
  131. {
  132. public:
  133.     ihint* clone();
  134.     void print(std::ostream& Stream);
  135.  
  136.     static mesh_topology_changed* instance();
  137. };
  138.  
  139. //////////////////////////////////////////////////////////////////////////////
  140. // mesh_deleted
  141.  
  142. /// Hint object that indicates a mesh was deleted
  143. class mesh_deleted :
  144.     public ihint
  145. {
  146. public:
  147.     ihint* clone();
  148.     void print(std::ostream& Stream);
  149.  
  150.     static mesh_deleted* instance();
  151. };
  152.     
  153. //////////////////////////////////////////////////////////////////////////////
  154. // file_changed
  155.  
  156. /// Hint object that indicates a file was changed
  157. class file_changed :
  158.     public ihint
  159. {
  160. public:
  161.     ihint* clone();
  162.     void print(std::ostream& Stream);
  163.  
  164.     static file_changed* instance();
  165. };
  166.  
  167. //////////////////////////////////////////////////////////////////////////////
  168. // any
  169.  
  170. /// Used when creating a hint-mapping that matches any incoming hint type.
  171. class any
  172. {
  173. public:
  174. };
  175.  
  176. //////////////////////////////////////////////////////////////////////////////
  177. // none
  178.  
  179. /// Used when creating a hint-mapping that maps to a NULL ("none") hint.
  180. class none
  181. {
  182. public:
  183. };
  184.  
  185. //////////////////////////////////////////////////////////////////////////////
  186. // unchanged
  187.  
  188. /// Used when creating a hint-mapping that does not convert hints.
  189. class unchanged
  190. {
  191. public:
  192. };
  193.  
  194. //////////////////////////////////////////////////////////////////////////////
  195. // hint_traits
  196.  
  197. /// Hint traits template responsible for matching and converting hints.
  198. template<typename HintT>
  199. class hint_traits
  200. {
  201. public:
  202. };
  203.  
  204. template<>
  205. class hint_traits<bitmap_dimensions_changed>
  206. {
  207. public:
  208.     static const bool_t match(ihint* Hint)
  209.     {
  210.         return dynamic_cast<bitmap_dimensions_changed*>(Hint);
  211.     }
  212.  
  213.     static ihint* convert(ihint*)
  214.     {
  215.         static bitmap_dimensions_changed hint;
  216.         return &hint;
  217.     }
  218. };
  219.  
  220. template<>
  221. class hint_traits<bitmap_pixels_changed>
  222. {
  223. public:
  224.     static const bool_t match(ihint* Hint)
  225.     {
  226.         return dynamic_cast<bitmap_pixels_changed*>(Hint);
  227.     }
  228.  
  229.     static ihint* convert(ihint*)
  230.     {
  231.         static bitmap_pixels_changed hint;
  232.         return &hint;
  233.     }
  234. };
  235.  
  236. template<>
  237. class hint_traits<selection_changed>
  238. {
  239. public:
  240.     static const bool_t match(ihint* Hint)
  241.     {
  242.         return dynamic_cast<selection_changed*>(Hint);
  243.     }
  244.  
  245.     static ihint* convert(ihint*)
  246.     {
  247.         static selection_changed hint;
  248.         return &hint;
  249.     }
  250. };
  251.  
  252. template<>
  253. class hint_traits<mesh_topology_changed>
  254. {
  255. public:
  256.     static const bool_t match(ihint* Hint)
  257.     {
  258.         return dynamic_cast<mesh_topology_changed*>(Hint);
  259.     }
  260.  
  261.     static ihint* convert(ihint*)
  262.     {
  263.         static mesh_topology_changed hint;
  264.         return &hint;
  265.     }
  266. };
  267.  
  268. template<>
  269. class hint_traits<mesh_geometry_changed>
  270. {
  271. public:
  272.     static const bool_t match(ihint* Hint)
  273.     {
  274.         return dynamic_cast<mesh_geometry_changed*>(Hint);
  275.     }
  276.  
  277.     static ihint* convert(ihint*)
  278.     {
  279.         static mesh_geometry_changed hint;
  280.         return &hint;
  281.     }
  282. };
  283.  
  284. template<>
  285. class hint_traits<any>
  286. {
  287. public:
  288.     static const bool_t match(ihint* Hint)
  289.     {
  290.         return true;
  291.     }
  292. };
  293.  
  294. template<>
  295. class hint_traits<none>
  296. {
  297. public:
  298.     static const bool_t match(ihint* Hint)
  299.     {
  300.         return false;
  301.     }
  302.  
  303.     static ihint* convert(ihint*)
  304.     {
  305.         return 0;
  306.     }
  307. };
  308.  
  309. template<>
  310. class hint_traits<unchanged>
  311. {
  312. public:
  313.     static ihint* convert(ihint* Hint)
  314.     {
  315.         return Hint;
  316.     }
  317. };
  318.  
  319. //////////////////////////////////////////////////////////////////////////////
  320. // last_conversion
  321.  
  322. class last_conversion
  323. {
  324. };
  325.  
  326. //////////////////////////////////////////////////////////////////////////////
  327. // convert
  328.  
  329. template<typename SourceT, typename TargetT, typename NextT = last_conversion>
  330. struct convert
  331. {
  332.     typedef SourceT Source;
  333.     typedef TargetT Target;
  334.     typedef NextT Next;
  335. };
  336.  
  337. namespace detail
  338. {
  339.  
  340. template<typename ListT>
  341. void execute(ihint* const Hint, const slot_t& Slot)
  342. {
  343.     if(hint_traits<typename ListT::Source>::match(Hint))
  344.     {
  345.         Slot(hint_traits<typename ListT::Target>::convert(Hint));
  346.     }
  347.     else
  348.     {
  349.         execute<typename ListT::Next>(Hint, Slot);
  350.     }
  351. }
  352.  
  353. template<>
  354. inline void execute<last_conversion>(ihint* const Hint, const slot_t& Slot)
  355. {
  356.     std::cerr << "unhandled hint: " << print(Hint) << std::endl;
  357. }
  358.  
  359. template<typename ListT>
  360. class converter
  361. {
  362. public:
  363.     converter(const slot_t& Slot) :
  364.         slot(Slot)
  365.     {
  366.     }
  367.  
  368.     void operator()(ihint* const Hint)
  369.     {
  370.         execute<ListT>(Hint, slot);
  371.     }
  372.  
  373. private:
  374.     slot_t slot;
  375. };
  376.  
  377. } // namespace detail
  378.  
  379. //////////////////////////////////////////////////////////////////////////////
  380. // converter
  381.  
  382. /// Factory function for creating hint-converter objects.  You can pass the
  383. /// result from converter() to the connect() method of a signal, to establish
  384. /// a hint-mapping.
  385. template<typename ListT>
  386. detail::converter<ListT> converter(const sigc::slot<void, ihint*>& Slot)
  387. {
  388.     return detail::converter<ListT>(Slot);
  389. }
  390.  
  391. } // namespace hint
  392.  
  393. } // namespace k3d
  394.  
  395. #endif // !K3DSDK_HINTS_H
  396.  
  397.