4 // Fraunhofer Institute for Open Communication Systems (FOKUS)
5 // Competence Center NETwork research (NET), St. Augustin, GERMANY
6 // Stefan Bund <g0dil@berlios.de>
8 // This program is free software; you can redistribute it and/or modify
9 // it under the terms of the GNU General Public License as published by
10 // the Free Software Foundation; either version 2 of the License, or
11 // (at your option) any later version.
13 // This program is distributed in the hope that it will be useful,
14 // but WITHOUT ANY WARRANTY; without even the implied warranty of
15 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 // GNU General Public License for more details.
18 // You should have received a copy of the GNU General Public License
19 // along with this program; if not, write to the
20 // Free Software Foundation, Inc.,
21 // 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
24 \brief Variables public header */
26 #ifndef HH_SENF_Scheduler_Console_Variables_
27 #define HH_SENF_Scheduler_Console_Variables_ 1
30 #include <boost/utility.hpp>
31 #include <boost/type_traits/is_convertible.hpp>
32 #include <boost/ref.hpp>
33 #include "ParsedCommand.hh"
35 #include "Variables.ih"
36 //#include "Variables.mpp"
37 ///////////////////////////////hh.p////////////////////////////////////////
42 class ScopedDirectoryBase;
43 template <class Variable> class VariableAttributor;
49 template <class Variable>
50 VariableAttributor<Variable> senf_console_add_node(
51 DirectoryNode & node, std::string const & name, Variable & var, int,
52 typename boost::disable_if< boost::is_convertible<Variable*, ScopedDirectoryBase*> >::type * = 0,
53 typename boost::disable_if< boost::is_convertible<Variable*, GenericNode*> >::type * = 0,
54 typename boost::disable_if_c<detail::ParsedCommandTraits<Variable>::is_callable>::type * = 0);
56 template <class Variable>
57 typename detail::VariableNodeCreator<Variable>::result_type
58 senf_console_add_node(DirectoryNode & node, std::string const & name,
59 boost::reference_wrapper<Variable> var, int);
61 template <class Variable, class Owner>
62 VariableAttributor<Variable> senf_console_add_node(
63 DirectoryNode & node, Owner & owner, std::string const & name, Variable & var, int,
64 typename boost::disable_if< boost::is_convertible<Variable*, ScopedDirectoryBase*> >::type * = 0,
65 typename boost::disable_if< boost::is_convertible<Variable*, GenericNode*> >::type * = 0,
66 typename boost::disable_if_c<detail::ParsedCommandTraits<Variable>::is_callable>::type * = 0);
68 template <class Variable, class Owner>
69 typename detail::VariableNodeCreator<Variable>::result_type
70 senf_console_add_node(DirectoryNode & node, Owner & owner, std::string const & name,
71 boost::reference_wrapper<Variable> var, int);
75 /** \brief Variable command attributes (const)
77 \see VariableAttributor
79 template <class Variable>
80 class ConstVariableAttributor
83 typedef typename detail::QueryVariable<Variable>::Traits::Overload QueryOverload;
84 typedef typename QueryOverload::Formatter Formatter;
85 typedef OverloadedCommandNode node_type;
86 typedef ConstVariableAttributor return_type;
88 ConstVariableAttributor doc(std::string const & doc);
89 ConstVariableAttributor shortdoc(std::string const & doc);
90 ConstVariableAttributor formatter(Formatter formatter);
92 OverloadedCommandNode & node() const; ///< Return the node object
93 operator OverloadedCommandNode & () const; ///< Automatically convert to node object
96 explicit ConstVariableAttributor(QueryOverload & queryOverload);
99 QueryOverload & queryOverload_;
101 friend class detail::VariableNodeCreator<Variable const>;
104 /** \brief Variable command attributes
106 Variable commands allow to register any arbitrary variable as a command node. The variable
107 will be registered as two command overloads: One which takes a single argument of the
108 variables type to set the variable and another one taking no arguments and just querying the
109 current variable value.
112 ScopedDirectory<> dir;
117 Variables should be registered only with a ScopedDirectory declared in the same scope
118 (e.g. as a class member for member variables). This ensures, that the variable node is
119 removed from the tree when the scope is destroyed.
121 Since a variable command is added as a combination of two ordinary overloads, it is possible
122 to register additional overloads with the same name before or after registering the
125 It is also possible, to register a variable read-only. To achieve this, just wrap it with \c
126 boost::cref(). Such a variable cannot be changed only queried. Therefore, it does not have
127 the parser() and typeName() attributes.
129 dir.add("const_var", boost::cref(var))
132 \ingroup console_commands
134 template <class Variable>
135 class VariableAttributor
136 : public ConstVariableAttributor<Variable>
139 typedef typename detail::SetVariable<Variable>::Traits::Overload SetOverload;
140 typedef typename detail::ArgumentInfo<typename SetOverload::arg1_type>::Parser Parser;
141 typedef typename detail::SetVariable<Variable>::OnChangeHandler OnChangeHandler;
142 typedef OverloadedCommandNode node_type;
143 typedef VariableAttributor return_type;
145 typedef typename ConstVariableAttributor<Variable>::Formatter Formatter;
146 typedef typename ConstVariableAttributor<Variable>::QueryOverload QueryOverload;
148 VariableAttributor doc(std::string const & doc); ///< Set documentation of the variable
149 VariableAttributor shortdoc(std::string const & doc); ///< Set short documentation
150 VariableAttributor formatter(Formatter formatter); ///< Set formatter
151 /**< The \a formatter must be a callable with a signature
154 void formatter(Variable const & value, std::ostream & os);
156 The \a formatter takes the return value of the call \a
157 value and writes it properly formated to \a os. */
159 VariableAttributor parser(Parser parser); ///< Set argument parser
160 /**< The parser is an arbitrary callable object with
163 void parser(senf::console::ParseCommandInfo::TokensRange const & tokens, value_type & out);
166 where \c value_type is the type of the overload
167 parameter. The parser must read and parse the complete
168 \a tokens range and return the parsed value in \a
169 out. If the parser fails, it must raise a
170 senf::console::SyntaxErrorException. */
171 VariableAttributor typeName(std::string const & name); ///< Set name of the variable type
172 VariableAttributor onChange(OnChangeHandler handler); ///< Set change callback
173 /**< The \a handler callback is called, whenever the value
174 of the variable is changed. The new value has already
175 been set, when the callback is called, the old value is
176 passed to the callback. The callback must have a
177 signature compatible to
179 void handler(Variable const & oldValue);
185 VariableAttributor(QueryOverload & queryOverload, SetOverload & setOverload,
188 SetOverload & setOverload_;
191 friend class detail::VariableNodeCreator<Variable>;
195 ///////////////////////////////hh.e////////////////////////////////////////
196 //#include "Variables.cci"
197 //#include "Variables.ct"
198 #include "Variables.cti"
205 // comment-column: 40
206 // c-file-style: "senf"
207 // indent-tabs-mode: nil
208 // ispell-local-dictionary: "american"
209 // compile-command: "scons -u test"