00001 // See ../license.txt for license information. 00002 // 00003 // member.hpp 00004 // 00005 // 28-Jun-2003 phamilton Created 00006 // 00007 00008 #ifndef incREFLECT_MEMBER 00009 #define incREFLECT_MEMBER 00010 00011 // forwards 00012 #include <string> 00013 #include <vector> 00014 #include "../common/visitable_object.hpp" 00015 #include "boost/lexical_cast.hpp" 00016 #include "boost/filesystem/path.hpp" 00017 #include "config.hpp" 00018 00019 namespace ph { 00020 namespace reflect { 00021 00022 template <class T> 00023 class REFLECT_DECL member : public ph::common::member_base 00024 /** 00025 A member which represents a value based object. 00026 */ 00027 { 00028 protected: 00029 T *_ref; 00030 00031 public: 00032 member(T *ref) : 00033 _ref(ref) 00034 {}; 00035 00036 // member_base overrides. 00037 virtual std::string get() const 00038 { return ""; } 00039 virtual void set(const std::string &s) 00040 {}; 00041 }; 00042 00043 template <class T> 00044 class REFLECT_DECL const_member : public ph::common::member_base 00045 /** 00046 A member which represents a value based object. 00047 */ 00048 { 00049 protected: 00050 const T *_ref; 00051 00052 public: 00053 const_member(const T *ref) : 00054 _ref(ref) 00055 {}; 00056 00057 // member_base overrides. 00058 virtual std::string get() const 00059 { return ""; } 00060 virtual void set(const std::string &s) 00061 { 00062 // TBD: should throw from within here. 00063 }; 00064 }; 00065 00066 template <class T> 00067 class REFLECT_DECL pod_member : public member<T> 00068 /** 00069 A member which represents a value based object that 00070 can be converted to/from a string with lexical_cast<>. 00071 */ 00072 { 00073 public: 00074 pod_member(T *ref) : 00075 member<T>(ref) 00076 {}; 00077 00078 // member_base overrides. 00079 virtual std::string get() const 00080 { 00081 // this-> is required on gcc 3.4.3, but not 3.3. 00082 return boost::lexical_cast<std::string>(*this->_ref); 00083 } 00084 virtual void set(const std::string &s) 00085 { 00086 *this->_ref = boost::lexical_cast<T>(s); 00087 } 00088 }; 00089 00090 // specialize "bool" because lexical cast doesn't handle them. 00091 template <> 00092 class REFLECT_DECL pod_member<bool> : public member<bool> 00093 { 00094 public: 00095 pod_member(bool *ref) : 00096 member<bool>(ref) 00097 {}; 00098 00099 std::string get() const 00100 { 00101 return *this->_ref ? "true" : "false"; 00102 } 00103 void set(const std::string &s) 00104 { 00105 *this->_ref = s != "false"; 00106 } 00107 }; 00108 00109 template <class T> 00110 class REFLECT_DECL const_pod_member : public const_member<T> 00111 /** 00112 A member which represents a value based object that 00113 can be converted to/from a string with lexical_cast<>. 00114 */ 00115 { 00116 public: 00117 const_pod_member(const T *ref) : 00118 const_member<T>(ref) 00119 {}; 00120 00121 // member_base overrides. 00122 virtual std::string get() const 00123 { 00124 return boost::lexical_cast<std::string>(*this->_ref); 00125 } 00126 }; 00127 00128 template <> 00129 class REFLECT_DECL const_pod_member<bool> : public const_member<bool> 00130 { 00131 public: 00132 const_pod_member(const bool *ref) : 00133 const_member<bool>(ref) 00134 {}; 00135 00136 std::string get() const 00137 { 00138 return *this->_ref ? "true" : "false"; 00139 } 00140 }; 00141 00142 class REFLECT_DECL string_member : public member<std::string> 00143 /** 00144 A member which represents a string 00145 */ 00146 { 00147 public: 00148 string_member(std::string *ref) : 00149 member<std::string>(ref) 00150 {}; 00151 00152 // member_base overrides. 00153 virtual std::string get() const 00154 { 00155 return *this->_ref; 00156 } 00157 virtual void set(const std::string &s) 00158 { 00159 *this->_ref = s; 00160 } 00161 }; 00162 00163 class REFLECT_DECL const_string_member : public const_member<std::string> 00164 /** 00165 A member which represents a string 00166 */ 00167 { 00168 public: 00169 const_string_member(const std::string *ref) : 00170 const_member<std::string>(ref) 00171 {}; 00172 00173 // member_base overrides. 00174 virtual std::string get() const 00175 { 00176 return *this->_ref; 00177 } 00178 }; 00179 00180 class REFLECT_DECL path_member : public member<boost::filesystem::path> 00181 /** 00182 A member which represents a path. 00183 */ 00184 { 00185 public: 00186 path_member(boost::filesystem::path *ref) : 00187 member<boost::filesystem::path>(ref) 00188 {}; 00189 00190 // member_base overrides. 00191 virtual std::string get() const 00192 { 00193 return this->_ref->string(); 00194 } 00195 virtual void set(const std::string &s) 00196 { 00197 *this->_ref = s; 00198 } 00199 }; 00200 00201 class REFLECT_DECL const_path_member : public const_member<boost::filesystem::path> 00202 /** 00203 A member which represents a path. 00204 */ 00205 { 00206 public: 00207 const_path_member(const boost::filesystem::path *ref) : 00208 const_member<boost::filesystem::path>(ref) 00209 {}; 00210 00211 // member_base overrides. 00212 virtual std::string get() const 00213 { 00214 return this->_ref->string(); 00215 } 00216 }; 00217 00218 template <class T> 00219 class REFLECT_DECL other_member : public member<T> 00220 /** 00221 A member which represents some other type of member. Each 00222 needs to provide it's own "set/get" implementation. 00223 */ 00224 { 00225 public: 00226 other_member(T *ref) : 00227 member<T>(ref) 00228 {}; 00229 00230 // member overrides. 00231 virtual std::string get() const; 00232 virtual void set(const std::string &s); 00233 }; 00234 00235 template <class T> 00236 class REFLECT_DECL const_other_member : public const_member<T> 00237 /** 00238 A member which represents some other type of member. Each 00239 needs to provide it's own "set/get" implementation. 00240 */ 00241 { 00242 public: 00243 const_other_member(const T *ref) : 00244 const_member<T>(ref) 00245 {}; 00246 00247 // const_member overrides. 00248 virtual std::string get() const; 00249 }; 00250 00251 }; // reflect 00252 }; // ph 00253 00254 #endif // incREFLECT_MEMBER