You can subscribe to this list here.
2005 |
Jan
|
Feb
|
Mar
|
Apr
|
May
|
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
(1) |
Dec
(153) |
---|---|---|---|---|---|---|---|---|---|---|---|---|
2006 |
Jan
(48) |
Feb
(46) |
Mar
(12) |
Apr
(4) |
May
(4) |
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
|
Dec
|
2007 |
Jan
|
Feb
(263) |
Mar
(235) |
Apr
(66) |
May
(42) |
Jun
(270) |
Jul
(65) |
Aug
(2) |
Sep
|
Oct
|
Nov
|
Dec
|
2013 |
Jan
(1) |
Feb
|
Mar
|
Apr
|
May
|
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
|
Dec
|
From: Markus R. <rol...@us...> - 2005-12-05 21:24:54
|
Update of /cvsroot/simspark/simspark/spark/oxygen/geometryserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv16714/geometryserver Added Files: .cvsignore Log Message: --- NEW FILE: .cvsignore --- *.lo .deps .dirstamp .libs |
From: Markus R. <rol...@us...> - 2005-12-05 21:24:53
|
Update of /cvsroot/simspark/simspark/spark/oxygen/sceneserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv16714/sceneserver Added Files: .cvsignore Log Message: --- NEW FILE: .cvsignore --- *.lo .deps .dirstamp .libs |
From: Markus R. <rol...@us...> - 2005-12-05 21:24:53
|
Update of /cvsroot/simspark/simspark/spark/oxygen/spadesserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv16714/spadesserver Added Files: .cvsignore Log Message: --- NEW FILE: .cvsignore --- *.lo .deps .dirstamp .libs |
From: Markus R. <rol...@us...> - 2005-12-05 21:24:52
|
Update of /cvsroot/simspark/simspark/spark/oxygen/monitorserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv16714/monitorserver Added Files: .cvsignore Log Message: --- NEW FILE: .cvsignore --- *.lo .deps .dirstamp .libs |
From: Markus R. <rol...@us...> - 2005-12-05 21:24:51
|
Update of /cvsroot/simspark/simspark/spark/oxygen/gamecontrolserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv16714/gamecontrolserver Added Files: .cvsignore Log Message: --- NEW FILE: .cvsignore --- .deps .dirstamp .libs *.lo |
Update of /cvsroot/simspark/simspark/spark/oxygen/sceneserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv15620/sceneserver Added Files: basenode.cpp basenode.h basenode_c.cpp camera.cpp camera.h camera_c.cpp fpscontroller.cpp fpscontroller.h fpscontroller_c.cpp scene.cpp scene.h scene_c.cpp sceneimporter.h sceneimporter_c.cpp sceneserver.cpp sceneserver.h sceneserver_c.cpp transform.cpp transform.h transform_c.cpp Log Message: --- NEW FILE: transform.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: transform.cpp,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "transform.h" #include "sceneserver.h" using namespace boost; using namespace oxygen; using namespace salt; using namespace zeitgeist; Transform::Transform() : BaseNode() { mChangedMark = -1; mLocalTransform.Identity(); mOldLocalTransform.Identity(); mWorldTransform.Identity(); SetName("transform"); } Transform::~Transform() { } int Transform::GetChangedMark() const { return mChangedMark; } const salt::Matrix& Transform::GetLocalTransform() const { return mLocalTransform; } const salt::Matrix& Transform::GetOldLocalTransform() const { return mOldLocalTransform; } const salt::Matrix& Transform::GetWorldTransform() const { return mWorldTransform; } void Transform::SetLocalTransform(const salt::Matrix &transform) { mChangedMark = SceneServer::GetTransformMark(); mOldLocalTransform = mLocalTransform; mLocalTransform = transform; } void Transform::SetWorldTransform(const salt::Matrix &transform) { shared_ptr<BaseNode> parent = shared_static_cast<BaseNode> (make_shared(mParent)); if (parent.get() == 0) { return; } mChangedMark = SceneServer::GetTransformMark(); mOldLocalTransform = mLocalTransform; mLocalTransform = transform; parent->SetWorldTransform(mIdentityMatrix); } void Transform::SetLocalPos(const salt::Vector3f &pos) { mChangedMark = SceneServer::GetTransformMark(); mOldLocalTransform = mLocalTransform; mLocalTransform.Pos() = pos; UpdateHierarchyInternal(); } void Transform::SetLocalRotation(const salt::Vector3f &rot) { mChangedMark = SceneServer::GetTransformMark(); mOldLocalTransform = mLocalTransform; Vector3f pos = mLocalTransform.Pos(); mLocalTransform.RotationX(gDegToRad(rot[0])); mLocalTransform.RotateY(gDegToRad(rot[1])); mLocalTransform.RotateZ(gDegToRad(rot[2])); mLocalTransform.Pos() = pos; UpdateHierarchyInternal(); } void Transform::OnLink() { UpdateHierarchyInternal(); } void Transform::UpdateHierarchyInternal() { shared_ptr<BaseNode> parent = shared_static_cast<BaseNode>(make_shared(mParent)); // no parent, return local transform if (parent.get() == NULL) { mWorldTransform = mLocalTransform; } else { mWorldTransform = parent->GetWorldTransform() * mLocalTransform; } } --- NEW FILE: scene.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: scene.cpp,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "scene.h" using namespace boost; using namespace oxygen; using namespace salt; using namespace zeitgeist; Scene::Scene() : BaseNode(), mModified(false) { } Scene::~Scene() { } const salt::Matrix& Scene::GetWorldTransform() const { return mIdentityMatrix; } void Scene::SetWorldTransform(const salt::Matrix &/*transform*/) { } void Scene::SetModified(bool modified) { mModified = modified; } bool Scene::GetModified() { return mModified; } --- NEW FILE: basenode.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: basenode.h,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. BaseNode NOTE: HISTORY: 05.11.02 - MK - Initial version TODO: TOFIX: */ #ifndef OXYGEN_BASENODE_H #define OXYGEN_BASENODE_H #include <salt/matrix.h> #include <salt/bounds.h> #include <zeitgeist/node.h> namespace oxygen { class Scene; /** BaseNode is the base class for all nodes which are part of the scene hierarchy. It's Hierarchy functionality (children, naming, etc..) is inherited from zeitgeist. It does NOT have an explicit local and world transform. */ class BaseNode : public zeitgeist::Node { // // Functions // public: BaseNode(); virtual ~BaseNode(); // transformation related /** return the local transform of this node. (default: returns * identity) */ virtual const salt::Matrix& GetLocalTransform() const; /** returns the world transform of this node (default: returns * parents world transform) */ virtual const salt::Matrix& GetWorldTransform() const; /** sets the local transform of this node (default: ignored) */ virtual void SetLocalTransform(const salt::Matrix &transform); /** sets the world transform of this node (default: ignored) */ virtual void SetWorldTransform(const salt::Matrix &transform); // bounding box related /** computes the local bounding box of the node */ virtual void ComputeBoundingBox(); /** returns the world bounding box of this node */ const salt::AABB3& GetWorldBoundingBox() const; // scene graph update passes /** updates internal state before physics calculation */ void PrePhysicsUpdate(float deltaTime); /** updates internal state after physics calculation */ void PostPhysicsUpdate(); /** update hierarchical data (position, bounding volumes, etc..) */ void UpdateHierarchy(); /** moves up the hierarchy, until it finds a scene */ boost::shared_ptr<Scene> GetScene(); /** enables debug mode controls */ void EnableDebugMode(); /** disabled debug mode controls */ void DisableDebugMode(); /** imports a scene from a file below this Node */ bool ImportScene(const std::string& fileName, boost::shared_ptr<zeitgeist::ParameterList> parameter); protected: /** returns the corresponding local coordinates to the given world coordinates */ salt::Vector3f GetLocalPos(const salt::Vector3f& worldPos); /** updates internal state before physics calculation */ virtual void PrePhysicsUpdateInternal(float deltaTime); /** updates internal state after physics calculation */ virtual void PostPhysicsUpdateInternal(); /** updates hierarchical date (position, bounding volumes, etc..) */ virtual void UpdateHierarchyInternal(); // // Members // protected: /** the identity matrix */ static const salt::Matrix mIdentityMatrix; /** debug mode (for additional visualization) */ bool mDebugMode; /** local bounding box */ salt::AABB3 mLocalBoundingBox; /** world bounding box */ salt::AABB3 mWorldBoundingBox; }; DECLARE_CLASS(BaseNode); } //namespace oxygen #endif //OXYGEN_BASENODE_H --- NEW FILE: transform.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: transform.h,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. Transform NOTE: HISTORY: 05.11.02 - MK - Initial version TODO: TOFIX: */ #ifndef OXYGEN_TRANSFORM_H #define OXYGEN_TRANSFORM_H #include "basenode.h" namespace oxygen { /** Transform is used to do local transforms relative to a parent node. */ class Transform : public BaseNode { // // Functions // public: Transform(); virtual ~Transform(); // transformation related /** returns the old local transform of this node */ const salt::Matrix& GetOldLocalTransform() const; /** returns the local transform of this node */ virtual const salt::Matrix& GetLocalTransform() const; /** returns the world transform of this node */ virtual const salt::Matrix& GetWorldTransform() const; /** sets the local transform of this node */ virtual void SetLocalTransform(const salt::Matrix &transform); /** sets the world transform of this node */ virtual void SetWorldTransform(const salt::Matrix &transform); /** sets the local position of this node */ void SetLocalPos(const salt::Vector3f &pos); /** sets the local rotation of this node in degrees */ void SetLocalRotation(const salt::Vector3f &rot); /** returns the current transform mark */ int GetChangedMark() const; protected: /** upon linkage, we have to update our world transform */ virtual void OnLink(); private: /** updates hierarchical date (position, bounding volumes, etc..) */ virtual void UpdateHierarchyInternal(); private: /** local transformation relative to parent */ salt::Matrix mLocalTransform; /** world transform generated by multiplying the parent's world transform with the local transform */ salt::Matrix mWorldTransform; /** Transform mark from the SceneServer; this value is updated with the the current value if the local transform matrix is modified */ int mChangedMark; /** the previous transformation relative to the parent */ salt::Matrix mOldLocalTransform; }; DECLARE_CLASS(Transform); } //namespace oxygen #endif //OXYGEN_TRANSFORM_H --- NEW FILE: fpscontroller_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: fpscontroller_c.cpp,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "fpscontroller.h" using namespace boost; using namespace oxygen; FUNCTION(FPSController,setAcceleration) { float inAccel; if ( (in.GetSize() != 1) || (! in.GetValue(in.begin(),inAccel)) ) { return false; } obj->SetAcceleration(inAccel); return true; } FUNCTION(FPSController,getAcceleration) { return obj->GetAcceleration(); } void CLASS(FPSController)::DefineClass() { DEFINE_BASECLASS(oxygen/BodyController); DEFINE_FUNCTION(setAcceleration); DEFINE_FUNCTION(getAcceleration); } --- NEW FILE: fpscontroller.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: fpscontroller.h,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_FPSCONTROLLER_H #define OXYGEN_FPSCONTROLLER_H #include <oxygen/physicsserver/bodycontroller.h> namespace oxygen { /** \class FPSController is a BodyController, that provides first * person shooter (FPS) movement, i.e. moving forward, backward, * strafing etc. The node maintains a state for each movement. This * state can either be activated or deactivated with some accessor * functions. As long as a state is activated the node performs the * associated action during each time step. */ class FPSController : public BodyController { // // Functions // public: FPSController(); virtual ~FPSController(); /** adds a delta increment to the current horizontal angle */ void AdjustHAngle(const float delta); /** adds a delta increment to the current vertical angle */ void AdjustVAngle(const float delta); /** enables or disables forward movement */ void Forward(const bool state); /** enables or disables backwad movement */ void Backward(const bool state); /** enables or disables left strafing */ void StrafeLeft(const bool state); /** enables or disables right strafing */ void StrafeRight(const bool state); /** enables or disables up movement */ void Up(const bool state); /** enables or disables down movement */ void Down(const bool state); /** sets the applied acceleration */ void SetAcceleration(const float accel); /** returns the applied acceleration */ float GetAcceleration() const; protected: /** calculates and applies the force needed to perfom the * activated movements */ virtual void PrePhysicsUpdateInternal(float deltaTime); // // Members // protected: /** the acceleration of the controller */ float mAcceleration; /** the current horizontal angle */ float mHAngle; /** the current vertical angle */ float mVAngle; // event states /** event state 'forward' */ bool mForward; /** event state 'backward' */ bool mBackward; /** event state 'left' */ bool mLeft; /** event state 'right' */ bool mRight; /** event state 'up' */ bool mUp; /** event state 'down' */ bool mDown; }; DECLARE_CLASS(FPSController); } //namespace oxygen #endif //OXYGEN_FPSCONTROLLER_H --- NEW FILE: sceneimporter_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: sceneimporter_c.cpp,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "sceneimporter.h" using namespace oxygen; void CLASS(SceneImporter)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Leaf); } --- NEW FILE: camera.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: camera.h,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef KEROSIN_CAMERA_H #define KEROSIN_CAMERA_H #include "basenode.h" #include <salt/frustum.h> namespace oxygen { /** Camera encapsualtes all data needed to describe the viewpoint from * which a scene is rendered. The active camera is responsible to * construct a frustum needed to render the scene. */ class Camera : public BaseNode { // // Functions // public: Camera(); virtual ~Camera(); // set properties /** sets viewpoint properties */ void SetViewport(int x, int y, int width, int height); int GetViewportX(); int GetViewportY(); int GetViewportWidth(); int GetViewportHeight(); /** sets the field of view (FOV) */ void SetFOV(const float fov); /** sets the distance of the Z near plane */ void SetZNear(const float zNear); /** sets the distance of the Z far plane */ void SetZFar(const float zFar); /** adjusts the current FOV, i.e. adds a delta increment */ void AdjustFOV(const float fov); /** adjusts the distance of the Z near plane, i.e adds a delta increment */ void AdjustZNear(const float zNear); /** adjusts the distance of the Z far plane, i.e adds a delta increment */ void AdjustZFar(const float zFar); /** returns the field of View */ float GetFOV() const; /** returns the distance of the Z near plane */ float GetZNear() const; /** returns the distance of the Z far plane */ float GetZFar() const; /** returns the view transformation matrix */ const salt::Matrix& GetViewTransform() const; /** returns the projection matrix */ const salt::Matrix& GetProjectionTransform() const; /** fills in a frustum object with the correct parameters for this camera */ void DescribeFrustum(salt::Frustum& frustum) const; /** sets the view transform to be the inverted WorldTransform and sets up the projection transform matrix **/ void Bind(); protected: /** gets the right viewport resolution */ virtual void OnLink(); private: /** calculates the view matrix (world->view space transformation) */ virtual void UpdateHierarchyInternal(); // // Members // protected: /** horizontal field of view, default is 60 degrees */ float mFOV; /** near clipping plane, default is 1 */ float mZNear; /** far clipping plane, default is 2000 */ float mZFar; /** x-position of upper left viewport corner, default is 0 */ int mX; /** y-position of upper left viewport corner, default is 0 */ int mY; /** width of viewport, default is the engine window width */ int mWidth; /** height of viewport, default is the egine window height */ int mHeight; float mHalfWorldWidth; float mHalfWorldHeight; /** the view transformation matrix */ salt::Matrix mViewTransform; /** the projection matrix */ salt::Matrix mProjectionTransform; }; DECLARE_CLASS(Camera); } //namespace kerosin #endif //KEROSIN_CAMERA_H --- NEW FILE: scene.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: scene.h,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. Scene NOTE: HISTORY: 05.11.02 - MK - Initial version TODO: TOFIX: */ #ifndef OXYGEN_SCENE_H #define OXYGEN_SCENE_H #include "basenode.h" namespace oxygen { /** Scene is the root node of a simulatable/displayable hierarchy. It is usually created via the scene server. */ class Scene : public BaseNode { public: Scene(); ~Scene(); /** returns the world transform of this node (always identity, terminates upward recursion) */ virtual const salt::Matrix& GetWorldTransform() const; /** sets the world transform of this node */ virtual void SetWorldTransform(const salt::Matrix &transform); /** marks the scene as modified, i.e. scene nodes were added or removed since the last update. This useful for monitors to decide between an incremental or a full state update */ void SetModified(bool modified); /** returns true iff the scene is marked modified */ bool GetModified(); protected: /** true, if the scene is modified */ bool mModified; }; DECLARE_CLASS(Scene); } //namespace oxygen #endif //OXYGEN_SCENE_H --- NEW FILE: sceneimporter.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: sceneimporter.h,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_SCENEIMPORTER #define OXYGEN_SCENEIMPORTER #include <zeitgeist/class.h> #include <zeitgeist/leaf.h> #include <salt/fileclasses.h> namespace oxygen { class BaseNode; class SceneImporter : public zeitgeist::Leaf { public: SceneImporter() : zeitgeist::Leaf() {} virtual ~SceneImporter() {}; /** import a scene from a file */ virtual bool ImportScene(const std::string& fileName, boost::shared_ptr<BaseNode> root, boost::shared_ptr<zeitgeist::ParameterList> parameter) = 0; /** import a scene from a string description */ virtual bool ParseScene(const std::string& scene, boost::shared_ptr<BaseNode> root, boost::shared_ptr<zeitgeist::ParameterList> parameter) = 0; }; DECLARE_ABSTRACTCLASS(SceneImporter); } // namespace oxygen #endif // OXYGEN_SCENEIMPORTER --- NEW FILE: sceneserver.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: sceneserver.h,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. SceneServer NOTE: HISTORY: 05.11.02 - MK - Initial version TODO: TOFIX: */ #ifndef OXYGEN_SCENESERVER_H #define OXYGEN_SCENESERVER_H #include <zeitgeist/class.h> #include <zeitgeist/node.h> namespace oxygen { #if 0 } #endif class Scene; class Space; class World; class BaseNode; class Transform; /** The scene server manages displayable subtrees within the object hierarchy. Each subtree begins with a Scene node. The scene server knows which scene node is currently active and updates that node (and its corresponding subtree). */ class SceneServer : public zeitgeist::Node { // // Functions // public: SceneServer(); ~SceneServer(); /** creates a new scene hierarchy at a specific location, new hierarchy is also made current */ boost::shared_ptr<Scene> CreateScene(const std::string &location); /** sets the active scene */ bool SetActiveScene(const std::string &location); /** returns a reference to the current active scene */ boost::shared_ptr<Scene> GetActiveScene() { return mActiveScene; } /** updates the state of the current active scene (deltaTime is in seconds) */ void Update(float deltaTime); /** imports a scene from a file below the given BaseNode */ bool ImportScene(const std::string& fileName, boost::shared_ptr<BaseNode> root, boost::shared_ptr<zeitgeist::ParameterList> parameter); /** creates an instance of \param importerName and registers it as a SceneImporter to the SceneServer */ bool InitSceneImporter(const std::string& importerName); /** returns the current label for modified transform nodes */ static int GetTransformMark(); protected: // // Members // /** gets missing references */ void UpdateCache(); /** resets all cached references */ void ResetCache(); /** resets all cached references */ virtual void OnUnlink(); /** reparents all children of node to the parent of node; Their local transform matrix is multiplied with the local transform matrix of node */ void ReparentTransformChildren(boost::shared_ptr<Transform> node); /** recursively reparents all transform nodes whose only children are also transform node */ void RemoveTransformPaths(boost::shared_ptr<zeitgeist::Leaf> root); private: /** the current active scene */ boost::shared_ptr<Scene> mActiveScene; /** cached reference to the Space node below the active scene */ boost::shared_ptr<Space> mActiveSpace; /** cached reference to the World node below the active scene */ boost::shared_ptr<World> mActiveWorld; /** modified transform nodes are labeled with this value, the value is incremented each cycle to avoid a resetting */ static int mTransformMark; }; DECLARE_CLASS(SceneServer); } //namespace oxygen #endif //OXYGEN_SCENESERVER_H --- NEW FILE: sceneserver_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: sceneserver_c.cpp,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. SceneServer The scene server manages displayable subtrees within the object hierarchy. Each subtree begins with a Scene node. The scene server knows which scene node is currently active and updates/displays that node (and its corresponding subtree). */ #include "sceneserver.h" using namespace boost; using namespace oxygen; using namespace zeitgeist; using namespace std; FUNCTION(SceneServer,createScene) { string inLocation; if ( (in.GetSize() != 1) || (! in.GetValue(in.begin(),inLocation)) ) { return false; } obj->CreateScene(inLocation); return true; } FUNCTION(SceneServer,setActiveScene) { string inLocation; if ( (in.GetSize() != 1) || (! in.GetValue(in.begin(),inLocation)) ) { return false; } obj->SetActiveScene(inLocation); return true; } FUNCTION(SceneServer,initSceneImporter) { string inImporterName; if ( (in.GetSize() != 1) || (! in.GetValue(in.begin(),inImporterName)) ) { return false; } return obj->InitSceneImporter(inImporterName); } void CLASS(SceneServer)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Node); DEFINE_FUNCTION(createScene); DEFINE_FUNCTION(setActiveScene); DEFINE_FUNCTION(initSceneImporter); } --- NEW FILE: transform_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: transform_c.cpp,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "transform.h" using namespace boost; using namespace oxygen; using namespace zeitgeist; using namespace salt; FUNCTION(Transform,setLocalPos) { Vector3f inPos; if ( (in.GetSize() == 0) || (! in.GetValue(in.begin(), inPos)) ) { return false; } obj->SetLocalPos(inPos); return true; } FUNCTION(Transform,setLocalRotation) { Vector3f inRot; if ( (in.GetSize() == 0) || (! in.GetValue(in.begin(), inRot)) ) { return false; } obj->SetLocalRotation(inRot); return true; } FUNCTION(Transform,setLocalTransform) { // float InM00, float InM01, float InM02, float InM03, // float InM10, float InM11, float InM12, float InM13, // float InM20, float InM21, float InM22, float InM23, // float InM30, float InM31, float InM32, float InM33 if (in.GetSize() != 16) { return false; } float m[16]; ParameterList::TVector::const_iterator iter = in.begin(); for (int i=0;i<16;++i) { if (! in.GetValue(iter,m[i])) { return false; } ++iter; } obj->SetLocalTransform(Matrix(m)); return true; } void CLASS(Transform)::DefineClass() { DEFINE_BASECLASS(oxygen/BaseNode); DEFINE_FUNCTION(setLocalPos); DEFINE_FUNCTION(setLocalRotation); DEFINE_FUNCTION(setLocalTransform); } --- NEW FILE: fpscontroller.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: fpscontroller.cpp,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "fpscontroller.h" #include <oxygen/physicsserver/body.h> #include <zeitgeist/logserver/logserver.h> using namespace boost; using namespace oxygen; using namespace salt; FPSController::FPSController() : BodyController() { mHAngle = 0.0f; mVAngle = 0.0f; mForward = false; mBackward = false; mLeft = false; mRight = false; mUp = false; mDown = false; mAcceleration = 10; } FPSController::~FPSController() { } void FPSController::PrePhysicsUpdateInternal(float /*deltaTime*/) { if (mBody.get() == 0) { return; } // determine force direction Vector3f vec(0.0f,0.0f,0.0f); if (mForward) vec.y() += 1.0f; if (mBackward) vec.y() -= 1.0f; if (mRight) vec.x() += 1.0f; if (mLeft) vec.x() -= 1.0f; if (mUp) vec.z() += 1.0f; if (mDown) vec.z() -= 1.0f; // constrain angles if(mVAngle > 88.0f) { mVAngle = 88.0f; } else if(mVAngle<-88.0f) { mVAngle = -88.0f; } Matrix matrix; float hAngle = gDegToRad(-mHAngle); float vAngle = gDegToRad(-mVAngle); matrix.RotationZ(hAngle); matrix.RotateX(vAngle); mBody->SetRotation(matrix); if (vec.SquareLength() > 0) { float force = mBody->GetMass() * mAcceleration; vec *= force; Matrix fwd; fwd.RotationZ(hAngle); mBody->AddForce(vec.y() * fwd.Up()); Matrix side; side.RotationX(vAngle); mBody->AddForce(vec.x() * fwd.Right()); mBody->AddForce(vec.z() * Vector3f(0,0,1)); } } void FPSController::AdjustHAngle(const float delta) { mHAngle += delta; } void FPSController::AdjustVAngle(const float delta) { mVAngle += delta; } void FPSController::Forward(const bool state) { mForward = state; } void FPSController::Backward(const bool state) { mBackward = state; } void FPSController::StrafeLeft(const bool state) { mLeft = state; } void FPSController::StrafeRight(const bool state) { mRight= state; } void FPSController::Up(const bool state) { mUp = state; } void FPSController::Down(const bool state) { mDown = state; } void FPSController::SetAcceleration(const float accel) { mAcceleration = accel; } float FPSController::GetAcceleration() const { return mAcceleration; } --- NEW FILE: basenode.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: basenode.cpp,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. BaseNode */ #include "basenode.h" #include "sceneserver.h" #include "scene.h" #include <zeitgeist/logserver/logserver.h> using namespace boost; using namespace oxygen; using namespace salt; using namespace zeitgeist; using namespace std; const salt::Matrix BaseNode::mIdentityMatrix(salt::Matrix::GetIdentity()); BaseNode::BaseNode() : zeitgeist::Node(), mDebugMode(false) { } BaseNode::~BaseNode() { } const salt::Matrix& BaseNode::GetLocalTransform() const { return mIdentityMatrix; } const salt::Matrix& BaseNode::GetWorldTransform() const { shared_ptr<BaseNode> parent = shared_static_cast<BaseNode> (make_shared(mParent)); // no parent, return identity if (parent.get() == 0) { return mIdentityMatrix; } else { return parent->GetWorldTransform(); } } void BaseNode::SetLocalTransform(const salt::Matrix& /*transform*/) { } void BaseNode::SetWorldTransform(const salt::Matrix& transform) { shared_ptr<BaseNode> parent = shared_static_cast<BaseNode> (make_shared(mParent)); if (parent.get() == 0) { return; } parent->SetWorldTransform(transform); } // This routine is responsible for updating the local bounding box of // the node. The default behavior is to treat the node as a point. // Note that this is always called from Compute(). void BaseNode::ComputeBoundingBox() { mLocalBoundingBox.minVec.Set(0,0,0); mLocalBoundingBox.maxVec.Set(0,0,0); } void BaseNode::PrePhysicsUpdate(float deltaTime) { // perform update on hierarchy TLeafList baseNodes; ListChildrenSupportingClass<BaseNode>(baseNodes); for (TLeafList::iterator i = baseNodes.begin(); i!= baseNodes.end(); ++i) { shared_static_cast<BaseNode>(*i)->PrePhysicsUpdate(deltaTime); } // do the internal update. This can be overridden by derived classes // to add custom behavior PrePhysicsUpdateInternal(deltaTime); ComputeBoundingBox(); } void BaseNode::PostPhysicsUpdate() { // perform update on hierarchy TLeafList baseNodes; ListChildrenSupportingClass<BaseNode>(baseNodes); for (TLeafList::iterator i = baseNodes.begin(); i!= baseNodes.end(); ++i) { shared_static_cast<BaseNode>(*i)->PostPhysicsUpdate(); } // do the internal update this can be overridden by derived classes // to add custom behavior PostPhysicsUpdateInternal(); } void BaseNode::UpdateHierarchy() { // do the internal update this can be overridden by derived classes // to add custom behavior UpdateHierarchyInternal(); // generate the bounding volume of this node Matrix worldTransform = GetWorldTransform(); mWorldBoundingBox = mLocalBoundingBox; mWorldBoundingBox.TransformBy(worldTransform); // perform update on hierarchy TLeafList baseNodes; ListChildrenSupportingClass<BaseNode>(baseNodes); for (TLeafList::iterator i = baseNodes.begin(); i!= baseNodes.end(); ++i) { shared_ptr<BaseNode> node = shared_static_cast<BaseNode>(*i); node->UpdateHierarchy(); // here we merge our world bounding volume with the child // volumes mWorldBoundingBox.Encapsulate(node->GetWorldBoundingBox()); } } shared_ptr<Scene> BaseNode::GetScene() { // is this node the scene node ? shared_ptr<Scene> self = shared_dynamic_cast<Scene>(make_shared(GetSelf())); if (self.get() != 0) { return self; } // move up the hierarchy until we find a scene node return make_shared(FindParentSupportingClass<Scene>()); } void BaseNode::EnableDebugMode() { mDebugMode = true; } void BaseNode::DisableDebugMode() { mDebugMode = false; } void BaseNode::PrePhysicsUpdateInternal(float /*deltaTime*/) { } void BaseNode::PostPhysicsUpdateInternal() { } void BaseNode::UpdateHierarchyInternal() { } const salt::AABB3& BaseNode::GetWorldBoundingBox() const { return mWorldBoundingBox; } bool BaseNode::ImportScene(const string& fileName, shared_ptr<ParameterList> parameter) { shared_ptr<SceneServer> sceneServer = shared_dynamic_cast<SceneServer> (GetCore()->Get("/sys/server/scene")); if (sceneServer.get() == 0) { GetLog()->Error() << "(BaseNode) ERROR: SceneServer not found\n"; return false; } shared_ptr<BaseNode> node = shared_dynamic_cast<BaseNode> (make_shared(GetSelf())); return sceneServer->ImportScene(fileName,node,parameter); } salt::Vector3f BaseNode::GetLocalPos(const salt::Vector3f& worldPos) { Matrix invWorld = GetWorldTransform(); invWorld.InvertRotationMatrix(); return invWorld.Transform(worldPos); } --- NEW FILE: scene_c.cpp --- /* -*- mode: c++ -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: scene_c.cpp,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "scene.h" using namespace boost; using namespace oxygen; using namespace zeitgeist; void CLASS(Scene)::DefineClass() { DEFINE_BASECLASS(oxygen/BaseNode); } --- NEW FILE: camera.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: camera.cpp,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "camera.h" #include <salt/matrix.h> #include <zeitgeist/logserver/logserver.h> #include <zeitgeist/scriptserver/scriptserver.h> using namespace oxygen; using namespace salt; Camera::Camera() : BaseNode() { mViewTransform.Identity(); mFOV = 60.0f; mZNear = 1.0f; mZFar = 2000.0f; mX = 0; mY = 0; mWidth = 640; mHeight = 480; SetName("camera"); } Camera::~Camera() { } /** This is some dangerous looking code, but it's not as bad as it seems. The code extracts a frustum given the projection and view transforms. It is really fast and very generic because of that. */ void Camera::DescribeFrustum(Frustum& frustum) const { // concatenate projection and view transform Matrix frustumMatrix = mProjectionTransform * mViewTransform; // Get plane parameters float* m = frustumMatrix.m; Plane *p = &frustum.mPlanes[Frustum::PI_RIGHT]; p->normal.Set(m[3]-m[0], m[7]-m[4], m[11]-m[8]); p->d = m[15]-m[12]; p = &frustum.mPlanes[Frustum::PI_LEFT]; p->normal.Set(m[3]+m[0], m[7]+m[4], m[11]+m[8]); p->d = m[15]+m[12]; p = &frustum.mPlanes[Frustum::PI_BOTTOM]; p->normal.Set(m[3]+m[1], m[7]+m[5], m[11]+m[9]); p->d = m[15]+m[13]; p = &frustum.mPlanes[Frustum::PI_TOP]; p->normal.Set(m[3]-m[1], m[7]-m[5], m[11]-m[9]); p->d = m[15]-m[13]; p = &frustum.mPlanes[Frustum::PI_NEAR]; p->normal.Set(m[3]-m[2], m[7]-m[6], m[11]-m[10]); p->d = m[15]-m[14]; p = &frustum.mPlanes[Frustum::PI_FAR]; p->normal.Set(m[3]+m[2], m[7]+m[6], m[11]+m[10]); p->d = m[15]+m[14]; // Normalize all plane normals for(int i=0;i<6;++i) { frustum.mPlanes[i].Normalize(); } // set base position frustum.mBasePos = GetWorldTransform().Pos(); } void Camera::Bind() { mViewTransform = GetWorldTransform(); mViewTransform.RotateX(90); mViewTransform.InvertRotationMatrix(); // setup the projection matrix mProjectionTransform.CalcInfiniteFrustum( -mHalfWorldWidth, mHalfWorldWidth, -mHalfWorldHeight, mHalfWorldHeight, mZNear); } void Camera::OnLink() { bool gotSetup = ( GetScript()->GetVariable("Viewport.XRes", mWidth) && GetScript()->GetVariable("Viewport.YRes", mHeight) ); if (! gotSetup) { GetLog()->Error() << "(Camera) unable to read setup from ScriptServer\n"; } } void Camera::UpdateHierarchyInternal() { // make sure values are within bounds gClamp(mFOV, 10.0f, 170.0f); mHalfWorldWidth = mZNear * (float)tan(gDegToRad(mFOV*0.5f)); mHalfWorldHeight = mHalfWorldWidth * (mHeight/(float)mWidth); } void Camera::SetViewport(int x, int y, int width, int height) { mX = x; mY = y; mWidth = width; mHeight = height; } int Camera::GetViewportX() { return mX; } int Camera::GetViewportY() { return mY; } int Camera::GetViewportWidth() { return mWidth; } int Camera::GetViewportHeight() { return mHeight; } void Camera::SetFOV(const float fov) { mFOV = fov; } void Camera::SetZNear(const float zNear) { mZNear = zNear; } void Camera::SetZFar(const float zFar) { mZFar = zFar; } void Camera::AdjustFOV(const float fov) { mFOV+=fov; } void Camera::AdjustZNear(const float zNear) { mZNear+=zNear; } void Camera::AdjustZFar(const float zFar) { mZFar+=zFar; } float Camera::GetFOV() const { return mFOV; } float Camera::GetZNear() const { return mZNear; } float Camera::GetZFar()const { return mZFar; } const salt::Matrix& Camera::GetViewTransform() const { return mViewTransform; } const salt::Matrix& Camera::GetProjectionTransform() const { return mProjectionTransform; } --- NEW FILE: sceneserver.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: sceneserver.cpp,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "sceneserver.h" #include <zeitgeist/logserver/logserver.h> #include <zeitgeist/corecontext.h> #include <zeitgeist/fileserver/fileserver.h> #include <salt/vector.h> #include <salt/frustum.h> #include "transform.h" #include "scene.h" #include "sceneimporter.h" #include <oxygen/physicsserver/world.h> #include <oxygen/physicsserver/space.h> using namespace boost; using namespace oxygen; using namespace salt; using namespace zeitgeist; using namespace std; int SceneServer::mTransformMark = 0; SceneServer::SceneServer() : Node() { } SceneServer::~SceneServer() { } boost::shared_ptr<Scene> SceneServer::CreateScene(const std::string &location) { shared_ptr<CoreContext> context = GetCore()->CreateContext(); shared_ptr<Scene> scene = shared_static_cast<Scene> (context->New("oxygen/Scene", location)); if (scene.get() != 0) { ResetCache(); mActiveScene = scene; } return scene; } bool SceneServer::SetActiveScene(const std::string &location) { shared_ptr<Scene> scene = shared_dynamic_cast<Scene>(GetCore()->Get(location)); if (scene.get() != 0) { ResetCache(); mActiveScene = scene; return true; } return false; } void SceneServer::ResetCache() { mActiveScene.reset(); mActiveSpace.reset(); mActiveWorld.reset(); } void SceneServer::UpdateCache() { if (mActiveScene.get() == 0) { ResetCache(); return; } if (mActiveSpace.get() == 0) { // cache the space reference mActiveSpace = shared_dynamic_cast<Space> (mActiveScene->GetChildOfClass("Space")); } if (mActiveWorld.get() == 0) { // cache the world reference mActiveWorld = shared_dynamic_cast<World> (mActiveScene->GetChildOfClass("World")); } } void SceneServer::OnUnlink() { ResetCache(); } int SceneServer::GetTransformMark() { return mTransformMark; } /** Update the scene graph. We do not make the distinction between 'controllers' and 'scene graph nodes'. This design forces us to perform several update passes through the hierarchy. Nevertheless, the more homogenuous structure is worth it. An example Hierarchy: scene |- transform |- body | |- quakecontroller | |- camera The following passes are performed: 1st pass: PrePhysicsUpdate(deltaTime) The first update pass is responsible for updating the internal state of an object. For example, the quakecontroller has received input from the main application in terms of state changes like StrafeLeft, or Forward. As the controller is physics driven, it has to translate these commands to actual forces, which act on the body. This is done during this pass. After the first pass pyhsics simulation and collision are calculated using ODE. 2nd pass: PostPhysicsUpdate() This pass can be used to affect other nodes. For example, 'Body' has undergone physics simulation and collision detection. It has reached its final 'simulated' position, which has to be passed to the parent Transform node. 3rd pass: UpdateHierarchy() As the second pass affects the position of objects, we have to recalculate the transformation hierarchy before we can display the scene. */ void SceneServer::Update(float deltaTime) { if ( (deltaTime == 0.0f) || (mActiveScene.get() == 0) ) { return; } UpdateCache(); ++mTransformMark; mActiveScene->PrePhysicsUpdate(deltaTime); // determine collisions if (mActiveSpace.get() != 0) { mActiveSpace->Collide(); } // do physics if (mActiveWorld.get() != 0) { mActiveWorld->Step(deltaTime); } mActiveScene->PostPhysicsUpdate(); mActiveScene->UpdateHierarchy(); } bool SceneServer::ImportScene(const string& fileName, shared_ptr<BaseNode> root, shared_ptr<ParameterList> parameter) { if (! GetFile()->Exist(fileName)) { GetLog()->Error() << "(SceneServer) ERROR: cannot locate file '" << fileName << "'\n"; return false; } TLeafList importer; ListChildrenSupportingClass<SceneImporter>(importer); if (importer.size() == 0) { GetLog()->Error() << "(SceneServer) Warning: no SceneImporter registered\n"; } for ( TLeafList::iterator iter = importer.begin(); iter != importer.end(); ++iter ) { shared_ptr<SceneImporter> importer = shared_static_cast<SceneImporter>(*iter); if (importer->ImportScene(fileName,root,parameter)) { GetLog()->Normal() << "(SceneServer) imported scene file '" << fileName << " with '" << importer->GetName() << " at " << root->GetFullPath() << endl; RemoveTransformPaths(root); // mark the corresponding scene as modified shared_ptr<Scene> scene = root->GetScene(); if (scene.get() != 0) { scene->SetModified(true); } return true; } } GetLog()->Error() << "(SceneServer) ERROR: cannot import scene file '" << fileName << "'\n"; return false; } void SceneServer::ReparentTransformChildren(shared_ptr<Transform> node) { shared_ptr<BaseNode> parent = shared_dynamic_cast<BaseNode>(make_shared(node->GetParent())); // while not empty while (node->begin() != node->end()) { shared_ptr<Leaf> child = (*node->begin()); shared_ptr<Transform> tChild = shared_dynamic_cast<Transform>(child); if (tChild.get() != 0) { tChild->SetLocalTransform (node->GetLocalTransform() * tChild->GetLocalTransform()); } child->Unlink(); parent->AddChildReference(child); } } void SceneServer::RemoveTransformPaths(shared_ptr<Leaf> root) { if (root.get() == 0) { return; } // go top down and remove Transform nodes that only have Transform // node children and reparent them; note that reparented transform // nodes are automatically checked in the parent loop, as they are // appended to the child list in subsequent calls to // RemoveTransformPaths; this process leaves some transform node // without children, that are removed in a second pass for ( TLeafList::iterator iter = root->begin(); iter != root->end(); ++iter ) { RemoveTransformPaths(*iter); } shared_ptr<Transform> trans = shared_dynamic_cast<Transform>(root); bool tRoot = (trans.get() != 0); bool tChildOnly = true; TLeafList::iterator iter = root->begin(); while (iter != root->end()) { shared_ptr<Transform> tChild = shared_dynamic_cast<Transform>(*iter); if (tChild.get() == 0) { tChildOnly = false; } else { if (tChild->begin() == tChild->end()) { // remove a transform node without // children tChild->Unlink(); // restart as iter is now invalidated iter = root->begin(); continue; } } ++iter; } if ( (tRoot) && (tChildOnly)) { ReparentTransformChildren(trans); } } bool SceneServer::InitSceneImporter(const std::string& importerName) { shared_ptr<SceneImporter> importer = shared_dynamic_cast<SceneImporter>(GetCore()->New(importerName)); if (importer.get() == 0) { GetLog()->Error() << "ERROR (SceneServer::InitSceneImporter) " << "Unable to create '" << importerName << "'\n"; return false; } importer->SetName(importerName); AddChildReference(importer); GetLog()->Normal() << "(SceneServer) SceneImporter '" << importerName << "' registered\n"; return true; } --- NEW FILE: camera_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: camera_c.cpp,v 1.1 2005/12/05 21:21:17 rollmark Exp $ 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; version 2 of the License. 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 PARTICULA... [truncated message content] |
From: Markus R. <rol...@us...> - 2005-12-05 21:21:30
|
Update of /cvsroot/simspark/simspark/spark/oxygen/spadesserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv15620/spadesserver Added Files: paramreader.cpp paramreader.h paramreader_c.cpp paramstorer.cpp paramstorer.h spadesactevent.cpp spadesactevent.h spadescreatesenseevent.cpp spadescreatesenseevent.h spadesserver.cpp spadesserver.h spadesserver_c.cpp Log Message: --- NEW FILE: spadescreatesenseevent.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: spadescreatesenseevent.h,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_SPADESCREATESENSEEVENT_H #define OXYGEN_SPADESCREATESENSEEVENT_H #include <spades/CreateSenseEvent.hpp> namespace oxygen { #if 0 } #endif /** SpadesCreateSenseEvent implements the spades::CreateSenseEvent interface. It's purpose is to create a SenseEvent and to schedule it's successor SpadesCreateEvent. A note about the implementation: SpadesCreateSenseEvent uses the SpadesServer and the GameControlServer to do it's job. However it cannot be zeitgeist class, as this involves that the corresponding class object holds a shared pointer to every instance of this class. However spades is not aware of these shared pointers and destructs a registered ParamStorer instance using delete without notifying the shared pointers. This would result in dangling references. */ class SpadesCreateSenseEvent : public spades::CreateSenseEvent { public: SpadesCreateSenseEvent (spades::SimTime t, spades::AgentID a) : CreateSenseEvent (t, a) {} virtual ~SpadesCreateSenseEvent () {} virtual void Print (std::ostream & o) const; virtual bool realizeEventWorldModel(spades::WorldModel* pWM); virtual spades::SenseEvent* createSense(spades::WorldModel* p); }; } // namespace oxygen #endif // OXYGEN_SPADESCREATESENSEEVENT_H --- NEW FILE: spadescreatesenseevent.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: spadescreatesenseevent.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "spadescreatesenseevent.h" #include "spadesserver.h" #include <spades/SenseEvent.hpp> #include <zeitgeist/logserver/logserver.h> #include <oxygen/agentaspect/agentaspect.h> #include <oxygen/gamecontrolserver/gamecontrolserver.h> #include <oxygen/gamecontrolserver/baseparser.h> using namespace oxygen; using namespace spades; using namespace std; using namespace boost; void SpadesCreateSenseEvent::Print (std::ostream & o) const { o << "SpadesCreateSenseEvent(" << getTime () << ") for " << getAgent(); } bool SpadesCreateSenseEvent::realizeEventWorldModel(spades::WorldModel* pWM) { // we can't create a shared_ptr to the SpadesServer here, as this // shared_ptr wouldn't know of other shared_ptrs to the // SpadesServer SpadesServer* spadesServer = dynamic_cast<SpadesServer*>(pWM); if (spadesServer == 0) { // we can't use the LogServer here :( return false; } shared_ptr<GameControlServer> gcs(spadesServer->GetGameControlServer()); if (gcs.get() == 0) { spadesServer->GetLog()->Error() << "(SpadesCreateSenseEvent) GameControlServer not found.\n"; return false; } // query the game control server for the time until the next // SpadesCreateSenseInterval should be realized. The gameControlServer // returns this time in seconds float deltaSense = gcs->GetSenseInterval(static_cast<int>(getAgent())); // calculate the corresponding amount of time steps int senseInterval = static_cast<int>(deltaSense / spadesServer->GetTimePerStep()); // schedule the next CreateSenseEvent SimEngine* simEngine = spadesServer->GetSimEngine(); if (simEngine == 0) { spadesServer->GetLog()->Error() << "(SpadesCreateSenseEvent) spades SimEngine not found.\n"; return false; } SpadesCreateSenseEvent* event = new SpadesCreateSenseEvent (getTime() + senseInterval, getAgent()); simEngine->enqueueEvent(event); return true; } spades::SenseEvent* SpadesCreateSenseEvent::createSense(spades::WorldModel* p) { SpadesServer* spadesServer = dynamic_cast<SpadesServer*>(p); if (spadesServer == 0) { return 0; } shared_ptr<GameControlServer> gcs(spadesServer->GetGameControlServer()); if (gcs.get() == 0) { spadesServer->GetLog()->Error() << "(SpadesCreateSenseEvent) GameControlServer not found.\n"; return 0; } shared_ptr<BaseParser> parser = gcs->GetParser(); if (parser.get() == 0) { spadesServer->GetLog()->Error() << "ERROR: (SpadesCreateSenseEvent) got no parser from " << " the GameControlServer" << endl; return 0; } // lookup the AgentAspect int id = getAgent(); shared_ptr<AgentAspect> agent = gcs->GetAgentAspect(id); if (agent.get() == 0) { spadesServer->GetLog()->Error() << "ERROR: (SpadesCreateSenseEvent) got no AgentAspect for id " << id << " from the GameControlServer" << endl; return 0; } // get a list of senses from the agent and generate a string // describing them shared_ptr<PredicateList> senseList = agent->QueryPerceptors(); std::string senses = parser->Generate(senseList); // create the sense event float senseDelay = gcs->GetSenseLatency(getAgent()); SimTime senseArriveTime = getTime() + static_cast<int>(senseDelay / spadesServer->GetTimePerStep()); // // what's the correct value for ttype here ? // (see spades/shared/sharedtypes.hpp) // ThinkingType ttype = TT_Regular; SenseEvent* event = new SenseEvent (ttype, getTime(), senseArriveTime, getAgent()); event->setData(senses); return event; } --- NEW FILE: paramreader_c.cpp --- /* -*- mode: c++ -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: paramreader_c.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "paramreader.h" using namespace oxygen; void CLASS(ParamReader)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Node); } --- NEW FILE: paramstorer.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: paramstorer.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "paramstorer.h" using namespace oxygen; int ParamStorer::readCmdLineArgs(const std::string& key, int argc, const char* const* argv) { if (mParamReader != NULL) { return mParamReader->readCmdLineArgs(key,argc,argv); } return 0; } --- NEW FILE: paramstorer.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: paramstorer.h,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_PARAMSTORER_H__ #define OXYGEN_PARAMSTORER_H__ #include "paramreader.h" #include <spades/ParamReader.hpp> namespace oxygen { /** This class implements the spades::ParamReader::ParamStorer interface. It's purpose is to enable the user to set ruby variables using the command line. A note about the implementation: ParamStorer uses the ParamReader class to do the real parsing. This has the following reason. In order to access the ScriptServer to modify ruby variables the ParamStorer must be a ZeitGeist class. This involves that the corresponding class object holds a shared pointer to every instance of this class. However spades is not aware of these shared pointers and destructs a registered ParamStorer instance using delete without notifying the shared pointers. This would result in dangling references. In order to play well with spades this class is not derived from Zeitgeist::object. In order to access the ScriptServer this class uses the ParamReader instance. */ class ParamStorer : public spades::ParamReader::ParamStorer { public: ParamStorer(oxygen::ParamReader* paramReader) : spades::ParamReader::ParamStorer(), mParamReader(paramReader) {} virtual int readArgsFrom(const std::string& /*key*/, const char* /*fileid*/, const char* /*path*/, std::istream& /*is*/, bool /*have_argument*/) { // we read nothing from any files return RR_None; } virtual void print(std::ostream& /*o*/) const { // no output } // returns the number of args processed // otherwise see the RR_ values above virtual int readCmdLineArgs(const std::string& key, int argc, const char* const* argv); protected: /** The ParamReader we use to do the parsing */ oxygen::ParamReader* mParamReader; }; } // namespace oxygen #endif // OXYGEN_PARAMSTORER_H__ --- NEW FILE: spadesactevent.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: spadesactevent.h,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_SPADESACTEVENT_H #define OXYGEN_SPADESACTEVENT_H #include <spades/ActEvent.hpp> #include <oxygen/gamecontrolserver/actionobject.h> namespace oxygen { #if 0 } #endif class SpadesActEvent : public spades::ActEvent { public: SpadesActEvent ( spades::SimTime t, spades::AgentID a, boost::shared_ptr<ActionObject::TList> actionList ) : spades::ActEvent(t, a), mActionList(actionList) {}; virtual ~SpadesActEvent (){} virtual void Print (std::ostream & o) const; /** realizes the stored list of ActionObjects. As a sanity check it returns whether the world model did anything with this event. In our case always true. */ virtual bool realizeEventWorldModel(spades::WorldModel* pWM); protected: boost::shared_ptr<ActionObject::TList> mActionList; }; } // namespace oxygen #endif // OXYGEN_SPADESACTEVENT_H --- NEW FILE: paramreader.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: paramreader.h,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_PARAMETERREADER_H #define OXYGEN_PARAMETERREADER_H #include <zeitgeist/class.h> #include <zeitgeist/leaf.h> #include <spades/EngineParam.hpp> namespace oxygen { /*! */ class ParamReader : public zeitgeist::Leaf, public spades::EngineParam { public: ParamReader(); /** returns the number of args processed otherwise see the spades RR_values. This method is called from within the ParamStorer. */ int readCmdLineArgs(const std::string& key, int argc, const char* const* argv); }; DECLARE_CLASS(ParamReader); } // namespace oxygen #endif // OXYGEN_PARAMETERREADER_H --- NEW FILE: spadesserver_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: spadesserver_c.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "spadesserver.h" using namespace oxygen; using namespace std; FUNCTION(SpadesServer,queueAgents) { string inAgentType; int inNum; if ( (in.GetSize() != 2) || (! in.GetValue(in[0],inAgentType)) || (! in.GetValue(in[1],inNum)) ) { return false; } obj->QueueAgents(inAgentType,inNum); return true; } void CLASS(SpadesServer)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Node); DEFINE_FUNCTION(queueAgents); } --- NEW FILE: paramreader.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: paramreader.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "paramreader.h" #include "paramstorer.h" #include <zeitgeist/logserver/logserver.h> #include <zeitgeist/scriptserver/scriptserver.h> #include <sstream> using namespace zeitgeist; using namespace oxygen; using namespace boost; using namespace std; ParamReader::ParamReader() : zeitgeist::Leaf(), spades::EngineParam() { addParamStorer(new oxygen::ParamStorer(this)); } int ParamReader::readCmdLineArgs(const std::string& key, int argc, const char* const* argv) { // lookup the ScriptServer if (argc < 2) { return spades::ParamReader::ParamStorer::RR_None; } // check if varName is valid if (! GetScript()->ExistsVariable(key)) { GetLog()->Warning() << "WARNING: (ParamReader) Unknown variable '" << key << "'\n"; return spades::ParamReader::ParamStorer::RR_FormatErr; } // take next as the value std::string value = * (argv + 1); // eval "<key> = <value>" using ruby stringstream ss; ss << key << "=" << value; if (GetScript()->Eval(ss.str())) { GetLog()->Normal() << "(ParamReader) set '" << key << "' to " << value << "\n"; } return 1; } --- NEW FILE: spadesactevent.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: spadesactevent.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "spadesactevent.h" #include "spadesserver.h" #include <zeitgeist/logserver/logserver.h> #include <oxygen/gamecontrolserver/gamecontrolserver.h> #include <oxygen/agentaspect/agentaspect.h> using namespace oxygen; using namespace zeitgeist; using namespace boost; using namespace std; void SpadesActEvent::Print (std::ostream & /*o*/) const { } bool SpadesActEvent::realizeEventWorldModel(spades::WorldModel* pWM) { // we can't create a shared_ptr to the SpadesServer here, as this // shared_ptr wouldn't know of other shared_ptrs to the // SpadesServer SpadesServer* spadesServer = dynamic_cast<SpadesServer*>(pWM); if (spadesServer == NULL) { // we can't use the LogServer here :( return false; } shared_ptr<GameControlServer> gcs = spadesServer->GetGameControlServer(); if (gcs.get() == 0) { spadesServer->GetLog()->Error() << "(SpadesActEvent) GameControlServer not found." << endl; return false; } // lookup the AgentAspect int id = getAgent(); shared_ptr<AgentAspect> agent = gcs->GetAgentAspect(id); if (agent.get() == 0) { spadesServer->GetLog()->Warning() << "ERROR: (SpadesActEvent) no AgentAspect for id " << id << "found." << endl; return false; } // realize the stored actions agent->RealizeActions(mActionList); // indicate that we 'did something' with the event return true; } --- NEW FILE: spadesserver.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: spadesserver.h,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_SPADESSERVER_H #define OXYGEN_SPADESSERVER_H #include <spades/enginemain.hpp> #include <spades/SimEngine.hpp> #include <zeitgeist/class.h> #include <zeitgeist/node.h> #include "paramreader.h" #include <queue> namespace oxygen { class GameControlServer; class MonitorServer; class SceneServer; /*! The SpadesServer serves as an interface between the SceneServer and the agents */ class SpadesServer : public zeitgeist::Node, public spades::WorldModel { public: SpadesServer(); ~SpadesServer(); // Methods starting with small letters are SPADES interface methods. // Methods with a initial capital letter are additional methods needed // for the zeitgeist framework. /** setup script variables used to customize the SpadesServer */ virtual bool ConstructInternal(); /** set up GameControlServer and MonitorServer reference */ virtual void OnLink(); /** reset GameControlServer and MonitorServer reference */ virtual void OnUnlink(); /** helper function to locate the game control server */ boost::shared_ptr<GameControlServer> GetGameControlServer() const; /** returns the amount of time in seconds a single simulation step corresponds to. */ float GetTimePerStep() const; /** Get the value of the Spades.RunIntegratedCommserver variable. * \return true if the variable is set to true, false otherwise. */ bool GetRunIntegratedCommserver() const; /** Get the value of the Spades.CommServersWanted variable. On startup SpadesServer will wait until at least 'CommServersWanted' CommServers have connected before it initially unpauses the simulation. */ int GetCommServersWanted() const; /** Get the value of the Spades.MonitorInterval variable. * \return the number of simulation steps per monitor message. */ int GetMonitorInterval() const; /** Get the value of the Spades.SendAgentThinkTimes variable. */ bool GetSendAgentThinkTimes() const; /** queue up agents to be started. \param agentType agent type to be found in the SPADES agent database. \param num number of agents to be started of the given type. */ void QueueAgents(const std::string& agentType="default", int num=1); /** set simulation mode to normal */ void Unpause(); /** update cached variables */ virtual void UpdateCached(); // ---------------------------------------------------------------------- // SPADES interface methods start here /** You probably want to inherit some parameters from EngineParam and use that to parse the commandline. See the ParamReader class. */ spades::EngineParam* parseParameters(int argc, const char* const *argv); /** Most of the real initialization/finalization work should be * done here. We do this so that the SimEngine can initialize * after this class is created. * * @param pSE a pointer to the spades simulation engine * @return true */ bool initialize(spades::SimEngine* pSE); /** returns a pointer to the spades simulation engine */ spades::SimEngine* GetSimEngine(); /** @return true */ bool finalize(); /** This function should advance the world forward. Events can be * enqueed from this function. The time does *not* have to * advance all the way to the time_desired, and if you put events * in the queue, you should not advance past the time of those * events. The simulation time here is an integer type, so the * SpadesServer has to know how big a simulation step is. * * @param time_curr the current simulation step * @param time_desired the desired simulation step * @return a new simulation time t (time_curr <= t <= time_desired) */ spades::SimTime simToTime(spades::SimTime time_curr, spades::SimTime time_desired); /** Monitors are programs that can open up a connection to the * engine and get periodic updates about the state of the * world. These next three functions support this. */ /** This function is called once for every monitor. It should * return any header/setup information that is needed. */ spades::DataArray getMonitorHeaderInfo(); /** This function will be called periodically to get information * about the current state of the world. The format is completely * determined by what the monitors will expect; no processing is * done by the simulation engine */ spades::DataArray getMonitorInfo(spades::SimTime time); /** If a monitor sends information to the world model, this * function is called to process it. Note that only the data * section of the message (not the ID part which indicates that it * is a message for the world model and not the simulation engine) * is included here. If you need to keep the data, you must copy * it */ void parseMonitorMessage(const char* data, unsigned datalen); /** There is a latency (in simulation time) between when an action * is sent by the agent and when it takes effect. This function * needs to return the minimum of all possible values of that * latency. This is used to reason about causality */ spades::SimTime getMinActionLatency() const; /** Similar to getMinActionLatency, but the latency between when * the sensation is generated from the world and when it is * received by the agent */ spades::SimTime getMinSenseLatency() const; /** This function parses the action string received from the * agents Note that this method is const! parsing the act can * *not* affect the world at all, since this could then violate * causality. Also, at some point this functionality may be * moved to the communication server (which manages communication * with the agents) */ spades::ActEvent* parseAct(spades::SimTime t, spades::AgentID a, const char* data, unsigned datalen) const; /** When the simulation is paused, this is called peridically At * some point, this function should unpause the simulation The * simulation starts out in paused mode */ void pauseModeCallback(); /** The world model initiates startup requests for agents. This * function is called once the agent has been started * successfully */ bool agentConnect(spades::AgentID agent, spades::AgentTypeDB::AgentTypeConstIterator at); /** Any time an agent leaves the simulation (whether by crash, * graceful exit request, etc.), this function is called so that * the world model can update it's data structures */ bool agentDisappear(spades::AgentID agent, spades::AgentLostReason reason); /** Called every time a comm server connects. Usually, this can be * ignored as the WorldModel does not need to know when and how * many commservers connect, unless it wants to do it's own load * balancing */ void notifyCommserverConnect(spades::ServerID s); /** Called every time a comm server dsiconnects. Usually, this can * be ignored as the WorldModel does not need to know when and * how many commservers connect, unless it wants to do it's own * load balancing */ void notifyCommserverDisconnect(spades::ServerID s); protected: struct AgentItem { AgentItem(const std::string& agentType = "", int num = 0) : mAgentType(agentType), mNumber(num) {} std::string mAgentType; int mNumber; }; typedef std::list<AgentItem> TAgentQueue; /** Start up a number of agents of a given type. \param ai contains the agent type from the agent database and the number of agents to start. */ void StartAgents(const AgentItem& ai); private: /** the Spades simulation engine */ spades::SimEngine* mSimEngine; /** our commandline parser */ boost::shared_ptr<ParamReader> mParamReader; /** flag if there is a simulation mode change scheduled */ bool mSimulationModeChanged; /** the next simulation mode for a mode change */ spades::SimulationMode mNewSimulationMode; /** a queue of agents to be started up */ TAgentQueue mAgentQueue; /** the simTime offset in the scheduled times for the agents CreateSenseEvent */ float mOffsetCreateSense; /** the initial CreateSenseEvent simTime scheduled for the next connecing agent */ float mNextInitialCreateSense; /** a cached reference to the monitor server */ boost::shared_ptr<MonitorServer> mMonitorServer; /** a cached reference to the GameControlServer */ boost::shared_ptr<GameControlServer> mGameControlServer; /** a cached reference to the SceneServer */ boost::shared_ptr<SceneServer> mSceneServer; /** the cached Spades.TimePerStep value */ float mTimePerStep; }; DECLARE_CLASS(SpadesServer); } // namespace oxygen #endif // OXYGEN_SPADESSERVER_H --- NEW FILE: spadesserver.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: spadesserver.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "spadesserver.h" using namespace boost; using namespace zeitgeist; using namespace oxygen; using namespace spades; using namespace std; #include <zeitgeist/corecontext.h> #include <zeitgeist/logserver/logserver.h> #include <zeitgeist/scriptserver/scriptserver.h> #include <oxygen/sceneserver/sceneserver.h> #include <oxygen/gamecontrolserver/gamecontrolserver.h> #include <oxygen/monitorserver/monitorserver.h> #include <oxygen/gamecontrolserver/actionobject.h> #include <spades/SimEngine.hpp> #include <spades/EndSimulationEvent.hpp> #include "spadescreatesenseevent.h" #include "spadesactevent.h" SpadesServer::SpadesServer() : zeitgeist::Node(), spades::WorldModel(), mSimEngine(0), mSimulationModeChanged(false), mOffsetCreateSense(0),mNextInitialCreateSense(0) { } SpadesServer::~SpadesServer() { } bool SpadesServer::ConstructInternal() { // setup script variables used to customize the SpadesServer GetScript()->CreateVariable("Spades.TimePerStep", 0.01f); GetScript()->CreateVariable("Spades.MonitorInterval", 4); GetScript()->CreateVariable("Spades.RunIntegratedCommserver", false); GetScript()->CreateVariable("Spades.CommServersWanted", 1); GetScript()->CreateVariable("Spades.SendAgentThinkTimes", false); return true; } void SpadesServer::OnLink() { mMonitorServer = shared_dynamic_cast<MonitorServer> (GetCore()->Get("/sys/server/monitor")); if (mMonitorServer.get() == 0) { GetLog()->Error() << "ERROR: (SpadesServer) MonitorServer not found.\n"; } mGameControlServer = shared_dynamic_cast<GameControlServer> (GetCore()->Get("/sys/server/gamecontrol")); if (mGameControlServer.get() == 0) { GetLog()->Error() << "ERROR: (SpadesServer) GameControlServer not found.\n"; } mSceneServer = shared_dynamic_cast<SceneServer> (GetCore()->Get("/sys/server/scene")); if (mSceneServer.get() == 0) { GetLog()->Error() << "ERROR: (SpadesServer) SceneServer not found.\n"; } // cache frequently queried ruby values here mTimePerStep = 0.01f; } void SpadesServer::OnUnlink() { mMonitorServer.reset(); mGameControlServer.reset(); mSceneServer.reset(); } spades::SimEngine* SpadesServer::GetSimEngine() { return mSimEngine; } float SpadesServer::GetTimePerStep() const { return mTimePerStep; } int SpadesServer::GetCommServersWanted() const { int commServersWanted = 1; GetScript()->GetVariable("Spades.CommServersWanted",commServersWanted); return std::max<int>(1,commServersWanted); } bool SpadesServer::GetRunIntegratedCommserver() const { bool run_integrated_commserver = false; GetScript()->GetVariable("Spades.RunIntegratedCommserver", run_integrated_commserver); return run_integrated_commserver; } int SpadesServer::GetMonitorInterval() const { int monitor_interval = 10; GetScript()->GetVariable("Spades.MonitorInterval", monitor_interval); return monitor_interval; } bool SpadesServer::GetSendAgentThinkTimes() const { bool send_agent_think_times = false; GetScript()->GetVariable("Spades.SendAgentThinkTimes", send_agent_think_times); return send_agent_think_times; } boost::shared_ptr<GameControlServer> SpadesServer::GetGameControlServer() const { return mGameControlServer; } void SpadesServer::StartAgents(const AgentItem& ai) { GetLog()->Debug() << "SpadesServer::StartAgents(" << ai.mAgentType << ", " << ai.mNumber << ")\n"; if (!mSimEngine || mSimEngine->getNumCommServers () < 1) { GetLog()->Error() << "(SpadesServer) No simulation engine or comm server, " << "cannot start agents\n" << endl; return; } AgentTypeDB::AgentTypeConstIterator at = mSimEngine->getAgentTypeDB()->getAgentType(ai.mAgentType); if (at == mSimEngine->getAgentTypeDB()->nullIterator()) { GetLog()->Error() << "ERROR: (SpadesServer) could not find agent type " << ai.mAgentType << endl; return; } int num = std::max(ai.mNumber, 0); while (num > 0) { if (mSimEngine->startNewAgent(at) == AGENTID_INVALID) { num = 0; GetLog()->Error() << "ERROR: (SpadesServer) starting agent of type " << ai.mAgentType << " failed" << endl; } --num; } } void SpadesServer::Unpause() { mNewSimulationMode = SM_RunNormal; mSimulationModeChanged = true; } void SpadesServer::QueueAgents(const std::string& agentType, int num) { mAgentQueue.push_back(AgentItem(agentType, num)); } // ---------------------------------------------------------------------- // SPADES interface methods EngineParam* SpadesServer::parseParameters(int argc, const char *const *argv) { mParamReader = shared_static_cast<ParamReader>(GetCore()->New("oxygen/ParamReader")); // SimulationEngineMain uses the ParamReader we have to get the // command line options. It doesn't delete the ParamReader, so we // can return a simple pointer mParamReader->getOptions(argc, argv); // start an inprocess commserver mParamReader->setParam("run_integrated_commserver", GetRunIntegratedCommserver()); // send updates to the monitor every nth cycle mParamReader->setParam("monitor_interval", GetMonitorInterval()); // don't send think time messages to connected agents mParamReader->setParam("send_agent_think_times", GetSendAgentThinkTimes()); return mParamReader.get(); } bool SpadesServer::initialize(SimEngine* pSE) { mSimEngine = pSE; return true; } bool SpadesServer::finalize() { return true; } SimTime SpadesServer::simToTime(SimTime time_curr, SimTime time_desired) { int steps = time_desired - time_curr; if (steps <= 0) { GetLog()->Warning() << "WARNING: (SpadesServer) will not simulate <= 0 steps\n"; return time_curr; } if ( (mSceneServer.get() == 0) || (mGameControlServer.get() == 0) ) { GetLog()->Warning() << "WARNING: (SpadesServer) SceneServer " << "and/or GameControlServer missing.\n"; return time_curr; } int i = steps; while (i > 0) { mSceneServer->Update(mTimePerStep); mGameControlServer->Update(mTimePerStep); --i; } static bool once = true; if (mGameControlServer->IsFinished() && once) { once = false; // initiate shutdown here (what time should we use?) mSimEngine->enqueueEvent(new EndSimulationEvent(time_desired+1)); } // GetLog()->Debug() << "(SpadesServer) time_curr=" << time_curr // << " time_desired=" << time_desired << endl; // GetLog()->Debug() << "updated the scene by " << steps - i << " * " // << timePerStep << " seconds.\n"; // return the simulation time when the loop stopped // (the '- i' makes sense if we exit the while loop earlier) return time_desired - i; } DataArray SpadesServer::getMonitorHeaderInfo() { if (mMonitorServer.get() == 0) { return DataArray(); } return DataArray(mMonitorServer->GetMonitorHeaderInfo()); } DataArray SpadesServer::getMonitorInfo(SimTime /*time*/) { if (mMonitorServer.get() == 0) { return DataArray(); } return DataArray(mMonitorServer->GetMonitorInfo()); } void SpadesServer::parseMonitorMessage(const char* data, unsigned datalen) { if (mMonitorServer.get() == 0) { return; } return mMonitorServer->ParseMonitorMessage(string(data,datalen)); } SimTime SpadesServer::getMinActionLatency() const { return 1; } SimTime SpadesServer::getMinSenseLatency() const { return 1; } ActEvent* SpadesServer::parseAct(SimTime act_received_time, AgentID a, const char* data, unsigned datalen) const { if (mGameControlServer.get() == 0) { return 0; } shared_ptr<ActionObject::TList> actionList = mGameControlServer->Parse(a,std::string(data,datalen)); if (actionList.get() == 0) { return 0; } float latency = mGameControlServer->GetActionLatency(a); // pfr 5/24/2004 // the time act_received_time is the time that the commserver reports as the actions being // sent. Notably, this includes the thinking latency. // This is NOT the same as mSimEngine->getSimulationTime() (which is what was here before) // since SPADES does out of order event reception and processing reasoning SimTime arrival = act_received_time + static_cast<int>(latency / GetTimePerStep()); return new SpadesActEvent(arrival, a, actionList); } void SpadesServer::pauseModeCallback() { // the first time pauseModeCallback will be called is immediatly // after startup when SPADES is in SM_PausedInitial mode if (mSimEngine->getSimulationMode() == SM_PausedInitial) { int numConnected = mSimEngine->getNumCommServers(); GetLog()->Normal() << "(SpadesServer) waiting for a total of " << GetCommServersWanted() << " CommServers, " << numConnected << " already connected\n"; if (numConnected >= GetCommServersWanted()) { Unpause(); } else { return; } } if ( (mGameControlServer.get() != 0) && (! mAgentQueue.empty()) ) { int agentCount = 0; for ( TAgentQueue::iterator iter = mAgentQueue.begin(); iter != mAgentQueue.end(); ++iter ) { agentCount += (*iter).mNumber; } // todo: query the gcs, prob: currently deltaSense returned // for an agentId which is unknown at this point float deltaSense = 0.20; float offsetSec = deltaSense / agentCount; mOffsetCreateSense = (offsetSec / GetTimePerStep()); mNextInitialCreateSense = mSimEngine->getSimulationTime() + 1; GetLog()->Debug() << "(SpadesServer) Starting " << agentCount << " agents (delta sense: " << deltaSense<< ")\n" << "with an CreateSenseEvent offset of " << mOffsetCreateSense << " (" << offsetSec << " seconds)\n" << "starting at simTime " << mNextInitialCreateSense << "\n"; while (! mAgentQueue.empty()) { StartAgents(mAgentQueue.front()); mAgentQueue.pop_front(); } } if (mSimulationModeChanged) { mSimEngine->changeSimulationMode(mNewSimulationMode); mSimulationModeChanged = false; } } bool SpadesServer::agentConnect(AgentID agent, AgentTypeDB::AgentTypeConstIterator /*at*/) { // try to register the agent to the game control server shared_ptr<GameControlServer> gcs = GetGameControlServer(); if ( (mGameControlServer.get() == 0) || (! mGameControlServer->AgentConnect(static_cast<int>(agent))) ) { GetLog()->Normal() << "(SpadesServer) ERROR: cannot register agent " << "to the GameControlServer\n"; return false; } // schedule the first SpadesCreateSenseEvent SimTime time = static_cast<SimTime>(mNextInitialCreateSense); SpadesCreateSenseEvent* event = new SpadesCreateSenseEvent (time,agent); SimTime now = mSimEngine->getSimulationTime(); GetLog()->Normal() << "(SpadesServer) agentConnect (id " << agent << ") at simlation time " << now << ".\n" << "Initial CreateSenseEvent scheduled at " << time << "\n"; mNextInitialCreateSense += mOffsetCreateSense; mSimEngine->enqueueEvent(event); return true; } bool SpadesServer::agentDisappear(AgentID agent, AgentLostReason /*reason*/) { if (mGameControlServer.get() == 0) { return false; } return mGameControlServer->AgentDisappear(static_cast<int>(agent)); } void SpadesServer::notifyCommserverConnect(ServerID /*s*/) { } void SpadesServer::notifyCommserverDisconnect(ServerID /*s*/) { } void SpadesServer::UpdateCached() { GetScript()->GetVariable("Spades.TimePerStep", mTimePerStep); } |
Update of /cvsroot/simspark/simspark/spark/oxygen/simulationserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv15620/simulationserver Added Files: agentcontrol.cpp agentcontrol.h agentcontrol_c.cpp monitorcontrol.cpp monitorcontrol.h monitorcontrol_c.cpp netbuffer.cpp netbuffer.h netclient.cpp netclient.h netclient_c.cpp netcontrol.cpp netcontrol.h netcontrol_c.cpp netmessage.cpp netmessage.h netmessage_c.cpp simcontrolnode.cpp simcontrolnode.h simcontrolnode_c.cpp simulationserver.cpp simulationserver.h simulationserver_c.cpp Log Message: --- NEW FILE: simcontrolnode.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: simcontrolnode.h,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_SIMCONTROLNODE_H #define OXYGEN_SIMCONTROLNODE_H #include <zeitgeist/node.h> namespace oxygen { class SimulationServer; /** \class SimControlNode defines an interface for classes that are registered to the SimulationServer. The interface defines callbacks for the initial startup of the simulation, it's final shutdown and for different phases of each simulation cycle. SimControlNodes are used extend and customize the simulation runloop and to delegate tasks, like network management, reading of mouse and keyboard input, writing a simulation log, rendering etc. */ class SimControlNode : public zeitgeist::Node { public: SimControlNode(); virtual ~SimControlNode(); /** called once when the simulation is started */ virtual void InitSimulation() {}; /** called once before the simulation is shut down */ virtual void DoneSimulation() {}; /** called when a new simulation cycle starts, before the simulation is stepped */ virtual void StartCycle() {}; /** called each simulation cycle to send agent sensor information */ virtual void SenseAgent() {}; /** called each simulation cycle to carry out agent actions */ virtual void ActAgent() {}; /** called when the current simulation cycle ends */ virtual void EndCycle() {}; protected: /** returns a reference to the SimulationServer */ boost::shared_ptr<SimulationServer> GetSimulationServer(); }; DECLARE_CLASS(SimControlNode); } // namespace oxygen #endif // OXYGEN_SIMCONTROLNODE_H --- NEW FILE: monitorcontrol.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: monitorcontrol.h,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_MONITORCONTROL_H #define OXYGEN_MONITORCONTROL_H #include "netcontrol.h" namespace oxygen { class MonitorServer; /** \class MonitorConrol is a NetControl node that manages the communication with monitors in cooperation with the MonitorServer. */ class MonitorControl : public NetControl { public: MonitorControl(); virtual ~MonitorControl(); /** forwards all pending messages from all connected monitors to the MonitorServer */ virtual void StartCycle(); /** updates all connected monitors at the end of each simulation cycle */ virtual void EndCycle(); /** called when a new client connects */ virtual void ClientConnect(boost::shared_ptr<Client> client); /** returns the monitor update interval in cycles */ int GetMonitorInterval(); /** sets the monitor update interval in cycles */ void SetMonitorInterval(int i); protected: virtual void OnLink(); virtual void OnUnlink(); protected: /** cached reference to the MonitorServer */ boost::shared_ptr<MonitorServer> mMonitorServer; /** the update interval for the connected monitors in cycles */ int mMonitorInterval; }; DECLARE_CLASS(MonitorControl); } // namespace oxygen #endif // OXYGEN_MONITORCONTROL_H --- NEW FILE: agentcontrol.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: agentcontrol.h,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_AGENTCONTROL_H #define OXYGEN_AGENTCONTROL_H #include "netcontrol.h" namespace oxygen { class GameControlServer; /** \class AgentControl is a NetControl node that manages the communication with agents in cooperation with the GameControlServer. */ class AgentControl : public NetControl { public: AgentControl(); virtual ~AgentControl(); /** called when a new client connects */ virtual void ClientConnect(boost::shared_ptr<Client> client); /** called when a client disconnects */ virtual void ClientDisconnect(boost::shared_ptr<Client> client); /** forwards all pending messages from all connected agents to the GameControlServer */ virtual void StartCycle(); /** generates and sends sense updates to all connected agents */ virtual void EndCycle(); protected: virtual void OnLink(); virtual void OnUnlink(); protected: /** cached reference to the GameControlServer */ boost::shared_ptr<GameControlServer> mGameControlServer; }; DECLARE_CLASS(AgentControl); } // namespace oxygen #endif // OXYGEN_AGENTCONTROL_H --- NEW FILE: netmessage_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: netmessage_c.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "netmessage.h" using namespace oxygen; using namespace std; void CLASS(NetMessage)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Leaf); } --- NEW FILE: monitorcontrol.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: monitorcontrol.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "monitorcontrol.h" #include "simulationserver.h" #include "netmessage.h" #include <zeitgeist/logserver/logserver.h> #include <oxygen/monitorserver/monitorserver.h> #include <oxygen/sceneserver/sceneserver.h> #include <oxygen/sceneserver/scene.h> using namespace oxygen; using namespace zeitgeist; using namespace boost; using namespace std; MonitorControl::MonitorControl() : NetControl() { mLocalAddr.setPort(3200); mMonitorInterval = 30; } MonitorControl::~MonitorControl() { } void MonitorControl::OnLink() { NetControl::OnLink(); shared_ptr<SimulationServer> sim = GetSimulationServer(); if (sim.get() == 0) { GetLog()->Error() << "(MonitorControl) ERROR: SimulationServer not found\n"; return; } mMonitorServer = sim->GetMonitorServer(); } void MonitorControl::OnUnlink() { NetControl::OnUnlink(); mMonitorServer.reset(); } void MonitorControl::ClientConnect(shared_ptr<Client> client) { if ( (mMonitorServer.get() == 0) || (mNetMessage.get() == 0) ) { return; } string header = mMonitorServer->GetMonitorHeaderInfo(); mNetMessage->PrepareToSend(header); SendMessage(client->addr,header); } void MonitorControl::EndCycle() { NetControl::EndCycle(); const int cycle = GetSimulationServer()->GetCycle(); if (cycle % mMonitorInterval) { return; } if ( (mMonitorServer.get() == 0) || (mNetMessage.get() == 0) || (mClients.size() == 0) ) { return; } // send updates to all connected monitors string info = mMonitorServer->GetMonitorInfo(); mNetMessage->PrepareToSend(info); for ( TAddrMap::iterator iter = mClients.begin(); iter != mClients.end(); ++iter ) { SendMessage((*iter).second,info); } // reset the modified flag for the active scene shared_ptr<SceneServer> sceneServer = GetSimulationServer()->GetSceneServer(); if (sceneServer.get() !=0) { shared_ptr<Scene> scene = sceneServer->GetActiveScene(); if (scene.get() != 0) { scene->SetModified(false); } } } void MonitorControl::StartCycle() { NetControl::StartCycle(); if ( (mMonitorServer.get() == 0) || (mNetMessage.get() == 0) ) { return; } // pass all received messages to the MonitorServer for ( TBufferMap::iterator iter = mBuffers.begin(); iter != mBuffers.end(); ++iter ) { shared_ptr<NetBuffer>& netBuff = (*iter).second; if ( (netBuff.get() == 0) || (netBuff->IsEmpty()) ) { continue; } string message; while (mNetMessage->Extract(netBuff,message)) { mMonitorServer->ParseMonitorMessage(message); } } } int MonitorControl::GetMonitorInterval() { return mMonitorInterval; } void MonitorControl::SetMonitorInterval(int i) { mMonitorInterval = i; } --- NEW FILE: netmessage.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: netmessage.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "netmessage.h" #include "netbuffer.h" #include <netinet/in.h> using namespace oxygen; using namespace zeitgeist; using namespace std; using namespace boost; NetMessage::NetMessage() : Leaf() { } NetMessage::~NetMessage() { } void NetMessage::PrepareToSend(std::string& msg) { // prefix the message with it's payload length unsigned int len = htonl(msg.size()); string prefix((const char*)&len,sizeof(unsigned int)); msg = prefix + msg; } bool NetMessage::Extract(shared_ptr<NetBuffer> buffer, std::string& msg) { // a message is prefixed with it's payload length const unsigned int preSz = sizeof(unsigned int); string& data = buffer->GetData(); if (data.size() < preSz) { return false; } unsigned int msgLen = ntohl((*(unsigned int*)data.data())); if (data.size() < (msgLen + preSz)) { // incomplete message return false; } // copy to msg and cut from buffer msg = string(data.c_str() + preSz, msgLen); data.erase(0, preSz + msgLen); // zero terminate received data msg += '\0'; return true; } --- NEW FILE: simcontrolnode.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: simcontrolnode.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "simcontrolnode.h" #include "simulationserver.h" using namespace oxygen; using namespace zeitgeist; using namespace salt; using namespace std; using namespace boost; SimControlNode::SimControlNode() : Node() { } SimControlNode::~SimControlNode() { } shared_ptr<SimulationServer> SimControlNode::GetSimulationServer() { return shared_static_cast<SimulationServer> (make_shared(GetParent())); } --- NEW FILE: netbuffer.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: netbuffer.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "netbuffer.h" using namespace oxygen; using namespace rcss::net; using namespace std; void NetBuffer::AddFragment(const std::string& d) { mData += d; } const Addr& NetBuffer::GetAddr() const { return mAddr; } string& NetBuffer::GetData() { return mData; } bool NetBuffer::IsEmpty() const { return mData.empty(); } --- NEW FILE: simulationserver_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: simulationserver_c.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "simulationserver.h" using namespace oxygen; using namespace std; FUNCTION(SimulationServer,quit) { obj->Quit(); return true; } FUNCTION(SimulationServer,initControlNode) { string inClassName; string inName; if ( (in.GetSize() != 2) || (! in.GetValue(in[0],inClassName)) || (! in.GetValue(in[1],inName)) ) { return false; } return obj->InitControlNode(inClassName,inName); } FUNCTION(SimulationServer, getTime) { return obj->GetTime(); } FUNCTION(SimulationServer, setSimStep) { float inDeltaTime; if ( (in.GetSize() != 1) || (! in.GetValue(in[0], inDeltaTime)) ) { return false; } obj->SetSimStep(inDeltaTime); return true; } FUNCTION(SimulationServer, getSimStep) { return obj->GetSimStep(); } FUNCTION(SimulationServer, setAutoTimeMode) { bool inSet; if ( (in.GetSize() != 1) || (! in.GetValue(in[0], inSet)) ) { return false; } obj->SetAutoTimeMode(inSet); return true; } FUNCTION(SimulationServer, getAutoTimeMode) { return obj->GetAutoTimeMode(); } void CLASS(SimulationServer)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Node); DEFINE_FUNCTION(quit); DEFINE_FUNCTION(initControlNode); DEFINE_FUNCTION(getTime); DEFINE_FUNCTION(setSimStep); DEFINE_FUNCTION(getSimStep); DEFINE_FUNCTION(setAutoTimeMode); DEFINE_FUNCTION(getAutoTimeMode); } --- NEW FILE: agentcontrol_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: agentcontrol_c.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "agentcontrol.h" using namespace oxygen; using namespace std; void CLASS(AgentControl)::DefineClass() { DEFINE_BASECLASS(oxygen/NetControl); } --- NEW FILE: netbuffer.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: netbuffer.h,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_NETBUFFER_H #define OXYGEN_NETBUFFER_H #include <rcssnet/addr.hpp> namespace oxygen { /** \class NetBuffer is a buffer that is used to hold the raw network stream of data. The NetMessage class is responsible to extract meaningful messages. */ class NetBuffer { public: NetBuffer() {}; NetBuffer(rcss::net::Addr addr, const std::string& data) : mAddr(addr), mData(data) {} /** appends a fragment to the buffer */ void AddFragment(const std::string& d); /** returns true iff the buffer is empty*/ bool IsEmpty() const; /** returns the network address associated with this buffer */ const rcss::net::Addr& GetAddr() const; /** returns the managed buffer */ std::string& GetData(); protected: /** the associated network address */ rcss::net::Addr mAddr; /** the managed buffer */ std::string mData; }; } // namespace oxygen #endif // OXYGEN_NETBUFFER_H --- NEW FILE: netmessage.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: netmessage.h,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_NETMESSAGE_H #define OXYGEN_NETMESSAGE_H #include <zeitgeist/class.h> #include <zeitgeist/leaf.h> namespace oxygen { class NetBuffer; /** \class NetMessage is responsible for the segmentation of raw received network data into meaningful messages, stripping any meta message information (e.g. msg length prefixes). It further is responsible to prepare a message to be sent over the network, i.e. to add any necessary meta information. The default NetMessage class implements a simple length prefixed protocol, i.e. it adds the payload length to a string sent over the network. */ class NetMessage : public zeitgeist::Leaf { public: NetMessage(); virtual ~NetMessage(); /** prepares a message that is sent to a client, i.e. adds any neccessary meta information. The default implementation prefixes the message with its total length */ virtual void PrepareToSend(std::string& msg); /** extracts a message from a network receive buffer into 'msg', i.e. it removes any meta information and returns the first complete message. The extracted message must be removed from the network buffer. ExtractMessage returns true iff it successfully extracted a message. The default implementation expects length prefixed strings. */ virtual bool Extract(boost::shared_ptr<NetBuffer> buffer, std::string& msg); }; DECLARE_CLASS(NetMessage); } // namespace oxygen #endif // OXYGEN_NETMESSAGE_H --- NEW FILE: simulationserver.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: simulationserver.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "simulationserver.h" #include "simcontrolnode.h" #include <oxygen/monitorserver/monitorserver.h> #include <oxygen/sceneserver/sceneserver.h> #include <oxygen/gamecontrolserver/gamecontrolserver.h> #include <zeitgeist/logserver/logserver.h> #include <signal.h> using namespace oxygen; using namespace zeitgeist; using namespace salt; using namespace std; using namespace boost; bool SimulationServer::mExit = false; void SimulationServer::CatchSignal(int sig_num) { if (sig_num == SIGINT) { signal(SIGINT, CatchSignal); SimulationServer::mExit = true; std::cout << "(SimulationServer) caught SIGINT. exiting.\n"; } } SimulationServer::SimulationServer() : Node() { mSimTime = 0.0f; mSimStep = 0.2f; mAutoTime = true; mCycle = 0; mSumDeltaTime = 0; mArgC = 0; mArgV = 0; signal(SIGINT, CatchSignal); } SimulationServer::~SimulationServer() { } void SimulationServer::OnLink() { mMonitorServer = shared_dynamic_cast<MonitorServer> (GetCore()->Get("/sys/server/monitor")); if (mMonitorServer.get() == 0) { GetLog()->Error() << "(SimulationServer) ERROR: MonitorServer not found.\n"; } mGameControlServer = shared_dynamic_cast<GameControlServer> (GetCore()->Get("/sys/server/gamecontrol")); if (mGameControlServer.get() == 0) { GetLog()->Error() << "(SimulationServer) ERROR: GameControlServer not found.\n"; } mSceneServer = shared_dynamic_cast<SceneServer> (GetCore()->Get("/sys/server/scene")); if (mSceneServer.get() == 0) { GetLog()->Error() << "(SimulationServer) ERROR: SceneServer not found.\n"; } } void SimulationServer::OnUnlink() { mMonitorServer.reset(); mGameControlServer.reset(); mSceneServer.reset(); } void SimulationServer::Quit() { mExit = true; } int SimulationServer::GetArgC() { return mArgC; } char** SimulationServer::GetArgV() { return mArgV; } float SimulationServer::GetTime() { return mSimTime; } float SimulationServer::GetSimStep() { return mSimStep; } void SimulationServer::SetSimStep(float deltaTime) { mSimStep = deltaTime; } float SimulationServer::GetSumDeltaTime() { return mSumDeltaTime; } void SimulationServer::SetAutoTimeMode(bool set) { mAutoTime = set; } bool SimulationServer::GetAutoTimeMode() { return mAutoTime; } int SimulationServer::GetCycle() { return mCycle; } bool SimulationServer::InitControlNode(const std::string& className, const std::string& name) { shared_ptr<SimControlNode> importer = shared_dynamic_cast<SimControlNode>(GetCore()->New(className)); if (importer.get() == 0) { GetLog()->Error() << "(SimulationServer) ERROR: " << "Unable to create '" << className << "'\n"; return false; } importer->SetName(name); AddChildReference(importer); GetLog()->Normal() << "(SimulationServer) SimControlNode '" << name << "' registered\n"; return true; } shared_ptr<SimControlNode> SimulationServer::GetControlNode(const string& controlName) { shared_ptr<SimControlNode> ctrNode = shared_dynamic_cast<SimControlNode>(GetChild(controlName)); if (ctrNode.get() == 0) { GetLog()->Normal() << "(SimulationServer) SimControlNode '" << controlName << "' not found\n"; } return ctrNode; } void SimulationServer::AdvanceTime(float deltaTime) { mSumDeltaTime += deltaTime; } void SimulationServer::Step() { if ( (mSceneServer.get() == 0) || (mGameControlServer.get() == 0) ) { return; } if (mSimStep > 0) { // world is stepped in discrete steps while (mSumDeltaTime >= mSimStep) { mSceneServer->Update(mSimStep); mGameControlServer->Update(mSimStep); mSumDeltaTime -= mSimStep; mSimTime += mSimStep; } } else { // simulate passed time in one single step mSceneServer->Update(mSumDeltaTime); mGameControlServer->Update(mSimStep); mSimTime += mSumDeltaTime; mSumDeltaTime = 0; } } void SimulationServer::ControlEvent(EControlEvent event) { for ( TLeafList::iterator iter=begin(); iter != end(); ++iter ) { shared_ptr<SimControlNode> ctrNode = shared_dynamic_cast<SimControlNode>(*iter); if (ctrNode.get() == 0) { continue; } switch (event) { case CE_Init : ctrNode->InitSimulation(); break; case CE_Done : ctrNode->DoneSimulation(); break; case CE_StartCycle : ctrNode->StartCycle(); break; case CE_SenseAgent : ctrNode->SenseAgent(); break; case CE_ActAgent : ctrNode->ActAgent(); break; case CE_EndCycle : ctrNode->EndCycle(); break; default: GetLog()->Error() << "(SimulationServer) ERROR: unknown control event " << event << "\n"; return; } } } void SimulationServer::Run(int argc, char** argv) { GetLog()->Normal() << "(SimulationServer) entering runloop\n"; // cache argc and argv, to make it accessible for registerd // SimControlNodes mArgC = argc; mArgV = argv; ControlEvent(CE_Init); while (! mExit) { ++mCycle; ControlEvent(CE_StartCycle); ControlEvent(CE_SenseAgent); ControlEvent(CE_ActAgent); if (mAutoTime) { AdvanceTime(mSimStep); } Step(); ControlEvent(CE_EndCycle); } ControlEvent(CE_Done); mArgC = 0; mArgV = 0; GetLog()->Normal() << "(SimulationServer) leaving runloop at t=" << mSimTime << "\n"; } shared_ptr<GameControlServer> SimulationServer::GetGameControlServer() { return mGameControlServer; } shared_ptr<MonitorServer> SimulationServer::GetMonitorServer() { return mMonitorServer; } shared_ptr<SceneServer> SimulationServer::GetSceneServer() { return mSceneServer; } --- NEW FILE: monitorcontrol_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: monitorcontrol_c.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "monitorcontrol.h" using namespace oxygen; using namespace std; FUNCTION(MonitorControl, getMonitorInterval) { return obj->GetMonitorInterval(); } FUNCTION(MonitorControl, setMonitorInterval) { int inInterval; if ( (in.GetSize() != 1) || (! in.GetValue(in.begin(), inInterval)) ) { return false; } obj->SetMonitorInterval(inInterval); return true; } void CLASS(MonitorControl)::DefineClass() { DEFINE_BASECLASS(oxygen/NetControl); DEFINE_FUNCTION(getMonitorInterval); DEFINE_FUNCTION(setMonitorInterval); } --- NEW FILE: simcontrolnode_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: simcontrolnode_c.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "simcontrolnode.h" using namespace oxygen; using namespace std; void CLASS(SimControlNode)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Node); } --- NEW FILE: netclient_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: netclient_c.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "netclient.h" using namespace std; using namespace oxygen; FUNCTION(NetClient, getServer) { return obj->GetServer(); } FUNCTION(NetClient, setServer) { string inServer; if ( (in.GetSize() != 1) || (! in.GetValue(in[0], inServer)) ) { return false; } obj->SetServer(inServer); return true; } FUNCTION(NetClient, setClientTypeTCP) { obj->SetClientType(NetControl::ST_TCP); return true; } FUNCTION(NetClient, setClientTypeUDP) { obj->SetClientType(NetControl::ST_UDP); return true; } FUNCTION(NetClient, getPort) { return obj->GetPort(); } FUNCTION(NetClient, setPort) { int inPort; if ( (in.GetSize() != 1) || (! in.GetValue(in[0], inPort)) ) { return false; } obj->SetPort(inPort); return true; } void CLASS(NetClient)::DefineClass() { DEFINE_BASECLASS(oxygen/SimControlNode); DEFINE_FUNCTION(getServer); DEFINE_FUNCTION(setServer); DEFINE_FUNCTION(getPort); DEFINE_FUNCTION(setPort); DEFINE_FUNCTION(setClientTypeTCP); DEFINE_FUNCTION(setClientTypeUDP); } --- NEW FILE: netclient.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: netclient.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "netclient.h" #include <zeitgeist/logserver/logserver.h> #include <netinet/in.h> #include <rcssnet/exception.hpp> using namespace oxygen; using namespace zeitgeist; using namespace rcss::net; using namespace salt; using namespace boost; using namespace std; NetClient::NetClient() : SimControlNode() { mHost = "127.0.0.1"; mPort = 3200; mBufferSize = 64 * 1024; mBuffer = shared_array<char>(new char[mBufferSize]); mType = NetControl::ST_TCP; mNetBuffer = shared_ptr<NetBuffer>(new NetBuffer()); } NetClient::~NetClient() { } void NetClient::SetServer(const std::string& host) { mHost = host; } const std::string& NetClient::GetServer() const { return mHost; } void NetClient::SetPort(int port) { mPort = port; } int NetClient::GetPort() const { return mPort; } void NetClient::SetClientType(NetControl::ESocketType type) { mType = type; } NetControl::ESocketType NetClient::GetClientType() { return mType; } bool NetClient::Connect() { mSocket = NetControl::CreateSocket(mType); if (mSocket.get() == 0) { return false; } GetLog()->Normal() << "(NetClient) '" << GetName() << "'connecting to " << ((mType == NetControl::ST_UDP) ? "UDP " : "TCP ") << mHost << ":" << mPort << "\n"; try { Addr local(INADDR_ANY,INADDR_ANY); mSocket->bind(local); } catch (BindErr error) { GetLog()->Error() << "(NetClient) '" << GetName() << "' failed to bind socket with '" << error.what() << "'" << endl; mSocket->close(); return false; } try { Addr server(mPort,mHost); mSocket->connect(server); } catch (ConnectErr error) { GetLog()->Error() << "(NetClient) '" << GetName() << "' connection failed with: '" << error.what() << "'" << endl; mSocket->close(); mSocket.reset(); return false; } if (mSocket->isConnected()) { cout << "(NetClient) '" << GetName() << "' connected successfully" << endl; } // assure that a NetMessage object is registered mNetMessage = FindChildSupportingClass<NetMessage>(); if (mNetMessage.get() == 0) { mNetMessage = shared_ptr<NetMessage>(new NetMessage()); } return true; } void NetClient::SendMessage(const string& msg) { if (mNetMessage.get() == 0) { return; } string preparedMsg = msg; mNetMessage->PrepareToSend(preparedMsg);; if (mSocket.get() == 0) { return; } int rval = 0; if (mType == NetControl::ST_UDP) { Addr server(mPort,mHost); rval = mSocket->send(msg.data(), msg.size(), server); } else { rval = mSocket->send(preparedMsg.data(), preparedMsg.size()); } if (rval < 0) { GetLog()->Error() << "(NetClient::SendMessage) ERROR: " << "send returned error '" << strerror(errno) << "' " << endl; } } void NetClient::CloseConnection() { if (mSocket.get() == 0) { return; } mSocket->close(); mSocket.reset(); GetLog()->Normal() << "(NetClient) '" << GetName() << "' closed connection to " << mHost << ":" << mPort << "\n"; mNetMessage.reset(); } void NetClient::ReadFragments() { if (mSocket.get() == 0) { return; } for (;;) { // test for available data int fd = mSocket->getFD(); fd_set readfds; FD_ZERO(&readfds); FD_SET(fd,&readfds); timeval time; time.tv_sec = 0; time.tv_usec = 0; int rval = select(fd+1, &readfds, 0, 0, &time ); if (rval == 0) { break; } if (rval < 0) { GetLog()->Error() << "(NetClient) ERROR select on client " << "socket failed with '" << strerror(errno) << "'" << endl; CloseConnection(); return; } rval = mSocket->recv(mBuffer.get(),mBufferSize); if (rval == 0) { CloseConnection(); return; } if (rval < 0) { GetLog()->Error() << "(NetClient) '" << GetName() << "' ERROR: '" << GetName() << "' recv returned error '" << strerror(errno) << "' " << endl; return; } string fragment(mBuffer.get(),rval); mNetBuffer->AddFragment(string(mBuffer.get(),rval)); } } --- NEW FILE: netcontrol.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: netcontrol.h,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_NETCONTROL_H #define OXYGEN_NETCONTROL_H #include "simcontrolnode.h" #include "netbuffer.h" #include <rcssnet/socket.hpp> #include <boost/shared_array.hpp> namespace oxygen { class GameControlServer; class NetMessage; /** \class NetControl is a SimControlNode that accepts and manages a set of network client connections via UDP or TCP. With each simulation cycle it collects all pending client messages in a set of network buffers, each corresponding to a client. It furthes provides methods to send messages to connected clients. The segmentation of the received data into messages and the composition of messages is delegated to a NetMessage class that is registered to a NetControl node. It is responsible to manage the MetaProtocol, i.e. it adds and removes any additional message framing and type information. */ class NetControl : public SimControlNode { public: enum ESocketType { ST_TCP, ST_UDP }; struct Client { public: int id; rcss::net::Addr addr; boost::shared_ptr<rcss::net::Socket> socket; public: Client() : id(-1) {}; Client(int i, const rcss::net::Addr& a, boost::shared_ptr<rcss::net::Socket> s = boost::shared_ptr<rcss::net::Socket>() ) : id(i), addr(a), socket(s) {}; }; // mapping from a client remote address to Client struct typedef std::map<rcss::net::Addr, boost::shared_ptr<Client> > TAddrMap; // mapping from a client remote address to a corresponding buffer typedef std::map<rcss::net::Addr, boost::shared_ptr<NetBuffer> > TBufferMap; typedef std::list<rcss::net::Addr> TAddrList; public: NetControl(); virtual ~NetControl(); /** creates the managed socket, when the simulation starts */ virtual void InitSimulation(); /** called once before the simulation is shut down */ virtual void DoneSimulation(); /** called when a new simulation cycle starts, before the simulation is stepped */ virtual void StartCycle(); /** called when the current simulation cycle ends */ virtual void EndCycle(); /** called when a new client connects */ virtual void ClientConnect(boost::shared_ptr<Client> client); /** called when a client disconnects */ virtual void ClientDisconnect(boost::shared_ptr<Client> client); /** sets the local port, on which connections are accepted */ void SetServerPort(rcss::net::Addr::PortType port); /** returns the local port, on which connections are accepted */ rcss::net::Addr::PortType GetServerPort(); /** sets the type of the socket on which connections are accepted */ void SetServerType(ESocketType type); /** returns the type of the socket on which connections are accepted */ ESocketType GetServerType(); /** sends a message to the given client */ void SendMessage(boost::shared_ptr<Client> client, const std::string& msg); /** sends a message to the client with the given address */ void SendMessage(const rcss::net::Addr& addr, const std::string& msg); /** create a socket according to the given ESocketType */ static boost::shared_ptr<rcss::net::Socket> NetControl::CreateSocket(ESocketType type); protected: /** returns a human readable description of the socket type and port*/ std::string NetControl::DescribeSocketType(); /** checks for and accepts pending TCP connections */ void AcceptTCPConnections(); /** reads and stores all available messages */ void NetControl::ReadMessages(); /** reads and stores all available TCP messages */ void ReadTCPMessages(); /** reads and stores all available UDP messages. UDP fragments from unknown sources generate new client entries */ void ReadUDPMessages(); /** copies the message fragment with length \param size currently in the receive buffer to the input queue of the client with the remoted address \param addr */ void StoreFragment(const rcss::net::Addr& addr, int size); /** creates a new client entry. \param from is the remote adress of the client. \param socket gives the loacl socket for a TCP connection the for a TCP connection */ void AddClient(const rcss::net::Addr& from, boost::shared_ptr<rcss::net::Socket> socket = boost::shared_ptr<rcss::net::Socket>()); /** removes a client entry and closes the associated socket. \param from is the remote adress of the client. */ void RemoveClient(const rcss::net::Addr& from); /** removes all clients marked in the mCloseClients list */ void CloseDeadConnections(); protected: /** cached reference to the NetMessage child node */ boost::shared_ptr<NetMessage> mNetMessage; /** the local port, on which connections are accepted */ rcss::net::Addr mLocalAddr; /** the type of created socket */ ESocketType mSocketType; /** the socket used to accept connections */ boost::shared_ptr<rcss::net::Socket> mSocket; /** map of known clients, based on remote address */ TAddrMap mClients; /** list of client connections to be closed */ TAddrList mCloseClients; /** list of queued messages */ TBufferMap mBuffers; /** the size of the allocated receive buffer */ int mBufferSize; /** the receive buffer */ boost::shared_array<char> mBuffer; /** the next available unique client id */ int mClientId; }; DECLARE_CLASS(NetControl); } // namespace oxygen #endif // OXYGEN_NETCONTROL_H --- NEW FILE: netcontrol.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: netcontrol.cpp,v 1.1 2005/12/05 21:21:18 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "netcontrol.h" #include "netmessage.h" #include <zeitgeist/logserver/logserver.h> #include <netinet/in.h> #include <rcssnet/exception.hpp> #include <rcssnet/tcpsocket.hpp> #include <rcssnet/udpsocket.hpp> #include <sstream> #include <cerrno> using namespace rcss::net; using namespace oxygen; using namespace zeitgeist; using namespace boost; using namespace std; NetControl::NetControl() : SimControlNode() { mBufferSize = 64 * 1024; mBuffer = shared_array<char>(new char[mBufferSize]); mSocketType = ST_TCP; mLocalAddr = Addr(INADDR_ANY, INADDR_ANY); mClientId = 1; } NetControl::~NetControl() { } void NetControl::SetServerPort(Addr::PortType port) { mLocalAddr.setPort(port); } rcss::net::Addr::PortType NetControl::GetServerPort() { return mLocalAddr.getPort(); } void NetControl::SetServerType(ESocketType type) { mSocketType = type; } NetControl::ESocketType NetControl::GetServerType() { return mSocketType; } boost::shared_ptr<Socket> NetControl::CreateSocket(ESocketType type) { shared_ptr<Socket> socket; try { switch (type) { case ST_UDP: socket = shared_ptr<Socket>(new UDPSocket()); break; case ST_TCP: socket = shared_ptr<Socket>(new TCPSocket()); break; default: cerr << "(NetControl) ERROR: unknown socket type " << type << "\n"; break; } } catch (OpenErr error) { cerr << "(NetControl) failed to create socket with '" << error.what() << endl; } return socket; } string NetControl::DescribeSocketType() { stringstream ss; switch (mSocketType) { case ST_UDP: ss << "UDP"; break; case ST_TCP: ss << "TCP"; break; default: ss << "(unknown socket type)"; break; } ss << ":" << mLocalAddr.getPort(); return ss.str(); } void NetControl::InitSimulation() { // assert that the local port has been set if (mLocalAddr.getPort() == INADDR_ANY) { GetLog()->Error() << "(NetControl) ERROR: local port has no been set in '" << GetClass()->GetName() << "'\n"; return; } GetLog()->Normal() << "(NetControl) '" << GetName() << "' setting up a server on " << DescribeSocketType() << std::endl; mSocket = CreateSocket(mSocketType); if (mSocket.get() == 0) { return; } int ret = mSocket->setNonBlocking(true); if (ret < 0) { GetLog()->Error() << "(NetControl) failed to set server socket to non " << "blocking mode with '" << strerror(errno) << "'\n"; mSocket->close(); return; } try { mSocket->bind(mLocalAddr); } catch (BindErr error) { GetLog()->Error() << "(NetControl) failed to bind socket with '" << error.what() << "'" << endl; mSocket->close(); return; } try { if (mSocketType == ST_TCP) { #ifdef SOMAXCONN mSocket->listen(SOMAXCONN); #else mSocket->listen(50); #endif } } catch (ListenErr error) { GetLog()->Error() << "(NetControl) failed to listen on socket with '" << error.what() << "'" << endl; mSocket->close(); return; } // assure that a NetMessage object is registered mNetMessage = FindChildSupportingClass<NetMessage>(); if (mNetMessage.get() == 0) { mNetMessage = shared_ptr<NetMessage>(new NetMessage()); } } void NetControl::DoneSimulation() { // reset the cached NetMessage reference mNetMessage.reset(); // close all client connections for ( TAddrMap::iterator iter = mClients.begin(); iter != mClients.end(); ++iter ) { RemoveClient((*iter).second->addr); } // shutdown the server socket mSocket->close(); GetLog()->Normal() << "(NetControl) '" << GetName() << "' closed server socket " << DescribeSocketType() << std::endl; mSocket.reset(); mClients.clear(); } void NetControl::AddClient(const Addr& from, shared_ptr<Socket> socket) { shared_ptr<Client> client(new Client(mClientId,from,socket)); mClients[from] = client; GetLog()->Normal() << "(NetControl) '" << GetName() << "' accepted a " << ((socket.get() != 0) ? "TCP" : "UDP") << " connection from '" << from.getHostStr() << ":" << from.getPort() << "' id " << mClientId << endl; mClientId++; ClientConnect(client); } void NetControl::RemoveClient(const Addr& from) { TAddrMap::iterator mapIter = mClients.find(from); if (mapIter == mClients.end()) { GetLog()->Warning() << "(NetControl) '" << GetName() << "' RemoveClient called with an unknown client address\n"; return; } shared_ptr<Client> client = (*mapIter).second; ClientDisconnect(client); shared_ptr<Socket> socket = client->socket; GetLog()->Normal() << "(NetControl) '" << GetName() << "' closing a " << ((socket.get() != 0) ? "TCP" : "UDP") << " connection from '" << from.getHostStr() << ":" << from.getPort() << "' id " << client->id << endl; if (socket.get() != 0) { socket->close(); } mClients.erase(mapIter); } void NetControl::ClientConnect(shared_ptr<Client> /*client*/) { // empty callback, implemented in derived classes } void NetControl::ClientDisconnect(shared_ptr<Client> /*client*/) { // empty callback, implemented in derived classes } void NetControl::SendMessage(shared_ptr<Client> client, const string& msg) { if (client.get() == 0) { return; } int rval = 0; shared_ptr<Socket> socket = client->socket; if (socket.get() == 0) { // udp client if (mSocket.get() != 0) { rval = mSocket->send(msg.data(), msg.size(), client->addr); } } else { // tcp client rval = socket->send(msg.data(), msg.size()); } if (rval < 0) { GetLog()->Error() << "(NetControl::SendMessage) ERROR: '" << GetName() << "' send returned error '" << strerror(errno) << "' " << endl; } } void NetControl::SendMessage(const Addr& addr, const string& msg) { TAddrMap::iterator iter = mClients.find(addr); if (iter == mClients.end()) { GetLog()->Error() << "(NetControl::SendMessage) ERROR: unknown client address '" << addr.getHostStr() << ":" << addr.getPort() << "'\n"; return; } SendMessage((*iter).second,msg); } void NetControl::AcceptTCPConnections() { if ( (mSocketType != ST_TCP) || (mSocket.get() == 0) ) { return; } int fd = mSocket->getFD(); fd_set readfds; FD_ZERO(&readfds); FD_SET(fd,&readfds); timeval time; time.tv_sec = 0; time.tv_usec = 0; for(;;) { int ret = select(fd+1, &readfds, 0, 0, &time); if (ret == 0) { // no more connections pending break; } if (ret < 0) { GetLog()->Error() << "(NetControl) ERROR: '" << GetName() << "' select returned error on server socket " << DescribeSocketType() << ' ' << strerror(errno) << "\n" << "(NetControl) ERROR: closing server socket" << endl; mSocket->close(); mSocket.reset(); break; } try { Addr addr; shared_ptr<Socket> socket(mSocket->accept(addr)); int ret = socket->setNonBlocking(true); if (ret < 0) { GetLog()->Error() << "(NetControl) failed to set client socket to" << " non blocking mode with '" << strerror(errno) << "'. closing connection\n"; ... [truncated message content] |
From: Markus R. <rol...@us...> - 2005-12-05 21:20:30
|
Update of /cvsroot/simspark/simspark/spark/oxygen/spadesserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv15468/spadesserver Log Message: Directory /cvsroot/simspark/simspark/spark/oxygen/spadesserver added to the repository |
From: Markus R. <rol...@us...> - 2005-12-05 21:19:24
|
Update of /cvsroot/simspark/simspark/spark/oxygen/simulationserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv15117/simulationserver Log Message: Directory /cvsroot/simspark/simspark/spark/oxygen/simulationserver added to the repository |
From: Markus R. <rol...@us...> - 2005-12-05 21:18:31
|
Update of /cvsroot/simspark/simspark/spark/oxygen/sceneserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14848/sceneserver Log Message: Directory /cvsroot/simspark/simspark/spark/oxygen/sceneserver added to the repository |
From: Markus R. <rol...@us...> - 2005-12-05 21:17:10
|
Update of /cvsroot/simspark/simspark/spark/oxygen/geometryserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14301/geometryserver Added Files: geometryserver.cpp geometryserver.h geometryserver_c.cpp indexbuffer.cpp indexbuffer.h meshimporter.cpp meshimporter.h meshimporter_c.cpp stdmeshimporter.cpp stdmeshimporter.h stdmeshimporter_c.cpp trimesh.cpp trimesh.h Log Message: --- NEW FILE: meshimporter_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: meshimporter_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "meshimporter.h" using namespace oxygen; void CLASS(MeshImporter)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Leaf); } --- NEW FILE: meshimporter.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: meshimporter.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_MESHIMPORTER_H #define OXYGEN_MESHIMPORTER_H #include <zeitgeist/class.h> #include <zeitgeist/node.h> #include "trimesh.h" namespace oxygen { /** \class MeshImporter defines an interface for classes that import or generate trimeshes. MeshImporter classes are registered to the GeometryServer */ class MeshImporter : public zeitgeist::Leaf { public: MeshImporter() : Leaf() {}; virtual ~MeshImporter() {}; /** loads or generates a mesh referenced by the given name and optional list of parameters */ virtual boost::shared_ptr<TriMesh> ImportMesh (const std::string& name,__attribute__((unused)) const zeitgeist::ParameterList& parameter) = 0; /** returns a unique name for each combination of name and parameter. This is only useful for parameterized MeshImporters. The default implementation returns \param name */ virtual std::string MangleName (const std::string& name, const zeitgeist::ParameterList& parameter); }; DECLARE_ABSTRACTCLASS(MeshImporter); } // namespace oxgen #endif // OXYGEN_MESHIMPORTER_H --- NEW FILE: stdmeshimporter_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: stdmeshimporter_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "stdmeshimporter.h" using namespace oxygen; void CLASS(StdMeshImporter)::DefineClass() { DEFINE_BASECLASS(oxygen/MeshImporter); } --- NEW FILE: geometryserver.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: geometryserver.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_GEOMETRYSERVER_H #define OXYGEN_GEOMETRYSERVER_H #include <zeitgeist/class.h> #include <zeitgeist/node.h> #include "trimesh.h" namespace oxygen { /** \class GeometryServer manages a set of triangle meshes and a set of plugins to import or generate them. Triangle meshes are used for collision detection and rendering. */ class GeometryServer : public zeitgeist::Node { protected: typedef std::map<std::string, boost::shared_ptr<TriMesh> > TMeshMap; public: GeometryServer(); ~GeometryServer(); /** creates an instance of \param importerName and registers it as a MeshImporter to the GeometryServer */ bool InitMeshImporter(const std::string& importerName); /** imports the trimesh \param name, with the given parameters or returns a cached reference */ boost::shared_ptr<TriMesh> GetMesh (const std::string& name, const zeitgeist::ParameterList& parameter); protected: /** registers the standard mesh importer */ virtual void OnLink(); protected: /** the registry of cached trimeshes */ TMeshMap mMeshMap; }; DECLARE_CLASS(GeometryServer); } //namespace oxygen #endif //OXYGEN_GEOMETRYSERVER_H --- NEW FILE: stdmeshimporter.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: stdmeshimporter.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_STDMESHIMPORTER #define OXYGEN_STDMESHIMPORTER #include "meshimporter.h" namespace oxygen { /** \class StdMeshImporter is a MeshImporter that generates a standard set of meshes. These are spheres, boxes and capped cylinders. */ class StdMeshImporter : public MeshImporter { public: StdMeshImporter(); virtual ~StdMeshImporter(); /** generates a mesh referenced by the given name and optional list of parameters */ virtual boost::shared_ptr<TriMesh> ImportMesh (const std::string& name,const zeitgeist::ParameterList& parameter); /** returns a unique name for each parameterized capped cylinder mesh, and \param name otherwise */ virtual std::string MangleName (const std::string& name,const zeitgeist::ParameterList& parameter); protected: /** constructs a unit sphere */ boost::shared_ptr<TriMesh> UnitSphereMesh(); /** constructs a unit box */ boost::shared_ptr<TriMesh> UnitBoxMesh(); /** constructs a unit capped cylinder */ boost::shared_ptr<TriMesh> UnitCCylinder (const zeitgeist::ParameterList& parameter); }; DECLARE_CLASS(StdMeshImporter); } // namespace oxygen #endif // OXYGEN_STDMESHIMPORTER --- NEW FILE: trimesh.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: trimesh.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "trimesh.h" using namespace oxygen; using namespace std; using namespace boost; TriMesh::TriMesh() : mVertexCount(0) { } TriMesh::~TriMesh() { } void TriMesh::SetPos(shared_array<float> pos, int vertexCount) { mPos = pos; mVertexCount = vertexCount; } void TriMesh::SetTexCoords(shared_array<float> texCoords) { mTexCoords = texCoords; } void TriMesh::SetNormals(shared_array<float> normal) { mNormal = normal; } const shared_array<float> TriMesh::GetPos() const { return mPos; } int TriMesh::GetVertexCount() const { return mVertexCount; } const shared_array<float> TriMesh::GetTexCoords() const { return mTexCoords; } const shared_array<float> TriMesh::GetNormals() const { return mNormal; } void TriMesh::AddFace(boost::shared_ptr<IndexBuffer> indeces, const std::string& material) { mFaces.push_back(Face(indeces, material)); } void TriMesh::AddFace(const Face& face) { mFaces.push_back(face); } const TriMesh::TFaces& TriMesh::GetFaces() const { return mFaces; } const std::string& TriMesh::GetName() const { return mName; } void TriMesh::SetName(const std::string& name) { mName = name; } --- NEW FILE: indexbuffer.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: indexbuffer.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "indexbuffer.h" #include <string.h> using namespace oxygen; using namespace boost; IndexBuffer::IndexBuffer() : mMaxIndex(0), mNumIndex(0), mIndex(0) {} IndexBuffer::~IndexBuffer() { } void IndexBuffer::Cache(unsigned int numIndex, unsigned int *index) { EnsureFit(numIndex); // append new index data to our cache memcpy(&mIndex[mNumIndex], index, numIndex*sizeof(unsigned int)); mNumIndex += numIndex; } void IndexBuffer::Cache(unsigned int newIndex) { Cache(1, &newIndex); } void IndexBuffer::EnsureFit(unsigned int count) { if(mIndex.get() == 0) { mIndex = shared_array<unsigned int>(new unsigned int[count]); mMaxIndex = count; mNumIndex = 0; } else { // check if there's enough room in our index cache const unsigned int reqSize = mNumIndex+count; if(mMaxIndex < reqSize) { // we don't have enough room ... so make room unsigned int newSize = mMaxIndex*2; while(newSize<reqSize) { newSize *= 2; } // allocate new memory shared_array<unsigned int> newIndex(new unsigned int[newSize]); // copy old data memcpy(newIndex.get(), mIndex.get(), mNumIndex*sizeof(unsigned int)); mIndex = newIndex; mMaxIndex = newSize; } } } void IndexBuffer::Flush() { mNumIndex = 0; } int IndexBuffer::GetNumIndex() const { return mNumIndex; } shared_array<unsigned int> IndexBuffer::GetIndex() const { return mIndex; } --- NEW FILE: indexbuffer.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: indexbuffer.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_INDEXBUFFER_H #define OXYGEN_INDEXBUFFER_H #include <boost/shared_array.hpp> namespace oxygen { /** IndexBuffer is intended as a cache for indeces pointing into a vertexbuffer to describe a set of triangles. It is used together with the StaticMesh class */ class IndexBuffer { public: IndexBuffer(); virtual ~IndexBuffer(); /** caches (i.e. copies) an index list for rendering at a later point in time, growing the index cache if necessary. \param numIndex number of indices to add to the cache \param index pointer to index data */ void Cache(unsigned int numIndex, unsigned int *index); /** appends a single index */ void Cache(unsigned int newIndex); /** empties the index buffer */ void Flush(); /** returns the number of cached indeces */ int GetNumIndex() const; /** returns a cached index */ boost::shared_array<unsigned int> GetIndex() const; /** ensures that the index buffer can hold the additional (!) number of elements (creates new storage on demand, copys old data) */ void EnsureFit(unsigned int count); protected: /** the maximum number of indices we can cache with the allocated memory */ unsigned int mMaxIndex; /** the number of indices currently cached */ unsigned int mNumIndex; /** pointer to the memory, where we cache the indices */ boost::shared_array<unsigned int> mIndex; }; } #endif //OXYGEN_INDEXBUFFER_H --- NEW FILE: geometryserver_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: geometryserver_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "geometryserver.h" using namespace oxygen; using namespace std; FUNCTION(GeometryServer,initMeshImporter) { string inImporterName; if ( (in.GetSize() != 1) || (! in.GetValue(in.begin(),inImporterName)) ) { return false; } return obj->InitMeshImporter(inImporterName); } void CLASS(GeometryServer)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Node); DEFINE_FUNCTION(initMeshImporter); } --- NEW FILE: meshimporter.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: meshimporter.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "meshimporter.h" using namespace oxygen; using namespace zeitgeist; using namespace boost; using namespace std; string MeshImporter::MangleName (const string& name, const ParameterList& /*parameter*/) { return name; } --- NEW FILE: geometryserver.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: geometryserver.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "geometryserver.h" #include "meshimporter.h" #include <zeitgeist/logserver/logserver.h> using namespace oxygen; using namespace zeitgeist; using namespace salt; using namespace std; using namespace boost; GeometryServer::GeometryServer() : Node() { } GeometryServer::~GeometryServer() { } void GeometryServer::OnLink() { if (mChildren.size() == 0) { InitMeshImporter("oxygen/StdMeshImporter"); } } bool GeometryServer::InitMeshImporter(const string& importerName) { shared_ptr<MeshImporter> importer = shared_dynamic_cast<MeshImporter>(GetCore()->New(importerName)); if (importer.get() == 0) { GetLog()->Error() << "(GeometryServer) ERROR: " << "unable to create '" << importerName << "'\n"; return false; } importer->SetName(importerName); AddChildReference(importer); GetLog()->Normal() << "(GeometryServer) MeshImporter '" << importerName << "' registered\n"; return true; } shared_ptr<TriMesh> GeometryServer::GetMesh (const string& name, const::ParameterList& parameter) { // try a direct match string meshName = name; TMeshMap::iterator meshIter = mMeshMap.find(meshName); if (meshIter != mMeshMap.end()) { return (*meshIter).second; } TLeafList importer; ListChildrenSupportingClass<MeshImporter>(importer); if (importer.size() == 0) { GetLog()->Error() << "(GeometryServer) Warning: no MeshImporter registered\n"; return shared_ptr<TriMesh>(); } // try to mangle the name for ( TLeafList::iterator iter = importer.begin(); iter != importer.end(); ++iter ) { shared_ptr<MeshImporter> importer = shared_static_cast<MeshImporter>(*iter); string str = importer->MangleName(name, parameter); if (str != meshName) { meshName = str; meshIter = mMeshMap.find(meshName); if (meshIter != mMeshMap.end()) { return (*meshIter).second; } } } // try to import the mesh for ( TLeafList::iterator iter = importer.begin(); iter != importer.end(); ++iter ) { shared_ptr<MeshImporter> importer = shared_static_cast<MeshImporter>(*iter); shared_ptr<TriMesh> mesh = importer->ImportMesh(name,parameter); if (mesh.get() == 0) { continue; } string meshName = mesh->GetName(); if (meshName == "") { mesh->SetName(name); meshName = name; } GetLog()->Normal() << "(GeometryServer) imported mesh '" << meshName << " with '" << importer->GetName() << "'\n"; mMeshMap[meshName] = mesh; return mesh; } GetLog()->Error() << "(GeometryServer) ERROR: cannot import mesh '" << name << "'\n"; return shared_ptr<TriMesh>(); } --- NEW FILE: stdmeshimporter.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: stdmeshimporter.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "stdmeshimporter.h" #include <salt/gmath.h> #include <sstream> #include <zeitgeist/logserver/logserver.h> using namespace zeitgeist; using namespace oxygen; using namespace boost; using namespace salt; using namespace std; StdMeshImporter::StdMeshImporter() : MeshImporter() { } StdMeshImporter::~StdMeshImporter() { } static const string gSphereStr = "StdUnitSphere"; static const string gBoxStr = "StdUnitBox"; static const string gCCylinderStr = "StdCCylinder"; shared_ptr<TriMesh> StdMeshImporter::ImportMesh(const std::string& name,const ParameterList& parameter) { if (name == gSphereStr) { return UnitSphereMesh(); } if (name == gBoxStr) { return UnitBoxMesh(); } if (name == gCCylinderStr) { return UnitCCylinder(parameter); } return shared_ptr<TriMesh>(); } // // unit sphere // // This code is thanks to John Ratcliff static const int gNumSphereVertices = 114; static const int gNumSphereFaces = 224; static float gSphereVertices[gNumSphereVertices*3] = { 0.0000f,0.0000f,1.0000f, 0.0000f,0.3827f,0.9239f, -0.1464f,0.3536f,0.9239f, -0.2706f,0.2706f,0.9239f, -0.3536f,0.1464f,0.9239f, -0.3827f,0.0000f,0.9239f, -0.3536f,-0.1464f,0.9239f, -0.2706f,-0.2706f,0.9239f, -0.1464f,-0.3536f,0.9239f, 0.0000f,-0.3827f,0.9239f, 0.1464f,-0.3536f,0.9239f, 0.2706f,-0.2706f,0.9239f, 0.3536f,-0.1464f,0.9239f, 0.3827f,0.0000f,0.9239f, 0.3536f,0.1464f,0.9239f, 0.2706f,0.2706f,0.9239f, 0.1464f,0.3536f,0.9239f, 0.0000f,0.7071f,0.7071f, -0.2706f,0.6533f,0.7071f, -0.5000f,0.5000f,0.7071f, -0.6533f,0.2706f,0.7071f, -0.7071f,0.0000f,0.7071f, -0.6533f,-0.2706f,0.7071f, -0.5000f,-0.5000f,0.7071f, -0.2706f,-0.6533f,0.7071f, 0.0000f,-0.7071f,0.7071f, 0.2706f,-0.6533f,0.7071f, 0.5000f,-0.5000f,0.7071f, 0.6533f,-0.2706f,0.7071f, 0.7071f,0.0000f,0.7071f, 0.6533f,0.2706f,0.7071f, 0.5000f,0.5000f,0.7071f, 0.2706f,0.6533f,0.7071f, 0.0000f,0.9239f,0.3827f, -0.3536f,0.8536f,0.3827f, -0.6533f,0.6533f,0.3827f, -0.8536f,0.3536f,0.3827f, -0.9239f,0.0000f,0.3827f, -0.8536f,-0.3536f,0.3827f, -0.6533f,-0.6533f,0.3827f, -0.3536f,-0.8536f,0.3827f, 0.0000f,-0.9239f,0.3827f, 0.3536f,-0.8536f,0.3827f, 0.6533f,-0.6533f,0.3827f, 0.8536f,-0.3536f,0.3827f, 0.9239f,0.0000f,0.3827f, 0.8536f,0.3536f,0.3827f, 0.6533f,0.6533f,0.3827f, 0.3536f,0.8536f,0.3827f, 0.0000f,1.0000f,0.0000f, -0.3827f,0.9239f,0.0000f, -0.7071f,0.7071f,0.0000f, -0.9239f,0.3827f,0.0000f, -1.0000f,0.0000f,0.0000f, -0.9239f,-0.3827f,0.0000f, -0.7071f,-0.7071f,0.0000f, -0.3827f,-0.9239f,0.0000f, 0.0000f,-1.0000f,0.0000f, 0.3827f,-0.9239f,0.0000f, 0.7071f,-0.7071f,0.0000f, 0.9239f,-0.3827f,0.0000f, 1.0000f,0.0000f,0.0000f, 0.9239f,0.3827f,0.0000f, 0.7071f,0.7071f,0.0000f, 0.3827f,0.9239f,0.0000f, 0.0000f,0.9239f,-0.3827f, -0.3536f,0.8536f,-0.3827f, -0.6533f,0.6533f,-0.3827f, -0.8536f,0.3536f,-0.3827f, -0.9239f,0.0000f,-0.3827f, -0.8536f,-0.3536f,-0.3827f, -0.6533f,-0.6533f,-0.3827f, -0.3536f,-0.8536f,-0.3827f, 0.0000f,-0.9239f,-0.3827f, 0.3536f,-0.8536f,-0.3827f, 0.6533f,-0.6533f,-0.3827f, 0.8536f,-0.3536f,-0.3827f, 0.9239f,0.0000f,-0.3827f, 0.8536f,0.3536f,-0.3827f, 0.6533f,0.6533f,-0.3827f, 0.3536f,0.8536f,-0.3827f, 0.0000f,0.7071f,-0.7071f, -0.2706f,0.6533f,-0.7071f, -0.5000f,0.5000f,-0.7071f, -0.6533f,0.2706f,-0.7071f, -0.7071f,0.0000f,-0.7071f, -0.6533f,-0.2706f,-0.7071f, -0.5000f,-0.5000f,-0.7071f, -0.2706f,-0.6533f,-0.7071f, 0.0000f,-0.7071f,-0.7071f, 0.2706f,-0.6533f,-0.7071f, 0.5000f,-0.5000f,-0.7071f, 0.6533f,-0.2706f,-0.7071f, 0.7071f,0.0000f,-0.7071f, 0.6533f,0.2706f,-0.7071f, 0.5000f,0.5000f,-0.7071f, 0.2706f,0.6533f,-0.7071f, 0.0000f,0.3827f,-0.9239f, -0.1464f,0.3536f,-0.9239f, -0.2706f,0.2706f,-0.9239f, -0.3536f,0.1464f,-0.9239f, -0.3827f,0.0000f,-0.9239f, -0.3536f,-0.1464f,-0.9239f, -0.2706f,-0.2706f,-0.9239f, -0.1464f,-0.3536f,-0.9239f, 0.0000f,-0.3827f,-0.9239f, 0.1464f,-0.3536f,-0.9239f, 0.2706f,-0.2706f,-0.9239f, 0.3536f,-0.1464f,-0.9239f, 0.3827f,0.0000f,-0.9239f, 0.3536f,0.1464f,-0.9239f, 0.2706f,0.2706f,-0.9239f, 0.1464f,0.3536f,-0.9239f, 0.0000f,0.0000f,-1.0000f }; static unsigned int gSphereFaces[gNumSphereFaces*3] = { 0,1,2, 0,2,3, 0,3,4, 0,4,5, 0,5,6, 0,6,7, 0,7,8, 0,8,9, 0,9,10, 0,10,11, 0,11,12, 0,12,13, 0,13,14, 0,14,15, 0,15,16, 0,16,1, 1,17,18, 1,18,2, 2,18,19, 2,19,3, 3,19,20, 3,20,4, 4,20,21, 4,21,5, 5,21,22, 5,22,6, 6,22,23, 6,23,7, 7,23,24, 7,24,8, 8,24,25, 8,25,9, 9,25,26, 9,26,10, 10,26,27, 10,27,11, 11,27,28, 11,28,12, 12,28,29, 12,29,13, 13,29,30, 13,30,14, 14,30,31, 14,31,15, 15,31,32, 15,32,16, 16,32,17, 16,17,1, 17,33,34, 17,34,18, 18,34,35, 18,35,19, 19,35,36, 19,36,20, 20,36,37, 20,37,21, 21,37,38, 21,38,22, 22,38,39, 22,39,23, 23,39,40, 23,40,24, 24,40,41, 24,41,25, 25,41,42, 25,42,26, 26,42,43, 26,43,27, 27,43,44, 27,44,28, 28,44,45, 28,45,29, 29,45,46, 29,46,30, 30,46,47, 30,47,31, 31,47,48, 31,48,32, 32,48,33, 32,33,17, 33,49,50, 33,50,34, 34,50,51, 34,51,35, 35,51,52, 35,52,36, 36,52,53, 36,53,37, 37,53,54, 37,54,38, 38,54,55, 38,55,39, 39,55,56, 39,56,40, 40,56,57, 40,57,41, 41,57,58, 41,58,42, 42,58,59, 42,59,43, 43,59,60, 43,60,44, 44,60,61, 44,61,45, 45,61,62, 45,62,46, 46,62,63, 46,63,47, 47,63,64, 47,64,48, 48,64,49, 48,49,33, 49,65,66, 49,66,50, 50,66,67, 50,67,51, 51,67,68, 51,68,52, 52,68,69, 52,69,53, 53,69,70, 53,70,54, 54,70,71, 54,71,55, 55,71,72, 55,72,56, 56,72,73, 56,73,57, 57,73,74, 57,74,58, 58,74,75, 58,75,59, 59,75,76, 59,76,60, 60,76,77, 60,77,61, 61,77,78, 61,78,62, 62,78,79, 62,79,63, 63,79,80, 63,80,64, 64,80,65, 64,65,49, 65,81,82, 65,82,66, 66,82,83, 66,83,67, 67,83,84, 67,84,68, 68,84,85, 68,85,69, 69,85,86, 69,86,70, 70,86,87, 70,87,71, 71,87,88, 71,88,72, 72,88,89, 72,89,73, 73,89,90, 73,90,74, 74,90,91, 74,91,75, 75,91,92, 75,92,76, 76,92,93, 76,93,77, 77,93,94, 77,94,78, 78,94,95, 78,95,79, 79,95,96, 79,96,80, 80,96,81, 80,81,65, 81,97,98, 81,98,82, 82,98,99, 82,99,83, 83,99,100, 83,100,84, 84,100,101, 84,101,85, 85,101,102, 85,102,86, 86,102,103, 86,103,87, 87,103,104, 87,104,88, 88,104,105, 88,105,89, 89,105,106, 89,106,90, 90,106,107, 90,107,91, 91,107,108, 91,108,92, 92,108,109, 92,109,93, 93,109,110, 93,110,94, 94,110,111, 94,111,95, 95,111,112, 95,112,96, 96,112,97, 96,97,81, 113,98,97, 113,99,98, 113,100,99, 113,101,100, 113,102,101, 113,103,102, 113,104,103, 113,105,104, 113,106,105, 113,107,106, 113,108,107, 113,109,108, 113,110,109, 113,111,110, 113,112,111, 113,97,112 }; shared_ptr<TriMesh> StdMeshImporter::UnitSphereMesh() { shared_ptr<TriMesh> mesh(new TriMesh()); shared_array<float> pos(new float[gNumSphereVertices*3]); memcpy(pos.get(),gSphereVertices,gNumSphereVertices*3*sizeof(float)); mesh->SetPos(pos,gNumSphereVertices); // vertices on a unit sphere are identical to their corresponding // normal mesh->SetNormals(pos); shared_ptr<IndexBuffer> idx(new IndexBuffer()); idx->Cache(gNumSphereFaces*3,gSphereFaces); mesh->AddFace(idx); return mesh; } // // unit box // static const int gNumBoxVertices = 24; static const int gNumBoxFaces = 12; static float gBoxVertices[gNumBoxVertices*3] = { -0.5f,-0.5f,0.5f, 0.5f,-0.5f, 0.5f, 0.5f,0.5f,0.5f, -0.5f,0.5f,0.5f, -0.5f,-0.5f,-0.5f, -0.5f,0.5f,-0.5f, 0.5f,0.5f,-0.5f, 0.5f,-0.5f,-0.5f, -0.5f,0.5f,-0.5f, -0.5f,0.5f,0.5f, 0.5f,0.5f,0.5f, 0.5f,0.5f,-0.5f, -0.5f,-0.5f,-0.5f, 0.5f,-0.5f,-0.5f, 0.5f,-0.5f,0.5f, -0.5f,-0.5f,0.5f, 0.5f,-0.5f,-0.5f, 0.5f,0.5f,-0.5f, 0.5f,0.5f,0.5f, 0.5f,-0.5f,0.5f, -0.5f,-0.5f,-0.5f, -0.5f,-0.5f,0.5f, -0.5f,0.5f,0.5f, -0.5f,0.5f,-0.5f }; static float gBoxNormals[gNumBoxVertices*3] = { 0.0f,0.0f,1.0f, 0.0f,0.0f,1.0f, 0.0f,0.0f,1.0f, 0.0f,0.0f,1.0f, 0.0f,0.0f,-1.0f, 0.0f,0.0f,-1.0f, 0.0f,0.0f,-1.0f, 0.0f,0.0f,-1.0f, 0.0f,1.0f,0.0f, 0.0f,1.0f,0.0f, 0.0f,1.0f,0.0f, 0.0f,1.0f,0.0f, 0.0f,-1.0f,0.0f, 0.0f,-1.0f,0.0f, 0.0f,-1.0f,0.0f, 0.0f,-1.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,0.0f,0.0f, -1.0f,0.0f,0.0f, -1.0f,0.0f,0.0f, -1.0f,0.0f,0.0f, -1.0f,0.0f,0.0f }; static float gBoxTexCoords[gNumBoxVertices*3] = { 0.0f,0.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,1.0f,0.0f, 0.0f,1.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,1.0f,0.0f, 0.0f,1.0f,0.0f, 0.0f,0.0f,0.0f, 0.0f,1.0f,0.0f, 0.0f,0.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,1.0f,0.0f, 1.0f,1.0f,0.0f, 0.0f,1.0f,0.0f, 0.0f,0.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,1.0f,0.0f, 0.0f,1.0f,0.0f, 0.0f,0.0f,0.0f, 0.0f,0.0f,0.0f, 1.0f,0.0f,0.0f, 1.0f,1.0f,0.0f, 0.0f,1.0f,0.0f }; static unsigned int gBoxFaces[gNumSphereFaces*3] = { 0,1,2, 0,2,3, 4,5,6, 4,6,7, 8,9,10, 8,10,11, 12,13,14, 12,14,15, 16,17,18, 16,18,19, 20,21,22, 20,22,23 }; shared_ptr<TriMesh> StdMeshImporter::UnitBoxMesh() { shared_ptr<TriMesh> mesh(new TriMesh()); shared_array<float> pos(new float[gNumBoxVertices*3]); memcpy(pos.get(),gBoxVertices,gNumBoxVertices*3*sizeof(float)); mesh->SetPos(pos,gNumBoxVertices); shared_array<float> normals(new float[gNumBoxVertices*3]); memcpy(normals.get(),gBoxNormals,gNumBoxVertices*3*sizeof(float)); mesh->SetNormals(normals); shared_array<float> tex(new float[gNumBoxVertices*3]); memcpy(tex.get(), gBoxTexCoords,gNumBoxVertices*3*sizeof(float)); mesh->SetTexCoords(tex); shared_ptr<IndexBuffer> idx(new IndexBuffer()); idx->Cache(gNumBoxFaces*3,gBoxFaces); mesh->AddFace(idx); return mesh; } // // unit capped cylinder // static void AddVertex(float** at, float x, float y, float z) { (**at) = x; ++(*at); (**at) = y; ++(*at); (**at) = z; ++(*at); } std::string StdMeshImporter::MangleName (const string& name, const ParameterList& parameter) { if ( (name != gCCylinderStr) || (parameter.GetSize() < 2) ) { return name; } stringstream ss; ss << gCCylinderStr; float radius; if (parameter.GetValue(parameter[0],radius)) { ss << "R=" << radius; } float length; if (parameter.GetValue(parameter[1],length)) { ss << "L=" << length; } return ss.str(); } shared_ptr<TriMesh> StdMeshImporter::UnitCCylinder(const ParameterList& parameter) { // // code adapted from ODE's drawstuff lib // // generated capped clinder with r=1 and l=1 float ccRadius = 1; float ccLength = 1; GetLog()->Debug() << "(StdMeshImporter::UnitCCylinder) paramSize=" << parameter.GetSize() << "\n"; if (parameter.GetSize() >= 2) { parameter.GetValue(parameter[0],ccRadius); parameter.GetValue(parameter[1],ccLength); } // number of sides to the cylinder (divisible by 4): const int capped_cylinder_quality = 3; const int n = capped_cylinder_quality*4; int innerLoop = (n+1); int numVertices = innerLoop * 2; numVertices += (innerLoop * (n/4) * 2); numVertices += (innerLoop * (n/4) * 2); shared_array<float> pos(new float[numVertices * 3]); shared_array<float> normals(new float[numVertices * 3]); float* cVert = pos.get(); float* cNormal = normals.get(); int i,j; float tmp,nx,start_nx,start_ny; float l = ccLength * 0.5; float a = g2PI / n; float sa = gSin(a); float ca = gCos(a); // draw cylinder body // normal vector = (0,ny,nz) float ny = 1; float nz = 0; for (i=0; i<=n; ++i) { AddVertex(&cNormal,ny,nz,0); AddVertex(&cVert,ny*ccRadius,nz*ccRadius,l); AddVertex(&cNormal,ny,nz,0); AddVertex(&cVert,ny*ccRadius,nz*ccRadius,-l); // rotate ny,nz tmp = ca * ny - sa * nz; nz = sa*ny + ca*nz; ny = tmp; } // draw first cylinder cap start_nx = 0; start_ny = 1; for (j=0; j<(n/4); ++j) { // get start_n2 = rotated start_n float start_nx2 = ca*start_nx + sa*start_ny; float start_ny2 = -sa*start_nx + ca*start_ny; // get n=start_n and n2=start_n2 nx = start_nx; ny = start_ny; nz = 0; float nx2 = start_nx2; float ny2 = start_ny2; float nz2 = 0; for (i=0; i<=n; i++) { AddVertex(&cNormal,ny2,nz2,nx2); AddVertex(&cVert,ny2*ccRadius,nz2*ccRadius,l+nx2*ccRadius); AddVertex(&cNormal,ny,nz,nx); AddVertex(&cVert,ny*ccRadius,nz*ccRadius,l+nx*ccRadius); // rotate n,n2 tmp = ca*ny - sa*nz; nz = sa*ny + ca*nz; ny = tmp; tmp = ca*ny2- sa*nz2; nz2 = sa*ny2 + ca*nz2; ny2 = tmp; } start_nx = start_nx2; start_ny = start_ny2; } // draw second cylinder cap start_nx = 0; start_ny = 1; for (j=0; j<(n/4); j++) { // get start_n2 = rotated start_n float start_nx2 = ca*start_nx - sa*start_ny; float start_ny2 = sa*start_nx + ca*start_ny; // get n=start_n and n2=start_n2 nx = start_nx; ny = start_ny; nz = 0; float nx2 = start_nx2; float ny2 = start_ny2; float nz2 = 0; for (i=0; i<=n; i++) { AddVertex(&cNormal,ny,nz,nx); AddVertex(&cVert,ny*ccRadius,nz*ccRadius,-l+nx*ccRadius); AddVertex(&cNormal,ny2,nz2,nx2); AddVertex(&cVert,ny2*ccRadius,nz2*ccRadius,-l+nx2*ccRadius); // rotate n,n2 tmp = ca*ny - sa*nz; nz = sa*ny + ca*nz; ny = tmp; tmp = ca*ny2- sa*nz2; nz2 = sa*ny2 + ca*nz2; ny2 = tmp; } start_nx = start_nx2; start_ny = start_ny2; } shared_ptr<IndexBuffer> idx(new IndexBuffer()); // triangle strip -> triangles int numFaces = (numVertices - 2); idx->EnsureFit(numFaces*3); for (i=0;i<numFaces;++i) { if (i%2) { idx->Cache(i+1); idx->Cache(i); idx->Cache(i+2); } else { idx->Cache(i); idx->Cache(i+1); idx->Cache(i+2); } } shared_ptr<TriMesh> mesh(new TriMesh()); mesh->SetPos(pos,numVertices); mesh->SetNormals(normals); mesh->AddFace(idx); mesh->SetName(MangleName(gCCylinderStr,parameter)); return mesh; } --- NEW FILE: trimesh.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: trimesh.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_TRIMESH #define OXYGEN_TRIMESH #include "indexbuffer.h" #include <list> #include <boost/shared_array.hpp> #include <boost/shared_ptr.hpp> #include <string> namespace oxygen { /** \class TriMesh (triangle mesh) encapsulates a list of vertices, texture coordinates and normals together with an associated list of index lists. Each index list additionally stores the name of a material. Triangle meshes describe arbitrary geometry. They are used for collision detection and rendering. Vertices, texture coordinates and normales are each stored as a list of floats, with three consecutive values for each vector. Indeces are stored using the IndexBuffer class as as list of unsigned int values. */ class TriMesh { public: struct Face { public: boost::shared_ptr<IndexBuffer> indeces; std::string material; public: Face(boost::shared_ptr<IndexBuffer> i, std::string m) : indeces(i), material(m) {}; }; typedef std::list<Face> TFaces; public: TriMesh(); ~TriMesh(); /** sets the list of vertices and their number*/ void SetPos(boost::shared_array<float> pos, int vertexCount); /** returns the list of vertices */ const boost::shared_array<float> GetPos() const; /** returns the number of stored vertices */ int GetVertexCount() const; /** sets the list of texture coordinates */ void SetTexCoords(boost::shared_array<float> texCoords); /** returns the list of texture coordinates */ const boost::shared_array<float> GetTexCoords() const; /** sets the list of surface normals */ void SetNormals(boost::shared_array<float> normal); /** returns the list of surface normals */ const boost::shared_array<float> GetNormals() const; /** adds a face, i.e. a list of indeces. Each consecutive triple describes one triangle */ void AddFace(boost::shared_ptr<IndexBuffer> indeces, const std::string& material = "default"); /** adds a face, i.e. a list of indeces. Each consecutive triple describes one triangle */ void AddFace(const Face& face); /** returns the list of faces */ const TFaces& GetFaces() const; /** returns the name of this trimesh */ const std::string& GetName() const; /** sets the name of this trimesh */ void SetName(const std::string& name); protected: /** the unique name of this trimesh */ std::string mName; /** the number of stored vertices */ int mVertexCount; /** the list of vertices */ boost::shared_array<float> mPos; /** the list of texture coordinates */ boost::shared_array<float> mTexCoords; /** the list of surface normals */ boost::shared_array<float> mNormal; /** the list of faces */ TFaces mFaces; }; } // namespace oxygen #endif // OXYGEN_TRIMESH |
Update of /cvsroot/simspark/simspark/spark/oxygen/physicsserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14301/physicsserver Added Files: angularmotor.cpp angularmotor.h angularmotor_c.cpp balljoint.cpp balljoint.h balljoint_c.cpp body.cpp body.h body_c.cpp bodycontroller.cpp bodycontroller.h bodycontroller_c.cpp boxcollider.cpp boxcollider.h boxcollider_c.cpp ccylindercollider.cpp ccylindercollider.h ccylindercollider_c.cpp collider.cpp collider.h collider_c.cpp collisionhandler.cpp collisionhandler.h collisionhandler_c.cpp contactjointhandler.cpp contactjointhandler.h contactjointhandler_c.cpp dragcontroller.cpp dragcontroller.h dragcontroller_c.cpp fixedjoint.cpp fixedjoint.h fixedjoint_c.cpp hinge2joint.cpp hinge2joint.h hinge2joint_c.cpp hingejoint.cpp hingejoint.h hingejoint_c.cpp joint.cpp joint.h joint_c.cpp odeobject.cpp odeobject.h odeobject_c.cpp physicsserver.cpp physicsserver.h physicsserver_c.cpp planecollider.cpp planecollider.h planecollider_c.cpp raycollider.cpp raycollider.h raycollider_c.cpp recorderhandler.cpp recorderhandler.h recorderhandler_c.cpp sliderjoint.cpp sliderjoint.h sliderjoint_c.cpp space.cpp space.h space_c.cpp spherecollider.cpp spherecollider.h spherecollider_c.cpp universaljoint.cpp universaljoint.h universaljoint_c.cpp velocitycontroller.cpp velocitycontroller.h velocitycontroller_c.cpp world.cpp world.h world_c.cpp Log Message: --- NEW FILE: recorderhandler.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: recorderhandler.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "recorderhandler.h" #include "collider.h" using namespace oxygen; using namespace boost; void RecorderHandler::HandleCollision (boost::shared_ptr<Collider> collidee, dContact& /*contact*/) { mCollisionSet.insert(weak_ptr<Collider>(collidee)); } void RecorderHandler::Clear() { mCollisionSet.clear(); } void RecorderHandler::GetParentsSupportingClass (const std::string &name, TParentList &list) { for ( RecorderHandler::TCollisionSet::const_iterator iter = mCollisionSet.begin(); iter != mCollisionSet.end(); ++iter ) { shared_ptr<Collider> collidee = make_shared(*iter); if (collidee.get() == 0) { continue; } weak_ptr<Node> parent = collidee->GetParentSupportingClass(name); if (! parent.expired()) { list.push_back(parent); } } } --- NEW FILE: recorderhandler.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: recorderhandler.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_RECORDERHANDLER_H #define OXYGEN_COLLISIONRECORDER_H #include "collisionhandler.h" #include <set> namespace oxygen { /** \class RecorderHandler is a CollisionHandler that accumulates collision information of the Collider it belongs to. It is the resonsibility of the user to reset the recorder. */ class RecorderHandler : public CollisionHandler { public: typedef std::set<boost::weak_ptr<Collider> > TCollisionSet; typedef std::list<boost::weak_ptr<Node> > TParentList; public: RecorderHandler() : CollisionHandler() {}; virtual ~RecorderHandler() {}; /** stores the collidee into the internal CollisionSet \param collidee is the geom ID of the colliders collision partner \param holds the contact points between the two affected geoms as returned from the ODE dCollide function */ virtual void HandleCollision (boost::shared_ptr<Collider> collidee, dContact& contact); /** removes all stored collisions from the recorder */ void Clear(); /** constructs a list of nodes that are parent nodes of the stored collidee nodes and are an instance of or are derived from the given class. \param name is the name of the class the parent nodes must support \param list is the list that receives the parent nodes */ void GetParentsSupportingClass(const std::string &name, TParentList &list); protected: TCollisionSet mCollisionSet; }; DECLARE_CLASS(RecorderHandler); } //namespace oxygen #endif // OXYGEN_COLLISIONRECORDER_H --- NEW FILE: physicsserver.cpp --- /* -*- mode: c++ -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: physicsserver.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "physicsserver.h" #include <ode/ode.h> using namespace oxygen; PhysicsServer::PhysicsServer() { } PhysicsServer::~PhysicsServer() { // release memory associated with ode dCloseODE(); } --- NEW FILE: contactjointhandler.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: contactjointhandler.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_CONTACTJOINTHANDLER_H #define OXYGEN_CONTACTJOINTHANDLER_H #include "collisionhandler.h" namespace oxygen { /** \class ContactJointHandler is a CollisionHandler that creates an ODE contact joint between the two bodies associated with the two affected collision geoms. */ class ContactJointHandler : public CollisionHandler { public: ContactJointHandler(); virtual ~ContactJointHandler(); /** Check if the collidee also has a ContactJoint handler registered to it. If yes, create a contact joint between the bodies corresponding to our Collider and the collidee's geom using the surface parameters stored in the mSurfaceParameter member. \param collidee is the geom ID of the colliders collision partner \param holds the contact points between the two affected geoms as returned from the ODE dCollide function */ virtual void HandleCollision (boost::shared_ptr<Collider> collidee, dContact& contact); /** the ContactJointHandler is not a symmetric handler. See CollisionHandler::IsSymmetricHandler for an explanation */ virtual bool IsSymmetricHandler() { return false; } /** sets the surface parameters for the contact joints that the CollisionHandler creates */ void SetSurfaceParameter(const dSurfaceParameters& surface); /** sets or resets a contact mode flag in the surface parameter*/ void SetContactMode(int mode, bool set); /** sets or resets the dContactBounce mode flag */ void SetContactBounceMode(bool set); /** sets the bounce value */ void SetBounceValue(float bounce); /** sets the mininum incoming velocity necessary for bounce */ void SetMinBounceVel(float vel); /** sets or resets the error reduction parameter (ERP) mode, useful to make surfaces soft */ void SetContactSoftERPMode(bool set); /** sets the contact normal error reduction parameter (ERP) */ void SetContactSoftERP(float erp); /** sets or resets the constraint force mixing mode (CFM), useful to make surfaces soft */ void SetContactSoftCFMMode(bool set); /** sets the constraint force mixing parameter (CFM) */ void SetContactSoftCFM(float cfm); /** sets or resets the force dependent contact slip mode (FDS) */ void SetContactSlipMode (bool set); /** sets the force dependent slip (FDS) */ void SetContactSlip(float slip); /** sets the Coulomb friction coefficient */ void SetContactMu(float mu); protected: f_inline float MixValues(const float v1, const float v2, const int n) const; void CalcSurfaceParam(dSurfaceParameters& surface, const dSurfaceParameters& collideeParam); protected: /** the ODE surface parameters of the created contact joint */ dSurfaceParameters mSurfaceParameter; }; DECLARE_CLASS(ContactJointHandler); } //namespace oxygen #endif // OXYGEN_CONTACTJOINTHANDLER_H --- NEW FILE: body_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: body_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "body.h" using namespace boost; using namespace oxygen; using namespace zeitgeist; using namespace salt; FUNCTION(Body,enable) { obj->Enable(); return true; } FUNCTION(Body,disable) { obj->Disable(); return true; } FUNCTION(Body,isEnabled) { return obj->IsEnabled(); } FUNCTION(Body,useGravity) { bool inB; if ( (in.GetSize() != 1) || (! in.GetValue(in.begin(),inB)) ) { return false; } obj->UseGravity(inB); return true; } FUNCTION(Body,setMassParameters) { float inMass; // total mass of the rigid body Vector3f inCenter; // mass center in body frame // 3x3 inerta tensor in body frame // [ I11(0) I12(1) I13(2) ] // [ I12(3) I22(4) I23(5) ] // [ I13(6) I23(7) I33(8) ] // float inI[9]; if ( (in.GetSize() < 11) ) { return false; } ParameterList::TVector::const_iterator iter = in.begin(); if ( (! in.AdvanceValue(iter,inMass)) || (! in.AdvanceValue(iter,inCenter)) ) { return false; } dMass mass; mass.mass = inMass; mass.c[0] = inCenter[0]; mass.c[1] = inCenter[1]; mass.c[2] = inCenter[2]; for (int i=0;i<9;++i) { if (! in.AdvanceValue(iter,mass.I[i])) { return false; } } obj->SetMassParameters(mass); return true; } FUNCTION(Body,setMass) { float inMass; if ( (in.GetSize() != 1) || (! in.GetValue(in.begin(), inMass)) ) { return false; } obj->SetMass(inMass); return true; } FUNCTION(Body,getMass) { return obj->GetMass(); } FUNCTION(Body,setSphere) { float inDensity; float inRadius; if ( (in.GetSize() != 2) || (! in.GetValue(in[0],inDensity)) || (! in.GetValue(in[1],inRadius)) ) { return false; } obj->SetSphere(inDensity,inRadius); return true; } FUNCTION(Body,setSphereTotal) { float inMassTotal; float inRadius; if ( (in.GetSize() != 2) || (! in.GetValue(in[0],inMassTotal)) || (! in.GetValue(in[1],inRadius)) ) { return false; } obj->SetSphereTotal(inMassTotal,inRadius); return true; } FUNCTION(Body,setBox) { float inDensity; Vector3f inSize; if ( (in.GetSize() <= 1) || (! in.GetValue(in[0],inDensity)) || (! in.GetValue(in[1],inSize)) ) { return false; } obj->SetBox(inDensity,inSize); return true; } FUNCTION(Body,setBoxTotal) { float inMassTotal; Vector3f inSize; if ( (in.GetSize() <= 1) || (! in.GetValue(in[0],inMassTotal)) || (! in.GetValue(in[1],inSize)) ) { return false; } obj->SetBoxTotal(inMassTotal,inSize); return true; } FUNCTION(Body,setCylinder) { float inDensity; float inRadius; float inLength; if ( (in.GetSize() != 3) || (! in.GetValue(in[0],inDensity)) || (! in.GetValue(in[1],inRadius)) || (! in.GetValue(in[2],inLength)) ) { return false; } obj->SetCylinder(inDensity,inRadius,inLength); return true; } FUNCTION(Body,setCylinderTotal) { float inMassTotal; float inRadius; float inLength; if ( (in.GetSize() != 3) || (! in.GetValue(in[0],inMassTotal)) || (! in.GetValue(in[1],inRadius)) || (! in.GetValue(in[2],inLength)) ) { return false; } obj->SetCylinderTotal(inMassTotal,inRadius,inLength); return true; } FUNCTION(Body,setCappedCylinder) { float inDensity; float inRadius; float inLength; if ( (in.GetSize() != 3) || (! in.GetValue(in[0],inDensity)) || (! in.GetValue(in[1],inRadius)) || (! in.GetValue(in[2],inLength)) ) { return false; } obj->SetCappedCylinder(inDensity,inRadius,inLength); return true; } FUNCTION(Body,setCappedCylinderTotal) { float inMassTotal; float inRadius; float inLength; if ( (in.GetSize() != 3) || (! in.GetValue(in[0],inMassTotal)) || (! in.GetValue(in[1],inRadius)) || (! in.GetValue(in[2],inLength)) ) { return false; } obj->SetCappedCylinderTotal(inMassTotal,inRadius,inLength); return true; } FUNCTION(Body,setVelocity) { Vector3f inVel; if ( (in.GetSize() == 0) || (! in.GetValue(in.begin(), inVel)) ) { return false; } obj->SetVelocity(inVel); return true; } FUNCTION(Body,setAngularVelocity) { Vector3f inVel; if ( (in.GetSize() == 1) || (! in.GetValue(in.begin(), inVel)) ) { return false; } obj->SetAngularVelocity(inVel); return true; } FUNCTION(Body,addForce) { Vector3f inForce; if ( (in.GetSize() == 0) || (! in.GetValue(in.begin(), inForce)) ) { return false; } obj->AddForce(inForce); return true; } FUNCTION(Body,addTorque) { Vector3f inTorque; if ( (in.GetSize() == 0) || (! in.GetValue(in.begin(), inTorque)) ) { return false; } obj->AddForce(inTorque); return true; } FUNCTION(Body,setPosition) { Vector3f inPos; if ( (in.GetSize() == 0) || (! in.GetValue(in.begin(), inPos)) ) { return false; } obj->AddForce(inPos); return true; } void CLASS(Body)::DefineClass() { DEFINE_BASECLASS(oxygen/ODEObject); DEFINE_FUNCTION(enable); DEFINE_FUNCTION(disable); DEFINE_FUNCTION(isEnabled); DEFINE_FUNCTION(useGravity); DEFINE_FUNCTION(setSphere); DEFINE_FUNCTION(setSphereTotal); DEFINE_FUNCTION(setBox); DEFINE_FUNCTION(setBoxTotal); DEFINE_FUNCTION(setCylinder); DEFINE_FUNCTION(setCylinderTotal); DEFINE_FUNCTION(setCappedCylinder); DEFINE_FUNCTION(setCappedCylinderTotal); DEFINE_FUNCTION(setMass); DEFINE_FUNCTION(getMass); DEFINE_FUNCTION(setVelocity); DEFINE_FUNCTION(setAngularVelocity); DEFINE_FUNCTION(addForce); DEFINE_FUNCTION(addTorque); DEFINE_FUNCTION(setPosition); DEFINE_FUNCTION(setMassParameters); } --- NEW FILE: spherecollider.cpp --- /* -*- mode: c++ -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: spherecollider.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "spherecollider.h" using namespace oxygen; using namespace salt; SphereCollider::SphereCollider() : Collider() { } void SphereCollider::SetRadius(float r) { dGeomSphereSetRadius(mODEGeom, r); } float SphereCollider::GetRadius() const { return dGeomSphereGetRadius(mODEGeom); } bool SphereCollider::ConstructInternal() { if (! Collider::ConstructInternal()) { return false; } // create a unit sphere mODEGeom = dCreateSphere(0, 1.0f); return (mODEGeom != 0); } float SphereCollider::GetPointDepth(const Vector3f& pos) { Vector3f worldPos(GetWorldTransform() * pos); return dGeomSpherePointDepth (mODEGeom,worldPos[0],worldPos[1],worldPos[2]); } --- NEW FILE: collider.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: collider.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "collider.h" #include "space.h" #include "body.h" #include "collisionhandler.h" #include <oxygen/sceneserver/scene.h> #include <zeitgeist/logserver/logserver.h> using namespace oxygen; using namespace salt; using namespace boost; using namespace std; Collider::Collider() : ODEObject(), mODEGeom(0) { } Collider::~Collider() { if (mODEGeom) { dGeomDestroy(mODEGeom); mODEGeom = 0; } } void Collider::OnLink() { ODEObject::OnLink(); if (mODEGeom == 0) { return; } // if we have a space add the geom to it dSpaceID space = GetSpaceID(); if ( (space) && (! dSpaceQuery(space, mODEGeom)) ) { dGeomSetData(mODEGeom, this); dSpaceAdd(space, mODEGeom); } // if there is a Body below our parent, link to it shared_ptr<Body> body = shared_static_cast<Body> (make_shared(GetParent())->GetChildOfClass("Body")); if (body.get() != 0) { dGeomSetBody (mODEGeom, body->GetODEBody()); } else { // no body node found, setup initial position and // orientation identical to the parent node SetRotation(GetWorldTransform()); SetPosition(Vector3f(0,0,0)); } } void Collider::OnUnlink() { ODEObject::OnUnlink(); // remove collision geometry from space dSpaceID space = GetSpaceID(); if ( (mODEGeom == 0) || (space == 0) ) { return; } if ( (space) && (dSpaceQuery(space, mODEGeom)) ) { dSpaceRemove(space, mODEGeom); } } void Collider::PrePhysicsUpdateInternal(float /*deltaTime*/) { if (GetChildSupportingClass("CollisionHandler").get() == 0) { // for convenience we add a ContactJointHandler if no // other handler is registered. This behaviour covers the // majority of all use cases and eases the creation of // Colliders. AddCollisionHandler("oxygen/ContactJointHandler"); } } dGeomID Collider::GetODEGeom() { return mODEGeom; } bool Collider::AddCollisionHandler(const std::string& handlerName) { GetCore()->New(handlerName); shared_ptr<CollisionHandler> handler = shared_dynamic_cast<CollisionHandler>(GetCore()->New(handlerName)); if (handler.get() == 0) { GetLog()->Error() << "ERROR: (Collider) Cannot create CollisionHandler " << handlerName << "\n"; return false; } return AddChildReference(handler); } void Collider::OnCollision (boost::shared_ptr<Collider> collidee, dContact& contact, ECollisionType type) { TLeafList handlers; ListChildrenSupportingClass<CollisionHandler>(handlers); for ( TLeafList::iterator iter = handlers.begin(); iter != handlers.end(); ++iter ) { shared_ptr<CollisionHandler> handler = shared_static_cast<CollisionHandler>(*iter); if ( (type == CT_SYMMETRIC) && (! handler->IsSymmetricHandler()) ) { continue; } handler->HandleCollision(collidee, contact); } } shared_ptr<Collider> Collider::GetCollider(dGeomID id) { if (id == 0) { return shared_ptr<Collider>(); } Collider* collPtr = static_cast<Collider*>(dGeomGetData(id)); if (collPtr == 0) { // we cannot use the logserver here cerr << "ERROR: (Collider) no Collider found for dGeomID " << id << "\n"; return shared_ptr<Collider>(); } shared_ptr<Collider> collider = shared_static_cast<Collider> (make_shared(collPtr->GetSelf())); if (collider.get() == 0) { // we cannot use the logserver here cerr << "ERROR: (Collider) got no shared_ptr for dGeomID " << id << "\n"; } return collider; } void Collider::SetRotation(const Matrix& rot) { dMatrix3 m; ConvertRotationMatrix(rot,m); dGeomSetRotation(mODEGeom,m); } void Collider::SetPosition(const Vector3f& pos) { Vector3f globalPos(GetWorldTransform() * pos); dGeomSetPosition (mODEGeom, globalPos[0], globalPos[1], globalPos[2]); } bool Collider::Intersects(boost::shared_ptr<Collider> collider) { if ( (mODEGeom == 0) || (collider.get() == 0) ) { return false; } dContactGeom contact; return dCollide ( mODEGeom, collider->GetODEGeom(), 1, /* ask for at most one collision point */ &contact, sizeof(contact) ) > 0; } --- NEW FILE: universaljoint_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: universaljoint_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "universaljoint.h" using namespace boost; using namespace oxygen; using namespace salt; FUNCTION(UniversalJoint,setAnchor) { Vector3f inAnchor; if ( (in.GetSize() == 0) || (! in.GetValue(in.begin(), inAnchor)) ) { return false; } obj->SetAnchor(inAnchor); return true; } FUNCTION(UniversalJoint,getAngle) { int inAxisIndex; if ( (in.GetSize() != 0) || (! in.GetValue(in.begin(), inAxisIndex)) ) { return false; } obj->GetAngle(static_cast<Joint::EAxisIndex>(inAxisIndex)); return true; } FUNCTION(UniversalJoint,getAngleRate) { int inAxisIndex; if ( (in.GetSize() != 0) || (! in.GetValue(in.begin(), inAxisIndex)) ) { return false; } obj->GetAngleRate(static_cast<Joint::EAxisIndex>(inAxisIndex)); return true; } void CLASS(UniversalJoint)::DefineClass() { DEFINE_BASECLASS(oxygen/Joint); DEFINE_FUNCTION(setAnchor); DEFINE_FUNCTION(getAngle); DEFINE_FUNCTION(getAngleRate); } --- NEW FILE: angularmotor.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: angularmotor.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "angularmotor.h" #include <zeitgeist/logserver/logserver.h> using namespace oxygen; using namespace boost; using namespace salt; AngularMotor::AngularMotor() : Joint() { } AngularMotor::~AngularMotor() { } void AngularMotor::OnLink() { dWorldID world = GetWorldID(); if (world == 0) { return; } mODEJoint = dJointCreateAMotor(world, 0); } void AngularMotor::SetMode(EMotorMode mode) { dJointSetAMotorMode(mODEJoint,mode); } AngularMotor::EMotorMode AngularMotor::GetMode() { return static_cast<EMotorMode>(dJointGetAMotorMode(mODEJoint)); } void AngularMotor::SetNumAxes(int num) { if ( (num < 0) || (num > 3) ) { return; } dJointSetAMotorNumAxes(mODEJoint, num); } int AngularMotor::GetNumAxes() { return dJointGetAMotorNumAxes(mODEJoint); } void AngularMotor::SetMotorAxis(EAxisIndex idx, EAxisAnchor anchor, const salt::Vector3f& axis) { Vector3f globalAxis = GetWorldTransform() * axis; dJointSetAMotorAxis (mODEJoint, idx, anchor, globalAxis[0], globalAxis[1], globalAxis[2]); } AngularMotor::EAxisAnchor AngularMotor::GetAxisAnchor(EAxisIndex idx) { return static_cast<EAxisAnchor>(dJointGetAMotorAxisRel (mODEJoint, idx)); } Vector3f AngularMotor::GetMotorAxis(EAxisIndex idx) { dVector3 dAxis; dJointGetAMotorAxis(mODEJoint,idx,dAxis); return Vector3f(dAxis[0],dAxis[1],dAxis[2]); } void AngularMotor::SetAxisAngle(EAxisIndex idx, float degAngle) { dJointSetAMotorAngle(mODEJoint, idx, gDegToRad(degAngle)); } float AngularMotor::GetAxisAngle(EAxisIndex idx) { return gRadToDeg(dJointGetAMotorAngle(mODEJoint, idx)); } float AngularMotor::GetAxisAngleRate(EAxisIndex idx) { return gRadToDeg(dJointGetAMotorAngleRate(mODEJoint,idx)); } void AngularMotor::SetParameter(int parameter, float value) { dJointSetAMotorParam(mODEJoint, parameter, value); } float AngularMotor::GetParameter(int parameter) { return dJointGetAMotorParam(mODEJoint, parameter); } --- NEW FILE: balljoint_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: balljoint_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "balljoint.h" using namespace boost; using namespace oxygen; using namespace salt; FUNCTION(BallJoint,setAnchor) { Vector3f inAnchor; if ( (in.GetSize() == 0) || (! in.GetValue(in.begin(), inAnchor)) ) { return false; } obj->SetAnchor(inAnchor); return true; } void CLASS(BallJoint)::DefineClass() { DEFINE_BASECLASS(oxygen/Joint); DEFINE_FUNCTION(setAnchor); } --- NEW FILE: contactjointhandler.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: contactjointhandler.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "contactjointhandler.h" #include "collider.h" #include "world.h" #include "space.h" #include <zeitgeist/logserver/logserver.h> using namespace oxygen; using namespace boost; ContactJointHandler::ContactJointHandler() : CollisionHandler() { // set up default contact surface parameters mSurfaceParameter.mode = dContactBounce; mSurfaceParameter.mu = dInfinity; mSurfaceParameter.bounce = 0.8f; mSurfaceParameter.bounce_vel = 2.0f; } ContactJointHandler::~ContactJointHandler() { } float ContactJointHandler::MixValues(const float v1, const float v2, const int n) const { switch(n) { default: case 0: // undefined, default 0 return 0.0f; case 1: // first one defined return v1; case 2: // second one defined return v2; case 3: // both defined, return average return (v1 + v2) / 2.0f; } } void ContactJointHandler::CalcSurfaceParam(dSurfaceParameters& surface, const dSurfaceParameters& collideeParam) { // init surface surface.mode = 0; // calculate average mu; mu can be dInfinity, so first multiply with // 0.5 and the sum up to avoid a range error surface.mu = mSurfaceParameter.mu*0.5f + collideeParam.mu*0.5f; // soft cfm const int nCfm = ((mSurfaceParameter.mode & dContactSoftCFM) ? 1:0) + ((collideeParam.mode & dContactSoftCFM) ? 2:0); if (nCfm>0) { surface.soft_cfm = MixValues (mSurfaceParameter.soft_cfm, collideeParam.soft_cfm, nCfm); surface.mode |= dContactSoftCFM; } // soft_erp const int nErp = ((mSurfaceParameter.mode & dContactSoftERP) ? 1:0) + ((collideeParam.mode & dContactSoftERP) ? 2:0); if (nErp>0) { surface.soft_erp = MixValues (mSurfaceParameter.soft_erp, collideeParam.soft_erp, nErp); surface.mode |= dContactSoftERP; } // bounce const int nBounce = ((mSurfaceParameter.mode & dContactBounce) ? 1:0) + ((collideeParam.mode & dContactBounce) ? 2:0); if (nBounce>0) { surface.bounce = MixValues (mSurfaceParameter.bounce, collideeParam.bounce, nBounce); surface.bounce_vel = MixValues (mSurfaceParameter.bounce_vel, collideeParam.bounce_vel, nBounce); surface.mode |= dContactBounce; } } void ContactJointHandler::HandleCollision(shared_ptr<Collider> collidee, dContact& contact) { if ( (mCollider.get() == 0) || (mWorld.get() == 0) || (mSpace.get() == 0) ) { return; } // to create a contact joint it we must have at least one body to // attach it to. dBodyID myBody = dGeomGetBody(mCollider->GetODEGeom()); dBodyID collideeBody = dGeomGetBody(collidee->GetODEGeom()); if ( (myBody == 0) && (collideeBody == 0) ) { return; } // check if the collidee has a ContactJointHandler registered to it shared_ptr<ContactJointHandler> handler = collidee->FindChildSupportingClass<ContactJointHandler>(); if (handler.get() == 0) { return; } // calculate the resulting surface parameters CalcSurfaceParam(contact.surface,handler->mSurfaceParameter); // create the contact joint and attach it to the body dJointID joint = dJointCreateContact (mWorld->GetODEWorld(), mSpace->GetODEJointGroup(), &contact); dJointAttach (joint, myBody, collideeBody); } void ContactJointHandler::SetSurfaceParameter(const dSurfaceParameters& surface) { mSurfaceParameter = surface; } void ContactJointHandler::SetContactMode(int mode, bool set) { if (set) { mSurfaceParameter.mode |= mode; } else { mSurfaceParameter.mode &= ~mode; } } void ContactJointHandler::SetContactBounceMode(bool set) { SetContactMode(dContactBounce,set); } void ContactJointHandler::SetMinBounceVel(float vel) { mSurfaceParameter.bounce_vel = std::max<float>(0.0f,vel); } void ContactJointHandler::SetBounceValue(float bounce) { mSurfaceParameter.bounce = std::max<float>(0.0f,bounce); } void ContactJointHandler::SetContactSoftERPMode(bool set) { SetContactMode(dContactSoftERP,set); } void ContactJointHandler::SetContactSoftERP(float erp) { salt::gClamp(erp,0.0f,1.0f); mSurfaceParameter.soft_erp = erp; } void ContactJointHandler::SetContactSoftCFMMode(bool set) { SetContactMode(dContactSoftCFM,set); } void ContactJointHandler::SetContactSoftCFM(float cfm) { mSurfaceParameter.soft_cfm = std::max<float>(0.0f,cfm); } void ContactJointHandler::SetContactSlipMode (bool set) { SetContactMode(dContactSlip1,set); SetContactMode(dContactSlip2,set); } void ContactJointHandler::SetContactSlip(float slip) { mSurfaceParameter.slip1 = slip; mSurfaceParameter.slip2 = slip; } void ContactJointHandler::SetContactMu(float mu) { mSurfaceParameter.mu = mu; } --- NEW FILE: joint.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2003 Koblenz University $Id: joint.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include <zeitgeist/logserver/logserver.h> #include "joint.h" #include "body.h" using namespace oxygen; using namespace boost; using namespace std; using namespace salt; Joint::Joint() : ODEObject(), mODEJoint(0) { } Joint::~Joint() { EnableFeedback(false); if (mODEJoint) { dJointDestroy(mODEJoint); mODEJoint = 0; } } void Joint::OnLink() { if (mODEJoint == 0) { return; } dJointSetData(mODEJoint, this); } shared_ptr<Joint> Joint::GetJoint(dJointID id) { if (id == 0) { return shared_ptr<Joint>(); } Joint* jointPtr = static_cast<Joint*>(dJointGetData(id)); if (jointPtr == 0) { // we cannot use the logserver here cerr << "ERROR: (Joint) no joint found for dJointID " << id << "\n"; return shared_ptr<Joint>(); } shared_ptr<Joint> joint = shared_static_cast<Joint> (make_shared(jointPtr->GetSelf())); if (joint.get() == 0) { // we cannot use the logserver here cerr << "ERROR: (Joint) got no shared_ptr for dJointID " << id << "\n"; } return joint; } void Joint::Attach(shared_ptr<Body> body1, shared_ptr<Body> body2) { if (mODEJoint == 0) { GetLog()->Error() << "(Joint) ERROR: Attach called with uninitialized ODE joint\n"; return; } const dBodyID id1 = (body1.get() == 0) ? 0 : body1->GetODEBody(); const dBodyID id2 = (body2.get() == 0) ? 0 : body2->GetODEBody(); dJointAttach(mODEJoint, id1, id2); } shared_ptr<Body> Joint::GetBody(const std::string& path) { if (path.empty()) { return shared_ptr<Body>(); } shared_ptr<Leaf> mySelf = shared_static_cast<Leaf> (make_shared(GetSelf())); shared_ptr<Leaf> leaf = GetCore()->Get(path,mySelf); if (leaf.get() == 0) { GetLog()->Error() << "(Joint) ERROR: cannot find node '" << path << "'\n"; return shared_ptr<Body>(); } shared_ptr<Body> body = shared_dynamic_cast<Body>(leaf); if (body.get() == 0) { GetLog()->Error() << "(Joint) ERROR: node '" << path << "' is not a Body node \n"; } return body; } void Joint::Attach(const std::string& path1, const std::string& path2) { shared_ptr<Body> body1 = GetBody(path1); shared_ptr<Body> body2 = GetBody(path2); Attach(body1,body2); } int Joint::GetType() { return dJointGetType(mODEJoint); } boost::shared_ptr<Body> Joint::GetBody(EBodyIndex idx) { return Body::GetBody(dJointGetBody(mODEJoint, idx)); } bool Joint::AreConnected (shared_ptr<Body> body1, shared_ptr<Body> body2) { if ( (body1.get() == 0) || (body2.get() == 0) ) { return false; } return dAreConnected(body1->GetODEBody(),body2->GetODEBody()); } bool Joint::AreConnectedExcluding (shared_ptr<Body> body1, shared_ptr<Body> body2, int joint_type) { if ( (body1.get() == 0) || (body2.get() == 0) ) { return false; } return dAreConnectedExcluding(body1->GetODEBody(),body2->GetODEBody(), joint_type); } void Joint::EnableFeedback(bool enable) { if (enable) { if (mFeedback.get() == 0) { mFeedback = shared_ptr<dJointFeedback>(new dJointFeedback()); memset(mFeedback.get(),0,sizeof(dJointFeedback)); } } else { if (mFeedback.get() != 0) { mFeedback.reset(); } } dJointSetFeedback(mODEJoint,mFeedback.get()); } bool Joint::FeedBackEnabled() { return (dJointGetFeedback(mODEJoint) != 0); } Vector3f Joint::GetFeedbackForce(EBodyIndex idx) { dJointFeedback* fb = mFeedback.get(); if (fb == 0) { return Vector3f(0,0,0); } switch (idx) { case BI_FIRST : return Vector3f( fb->f1[0], fb->f1[1], fb->f1[2] ); case BI_SECOND : return Vector3f( fb->f2[0], fb->f2[1], fb->f2[2] ); default: return Vector3f(0,0,0); } } Vector3f Joint::GetFeedbackTorque(EBodyIndex idx) { dJointFeedback* fb = mFeedback.get(); if (fb == 0) { return Vector3f(0,0,0); } switch (idx) { case BI_FIRST : return Vector3f( fb->t1[0], fb->t1[1], fb->t1[2] ); case BI_SECOND : return Vector3f( fb->t2[0], fb->t2[1], fb->t2[2] ); default: return Vector3f(0,0,0); } } void Joint::SetBounce(EAxisIndex idx, float bounce) { SetParameter(dParamBounce + (idx * dParamGroup),bounce); } float Joint::GetBounce(EAxisIndex idx) { return GetParameter(dParamBounce + (idx * dParamGroup)); } void Joint::SetLowStopPos(EAxisIndex idx, float pos) { SetParameter(dParamLoStop + (idx * dParamGroup), pos); } float Joint::GetLowStopPos(EAxisIndex idx) { return GetParameter(dParamLoStop + (idx * dParamGroup)); } void Joint::SetHighStopPos(EAxisIndex idx, float pos) { SetParameter(dParamHiStop + (idx * dParamGroup), pos); } float Joint::GetHighStopPos(EAxisIndex idx) { return GetParameter(dParamHiStop + (idx * dParamGroup)); } void Joint::SetLowStopDeg(EAxisIndex idx, float deg) { SetParameter(dParamLoStop + (idx * dParamGroup), gDegToRad(deg)); } float Joint::GetLowStopDeg(EAxisIndex idx) { return gRadToDeg(GetParameter(dParamLoStop + (idx * dParamGroup))); } void Joint::SetHighStopDeg(EAxisIndex idx, float deg) { SetParameter(dParamHiStop + (idx * dParamGroup), gDegToRad(deg)); } float Joint::GetHighStopDeg(EAxisIndex idx) { return gRadToDeg(GetParameter(dParamHiStop + (idx * dParamGroup))); } void Joint::SetCFM(EAxisIndex idx, float cfm) { SetParameter(dParamCFM + (idx * dParamGroup), cfm); } float Joint::GetCFM(EAxisIndex idx) { return GetParameter(dParamCFM + (idx * dParamGroup)); } void Joint::SetStopCFM(EAxisIndex idx, float cfm) { SetParameter(dParamStopCFM + (idx * dParamGroup), cfm); } float Joint::GetStopCFM(EAxisIndex idx) { return GetParameter(dParamStopCFM + (idx * dParamGroup)); } void Joint::SetStopERP(EAxisIndex idx, float erp) { SetParameter(dParamStopERP + (idx * dParamGroup), erp); } float Joint::GetStopERP(EAxisIndex idx) { return GetParameter(dParamStopERP + (idx * dParamGroup)); } void Joint::SetSuspensionERP(EAxisIndex idx, float erp) { SetParameter(dParamSuspensionERP + (idx * dParamGroup), erp); } float Joint::GetSuspensionERP(EAxisIndex idx) { return GetParameter(dParamSuspensionERP + (idx * dParamGroup)); } void Joint::SetSuspensionCFM(EAxisIndex idx, float cfm) { SetParameter(dParamSuspensionCFM + (idx * dParamGroup), cfm); } float Joint::GetSuspensionCFM(EAxisIndex idx) { return GetParameter(dParamSuspensionCFM + (idx * dParamGroup)); } void Joint::SetLinearMotorVelocity(EAxisIndex idx, float vel) { SetParameter(dParamVel + (idx * dParamGroup), vel); } float Joint::GetLinearMotorVelocity(EAxisIndex idx) { return GetParameter(dParamVel + (idx * dParamGroup)); } void Joint::SetAngularMotorVelocity(EAxisIndex idx, float deg) { SetParameter(dParamVel + (idx * dParamGroup), gDegToRad(deg)); } float Joint::GetAngularMotorVelocity(EAxisIndex idx) { return gRadToDeg(GetParameter(dParamVel + (idx * dParamGroup))); } void Joint::SetMaxMotorForce(EAxisIndex idx, float f) { SetParameter(dParamFMax + (idx * dParamGroup), f); } float Joint::GetMaxMotorForce(EAxisIndex idx) { return GetParameter(dParamFMax + (idx * dParamGroup)); } --- NEW FILE: odeobject.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: odeobject.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_ODEOBJECT_H #define OXYGEN_ODEOBJECT_H #include <oxygen/sceneserver/basenode.h> #include <ode/ode.h> namespace oxygen { class Space; class World; /** ODEObject is the base of all classes encapsulating ODE concepts */ class ODEObject : public BaseNode { public: // // Functions // ODEObject() : BaseNode() {}; virtual ~ODEObject() {}; protected: /** returns the world node */ boost::shared_ptr<World> GetWorld(); /** returns the space node */ boost::shared_ptr<Space> GetSpace(); /** returns the ODE world handle */ dWorldID GetWorldID(); /** returns the ODE space handle */ dSpaceID GetSpaceID(); /** converts the rotation part of a salt::Matrix to an ODE dMatrix3 */ void ConvertRotationMatrix(const salt::Matrix& rot, dMatrix3& matrix); }; DECLARE_ABSTRACTCLASS(ODEObject); } //namespace oxygen #endif //OXYGEN_ODEOBJECT_H --- NEW FILE: ccylindercollider.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: ccylindercollider.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_CCYLINDERCOLLIDER_H #define OXYGEN_CCYLINDERCOLLIDER_H #include "collider.h" namespace oxygen { /** CCylinderCollider encapsulates an ODE capped cylinder geometry object. A capped cylinder is like a normal cylinder except it has half-sphere caps at its ends. This feature makes the internal collision detection code particularly fast and accurate. */ class CCylinderCollider : public Collider { // // Functions // public: CCylinderCollider(); /** sets the parameters of the capped cylinder. \param radius is the radius of the caps, and of the cylinder itself \param length is the height of the cylinder, not counting the caps */ void SetParams(float radius, float length); /** sets the radius of the capped cylinder */ void SetRadius(float radius); /** sets the length of the capped cylinder */ void SetLength(float length); /** gets the radius and the length of the capped cylinder */ void GetParams(float& radius, float& length); /** returns the radius of the capped cylinder */ float GetRadius(); /** return the length of the capped cylinder */ float GetLength(); /** returns the depth of the given relative position in the managed capped cylinder geom. Points inside the geom will have positive depth, points outside it will have negative depth, and points on the surface will have zero depth. */ float GetPointDepth(const salt::Vector3f& pos); protected: /** constructs a default capped cylinder with an radius of 1 and a length of 1 */ virtual bool ConstructInternal(); }; DECLARE_CLASS(CCylinderCollider); } //namespace oxygen #endif //OXYGEN_CCYLINDERCOLLIDER_H --- NEW FILE: joint.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: joint.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_JOINT_H #define OXYGEN_JOINT_H #include "odeobject.h" namespace oxygen { class Body; /** \class Joint encapsulates an ODE joint object. A joint is a relationship (a constraint) that is enforced between two bodies so that they can only have certain positions and orientations relative to each other. Note that the joint geometry parameter setting functions should only be called after the joint has been attached to bodies, and those bodies have been correctly positioned, otherwise the joint may not be initialized correctly. If the joint is not already attached, these functions will do nothing. The default anchor for all joints is global (0,0,0). The default axis for all joints is global (1,0,0). There are no functions to set joint angles or positions (or their rates) directly, instead you must set the corresponding body positions and velocities. */ class Joint : public ODEObject { public: enum EBodyIndex { BI_FIRST = 0, BI_SECOND = 1 }; enum EAxisIndex { AI_FIRST = 0, AI_SECOND = 1, AI_THIRD = 2 }; Joint(); virtual ~Joint(); /** attaches the joint to some new bodies. If the joint is already attached, it will be detached from the old bodies first. To attach this joint to only one body, set body1 or body2 to null. A null body refers to the static environment. Setting both bodies to zero puts the joint into "limbo", i.e. it will have no effect on the simulation. */ virtual void Attach(boost::shared_ptr<Body> body1, boost::shared_ptr<Body> body2); /** attaches the joint to some new bodies, that are given as path expressions. These path expressions are allowed to be relative to this joint node. */ void Attach(const std::string& path1, const std::string& path2); /** returns one of the bodies that this joint connects, according to the given EBodyIndex */ boost::shared_ptr<Body> GetBody(EBodyIndex idx); /** returns the Joint node corresponding to the given ODE joint */ static boost::shared_ptr<Joint> GetJoint(dJointID id); /** returns the type of the managed ODE joint, possible return values are dJointTypeNone, dJointTypeBall, dJointTypeHinge, dJointTypeSlider, dJointTypeContact, dJointTypeUniversal, dJointTypeHinge2, dJointTypeFixed or dJointTypeAMotor. */ int GetType(); /** returns true if the two given bodies are connected by a joint */ static bool AreConnected (boost::shared_ptr<Body> body1, boost::shared_ptr<Body> body2); /** returns true if the two given bodies are connected together by a joint that does not have the given joint type. For possible joint type constants see GetType() */ static bool AreConnectedExcluding (boost::shared_ptr<Body> body1, boost::shared_ptr<Body> body2, int joint_type); /** during the world time step, the forces that are applied by each joint are added directly to the joined bodies, and the user normally has no way of telling which joint contributed how much force. If this information is desired the joint can be enabled to collect feedback information. By default a joint does not collect any feedback information. */ void EnableFeedback(bool enable); /** returns true if the joint is set to collect feedback information */ bool FeedBackEnabled(); /** queries the force that the joint applied to one body attached to it during the last timestep. */ salt::Vector3f GetFeedbackForce(EBodyIndex idx); /** queries the torque that the joint applied to one body attached to it during the last timestep. */ salt::Vector3f GetFeedbackTorque(EBodyIndex idx); /** sets the bouncyness of the stops. This is a restitution parameter in the range 0..1. 0 means the stops are not bouncy at all, 1 means maximum bouncyness. */ void SetBounce(EAxisIndex idx, float bounce); /** returns the bouncyness of the stops */ float GetBounce(EAxisIndex idx); /** sets the low stop angle in degrees, this stop must be greater than -180 to be effective */ void SetLowStopDeg(EAxisIndex idx, float deg); /** returns the low stop angle in degrees */ float GetLowStopDeg(EAxisIndex idx); /** sets the high stop angle in degrees, this stop must be less than +180 to be effective */ void SetHighStopDeg(EAxisIndex idx, float deg); /** returns the high stop angle in degrees */ float GetHighStopDeg(EAxisIndex idx); /** sets the low stop position */ void SetLowStopPos(EAxisIndex idx, float deg); /** returns the low stop position */ float GetLowStopPos(EAxisIndex idx); /** sets the high stop position */ void SetHighStopPos(EAxisIndex idx, float deg); /** returns the high stop position */ float GetHighStopPos(EAxisIndex idx); /** the constraint force mixing (CFM) value used when not at a stop */ void SetCFM(EAxisIndex idx, float cfm); /** returns the constraint force mixing value used when not a a stop */ float GetCFM(EAxisIndex idx); /** sets the constraint force mixing (CFM) value used by the stops. Together with the ERP value this can be used to get spongy or soft stops. This is intended for unpowered joints, it does not really work as expected when a powered joint reaches its limit. */ void SetStopCFM(EAxisIndex idx, float cfm); /** returns the constraint force mixing value used by the stops */ float GetStopCFM(EAxisIndex idx); /** sets the error reduction parameter (ERP) used by the stops. */ void SetStopERP(EAxisIndex idx, float erp); /** returns the error reduction parameter used by the stops */ float GetStopERP(EAxisIndex idx); /** sets the suspension error reduction parameter (ERP). As of ode 0.039 this is only implemented on the hinge-2 joint. */ void SetSuspensionERP(EAxisIndex idx, float erp); /** returns the suspension error reduction parameter (ERP). As of ode 0.039 this is only implemented on the hinge-2 joint. */ float GetSuspensionERP(EAxisIndex idx); /** sets the suspension constraint force mixing value. As of ode 0.039 this is only implemented on the hinge-2 joint. */ void SetSuspensionCFM(EAxisIndex idx, float cfm); /** returns the suspension constraint force mixing value. As of ode 0.039 this is only implemented on the hinge-2 joint. */ float GetSuspensionCFM(EAxisIndex idx... [truncated message content] |
From: Markus R. <rol...@us...> - 2005-12-05 21:17:01
|
Update of /cvsroot/simspark/simspark/spark/oxygen/monitorserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14301/monitorserver Added Files: custommonitor.cpp custommonitor.h custommonitor_c.cpp monitorcmdparser.cpp monitorcmdparser.h monitorcmdparser_c.cpp monitoritem.h monitoritem_c.cpp monitorserver.cpp monitorserver.h monitorserver_c.cpp monitorsystem.cpp monitorsystem.h monitorsystem_c.cpp Log Message: --- NEW FILE: monitorcmdparser.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: monitorcmdparser.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_MONITORCMDPARSER_H #define OXYGEN_MONITORCMDPARSER_H #include <zeitgeist/leaf.h> #include <oxygen/gamecontrolserver/predicate.h> namespace oxygen { class MonitorCmdParser : public zeitgeist::Leaf { public: MonitorCmdParser(); virtual ~MonitorCmdParser(); /** This function is called from the monitor server implementation to parse any command strings received from the monitor client process */ virtual void ParseMonitorMessage(const std::string& data) = 0; }; } // namespace oxygen DECLARE_ABSTRACTCLASS(MonitorCmdParser); #endif // OXYGEN_MONITORCMDPARSER_H --- NEW FILE: monitorsystem.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: monitorsystem.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "monitorsystem.h" using namespace oxygen; MonitorSystem::MonitorSystem() : Node() { } MonitorSystem::~MonitorSystem() { } --- NEW FILE: monitorcmdparser_c.cpp --- /* -*- mode: c++; c-basic-indent: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: monitorcmdparser_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "monitorcmdparser.h" using namespace oxygen; void CLASS(MonitorCmdParser)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Leaf); } --- NEW FILE: monitorsystem_c.cpp --- /* -*- mode: c++; c-basic-indent: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: monitorsystem_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "monitorsystem.h" using namespace oxygen; void CLASS(MonitorSystem)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Leaf); } --- NEW FILE: monitorserver_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: monitorserver_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "monitorserver.h" using namespace oxygen; using namespace std; FUNCTION(MonitorServer,registerMonitorSystem) { string inMonitorSysName; return ( (in.GetSize() == 1) && (in.GetValue(in.begin(), inMonitorSysName)) && (obj->RegisterMonitorSystem(inMonitorSysName)) ); } FUNCTION(MonitorServer,registerMonitorItem) { string inMonitorItemName; return ( (in.GetSize() == 1) && (in.GetValue(in.begin(), inMonitorItemName)) && (obj->RegisterMonitorItem(inMonitorItemName)) ); } void CLASS(MonitorServer)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Node); DEFINE_FUNCTION(registerMonitorSystem); DEFINE_FUNCTION(registerMonitorItem); } --- NEW FILE: monitoritem.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: monitoritem.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_MONITORITEM_H #define OXYGEN_MONITORITEM_H #include <zeitgeist/leaf.h> #include <oxygen/gamecontrolserver/predicate.h> namespace oxygen { class MonitorItem : public zeitgeist::Leaf { public: MonitorItem() : Leaf() {} virtual ~MonitorItem() {} /** This function is called once for every MonitorSystem each time * a new client connects. It should append predicates to a list * that is sent using the active monitor */ virtual void GetInitialPredicates(PredicateList& pList) = 0; /** This function will be called periodically to append predicates to a list that is sent using the active monitor */ virtual void GetPredicates(PredicateList& pList) = 0; }; DECLARE_ABSTRACTCLASS(MonitorItem); } // namespace oxygen #endif // OXYGEN_MONITORITEM_H --- NEW FILE: custommonitor.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: custommonitor.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "custommonitor.h" using namespace oxygen; CustomMonitor::CustomMonitor() : zeitgeist::Leaf() { } CustomMonitor::~CustomMonitor() { } --- NEW FILE: custommonitor_c.cpp --- /* -*- mode: c++; c-basic-indent: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: custommonitor_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "custommonitor.h" using namespace oxygen; void CLASS(CustomMonitor)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Leaf); } --- NEW FILE: custommonitor.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: custommonitor.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_CUSTOMMONITOR_H #define OXYGEN_CUSTOMMONITOR_H #include <zeitgeist/leaf.h> #include <oxygen/gamecontrolserver/predicate.h> namespace oxygen { class CustomMonitor : public zeitgeist::Leaf { public: CustomMonitor(); virtual ~CustomMonitor(); /** This function will be called be called periodically from the monitor implementation to do any monitor updates. Custom predicates that the Monitor client receives are passed as a PredicateList */ virtual void ParseCustomPredicates(const oxygen::PredicateList& pList) = 0; }; } // namespace oxygen DECLARE_ABSTRACTCLASS(CustomMonitor); #endif // OXYGEN_CUSTOMMONITOR_H --- NEW FILE: monitoritem_c.cpp --- /* -*- mode: c++; c-basic-indent: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: monitoritem_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "monitoritem.h" using namespace oxygen; void CLASS(MonitorItem)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Leaf); } --- NEW FILE: monitorserver.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: monitorserver.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_MONITORSERVER_H #define OXYGEN_MONITORSERVER_H #include <zeitgeist/class.h> #include <zeitgeist/node.h> #include "monitorsystem.h" namespace oxygen { class MonitorServer : public zeitgeist::Node { public: MonitorServer(); virtual ~MonitorServer(); // one note about std::string. This class is capable of handling // binary data (i.e. not NULL terminated strings). Use the // std::string(basic_string(const charT* s, size_type n) // constructor to construct a string containing binary data and // the const charT* data() member to access binary data. /** This function creates an instance of class 'monitorSysName' * and adds it as a child node below this server */ bool RegisterMonitorSystem(const std::string& monitorSysName); /** This function creates an instance of class 'monitorItem' and adds it as a child node below this server */ bool RegisterMonitorItem(const std::string& monitorItemName); /** the following set of functions if called by the SpadesServer */ /** This function is called once for every monitor. It should * return any header/setup information that is needed. */ std::string GetMonitorHeaderInfo(); /** This function will be called periodically to get information * about the current state of the world. The format is completely * determined by what the monitors will expect; no processing is * done by the simulation engine */ std::string GetMonitorInfo(); /** If a monitor sends information to the world model, this * function is called to process it. */ void ParseMonitorMessage(const std::string& data); protected: /** returns a shared_ptr to the first registered MonitorSystem */ boost::shared_ptr<MonitorSystem> GetMonitorSystem(); /** collects a list of predicates from all registered MonitorItems */ void CollectItemPredicates(bool initial, PredicateList& pList); private: }; DECLARE_CLASS(MonitorServer); } // namespace oxygen #endif // OXYGEN_MONITORSERVER_H --- NEW FILE: monitorsystem.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: monitorsystem.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_MONITORSYSTEM_H #define OXYGEN_MONITORSYSTEM_H #include <zeitgeist/class.h> #include <zeitgeist/node.h> #include <oxygen/gamecontrolserver/predicate.h> namespace oxygen { class MonitorSystem : public zeitgeist::Node { public: MonitorSystem(); virtual ~MonitorSystem(); // one note about std::string. This class is capable of handling // binary data (i.e. not NULL terminated strings). Use the // std::string(basic_string(const charT* s, size_type n) // constructor to construct a string containing binary data and // the const charT* data() member to access binary data. /** This function is called once for every MonitorSystem each time * a new client connects. It should return any header/setup * information that is needed. * \param items holds a list of additional name value * pairs. These predicates are collected from MonitorItem objects * registered to the MonitorServer. The monitor should transfer * them to the client if possible. */ virtual std::string GetMonitorHeaderInfo(const PredicateList& pList) = 0; /** This function will be called periodically to get information * about the current state of the world. * \param items holds a list of additional name value pairs. These * predicates are collected from MonitorItem objects registered to * the MonitorServer. The monitor should transfer them to the * client if possible. */ virtual std::string GetMonitorInfo(const PredicateList& pList) = 0; /** If a monitor sends information to the world model, this * function is called to process it. */ virtual void ParseMonitorMessage(const std::string& /* data */) = 0; }; DECLARE_ABSTRACTCLASS(MonitorSystem); } // namespace oxygen #endif // OXYGEN_MONITORSYSTEM_H --- NEW FILE: monitorcmdparser.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: monitorcmdparser.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "monitorcmdparser.h" using namespace oxygen; MonitorCmdParser::MonitorCmdParser() : zeitgeist::Leaf() { } MonitorCmdParser::~MonitorCmdParser() { } --- NEW FILE: monitorserver.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: monitorserver.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include <zeitgeist/logserver/logserver.h> #include "monitorserver.h" #include "monitoritem.h" using namespace oxygen; using namespace boost; using namespace std; MonitorServer::MonitorServer() : Node() { } MonitorServer::~MonitorServer() { } bool MonitorServer::RegisterMonitorSystem(const std::string& monitorSysName) { // check if a monitor system of the requested type was already created shared_ptr<MonitorSystem> monitorSys = shared_dynamic_cast<MonitorSystem>(GetChildOfClass(monitorSysName)); if (monitorSys.get() != 0) { return true; } // create the monitor system monitorSys = shared_dynamic_cast<MonitorSystem>(GetCore()->New(monitorSysName)); if (monitorSys.get() == 0) { GetLog()->Error() << "ERROR: (MonitorServer) Cannot create monitor system '" << monitorSysName << "'" << std::endl; return false; } // link the monitor system in the hierarchy monitorSys->SetName(monitorSysName); if (! AddChildReference(monitorSys)) { GetLog()->Error() << "ERROR: (MonitorServer) Cannot link the monitor system '" << monitorSysName << "' to the hierarchy\n"; return false; } GetLog()->Debug() << "(MonitorServer) Registered monitor system '" << monitorSysName << "'\n"; return true; } bool MonitorServer::RegisterMonitorItem(const std::string& monitorItemName) { // check if a monitor item of the requested type was already created shared_ptr<MonitorItem> monitorItem = shared_dynamic_cast<MonitorItem>(GetChildOfClass(monitorItemName)); if (monitorItem.get() != 0) { return true; } // create the monitor item monitorItem = shared_dynamic_cast<MonitorItem>(GetCore()->New(monitorItemName)); if (monitorItem.get() == 0) { GetLog()->Error() << "ERROR: (MonitorServer) Cannot create monitor item '" << monitorItemName << "'" << std::endl; return false; } // link the monitor item in the hierarchy monitorItem->SetName(monitorItemName); if (! AddChildReference(monitorItem)) { GetLog()->Error() << "ERROR: (MonitorServer) Cannot link the monitor item '" << monitorItemName << "' to the hierarchy\n"; return false; } GetLog()->Debug() << "(MonitorServer) Registered monitor item '" << monitorItemName << "'\n"; return true; } boost::shared_ptr<MonitorSystem> MonitorServer::GetMonitorSystem() { return shared_static_cast<MonitorSystem> ( FindChildSupportingClass<MonitorSystem>() ); } void MonitorServer::CollectItemPredicates(bool initial, PredicateList& pList) { Leaf::TLeafList itemList; ListChildrenSupportingClass<MonitorItem>(itemList); for ( Leaf::TLeafList::const_iterator iter = itemList.begin(); iter != itemList.end(); ++iter ) { shared_ptr<MonitorItem> item = shared_static_cast<MonitorItem>(*iter); if (initial) { item->GetInitialPredicates(pList); } else { item->GetPredicates(pList); } } } string MonitorServer::GetMonitorHeaderInfo() { shared_ptr<MonitorSystem> monitorSystem = GetMonitorSystem(); if (monitorSystem.get() == 0) { GetLog()->Warning() << "WARNING: (MonitorServer) Monitor System missing.\n"; return string(); } PredicateList pList; CollectItemPredicates(true,pList); return monitorSystem->GetMonitorHeaderInfo(pList); } string MonitorServer::GetMonitorInfo() { shared_ptr<MonitorSystem> monitorSystem = GetMonitorSystem(); if (monitorSystem.get() == 0) { return string(); } PredicateList pList; CollectItemPredicates(false,pList); return monitorSystem->GetMonitorInfo(pList); } void MonitorServer::ParseMonitorMessage(const string& data) { shared_ptr<MonitorSystem> monitorSystem = GetMonitorSystem(); if (monitorSystem.get() != 0) { monitorSystem->ParseMonitorMessage(data); } } |
From: Markus R. <rol...@us...> - 2005-12-05 21:16:59
|
Update of /cvsroot/simspark/simspark/spark/oxygen/gamecontrolserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14301/gamecontrolserver Added Files: actionobject.h actionobject_c.cpp baseparser.h baseparser_c.cpp gamecontrolserver.cpp gamecontrolserver.h gamecontrolserver_c.cpp predicate.cpp predicate.h Log Message: --- NEW FILE: actionobject.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: actionobject.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_ACTIONOBJECT_H #define OXYGEN_ACTIONOBJECT_H #include <zeitgeist/object.h> #include <zeitgeist/class.h> namespace oxygen { #if 0 } #endif class ActionObject : public zeitgeist::Object { public: typedef std::list<boost::shared_ptr<ActionObject> > TList; public: ActionObject(const std::string& predicate) : Object(), mPredicate(predicate) {} virtual ~ActionObject() {} //! returns the described predicate std::string GetPredicate() { return mPredicate; } protected: //! the predicate a derived ActionObject describes std::string mPredicate; }; DECLARE_ABSTRACTCLASS(ActionObject); } // namespace oxygen #endif // OXYGEN_ACTIONOBJECT_H --- NEW FILE: gamecontrolserver_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: gamecontrolserver_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "gamecontrolserver.h" using namespace oxygen; using namespace std; FUNCTION(GameControlServer,initParser) { string inParserName; return( (in.GetSize() == 1) && (in.GetValue(in.begin(),inParserName)) && (obj->InitParser(inParserName)) ); } FUNCTION(GameControlServer,initEffector) { string inEffectorName; if ( (in.GetSize() != 1) || (! in.GetValue(in.begin(),inEffectorName)) ) { return false; } obj->InitEffector(inEffectorName); return true; } FUNCTION(GameControlServer,initControlAspect) { string inAspectName; return( (in.GetSize() == 1) && (in.GetValue(in.begin(),inAspectName)) && (obj->InitControlAspect(inAspectName)) ); } void CLASS(GameControlServer)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Node); DEFINE_FUNCTION(initParser); DEFINE_FUNCTION(initEffector); DEFINE_FUNCTION(initControlAspect); } --- NEW FILE: predicate.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2004 RoboCup Soccer Server 3D Maintenance Group $Id: predicate.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_PREDICATE_H #define OXYGEN_PREDICATE_H #include <list> #include <string> #include <functional> #include <boost/any.hpp> #include <salt/vector.h> #include <zeitgeist/logserver/logserver.h> namespace oxygen { /** \class Predicate encapsulates a predicate name together with its list of parameters. It is used as an internal representation for commands issued by agents and is interpreted by Effector classes. A BaseParser object is responsible to translate the received agent commands into a list of Predicates. An Effector is therefore independent from the command format used between an agent and the simulator. Predicates are further used to collect sensor data from the agents perceptors. A BaseParser is then used to translate these percepts into the format used to describe them to the corresponding agent. Again, the Perceptor is independent from the format used to transmit its data to the agent. */ class Predicate { public: /** \class Iterator encapsulates a ParameterList::TVectr::const_iterator together with a reference to the ParameterList the iterator belongs to. It tries to mimic the behaviour of an STL iterator as much as possible. This class is necessary because it is not sufficient for the FindParameter method to return a single iterator without the corresponding list as it is possible for list to be nested. A subsequent GetValue method would not be able to test if the end of a TParameterList is reached without knowing the list an iterator belongs to. */ struct Iterator { public: /** constructs an Iterator pointing to element i of list l */ Iterator(const zeitgeist::ParameterList* l, zeitgeist::ParameterList::TVector::const_iterator i); /** constructs an Iterator pointing to the first element of list l */ Iterator::Iterator(const zeitgeist::ParameterList* l); /** constructs an Iterator pointing to the first element of predicate::parameter */ Iterator(const Predicate& predicate); /** construct an Iterator pointing to Predicate::nullParamList. This empty static parameter list acts as a null element and avoids special cases for list==0 in the Iterator implementation. */ Iterator(); /** aeturns the element this Iterator points to */ const boost::any& operator * () const; /** advances this Iterator on element if possible */ void operator ++ (); /** constructs an Iterator pointing to the first element of the associated list */ Iterator begin() const; /** constructs an Iterator pointing to the end() element of the associated list */ Iterator end() const; /** \returns true if this Iterator and i are not identical */ bool operator != (const Iterator& i) const; /** \returns true if this Iterator and i are identical */ bool operator == (const Iterator& i) const; /** \returns a reference to the encapuslated iterator */ const zeitgeist::ParameterList::TVector::const_iterator& GetIterator() const; /** \returns a reference to the encapsulated iterator */ zeitgeist::ParameterList::TVector::const_iterator& GetIterator(); /** \returns a pointer to the associated list */ const zeitgeist::ParameterList* GetList() const; protected: /** the associated list */ const zeitgeist::ParameterList* list; /** the encapsulated iterator */ zeitgeist::ParameterList::TVector::const_iterator iter; }; public: const Iterator begin() const { return Iterator(¶meter,parameter.begin()); } /** find a parameter with a given name. For this method, we assume that parameters are represented by lists consisting of a name (a string) and (a number of) values. An example for the predicate init: init.name = "init"; init.parameter = [["teamname", "RoboLog"], ["unum", 1]]; The part after init is the list of parameters. To extract the teamname, do something like Predicate::iterator iter(myPredicate); if (FindParameter(iter, "teamname")) { GetValue(iter,name); } \param iter on success, iter will point to the first value of the parameter you are looking for. It will be unchanged otherwise. \param name Name of the parameter to find. \return true if parameter name was found. */ bool FindParameter(Iterator& iter, const std::string& name) const; /** finds and returns the first value of a parameter with a given name. This method tries to cover the most common use case of a ParameterList. It assumes that the parameters are a set lists consisting of name value pairs, e.g. for the predicate init init.name = "init"; init.parameter = [["teamname", "RoboLog"], ["unum", 1]]; For parameter entries with more than one value per parameter use the generic FindParameter/GetValue functions. \param name Name of the parameter to find. \param value reference to the value that will receive the parameter value on success \return true if parameter name was found. */ template<typename T> f_inline bool GetValue(const Iterator& iter, const std::string& name, T& value) const { Iterator tmp(iter); return AdvanceValue(tmp,name,value); } /** finds and returns the first value of a parameter with a given name. On success value contains the first parameter value and iter points to the second parameter value */ template<typename T> f_inline bool AdvanceValue(Iterator& iter, const std::string&name, T& value) const { if (! FindParameter(iter,name)) { return false; } return AdvanceValue(iter,value); } /** AdvanceValue tries to cast the parameter at iter to a value of type T. If successful it returns true, assigns the casted parameter to value and increments the iterator iter. Otherwise false is returned and value and iter are unchanged. */ template<typename T> f_inline bool AdvanceValue(Iterator& iter, T& value) const { return iter.GetList()->AdvanceValue(iter.GetIterator(),value); } /** GetValue has the same semantics as AdvanceValue except that it takes a const reference to iter that it does not increment. */ template<typename T> f_inline bool GetValue(const Iterator& iter, T& value) const { return iter.GetList()->GetValue(iter.GetIterator(),value); } template<typename T> f_inline bool GetAnyValue(const Iterator& iter, T& value) const { return iter.GetList()->GetAnyValue(iter.GetIterator(),value); } /** tries to inteprete the value iter points to as a ParameterList and points iter to it's first element. Returns true on success */ bool DescentList(Iterator& iter) const; public: /** the name of this predicate */ std::string name; /** the list of parameter values */ zeitgeist::ParameterList parameter; protected: static const zeitgeist::ParameterList nullParamList; }; /** A functional class to find a specific parameter for use as STL predicate. */ class ParameterName : public std::binary_function<boost::any,std::string,bool> { public: bool operator()(const boost::any& param, const std::string& pred) const; }; class PredicateList { public: typedef std::list<Predicate> TList; public: PredicateList(); virtual ~PredicateList(); /** returns an iterator pointing at the first contained Predicate */ TList::const_iterator begin() const; /** returns an iterator pointing at the last contained Predicate */ TList::const_iterator end() const; /** returns the number of values contained in the managed sequence */ int GetSize() const; /** removes all contained Predicates */ void Clear(); Predicate& AddPredicate(); protected: TList mList; }; } // namespace oxygen #endif // OXYGEN_PREDICATE_H --- NEW FILE: baseparser.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: baseparser.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_BASEPARSER_H #define OXYGEN_BASEPARSER_H #include <zeitgeist/class.h> #include <zeitgeist/node.h> #include "predicate.h" namespace oxygen { /** \class BaseParser defines the interface for a parser and generator that is used with the GameControlServer. A BaseParser is responsible to parse a string into a list of predicates (see \class Predicate) and to assemble a string representing a given list of predicates. */ class BaseParser : public zeitgeist::Leaf { public: /** parses the \param input string into a list of Predicates */ virtual boost::shared_ptr<PredicateList> Parse(const std::string& input) = 0; /** generates a string representing the given \param input list of predicates */ virtual std::string Generate(boost::shared_ptr<PredicateList> input) = 0; }; DECLARE_ABSTRACTCLASS(BaseParser); } // namespace oxygen #endif // OXYGEN_BASEPARSER_H --- NEW FILE: predicate.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: predicate.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "predicate.h" using namespace zeitgeist; using namespace oxygen; using namespace boost; using namespace std; /** The null element for Predicate::Iterator */ const zeitgeist::ParameterList Predicate::nullParamList; Predicate::Iterator::Iterator(const ParameterList* l, ParameterList::TVector::const_iterator i) : list(l),iter(i) {}; Predicate::Iterator::Iterator(const ParameterList* l) : list(l),iter(l->begin()) {} Predicate::Iterator::Iterator(const Predicate& predicate) : list(&predicate.parameter), iter(predicate.parameter.begin()) {} Predicate::Iterator::Iterator() : list(&nullParamList), iter(nullParamList.begin()) {}; const boost::any& Predicate::Iterator::operator * () const { return (*iter); } void Predicate::Iterator::operator ++ () { if (iter != list->end()) { ++iter; } } Predicate::Iterator Predicate::Iterator::begin() const { return Iterator(list, list->begin()); } Predicate::Iterator Predicate::Iterator::end() const { return Iterator(list, list->end()); } bool Predicate::Iterator::operator != (const Iterator& i) const { return ( (list != i.list) || (iter != i.iter) ); } bool Predicate::Iterator::operator == (const Iterator& i) const { return ( (list == i.list) && (iter == i.iter) ); } const ParameterList::TVector::const_iterator& Predicate::Iterator::GetIterator() const { return iter; } ParameterList::TVector::const_iterator& Predicate::Iterator::GetIterator() { return iter; } const ParameterList* Predicate::Iterator::GetList() const { return list; } /** implementation of class ParameterName */ bool ParameterName::operator()(const boost::any& param, const string& pred) const { try { // try get a ParameterList as an element const any* v = ¶m; const ParameterList* lst = any_cast<ParameterList>(v); if ( (lst == 0) || (lst->IsEmpty())) { return false; } string s; lst->GetValue(lst->begin(),s); return (pred == s); } catch(const boost::bad_any_cast &) { return false; } } bool Predicate::FindParameter(Iterator& iter, const string& name) const { const ParameterList* list = iter.GetList(); Iterator test ( list, find_if( list->begin(), list->end(), bind2nd(ParameterName(), name) ) ); if (test == test.end()) { return false; } // try to extract the first element as a parameter list const ParameterList* paramList = boost::any_cast<ParameterList>(&(*test)); if ( (paramList == 0) || (paramList->GetSize() < 2) ) { return false; } // return an iterator to the second element of the list, i.e. the // first parameter value iter = Iterator(paramList,paramList->begin()); ++iter; return true; } bool Predicate::DescentList(Iterator& iter) const { try { const any* v = &(*iter.GetIterator()); const ParameterList* l = any_cast<ParameterList>(v); iter = Iterator(l); return true; } catch(const std::bad_cast&) { return false; } } /** implementation of class PredicateList */ PredicateList::PredicateList() { } PredicateList::~PredicateList() { } PredicateList::TList::const_iterator PredicateList::begin() const { return mList.begin(); } PredicateList::TList::const_iterator PredicateList::end() const { return mList.end(); } Predicate& PredicateList::AddPredicate() { mList.push_back(Predicate()); return mList.back(); } int PredicateList::GetSize() const { return mList.size(); } void PredicateList::Clear() { mList.clear(); } --- NEW FILE: baseparser_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: baseparser_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "baseparser.h" using namespace oxygen; void CLASS(BaseParser)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Leaf); } --- NEW FILE: gamecontrolserver.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2004 RoboCup Soccer Server 3D Maintenance Group $Id: gamecontrolserver.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include <sstream> #include "gamecontrolserver.h" #include "baseparser.h" #include <oxygen/agentaspect/agentaspect.h> #include <oxygen/sceneserver/sceneserver.h> #include <oxygen/sceneserver/scene.h> #include <oxygen/controlaspect/controlaspect.h> #include <zeitgeist/logserver/logserver.h> #include <zeitgeist/scriptserver/scriptserver.h> #include <zeitgeist/corecontext.h> using namespace oxygen; using namespace zeitgeist; using namespace boost; using namespace std; GameControlServer::GameControlServer() : zeitgeist::Node() { mExit = false; } GameControlServer::~GameControlServer() { } bool GameControlServer::InitParser(const std::string& parserName) { mParser = shared_dynamic_cast<BaseParser>(GetCore()->New(parserName)); if (mParser.get() == 0) { GetLog()->Error() << "ERROR: (GameControlServer::InitParser) Unable to create " << parserName << "\n"; return false; } return true; } void GameControlServer::InitEffector(const std::string& effectorName) { mCreateEffector = effectorName; } bool GameControlServer::InitControlAspect(const string& aspectName) { shared_ptr<ControlAspect> aspect = shared_dynamic_cast<ControlAspect>(GetCore()->New(aspectName)); if (aspect.get() == 0) { GetLog()->Error() << "ERROR: (GameControlServer::InitControlAspect) " << "Unable to create " << aspectName << "\n"; return false; } aspect->SetName(aspectName); AddChildReference(aspect); return true; } shared_ptr<BaseParser> GameControlServer::GetParser() { return mParser; } shared_ptr<Scene> GameControlServer::GetActiveScene() { shared_ptr<SceneServer> sceneServer = shared_dynamic_cast<SceneServer>(GetCore()->Get("/sys/server/scene")); if (sceneServer.get() == 0) { GetLog()->Error() << "ERROR: (GameControlServer) SceneServer not found.\n"; return shared_ptr<Scene>(); } shared_ptr<Scene> scene = sceneServer->GetActiveScene(); if (scene.get() == 0) { GetLog()->Error() << "ERROR: (GameControlServer) SceneServer " << "reports no active scene\n"; } return scene; } bool GameControlServer::AgentConnect(int id) { // for map::insert(Elem), the test here is not required. map::insert does not // overwrite existing elements. The test is required to report if the agent // was already connected or not. if (mAgentMap.find(id) != mAgentMap.end()) { return false; } GetLog()->Normal() << "(GameControlServer) a new agent connected (id: " << id << ")\n"; shared_ptr<Scene> scene = GetActiveScene(); if (scene.get() == 0) { GetLog()->Error() << "(GameControlServer) ERROR: Got no active scene from the " << "SceneServer to create the AgentAspect in.\n"; return false; } // create a new AgentAspect for the ID in the scene and add it to // our map of AgentAspects shared_ptr<AgentAspect> aspect = shared_dynamic_cast<AgentAspect> (GetCore()->New("oxygen/AgentAspect")); if (aspect.get() == 0) { GetLog()->Error() << "ERROR: (GameControlServer) cannot create new AgentAspect\n"; return false; } stringstream name; name << "AgentAspect" << id; aspect->SetName(name.str()); scene->AddChildReference(aspect); mAgentMap[id] = aspect; // mark the scene as modified scene->SetModified(true); return aspect->Init(mCreateEffector); } bool GameControlServer::AgentDisappear(int id) { TAgentMap::iterator iter = mAgentMap.find(id); if (iter == mAgentMap.end()) { GetLog()->Error() << "ERROR: (GameControlServer) AgentDisappear called for " << "unknown agent id " << id << "\n"; return false; } // remove the AgentAspect from the Scene and our map. The // AgentAspect does all the necessary cleanup shared_ptr<Scene> scene = GetActiveScene(); if (scene.get() != 0) { (*iter).second->UnlinkChildren(); (*iter).second->Unlink(); // mark the scene as modified scene->SetModified(true); } else { GetLog()->Error() << "ERROR: (GameControlServer) failed to remove AgentAspect " << "for agent id " << id << "\n"; } mAgentMap.erase(id); GetLog()->Debug() << "(GameControlServer) An agent disconnected (id: " << id << ")\n"; return true; } float GameControlServer::GetSenseInterval(int /*id*/) { // the real thing should query the AgentAspect corresponding to // the agent. return 0.2; } float GameControlServer::GetSenseLatency(int /*id*/) { // the real thing should query the AgentAspect corresponding to // the agent return 0.1; } float GameControlServer::GetActionLatency(int /*id*/) { // the real thing should query the AgentAspect corresponding to // the agent. return 0.1; } shared_ptr<ActionObject::TList> GameControlServer::Parse(int id, const string& str) const { TAgentMap::const_iterator iter = mAgentMap.find(id); if (iter == mAgentMap.end()) { GetLog()->Error() << "ERROR: (GameControlServer::Parse) Parse " << "called with unknown agent id " << id << "\n"; return shared_ptr<ActionObject::TList>(); } if (mParser.get() == 0) { GetLog()->Error() << "ERROR: (GameControlServer::Parse) No parser registered.\n"; return shared_ptr<ActionObject::TList>(); } // use the parser to create a PredicateList shared_ptr<PredicateList> predicates(mParser->Parse(str)); // construct an ActionList using the registered effectors shared_ptr<ActionObject::TList> actionList(new ActionObject::TList()); // update the map of effectors below the agentaspect shared_ptr<AgentAspect> aspect = (*iter).second; aspect->UpdateEffectorMap(); for ( PredicateList::TList::const_iterator iter = predicates->begin(); iter != predicates->end(); ++iter ) { const Predicate& predicate = (*iter); shared_ptr<Effector> effector = aspect->GetEffector(predicate.name); if (effector.get() == 0) { GetLog()->Warning() << "(GameControlServer::Parse) No effector" << " registered for predicate " << predicate.name << "\n"; continue; } shared_ptr<ActionObject> action(effector->GetActionObject(predicate)); if (action.get() == 0) { continue; } actionList->push_back(action); } return actionList; } shared_ptr<AgentAspect> GameControlServer::GetAgentAspect(int id) { TAgentMap::iterator iter = mAgentMap.find(id); if (iter == mAgentMap.end()) { return shared_ptr<AgentAspect>(); } return (*iter).second; } void GameControlServer::Update(float deltaTime) { // build list of ControlAspects, NOT searching recursively TLeafList control; ListChildrenSupportingClass<ControlAspect>(control,false); // update all ControlAspects found for ( TLeafList::iterator iter = control.begin(); iter != control.end(); ++iter ) { shared_ptr<ControlAspect> aspect = shared_static_cast<ControlAspect>(*iter); aspect->Update(deltaTime); } } void GameControlServer::Quit() { mExit = true; } bool GameControlServer::IsFinished() const { return mExit; } --- NEW FILE: gamecontrolserver.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: gamecontrolserver.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_GAMECONTROLSERVER_H #define OXYGEN_GAMECONTROLSERVER_H #include "actionobject.h" #include "baseparser.h" #include <zeitgeist/class.h> #include <zeitgeist/node.h> namespace oxygen { class AgentAspect; class Effector; class Scene; class GameControlServer : public zeitgeist::Node { public: GameControlServer(); ~GameControlServer(); /** creates a parser instance and registers it to the GameControlServer \param parserName the name of the parser */ bool InitParser(const std::string& parserName); /** sets effectorName as the effector class that is initially created with every new AgentAspect instance. \param effectorName the init effector of the agent */ void InitEffector(const std::string& effectorName); /** creates an instance of aspectName and registers it as a ControlAspect to the GameControlServer. \param aspectName */ bool InitControlAspect(const std::string& aspectName); /** returns the parser currently registered to the GameControlServer */ boost::shared_ptr<BaseParser> GetParser(); /** parses a command string using the registerd parser and uses the registered effectors of the agent identified by param \id to construct an ActionObject. This method must be const as it is called from SpadesServer::ParseAct, which is const to prevent it from modifying the world model. */ boost::shared_ptr<ActionObject::TList> Parse (int id, const std::string& str) const; /** notifies the GameControlServer that an agent has connected to the simulation. \param id should be a unique identifier for the new agent. It is not assigned by the GameControlServer. */ bool AgentConnect(int id); /** notifies the GameControlServer that an agent has disappeared from the simulation. \param id was the unique identifier of the disappeared agent. The GameControlServer uses the AgentAspect corresponding to id to clean up after the agent left. */ bool AgentDisappear(int id); /** returns the time between to queries of the agents perceptors in seconds */ float GetSenseInterval(int id); /** GetSenseLatency returns latency it takes to query the sensors of an agent in seconds */ float GetSenseLatency(int id); /** GetActionLatency returns the latency it takes to realize an agent action in seconds */ float GetActionLatency(int id); /** returns the AgentAspect for the given \param id */ boost::shared_ptr<AgentAspect> GetAgentAspect(int id); /** This method is used to notify the GameControlServer that the game has advanced deltaTime seconds. The GameControlServer will in turn update all registered GameControlAspects below it. */ void Update(float deltaTime); /** This method is used to indicate that the simulation is finished. The GameControlServer knows that the simulatio is finished if one of the GameControlAspects below indicate that the simulation is finished. The finished state is set during GameControlServer::Update(). \return true if the simulation should be stopped. */ bool IsFinished() const; /** This method is used to set the simulation into the 'finished' state. */ void Quit(); protected: /** helper method that queries the SceneServer for the currently active Scene */ boost::shared_ptr<Scene> GetActiveScene(); protected: typedef std::map<int, boost::shared_ptr<AgentAspect> > TAgentMap; /** a map from agent IDs to agent instances */ TAgentMap mAgentMap; /** the parser instance used */ boost::shared_ptr<BaseParser> mParser; /** the name of the initial effector class of each new agent has to construct all remaining parts */ std::string mCreateEffector; /** flag if the simulation is over */ bool mExit; }; DECLARE_CLASS(GameControlServer); } // namespace oxygen #endif // OXYGEN_GAMECONTROLSERVER_H --- NEW FILE: actionobject_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: actionobject_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "actionobject.h" using namespace oxygen; void CLASS(ActionObject)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Leaf); } |
From: Markus R. <rol...@us...> - 2005-12-05 21:16:59
|
Update of /cvsroot/simspark/simspark/spark/oxygen/agentaspect In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14301/agentaspect Added Files: agentaspect.cpp agentaspect.h agentaspect_c.cpp createaction.h effector.cpp effector.h effector_c.cpp perceptor.cpp perceptor.h perceptor_c.cpp Log Message: --- NEW FILE: createaction.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: createaction.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_CREATEACTION_H #define OXYGEN_CREATEACTION_H #include <oxygen/gamecontrolserver/actionobject.h> namespace oxygen { class CreateAction : public oxygen::ActionObject { public: CreateAction() : ActionObject("create") {} virtual ~CreateAction() {} }; }; // namespace oxygen #endif // OXYGEN_CREATEACTION_H --- NEW FILE: effector_c.cpp --- /* -*- mode: c++; c-basic-indent: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: effector_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include <zeitgeist/class.h> #include "effector.h" using namespace oxygen; void CLASS(Effector)::DefineClass() { DEFINE_BASECLASS(oxygen/BaseNode); } --- NEW FILE: agentaspect.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: agentaspect.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "agentaspect.h" #include <zeitgeist/logserver/logserver.h> using namespace boost; using namespace oxygen; using namespace salt; using namespace std; AgentAspect::AgentAspect() : Transform() { SetName("agentAspect"); } AgentAspect::~AgentAspect() { } bool AgentAspect::RealizeActions(boost::shared_ptr<ActionObject::TList> actions) { UpdateEffectorMap(); for ( ActionObject::TList::iterator iter = actions->begin(); iter != actions->end(); ++iter ) { shared_ptr<ActionObject> action = (*iter); std::string predicate = action->GetPredicate(); shared_ptr<Effector> effector = GetEffector(predicate); if (effector.get() == 0) { GetLog()->Warning() << "(AgentAspect) No effector found for predicate " << predicate << "\n"; continue; } bool realized = effector->Realize(action); if (! realized) { GetLog()->Warning() << "(AgentAspect) Failed to realize predicate " << predicate << "\n"; } } return true; } shared_ptr<PredicateList> AgentAspect::QueryPerceptors() { // build list of perceptors, searching recursively TLeafList perceptors; ListChildrenSupportingClass<Perceptor>(perceptors,true); shared_ptr<PredicateList> predList(new PredicateList()); // query the perceptors for new data for ( TLeafList::iterator iter = perceptors.begin(); iter != perceptors.end(); ++iter ) { shared_static_cast<Perceptor>(*iter)->Percept(predList); } return predList; } shared_ptr<Effector> AgentAspect::GetEffector(const std::string predicate) const { TEffectorMap::const_iterator iter = mEffectorMap.find(predicate); if (iter == mEffectorMap.end()) { return shared_ptr<Effector>(); } return (*iter).second; } void AgentAspect::UpdateEffectorMap() { // build list of effectors, searching recursively TLeafList effectors; ListChildrenSupportingClass<Effector>(effectors,true); // build the effector map mEffectorMap.clear(); for ( TLeafList::iterator iter = effectors.begin(); iter != effectors.end(); ++iter ) { shared_ptr<Effector> effector = shared_static_cast<Effector>(*iter); mEffectorMap[effector->GetPredicate()] = effector; } } bool AgentAspect::Init(const string& createEffector) { shared_ptr<Effector> create = shared_dynamic_cast<Effector> (GetCore()->New(createEffector)); if (create.get() == 0) { GetLog()->Error() << "ERROR: (AgentAspect) Could not construct a createEffector '" << createEffector << "'\n"; return false; } create->SetName("_CreateEffector"); // link it into our hierarchy bool added = AddChildReference(create); if (! added) { GetLog()->Error() << "ERROR: (AgentAspect) failed to set up the CreateEffector '" << createEffector << "'\n"; return false; } else { GetLog()->Debug() << "(AgentAspect) created CreateEffector '" << createEffector << "'\n"; } return added; } --- NEW FILE: perceptor_c.cpp --- /* -*- mode: c++; c-basic-indent: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: perceptor_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "perceptor.h" using namespace boost; using namespace oxygen; FUNCTION(Perceptor,setPredicateName) { std::string inName; if ( (in.GetSize() != 1) || (! in.GetValue(in.begin(),inName)) ) { return false; } obj->SetPredicateName(inName); return true; } void CLASS(Perceptor)::DefineClass() { DEFINE_BASECLASS(oxygen/BaseNode); DEFINE_FUNCTION(setPredicateName); } --- NEW FILE: effector.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: effector.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_EFFECTOR_H #define OXYGEN_EFFECTOR_H // #ifdef HAVE_CONFIG_H // #include <config.h> // #endif #include <oxygen/sceneserver/basenode.h> #include <oxygen/gamecontrolserver/baseparser.h> namespace oxygen { class ActionObject; class AgentAspect; class Effector : public BaseNode { public: Effector() : BaseNode() {}; virtual ~Effector() {}; /** realizes the action described by the ActionObject */ virtual bool Realize(boost::shared_ptr<ActionObject> action) = 0; /** returns the name of the predicate this effector implements */ virtual std::string GetPredicate() = 0; /** constructs an Actionobject, describing a predicate */ virtual boost::shared_ptr<ActionObject> GetActionObject(const Predicate& predicate) = 0; protected: /** Returns the AgentAspect this Effector belongs to */ boost::shared_ptr<AgentAspect> GetAgentAspect(); }; DECLARE_ABSTRACTCLASS(Effector); } // namespace oxygen #endif //OXYGEN_EFFECTOR_H --- NEW FILE: agentaspect_c.cpp --- /* -*- mode: c++; c-basic-indent: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: agentaspect_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "agentaspect.h" using namespace boost; using namespace oxygen; void CLASS(AgentAspect)::DefineClass() { DEFINE_BASECLASS(oxygen/Transform); } --- NEW FILE: effector.cpp --- /* -*- mode: c++; c-basic-indent: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: effector.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "effector.h" #include "agentaspect.h" using namespace oxygen; using namespace boost; shared_ptr<AgentAspect> Effector::GetAgentAspect() { return shared_static_cast<AgentAspect> (make_shared(GetParentSupportingClass("AgentAspect"))); } --- NEW FILE: perceptor.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: perceptor.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_PERCEPTOR_H #define OXYGEN_PERCEPTOR_H #include <oxygen/sceneserver/basenode.h> #include <oxygen/gamecontrolserver/baseparser.h> namespace oxygen { class Perceptor : public oxygen::BaseNode { public: /*! This is called by agents to trigger the percept event implemented by this perceptor. The perceptor can return data through the PredicateList which is passed as a parameter. \return true, if valid data is available and false otherwise. */ virtual bool Percept(boost::shared_ptr<PredicateList> predList) = 0; //! set / change predicate name (for example for debugging purposes) void SetPredicateName(const std::string& my_name); protected: //! the predicate name std::string mPredicateName; }; DECLARE_ABSTRACTCLASS(Perceptor); } // namespace oxygen #endif //OXYGEN_PERCEPTOR_H --- NEW FILE: agentaspect.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: agentaspect.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_AGENTASPECT_H #define OXYGEN_AGENTASPECT_H // #ifdef HAVE_CONFIG_H // #include <config.h> // #endif #include <oxygen/sceneserver/transform.h> #include <oxygen/gamecontrolserver/actionobject.h> #include <oxygen/gamecontrolserver/baseparser.h> #include "effector.h" #include "perceptor.h" namespace oxygen { #if 0 } #endif class AgentAspect : public Transform { public: AgentAspect(); virtual ~AgentAspect(); /** Initializes the AgentAspect. Called immediately after the AgentAspect is created by the GameControlServer. \param createEffector is the name of the initial effector class that the agent uses to construct all remaining parts */ virtual bool Init(const std::string& createEffector); /** RealizeActions realizes the actions described by \param actions using the corresponding effectors */ virtual bool RealizeActions(boost::shared_ptr<ActionObject::TList> actions); /** QuerySensors collects data from all perceptors below this AgentAspect */ virtual boost::shared_ptr<PredicateList> QueryPerceptors(); /** updates the map of Effectors below this AgentAspect */ virtual void UpdateEffectorMap(); /** looks up the effector corresponding to a predicate */ virtual boost::shared_ptr<Effector> GetEffector(const std::string predicate) const; protected: typedef std::map<std::string, boost::shared_ptr<Effector> > TEffectorMap; //! the map of effectors below this AgentAspect TEffectorMap mEffectorMap; private: }; DECLARE_CLASS(AgentAspect); } // namespace oxygen #endif //OXYGEN_AGENTASPECT_H --- NEW FILE: perceptor.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: perceptor.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "perceptor.h" using namespace oxygen; void Perceptor::SetPredicateName(const std::string& my_name) { mPredicateName = my_name; } |
From: Markus R. <rol...@us...> - 2005-12-05 21:16:58
|
Update of /cvsroot/simspark/simspark/spark/oxygen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14301 Added Files: Makefile.am oxygen.cpp oxygen.h Log Message: --- NEW FILE: oxygen.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: oxygen.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_OXYGEN_H #define OXYGEN_OXYGEN_H #include "agentaspect/agentaspect.h" #include "agentaspect/effector.h" #include "agentaspect/perceptor.h" #include "controlaspect/controlaspect.h" #include "gamecontrolserver/baseparser.h" #include "gamecontrolserver/gamecontrolserver.h" #include "gamecontrolserver/actionobject.h" #include "physicsserver/body.h" #include "physicsserver/bodycontroller.h" #include "physicsserver/dragcontroller.h" #include "physicsserver/velocitycontroller.h" #include "physicsserver/boxcollider.h" #include "physicsserver/ccylindercollider.h" #include "physicsserver/collider.h" #include "physicsserver/odeobject.h" #include "physicsserver/physicsserver.h" #include "physicsserver/planecollider.h" #include "physicsserver/raycollider.h" #include "physicsserver/space.h" #include "physicsserver/spherecollider.h" #include "physicsserver/world.h" #include "physicsserver/collisionhandler.h" #include "physicsserver/contactjointhandler.h" #include "physicsserver/recorderhandler.h" #include "physicsserver/joint.h" #include "physicsserver/balljoint.h" #include "physicsserver/hingejoint.h" #include "physicsserver/fixedjoint.h" #include "physicsserver/sliderjoint.h" #include "physicsserver/universaljoint.h" #include "physicsserver/hinge2joint.h" #include "sceneserver/basenode.h" #include "sceneserver/camera.h" #include "sceneserver/fpscontroller.h" #include "sceneserver/scene.h" #include "sceneserver/sceneserver.h" #include "sceneserver/transform.h" #include "sceneserver/sceneimporter.h" #include "simulationserver/simulationserver.h" #include "simulationserver/simcontrolnode.h" #include "simulationserver/netcontrol.h" #include "simulationserver/netmessage.h" #include "simulationserver/agentcontrol.h" #include "simulationserver/monitorcontrol.h" #include "geometryserver/geometryserver.h" #include "geometryserver/meshimporter.h" #include "geometryserver/stdmeshimporter.h" #ifdef HAVE_SPADES_HEADERS #include "spadesserver/spadesserver.h" #include "spadesserver/paramreader.h" #endif #include "monitorserver/monitorserver.h" #include "monitorserver/monitorsystem.h" #include "monitorserver/custommonitor.h" #include "monitorserver/monitoritem.h" #include "monitorserver/monitorcmdparser.h" // control aspect #include <zeitgeist/zeitgeist.h> namespace oxygen { /** This is the main class, which initializes the Oxygen framework. It registers all internal classes. */ class Oxygen { public: /** initializes the oxygen framework \param zg is a reference to an already initialized zeitgeist framework in which the internal oxygen libraries get installed */ Oxygen(zeitgeist::Zeitgeist& zg); virtual ~Oxygen() {} private: Oxygen(const Oxygen& obj); Oxygen& operator=(const Oxygen& obj); }; } //namespace oxygen #endif // OXYGEN_OXYGEN_H --- NEW FILE: oxygen.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: oxygen.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "oxygen.h" using namespace oxygen; using namespace zeitgeist; Oxygen::Oxygen(zeitgeist::Zeitgeist& zg) { // scene graph zg.GetCore()->RegisterClassObject(new CLASS(SceneServer), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(BaseNode), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(Camera), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(FPSController), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(Scene), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(Transform), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(SceneImporter), "oxygen/"); // simulation zg.GetCore()->RegisterClassObject(new CLASS(SimulationServer), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(SimControlNode), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(NetControl), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(NetMessage), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(AgentControl), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(MonitorControl), "oxygen/"); // geometry zg.GetCore()->RegisterClassObject(new CLASS(GeometryServer), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(MeshImporter), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(StdMeshImporter), "oxygen/"); // physics zg.GetCore()->RegisterClassObject(new CLASS(PhysicsServer), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(Body), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(BodyController), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(DragController), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(VelocityController), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(ODEObject), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(Space), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(World), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(Joint), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(BallJoint), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(HingeJoint), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(FixedJoint), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(SliderJoint), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(UniversalJoint), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(Hinge2Joint), "oxygen/"); // collider zg.GetCore()->RegisterClassObject(new CLASS(Collider), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(BoxCollider), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(CCylinderCollider), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(PlaneCollider), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(RayCollider), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(SphereCollider), "oxygen/"); // collision handler zg.GetCore()->RegisterClassObject(new CLASS(CollisionHandler), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(ContactJointHandler), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(RecorderHandler), "oxygen/"); // agentaspect zg.GetCore()->RegisterClassObject(new CLASS(AgentAspect), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(Effector), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(Perceptor), "oxygen/"); #ifdef HAVE_SPADES_HEADERS // spades zg.GetCore()->RegisterClassObject(new CLASS(SpadesServer), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(ParamReader), "oxygen/"); #endif // monitor zg.GetCore()->RegisterClassObject(new CLASS(MonitorServer), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(MonitorSystem), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(CustomMonitor), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(MonitorItem), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(MonitorCmdParser),"oxygen/"); // game control and controlaspects zg.GetCore()->RegisterClassObject(new CLASS(BaseParser), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(GameControlServer), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(ControlAspect), "oxygen/"); zg.GetCore()->RegisterClassObject(new CLASS(ActionObject), "oxygen/"); // run the oxygen init script zg.GetCore()->GetRoot()->GetScript()->RunInitScript ( "oxygen.rb", "lib/oxygen", ScriptServer::IS_COMMON ); } --- NEW FILE: Makefile.am --- if DEBUG pkglib_LTLIBRARIES = liboxygen_debug.la liboxygen_debug_la_SOURCES = $(sources) $(spades_sources) liboxygen_debug_la_CXXFLAGS = -O -g -W -Wall -Woverloaded-virtual -Wno-deprecated liboxygen_debug_la_LIBADD = -lode ${spades_libs} liboxygen_debug_la_LDFLAGS = \ -version-info @oxygen_version_info@ \ ${top_srcdir}/utility/rcssnet/librcssnet3D.la else pkglib_LTLIBRARIES = liboxygen.la liboxygen_la_SOURCES = $(sources) $(spades_sources) liboxygen_la_CXXFLAGS = -O2 -Wno-deprecated liboxygen_la_LIBADD = -lode $(spades_libs) liboxygen_la_LDFLAGS = \ -version-info @oxygen_version_info@ \ ${top_srcdir}/utility/rcssnet/librcssnet3D.la endif AM_CPPFLAGS = -I${top_srcdir}/lib -I${top_srcdir}/utility @RUBY_CPPFLAGS@ ## define include directory local to the pkgincludedir libpkgincludedir = $(includedir)/@PACKAGE@/oxygen ## architecture independent data (scripts) to be installed and distributed dist_pkgdata_DATA = oxygen.rb bin_SCRIPTS = oxygen-config if BUILD_SPADES_MODULES spades_sources = \ spadesserver/spadesserver.cpp \ spadesserver/spadesserver_c.cpp \ spadesserver/paramreader.cpp \ spadesserver/paramreader_c.cpp \ spadesserver/paramstorer.cpp \ spadesserver/spadescreatesenseevent.cpp \ spadesserver/spadesactevent.cpp spades_headers = \ spadesserver/spadesserver.h \ spadesserver/paramreader.h \ spadesserver/paramstorer.h \ spadesserver/spadescreatesenseevent.h \ spadesserver/spadesactevent.h spades_libs = -lspades else spades_sources = spades_headers = spades_libs = endif sources = \ agentaspect/agentaspect.cpp \ agentaspect/agentaspect_c.cpp \ agentaspect/effector.cpp \ agentaspect/effector_c.cpp \ agentaspect/perceptor.cpp \ agentaspect/perceptor_c.cpp \ controlaspect/controlaspect.cpp \ controlaspect/controlaspect_c.cpp \ gamecontrolserver/actionobject_c.cpp \ gamecontrolserver/baseparser_c.cpp \ gamecontrolserver/gamecontrolserver.cpp \ gamecontrolserver/gamecontrolserver_c.cpp \ gamecontrolserver/predicate.cpp \ oxygen.cpp \ physicsserver/body.cpp \ physicsserver/body_c.cpp \ physicsserver/bodycontroller.cpp \ physicsserver/bodycontroller_c.cpp \ physicsserver/boxcollider.cpp \ physicsserver/boxcollider_c.cpp \ physicsserver/ccylindercollider.cpp \ physicsserver/ccylindercollider_c.cpp \ physicsserver/collider.cpp \ physicsserver/collider_c.cpp \ physicsserver/collisionhandler.cpp \ physicsserver/collisionhandler_c.cpp \ physicsserver/contactjointhandler.cpp \ physicsserver/contactjointhandler_c.cpp \ physicsserver/odeobject.cpp \ physicsserver/odeobject_c.cpp \ physicsserver/physicsserver.cpp \ physicsserver/physicsserver_c.cpp \ physicsserver/planecollider.cpp \ physicsserver/planecollider_c.cpp \ physicsserver/raycollider.cpp \ physicsserver/raycollider_c.cpp \ physicsserver/recorderhandler.cpp \ physicsserver/recorderhandler_c.cpp \ physicsserver/space.cpp \ physicsserver/space_c.cpp \ physicsserver/spherecollider.cpp \ physicsserver/spherecollider_c.cpp \ physicsserver/world.cpp \ physicsserver/world_c.cpp \ physicsserver/dragcontroller.cpp \ physicsserver/dragcontroller_c.cpp \ physicsserver/velocitycontroller.cpp \ physicsserver/velocitycontroller_c.cpp \ physicsserver/joint.cpp \ physicsserver/joint_c.cpp \ physicsserver/balljoint.cpp \ physicsserver/balljoint_c.cpp \ physicsserver/hingejoint.cpp \ physicsserver/hingejoint_c.cpp \ physicsserver/fixedjoint.cpp \ physicsserver/fixedjoint_c.cpp \ physicsserver/sliderjoint.cpp \ physicsserver/sliderjoint_c.cpp \ physicsserver/universaljoint.cpp \ physicsserver/universaljoint_c.cpp \ physicsserver/hinge2joint.cpp \ physicsserver/hinge2joint_c.cpp \ physicsserver/angularmotor.cpp \ physicsserver/angularmotor_c.cpp \ sceneserver/basenode.cpp \ sceneserver/basenode_c.cpp \ sceneserver/fpscontroller.cpp \ sceneserver/fpscontroller_c.cpp \ sceneserver/scene.cpp \ sceneserver/scene_c.cpp \ sceneserver/sceneserver.cpp \ sceneserver/sceneserver_c.cpp \ sceneserver/sceneimporter_c.cpp \ sceneserver/transform.cpp \ sceneserver/transform_c.cpp \ sceneserver/camera.cpp \ sceneserver/camera_c.cpp \ simulationserver/simulationserver.h \ simulationserver/simulationserver.cpp \ simulationserver/simulationserver_c.cpp \ simulationserver/simcontrolnode.cpp \ simulationserver/simcontrolnode_c.cpp \ simulationserver/agentcontrol.cpp \ simulationserver/agentcontrol_c.cpp \ simulationserver/monitorcontrol.cpp \ simulationserver/monitorcontrol_c.cpp \ simulationserver/netcontrol.cpp \ simulationserver/netcontrol_c.cpp \ simulationserver/netclient.cpp \ simulationserver/netclient_c.cpp \ simulationserver/netmessage.cpp \ simulationserver/netmessage_c.cpp \ simulationserver/netbuffer.cpp \ geometryserver/geometryserver.h \ geometryserver/geometryserver.cpp \ geometryserver/geometryserver_c.cpp \ geometryserver/meshimporter.cpp \ geometryserver/meshimporter_c.cpp \ geometryserver/stdmeshimporter.cpp \ geometryserver/stdmeshimporter_c.cpp \ geometryserver/trimesh.cpp \ geometryserver/indexbuffer.cpp \ monitorserver/monitorserver.cpp \ monitorserver/monitorserver_c.cpp \ monitorserver/monitorsystem.cpp \ monitorserver/monitorsystem_c.cpp \ monitorserver/monitoritem_c.cpp \ monitorserver/custommonitor.cpp \ monitorserver/custommonitor_c.cpp \ monitorserver/monitorcmdparser.cpp \ monitorserver/monitorcmdparser_c.cpp nobase_libpkginclude_HEADERS = \ agentaspect/agentaspect.h \ agentaspect/effector.h \ agentaspect/perceptor.h \ agentaspect/createaction.h \ controlaspect/controlaspect.h \ gamecontrolserver/predicate.h \ gamecontrolserver/gamecontrolserver.h \ gamecontrolserver/baseparser.h \ gamecontrolserver/actionobject.h \ oxygen.h \ physicsserver/body.h \ physicsserver/bodycontroller.h \ physicsserver/boxcollider.h \ physicsserver/ccylindercollider.h \ physicsserver/collider.h \ physicsserver/collisionhandler.h \ physicsserver/contactjointhandler.h \ physicsserver/odeobject.h \ physicsserver/physicsserver.h \ physicsserver/planecollider.h \ physicsserver/raycollider.h \ physicsserver/recorderhandler.h \ physicsserver/space.h \ physicsserver/spherecollider.h \ physicsserver/world.h \ physicsserver/dragcontroller.h \ physicsserver/velocitycontroller.h \ physicsserver/joint.h \ physicsserver/balljoint.h \ physicsserver/hingejoint.h \ physicsserver/fixedjoint.h \ physicsserver/sliderjoint.h \ physicsserver/universaljoint.h \ physicsserver/hinge2joint.h \ physicsserver/angularmotor.h \ sceneserver/sceneimporter.h \ sceneserver/basenode.h \ sceneserver/fpscontroller.h \ sceneserver/scene.h \ sceneserver/sceneserver.h \ sceneserver/sceneimporter.h \ sceneserver/transform.h \ sceneserver/camera.h \ simulationserver/simulationserver.h \ simulationserver/simcontrolnode.h \ simulationserver/agentcontrol.h \ simulationserver/monitorcontrol.h \ simulationserver/netcontrol.h \ simulationserver/netclient.h \ simulationserver/netmessage.h \ simulationserver/netbuffer.h \ geometryserver/geometryserver.h \ geometryserver/meshimporter.h \ geometryserver/stdmeshimporter.h \ geometryserver/trimesh.h \ geometryserver/indexbuffer.h \ monitorserver/monitorserver.h \ monitorserver/monitorsystem.h \ monitorserver/monitoritem.h \ monitorserver/custommonitor.h \ monitorserver/monitorcmdparser.h \ $(spades_headers) |
From: Markus R. <rol...@us...> - 2005-12-05 21:16:57
|
Update of /cvsroot/simspark/simspark/spark/oxygen/controlaspect In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14301/controlaspect Added Files: controlaspect.cpp controlaspect.h controlaspect_c.cpp Log Message: --- NEW FILE: controlaspect.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: controlaspect.h,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef OXYGEN_CONTROLASPECT_H #define OXYGEN_CONTROLASPECT_H #include <oxygen/sceneserver/basenode.h> namespace oxygen { class Scene; class ControlAspect : public BaseNode { public: ControlAspect() {}; virtual ~ControlAspect() {}; /** called during the update of the GameControlServer to allow the ControlAspect to perform any necessary checks. \param time is the time passed since the last update in seconds */ virtual void Update(float deltaTime) = 0; /** queries the SceneServer for the currently active scene node */ boost::shared_ptr<Scene> GetActiveScene(); /** returns a reference to a ControlAspect registered to the GameControlServer */ boost::shared_ptr<ControlAspect> GetControlAspect(const std::string& name); }; DECLARE_ABSTRACTCLASS(ControlAspect); } // namespace oxygen #endif //OXYGEN_CONTROLASPECT_H --- NEW FILE: controlaspect.cpp --- /* -*- mode: c++; c-basic-indent: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: controlaspect.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "controlaspect.h" #include <zeitgeist/logserver/logserver.h> #include <oxygen/sceneserver/sceneserver.h> using namespace std; using namespace boost; using namespace oxygen; using namespace zeitgeist; shared_ptr<Scene> ControlAspect::GetActiveScene() { shared_ptr<SceneServer> sceneServer = shared_dynamic_cast<SceneServer>(GetCore()->Get("/sys/server/scene")); if (sceneServer.get() == 0) { GetLog()->Error() << "(ControlAspect) cannot get SceneServer\n"; return shared_ptr<Scene>(); } shared_ptr<Scene> activeScene = sceneServer->GetActiveScene(); if (activeScene.get() == 0) { GetLog()->Error() << "(ControlAspect) SceneServer reported no active scene\n"; return shared_ptr<Scene>(); } return activeScene; } shared_ptr<ControlAspect> ControlAspect::GetControlAspect(const string& name) { static const string gcsPath = "/sys/server/gamecontrol/"; shared_ptr<ControlAspect> aspect = shared_dynamic_cast<ControlAspect> (GetCore()->Get(gcsPath + name)); if (aspect.get() == 0) { GetLog()->Error() << "(ControlAspect) found no " << name << "\n"; } return aspect; } --- NEW FILE: controlaspect_c.cpp --- /* -*- mode: c++; c-basic-indent: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2003 RoboCup Soccer Server 3D Maintenance Group $Id: controlaspect_c.cpp,v 1.1 2005/12/05 21:16:49 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "controlaspect.h" using namespace boost; using namespace oxygen; void CLASS(ControlAspect)::DefineClass() { DEFINE_BASECLASS(oxygen/BaseNode); } |
From: Markus R. <rol...@us...> - 2005-12-05 21:16:05
|
Update of /cvsroot/simspark/simspark/spark/oxygen/physicsserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14165/physicsserver Log Message: Directory /cvsroot/simspark/simspark/spark/oxygen/physicsserver added to the repository |
From: Markus R. <rol...@us...> - 2005-12-05 21:13:01
|
Update of /cvsroot/simspark/simspark/spark/oxygen/monitorserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv13625/monitorserver Log Message: Directory /cvsroot/simspark/simspark/spark/oxygen/monitorserver added to the repository |
From: Markus R. <rol...@us...> - 2005-12-05 21:11:46
|
Update of /cvsroot/simspark/simspark/spark/oxygen/geometryserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv13468/geometryserver Log Message: Directory /cvsroot/simspark/simspark/spark/oxygen/geometryserver added to the repository |
From: Markus R. <rol...@us...> - 2005-12-05 21:10:27
|
Update of /cvsroot/simspark/simspark/spark/oxygen/gamecontrolserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv12901/gamecontrolserver Log Message: Directory /cvsroot/simspark/simspark/spark/oxygen/gamecontrolserver added to the repository |
From: Markus R. <rol...@us...> - 2005-12-05 21:09:37
|
Update of /cvsroot/simspark/simspark/spark/oxygen/controlaspect In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv12675/controlaspect Log Message: Directory /cvsroot/simspark/simspark/spark/oxygen/controlaspect added to the repository |
From: Markus R. <rol...@us...> - 2005-12-05 21:07:00
|
Update of /cvsroot/simspark/simspark/spark/oxygen/agentaspect In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv12032/agentaspect Log Message: Directory /cvsroot/simspark/simspark/spark/oxygen/agentaspect added to the repository |
From: Markus R. <rol...@us...> - 2005-12-05 21:05:14
|
Update of /cvsroot/simspark/simspark/spark/zeitgeist/randomserver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv11684/randomserver Added Files: randomserver.cpp randomserver.h randomserver_c.cpp Log Message: --- NEW FILE: randomserver.h --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2004 RoboCup Soccer Server 3D Maintenance Group $Id: randomserver.h,v 1.1 2005/12/05 21:05:01 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifndef ZEITGEIST_RANDOMSERVER_H #define ZEITGEIST_RANDOMSERVER_H #include <salt/random.h> #include <zeitgeist/node.h> #include <sys/time.h> namespace zeitgeist { /** The random server provides access to the salt RandomEngine from with the * zeitgeist framework. Additionally, it provides interfaces to set a seed * and access some distributions. */ class RandomServer : public Node { public: /** constructs a RandomServer */ RandomServer() {} virtual ~RandomServer() {} /** set a random seed */ void Seed(salt::RandomEngine::result_type seed) { if (seed == 0) { timeval tv; gettimeofday(&tv,0); seed = tv.tv_usec; } salt::RandomEngine::instance(seed); } /** get a uniformly distributed random number */ template<class RealType> RealType GetUniformRandom(RealType min, RealType max) const { return salt::UniformRNG<RealType>(min,max)(); } template<class RealType> RealType GetNormalRandom(RealType mean, RealType sigma) const { return salt::NormalRNG<RealType>(mean,sigma)(); } template<class RealType> RealType GetExponentialRandom(RealType lambda) const { return salt::ExponentialRNG<RealType>(lambda)(); } }; DECLARE_CLASS(RandomServer); } //namespace zeitgeist #endif //ZEITGEIST_LOGSERVER_H --- NEW FILE: randomserver_c.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2004 RoboCup Soccer Server 3D Maintenance Group $Id: randomserver_c.cpp,v 1.1 2005/12/05 21:05:01 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "randomserver.h" #include <cmath> using namespace boost; using namespace zeitgeist; FUNCTION(RandomServer,seed) { int inSeed; if ( (in.GetSize() != 1) || (! in.GetValue(in.begin(),inSeed)) ) { return false; } obj->Seed(inSeed); return true; } FUNCTION(RandomServer,uniformRND) { float inMin; float inMax; if ( (in.GetSize() != 2) || (! in.GetValue(in[0],inMin)) || (! in.GetValue(in[1],inMax)) ) { return 0.0f; } return obj->GetUniformRandom(inMin,inMax); } FUNCTION(RandomServer,normalRND) { float inMean; float inSigma; if ( (in.GetSize() != 2) || (! in.GetValue(in[0],inMean)) || (! in.GetValue(in[1],inSigma)) ) { return 0.0f; } return obj->GetNormalRandom(inMean,inSigma); } FUNCTION(RandomServer,exponentialRND) { float inLambda; if ( (in.GetSize() != 1) || (! in.GetValue(in[0],inLambda)) ) { return 0.0f; } return obj->GetExponentialRandom(inLambda); } void CLASS(RandomServer)::DefineClass() { DEFINE_BASECLASS(zeitgeist/Node); DEFINE_FUNCTION(seed); DEFINE_FUNCTION(uniformRND); DEFINE_FUNCTION(normalRND); DEFINE_FUNCTION(exponentialRND); } --- NEW FILE: randomserver.cpp --- /* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- this file is part of rcssserver3D Fri May 9 2003 Copyright (C) 2002,2003 Koblenz University Copyright (C) 2004 RoboCup Soccer Server 3D Maintenance Group $Id: randomserver.cpp,v 1.1 2005/12/05 21:05:01 rollmark Exp $ 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; version 2 of the License. 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. 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., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "randomserver.h" #include <cmath> #if 0 void RandomServer::Seed(salt::RandomEngine::result_type seed) { salt::RandomEngine.instance(seed); } #endif |