X-Git-Url: http://g0dil.de/git?a=blobdiff_plain;f=senf%2FUtils%2FConsole%2FVariables.hh;h=9c2224b55135f962d7b1512125dc6521df41df53;hb=0003d55730b447329342161d12cf2ed23b63459e;hp=4f93a93fcd3bd3d9862a1877a0a21478d4cb9a40;hpb=601d1f509f5bb24df167a4dd5a20da67a0af9af8;p=senf.git diff --git a/senf/Utils/Console/Variables.hh b/senf/Utils/Console/Variables.hh index 4f93a93..9c2224b 100644 --- a/senf/Utils/Console/Variables.hh +++ b/senf/Utils/Console/Variables.hh @@ -1,24 +1,29 @@ // $Id$ // -// Copyright (C) 2008 +// Copyright (C) 2008 // Fraunhofer Institute for Open Communication Systems (FOKUS) -// Competence Center NETwork research (NET), St. Augustin, GERMANY -// Stefan Bund // -// This program is free software; you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation; either version 2 of the License, or -// (at your option) any later version. +// The contents of this file are subject to the Fraunhofer FOKUS Public License +// Version 1.0 (the "License"); you may not use this file except in compliance +// with the License. You may obtain a copy of the License at +// http://senf.berlios.de/license.html // -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. +// The Fraunhofer FOKUS Public License Version 1.0 is based on, +// but modifies the Mozilla Public License Version 1.1. +// See the full license text for the amendments. // -// You should have received a copy of the GNU General Public License -// along with this program; if not, write to the -// Free Software Foundation, Inc., -// 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +// Software distributed under the License is distributed on an "AS IS" basis, +// WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License +// for the specific language governing rights and limitations under the License. +// +// The Original Code is Fraunhofer FOKUS code. +// +// The Initial Developer of the Original Code is Fraunhofer-Gesellschaft e.V. +// (registered association), Hansastraße 27 c, 80686 Munich, Germany. +// All Rights Reserved. +// +// Contributor(s): +// Stefan Bund /** \file \brief Variables public header */ @@ -30,11 +35,11 @@ #include #include #include -#include "ParsedCommand.hh" +#include "Node.hh" #include "Variables.ih" //#include "Variables.mpp" -///////////////////////////////hh.p//////////////////////////////////////// +//-///////////////////////////////////////////////////////////////////////////////////////////////// namespace senf { namespace console { @@ -42,66 +47,37 @@ namespace console { class ScopedDirectoryBase; template class VariableAttributor; - +namespace factory { #ifndef DOXYGEN template - VariableAttributor senf_console_add_node( - DirectoryNode & node, std::string const & name, Variable & var, int, - typename boost::disable_if< boost::is_convertible >::type * = 0, - typename boost::disable_if< boost::is_convertible >::type * = 0, - typename boost::disable_if_c::is_callable>::type * = 0); - - template - typename detail::VariableNodeCreator::result_type - senf_console_add_node(DirectoryNode & node, std::string const & name, - boost::reference_wrapper var, int); - - template - VariableAttributor senf_console_add_node( - DirectoryNode & node, Owner & owner, std::string const & name, Variable & var, int, - typename boost::disable_if< boost::is_convertible >::type * = 0, - typename boost::disable_if< boost::is_convertible >::type * = 0, - typename boost::disable_if_c::is_callable>::type * = 0); - - template - typename detail::VariableNodeCreator::result_type - senf_console_add_node(DirectoryNode & node, Owner & owner, std::string const & name, - boost::reference_wrapper var, int); - -#endif - - /** \brief Variable command attributes (const) - - \see VariableAttributor - */ - template - class ConstVariableAttributor + class ConstVariableFactory + : public detail::NodeFactory { public: typedef typename detail::QueryVariable::Traits::Overload QueryOverload; typedef typename QueryOverload::Formatter Formatter; typedef OverloadedCommandNode node_type; - typedef ConstVariableAttributor return_type; + typedef OverloadedCommandNode & result_type; - ConstVariableAttributor doc(std::string const & doc); - ConstVariableAttributor shortdoc(std::string const & doc); - ConstVariableAttributor formatter(Formatter formatter); + ConstVariableFactory doc(std::string const & doc); + ConstVariableFactory shortdoc(std::string const & doc); + ConstVariableFactory formatter(Formatter formatter); - OverloadedCommandNode & node() const; ///< Return the node object - operator OverloadedCommandNode & () const; ///< Automatically convert to node object + OverloadedCommandNode & create(DirectoryNode & dir, std::string const & name) const; - protected: - explicit ConstVariableAttributor(QueryOverload & queryOverload); + explicit ConstVariableFactory(Variable const & var); private: - QueryOverload & queryOverload_; - - friend class detail::VariableNodeCreator; + typename QueryOverload::ptr queryOverload_; + boost::optional doc_; + boost::optional shortdoc_; }; - - /** \brief Variable command attributes + +#endif + + /** \brief Variable node factory Variable commands allow to register any arbitrary variable as a command node. The variable will be registered as two command overloads: One which takes a single argument of the @@ -111,7 +87,7 @@ namespace console { int var; ScopedDirectory<> dir; - dir.add("var", var); + dir.add("var", fty::Variable(var)); \endcode Variables should be registered only with a ScopedDirectory declared in the same scope @@ -120,79 +96,101 @@ namespace console { Since a variable command is added as a combination of two ordinary overloads, it is possible to register additional overloads with the same name before or after registering the - variable. + variable. It is also possible, to register a variable read-only. To achieve this, just wrap it with \c - boost::cref(). Such a variable cannot be changed only queried. Therefore, it does not have - the parser() and typeName() attributes. + boost::cref(). Such a variable only queried. Therefore, it does not have the parser() and + typeName() attributes. \code - dir.add("const_var", boost::cref(var)) + dir.add("const_var", fty::Variable(boost::cref(var))); \endcode - \ingroup console_commands + \note Even though the interface is documented as a class, in reality it is implemented using + factory functions returning instances of an internal factory class. + + \see \ref console_variables */ +#ifdef DOXYGEN + class Variable +#else template - class VariableAttributor - : public ConstVariableAttributor + class VariableFactory + : public ConstVariableFactory +#endif { public: typedef typename detail::SetVariable::Traits::Overload SetOverload; typedef typename detail::ArgumentInfo::Parser Parser; typedef typename detail::SetVariable::OnChangeHandler OnChangeHandler; - typedef OverloadedCommandNode node_type; - typedef VariableAttributor return_type; - - typedef typename ConstVariableAttributor::Formatter Formatter; - typedef typename ConstVariableAttributor::QueryOverload QueryOverload; - - VariableAttributor doc(std::string const & doc); ///< Set documentation of the variable - VariableAttributor shortdoc(std::string const & doc); ///< Set short documentation - VariableAttributor formatter(Formatter formatter); ///< Set formatter - /**< The \a formatter must be a callable with a signature - compatible with - \code - void formatter(Variable const & value, std::ostream & os); - \endcode - The \a formatter takes the return value of the call \a - value and writes it properly formated to \a os. */ - - VariableAttributor parser(Parser parser); ///< Set argument parser - /**< The parser is an arbitrary callable object with - the signature - \code - void parser(senf::console::ParseCommandInfo::TokensRange const & tokens, value_type & out); - \endcode - - where \c value_type is the type of the overload - parameter. The parser must read and parse the complete - \a tokens range and return the parsed value in \a - out. If the parser fails, it must raise a - senf::console::SyntaxErrorException. */ - VariableAttributor typeName(std::string const & name); ///< Set name of the variable type - VariableAttributor onChange(OnChangeHandler handler); ///< Set change callback - /**< The \a handler callback is called, whenever the value - of the variable is changed. The new value has already - been set, when the callback is called, the old value is - passed to the callback. The callback must have a - signature compatible to - \code - void handler(Variable const & oldValue); - \endcode */ - + + typedef typename ConstVariableFactory::Formatter Formatter; + typedef typename ConstVariableFactory::QueryOverload QueryOverload; + + VariableFactory doc(std::string const & doc); ///< Set documentation of the variable + VariableFactory shortdoc(std::string const & doc); ///< Set short documentation + VariableFactory formatter(Formatter formatter); ///< Set formatter + /**< The \a formatter must be a callable with a signature + compatible with + \code + void formatter(Variable const & value, std::ostream & os); + \endcode + The \a formatter takes the return value of the call \a + value and writes it properly formated to \a os. */ + VariableFactory parser(Parser parser); ///< Set argument parser + /**< The parser is an arbitrary callable object with + the signature + \code + void parser(senf::console::ParseCommandInfo::TokensRange const & tokens, value_type & out); + \endcode + + where \c value_type is the type of the overload + parameter. The parser must read and parse the complete + \a tokens range and return the parsed value in \a + out. If the parser fails, it must raise a + senf::console::SyntaxErrorException. */ + VariableFactory typeName(std::string const & name); ///< Set name of the variable type + VariableFactory onChange(OnChangeHandler handler); ///< Set change callback + /**< The \a handler callback is called, whenever the value + of the variable is changed. The new value has already + been set, when the callback is called, the old value is + passed to the callback. The callback must have a + signature compatible to + \code + void handler(Variable const & oldValue); + \endcode */ + + explicit VariableFactory(Variable & var); ///< Create Variable node + protected: private: - VariableAttributor(QueryOverload & queryOverload, SetOverload & setOverload, - Variable & var); + OverloadedCommandNode & create(DirectoryNode & dir, std::string const & name) const; - SetOverload & setOverload_; + typename SetOverload::ptr setOverload_; Variable & var_; - friend class detail::VariableNodeCreator; + friend class senf::console::DirectoryNode; }; -}} -///////////////////////////////hh.e//////////////////////////////////////// +#ifndef DOXYGEN + + template + VariableFactory Variable(Var & var); + + template + VariableFactory Variable(boost::reference_wrapper var); + + template + ConstVariableFactory Variable(Var const & var); + + template + ConstVariableFactory Variable(boost::reference_wrapper var); + +#endif + +}}} + +//-///////////////////////////////////////////////////////////////////////////////////////////////// //#include "Variables.cci" //#include "Variables.ct" #include "Variables.cti"