]> git.mxchange.org Git - simgear.git/commitdiff
Tweak APi for GCC happiness.
authorJames Turner <zakalawe@mac.com>
Sat, 9 Feb 2013 14:11:48 +0000 (14:11 +0000)
committerJames Turner <zakalawe@mac.com>
Sat, 9 Feb 2013 14:11:48 +0000 (14:11 +0000)
simgear/structure/commands.cxx
simgear/structure/commands.cxx~ [new file with mode: 0644]
simgear/structure/commands.hxx
simgear/structure/commands.hxx~ [new file with mode: 0644]

index 3a221321c3f1593238aab84d7e1dbb4223bd3556..ae0001f92c7ce68299c7fd951ba0b1e5f62dbf19 100644 (file)
@@ -52,7 +52,7 @@ SGCommandMgr::instance()
 }
 
 void
-SGCommandMgr::addCommand (const std::string &name, Command* command)
+SGCommandMgr::addCommandObject (const std::string &name, Command* command)
 {
     if (_commands.find(name) != _commands.end())
         throw sg_exception("duplicate command name:" + name);
diff --git a/simgear/structure/commands.cxx~ b/simgear/structure/commands.cxx~
new file mode 100644 (file)
index 0000000..3a22132
--- /dev/null
@@ -0,0 +1,100 @@
+// commands.cxx - encapsulated commands.
+// Started Spring 2001 by David Megginson, david@megginson.com
+// This code is released into the Public Domain.
+//
+// $Id$
+
+#ifdef HAVE_CONFIG_H
+#  include <simgear_config.h>
+#endif
+
+#include <memory>
+#include <simgear/props/props_io.hxx>
+
+#include "commands.hxx"
+
+#include <simgear/structure/exception.hxx>
+#include <simgear/threads/SGThread.hxx>
+#include <simgear/threads/SGGuard.hxx>
+#include <simgear/debug/logstream.hxx>
+
+\f
+////////////////////////////////////////////////////////////////////////
+// Implementation of SGCommandMgr class.
+////////////////////////////////////////////////////////////////////////
+
+
+SGCommandMgr::SGCommandMgr ()
+{
+  // no-op
+}
+
+SGCommandMgr::~SGCommandMgr ()
+{
+  // no-op
+}
+
+SGMutex SGCommandMgr::_instanceMutex;
+
+SGCommandMgr*
+SGCommandMgr::instance()
+{
+  static std::auto_ptr<SGCommandMgr> mgr;
+  if (mgr.get())
+    return mgr.get();
+
+  SGGuard<SGMutex> lock(_instanceMutex);
+  if (mgr.get())
+    return mgr.get();
+
+  mgr = std::auto_ptr<SGCommandMgr>(new SGCommandMgr);
+  return mgr.get();
+}
+
+void
+SGCommandMgr::addCommand (const std::string &name, Command* command)
+{
+    if (_commands.find(name) != _commands.end())
+        throw sg_exception("duplicate command name:" + name);
+    
+  _commands[name] = command;
+}
+
+SGCommandMgr::Command*
+SGCommandMgr::getCommand (const std::string &name) const
+{
+  const command_map::const_iterator it = _commands.find(name);
+  return (it != _commands.end() ? it->second : 0);
+}
+
+string_list
+SGCommandMgr::getCommandNames () const
+{
+  string_list names;
+  command_map::const_iterator it = _commands.begin();
+  command_map::const_iterator last = _commands.end();
+  while (it != last) {
+    names.push_back(it->first);
+    ++it;
+  }
+  return names;
+}
+
+bool
+SGCommandMgr::execute (const std::string &name, const SGPropertyNode * arg) const
+{
+  Command* command = getCommand(name);
+  if (command == 0)
+    return false;
+
+
+  try {
+    return (*command)(arg);
+  } catch (sg_exception& e) {
+    SG_LOG(SG_GENERAL, SG_ALERT, "command '" << name << "' failed with exception\n"
+      << "\tmessage:" << e.getMessage() << " (from " << e.getOrigin() << ")");
+    return false;
+  }
+}
+
+// end of commands.cxx
index c03ef5dc1ca0a05ba56db0e509c1b607bb6e3f5f..699cd055ded50e3b9df394abf4116cf488ff8920 100644 (file)
@@ -45,17 +45,19 @@ public:
         virtual bool operator()(const SGPropertyNode * arg) = 0;
     };
 
+    
+         typedef bool (*command_t) (const SGPropertyNode * arg);
+
 private:
-    template< typename Fun >
     class FunctionCommand : public Command
     {
     public:
-        FunctionCommand( const Fun* fun )
+        FunctionCommand( command_t fun )
        : f_(fun) {}
 
         virtual bool operator()(const SGPropertyNode * arg) { return (*f_)(arg); }
     private:
-        Fun* f_;
+        command_t f_;
     };
 
     template< class ObjPtr, typename MemFn >
@@ -78,12 +80,6 @@ private:
     * Helper template functions.
     */
 
-   template< typename Fun >
-   Command* make_functor( const Fun* fun )
-   {
-       return new FunctionCommand<Fun>(fun);
-   }
-
    template< class ObjPtr, typename MemFn >
    Command* make_functor( const ObjPtr& pObj, MemFn pMemFn )
    {
@@ -91,8 +87,7 @@ private:
    }
    
 public:
-    
-  typedef bool (*command_t) (const SGPropertyNode * arg);
+
 
   /**
    * Destructor.
@@ -113,16 +108,15 @@ public:
    * a bool result.  The argument is always a const pointer to
    * an SGPropertyNode (which may contain multiple values).
    */
-  template<typename FUNC>
-  void addCommand(const std::string& name, const FUNC* f)
-  { addCommand(name, make_functor(f)); }
+  void addCommand(const std::string& name, command_t f)
+  { addCommandObject(name, new FunctionCommand(f)); }
        
-  void addCommand (const std::string &name, Command* command);
+  void addCommandObject (const std::string &name, Command* command);
 
   template<class OBJ, typename METHOD>
   void addCommand(const std::string& name, const OBJ& o, METHOD m)
   { 
-    addCommand(name, make_functor(o,m));
+    addCommandObject(name, make_functor(o,m));
   }
   
   /**
diff --git a/simgear/structure/commands.hxx~ b/simgear/structure/commands.hxx~
new file mode 100644 (file)
index 0000000..503bdd1
--- /dev/null
@@ -0,0 +1,171 @@
+/**
+ * \file commands.hxx
+ * Interface definition for encapsulated commands.
+ * Started Spring 2001 by David Megginson, david@megginson.com
+ * This code is released into the Public Domain.
+ *
+ * $Id$
+ */
+
+#ifndef __COMMANDS_HXX
+#define __COMMANDS_HXX
+
+
+#include <simgear/compiler.h>
+
+#include <string>
+#include <map>
+
+#include <simgear/threads/SGThread.hxx>
+#include <simgear/math/sg_types.hxx>
+
+// forward decls
+class SGPropertyNode;
+     
+/**
+ * Manage commands.
+ *
+ * <p>This class allows the application to register and unregister
+ * commands, and provides shortcuts for executing them.  Commands are
+ * simple functions that take a const pointer to an SGPropertyNode:
+ * the function may use the nodes children as parameters.</p>
+ *
+ * @author David Megginson, david@megginson.com
+ */
+class SGCommandMgr
+{
+public:
+    /**
+     * Command functor object
+     */
+    class Command
+    {
+    public:
+        virtual ~Command() { }
+        virtual bool operator()(const SGPropertyNode * arg) = 0;
+    };
+
+    
+         typedef bool (*command_t) (const SGPropertyNode * arg);
+
+private:
+    class FunctionCommand : public Command
+    {
+    public:
+        FunctionCommand( command_t fun )
+       : f_(fun) {}
+
+        virtual bool operator()(const SGPropertyNode * arg) { return (*f_)(arg); }
+    private:
+        command_t f_;
+    };
+
+    template< class ObjPtr, typename MemFn >
+    class MethodCommand : public Command
+    {
+    public:
+        MethodCommand( const ObjPtr& pObj, MemFn pMemFn ) :
+         pObj_(pObj), pMemFn_(pMemFn) {}
+
+        virtual bool operator()(const SGPropertyNode * arg)
+        {
+            return ((*pObj_).*pMemFn_)(arg);
+        }
+    private:
+        ObjPtr pObj_;
+        MemFn pMemFn_;
+    };
+    
+   /**
+    * Helper template functions.
+    */
+
+   template< class ObjPtr, typename MemFn >
+   Command* make_functor( const ObjPtr& pObj, MemFn pMemFn )
+   {
+       return new MethodCommand<ObjPtr,MemFn>(pObj, pMemFn );
+   }
+   
+public:
+
+
+  /**
+   * Destructor.
+   */
+  virtual ~SGCommandMgr ();
+
+  /**
+   * Implement the classical singleton.
+   */
+  static SGCommandMgr* instance();
+
+  /**
+   * Register a new command with the manager.
+   *
+   * @param name The command name.  Any existing command with
+   * the same name will silently be overwritten.
+   * @param command A pointer to a one-arg function returning
+   * a bool result.  The argument is always a const pointer to
+   * an SGPropertyNode (which may contain multiple values).
+   */
+  void addCommand(const std::string& name, command_t f)
+  { addCommandObject(name, new FunctionCommand(f); }
+       
+  void addCommandObject (const std::string &name, Command* command);
+
+  template<class OBJ, typename METHOD>
+  void addCommand(const std::string& name, const OBJ& o, METHOD m)
+  { 
+    addCommandObject(name, make_functor(o,m));
+  }
+  
+  /**
+   * Look up an existing command.
+   *
+   * @param name The command name.
+   * @return A pointer to the command, or 0 if there is no registered
+   * command with the name specified.
+   */
+  virtual Command* getCommand (const std::string &name) const;
+
+
+  /**
+   * Get a list of all existing command names.
+   *
+   * @return A (possibly empty) vector of the names of all registered
+   * commands.
+   */
+  virtual string_list getCommandNames () const;
+
+
+  /**
+   * Execute a command.
+   *
+   * @param name The name of the command.
+   * @param arg A const pointer to an SGPropertyNode.  The node
+   * may have a value and/or children, etc., so that it is possible
+   * to pass an arbitrarily complex data structure to a command.
+   * @return true if the command is present and executes successfully,
+   * false otherwise.
+   */
+  virtual bool execute (const std::string &name, const SGPropertyNode * arg) const;
+
+protected:
+  /**
+   * Default constructor.
+   */
+  SGCommandMgr ();
+
+
+private:
+
+  typedef std::map<std::string,Command*> command_map;
+  command_map _commands;
+
+  static SGMutex _instanceMutex;
+
+};
+
+#endif // __COMMANDS_HXX
+
+// end of commands.hxx