From: <pat...@us...> - 2016-05-29 05:27:59
|
Revision: 405 http://sourceforge.net/p/simspark/svn/405 Author: patmac369 Date: 2016-05-29 05:27:56 +0000 (Sun, 29 May 2016) Log Message: ----------- Adding changes for the RoboCup 2016 competition. Additions are the following: - Updated and revised foul model - Most free kicks are now indirect and direct_free_kick playmodes are added - Keepaway mode - Say messages with illegal characters are thrown out - Plugin for sending draw commands to roboviz (rvdraw) Modified Paths: -------------- trunk/rcssserver3d/CMakeLists.txt trunk/rcssserver3d/cmake/FindODE.cmake trunk/rcssserver3d/plugin/soccer/CMakeLists.txt trunk/rcssserver3d/plugin/soccer/agentcollisionhandler/agentcollisionhandler.cpp trunk/rcssserver3d/plugin/soccer/agentstate/agentstate.h trunk/rcssserver3d/plugin/soccer/ballstateaspect/ballstateaspect.cpp trunk/rcssserver3d/plugin/soccer/ballstateaspect/ballstateaspect.h trunk/rcssserver3d/plugin/soccer/internalsoccermonitor/internalsoccerinput.cpp trunk/rcssserver3d/plugin/soccer/internalsoccermonitor/internalsoccerinput.h trunk/rcssserver3d/plugin/soccer/sayeffector/sayeffector.cpp trunk/rcssserver3d/plugin/soccer/soccerbase/soccerbase.cpp trunk/rcssserver3d/plugin/soccer/soccerruleaspect/soccerruleaspect.cpp trunk/rcssserver3d/plugin/soccer/soccerruleaspect/soccerruleaspect.h trunk/rcssserver3d/plugin/soccer/soccertypes.h trunk/rcssserver3d/plugin/soccer/trainercommandparser/trainercommandparser.cpp trunk/rcssserver3d/plugin/soccermonitor/soccerinput.cpp trunk/rcssserver3d/plugin/soccermonitor/soccerinput.h trunk/rcssserver3d/rcssmonitor3d/soccerbindings.rb trunk/rcssserver3d/rcssserver3d/main.cpp trunk/rcssserver3d/rcssserver3d/naosoccersim.rb Added Paths: ----------- trunk/rcssserver3d/plugin/soccer/rvdraw/ trunk/rcssserver3d/plugin/soccer/rvdraw/rvdraw.cpp trunk/rcssserver3d/plugin/soccer/rvdraw/rvdraw.h Modified: trunk/rcssserver3d/CMakeLists.txt =================================================================== --- trunk/rcssserver3d/CMakeLists.txt 2015-09-12 01:48:59 UTC (rev 404) +++ trunk/rcssserver3d/CMakeLists.txt 2016-05-29 05:27:56 UTC (rev 405) @@ -1,8 +1,13 @@ cmake_minimum_required(VERSION 2.6) project(rcssserver3d CXX C) -set(PACKAGE_VERSION "0.6.10") +set(PACKAGE_VERSION "0.6.11") +option(RVDRAW "Enable roboviz drawings" OFF) +if (RVDRAW) + add_definitions(-DRVDRAW) +endif (RVDRAW) + ########## check for headerfiles/libraries ########## include(CheckIncludeFile) check_include_file("sys/socket.h" HAVE_SYS_SOCKET_H) @@ -26,7 +31,7 @@ find_package(Spark REQUIRED) find_package(Freetype REQUIRED) -find_package(Boost REQUIRED system) +find_package(Boost REQUIRED system regex) find_package(SDL REQUIRED) find_package(DevIL REQUIRED) find_package(ODE REQUIRED) Modified: trunk/rcssserver3d/cmake/FindODE.cmake =================================================================== --- trunk/rcssserver3d/cmake/FindODE.cmake 2015-09-12 01:48:59 UTC (rev 404) +++ trunk/rcssserver3d/cmake/FindODE.cmake 2016-05-29 05:27:56 UTC (rev 405) @@ -97,6 +97,7 @@ ${ODE_CONFIG_PREFIX}/lib /usr/lib /usr/lib64 + /usr/lib/x86_64-linux-gnu /usr/local/lib $ENV{ODE_HOME}/lib C:/library/ode/lib/ Modified: trunk/rcssserver3d/plugin/soccer/CMakeLists.txt =================================================================== --- trunk/rcssserver3d/plugin/soccer/CMakeLists.txt 2015-09-12 01:48:59 UTC (rev 404) +++ trunk/rcssserver3d/plugin/soccer/CMakeLists.txt 2016-05-29 05:27:56 UTC (rev 405) @@ -51,6 +51,11 @@ rcs3dmonitor/rcs3dmonitor.h ) +if (RVDRAW) + list(APPEND soccer_LIB_HDRS rvdraw/rvdraw.h) +endif (RVDRAW) + + set(soccer_LIB_SRCS export.cpp agentstate/agentstate.cpp @@ -131,6 +136,11 @@ rcs3dmonitor/rcs3dmonitor_c.cpp ) +if (RVDRAW) + list(APPEND soccer_LIB_SRCS rvdraw/rvdraw.cpp) +endif (RVDRAW) + + include_directories(${CMAKE_CURRENT_SOURCE_DIR} ${FREETYPE_INCLUDE_DIRS} ${IL_INCLUDE_DIR}) Modified: trunk/rcssserver3d/plugin/soccer/agentcollisionhandler/agentcollisionhandler.cpp =================================================================== --- trunk/rcssserver3d/plugin/soccer/agentcollisionhandler/agentcollisionhandler.cpp 2015-09-12 01:48:59 UTC (rev 404) +++ trunk/rcssserver3d/plugin/soccer/agentcollisionhandler/agentcollisionhandler.cpp 2016-05-29 05:27:56 UTC (rev 405) @@ -7,6 +7,8 @@ { } +#include <ode/ode.h> + void AgentCollisionHandler::HandleCollision(boost::shared_ptr<Collider> collidee, GenericContact& contact) { if (!mAgentState.get()) @@ -44,6 +46,14 @@ myGroup->clear(); mAgentState->SetTouchGroup(otherGroup); } + dContact& ODEContact = (dContact&) contact; + //GetLog()->Error() << "(AgentCollisionHandler) contact pos " << ODEContact.geom.pos[0]<<","<< ODEContact.geom.pos[1] << ","<< ODEContact.geom.pos[2] << "\n"; + mAgentState->mCollisionPos.x() = ODEContact.geom.pos[0]; + mAgentState->mCollisionPos.y() = ODEContact.geom.pos[1]; + mAgentState->mCollisionPos.z() = ODEContact.geom.pos[2]; + other->mCollisionPos.x() = ODEContact.geom.pos[0]; + other->mCollisionPos.y() = ODEContact.geom.pos[1]; + other->mCollisionPos.z() = ODEContact.geom.pos[2]; } } Modified: trunk/rcssserver3d/plugin/soccer/agentstate/agentstate.h =================================================================== --- trunk/rcssserver3d/plugin/soccer/agentstate/agentstate.h 2015-09-12 01:48:59 UTC (rev 404) +++ trunk/rcssserver3d/plugin/soccer/agentstate/agentstate.h 2016-05-29 05:27:56 UTC (rev 405) @@ -122,6 +122,9 @@ /** Set the current touch group */ void SetTouchGroup(boost::shared_ptr<TouchGroup> group); + /** Point at which collision with another agent occurred */ + salt::Vector3f mCollisionPos; + protected: /** team index */ TTeamIndex mTeamIndex; Modified: trunk/rcssserver3d/plugin/soccer/ballstateaspect/ballstateaspect.cpp =================================================================== --- trunk/rcssserver3d/plugin/soccer/ballstateaspect/ballstateaspect.cpp 2015-09-12 01:48:59 UTC (rev 404) +++ trunk/rcssserver3d/plugin/soccer/ballstateaspect/ballstateaspect.cpp 2016-05-29 05:27:56 UTC (rev 405) @@ -49,6 +49,13 @@ { } + +bool BallStateAspect::GetCollidingAgents(list<boost::shared_ptr<AgentAspect> >& agents) +{ + agents = mCollidingAgents; + return agents.size() > 0; +} + bool BallStateAspect::GetLastCollidingAgent(boost::shared_ptr<AgentAspect>& agent, TTime& time) { @@ -67,10 +74,11 @@ return (agent.get() != 0); } -void BallStateAspect::UpdateLastCollidingAgent() +void BallStateAspect::UpdateCollidingAgents() { mCollidingWithLeftTeamAgent = false; mCollidingWithRightTeamAgent = false; + mCollidingAgents = list<boost::shared_ptr<AgentAspect> >(); // get a list of agents that collided with the ball since the last // update of the recorder and remember the first returned node as @@ -96,6 +104,7 @@ " get AgentState from an AgentAspect\n"; } else { + mCollidingAgents.push_back(agent); TTeamIndex team = agentState->GetTeamIndex(); if (team == TI_LEFT) { mCollidingWithLeftTeamAgent = true; @@ -184,7 +193,7 @@ return; } - UpdateLastCollidingAgent(); + UpdateCollidingAgents(); UpdateBallOnField(); UpdateLastValidBallPos(); UpdateGoalState(); Modified: trunk/rcssserver3d/plugin/soccer/ballstateaspect/ballstateaspect.h =================================================================== --- trunk/rcssserver3d/plugin/soccer/ballstateaspect/ballstateaspect.h 2015-09-12 01:48:59 UTC (rev 404) +++ trunk/rcssserver3d/plugin/soccer/ballstateaspect/ballstateaspect.h 2016-05-29 05:27:56 UTC (rev 405) @@ -47,6 +47,11 @@ */ virtual void Update(float deltaTime); + /** returns list of agents colliding with the ball + */ + bool GetCollidingAgents + (std::list<boost::shared_ptr<oxygen::AgentAspect> >& agents); + /** returns the last agent that collided with the ball and the time when this happened*/ bool GetLastCollidingAgent @@ -88,10 +93,8 @@ /** reset the reference to the ball and field recorder */ virtual void OnUnlink(); - /** updates the reference to the last agent that collided with the - ball - */ - void UpdateLastCollidingAgent(); + /** updates the references to agents colliding with the ball */ + void UpdateCollidingAgents(); /** checks if the ball is on the playing field an updates the mBallOnField flag @@ -120,6 +123,9 @@ /** reference to the right goal recorder */ boost::shared_ptr<oxygen::RecorderHandler> mRightGoalRecorder; + /** list of references to agents currently colliding with the ball */ + std::list<boost::shared_ptr<oxygen::AgentAspect> > mCollidingAgents; + /** holds a reference to the last agent that collided with the ball */ boost::shared_ptr<oxygen::AgentAspect> mLastCollidingAgent; Modified: trunk/rcssserver3d/plugin/soccer/internalsoccermonitor/internalsoccerinput.cpp =================================================================== --- trunk/rcssserver3d/plugin/soccer/internalsoccermonitor/internalsoccerinput.cpp 2015-09-12 01:48:59 UTC (rev 404) +++ trunk/rcssserver3d/plugin/soccer/internalsoccermonitor/internalsoccerinput.cpp 2016-05-29 05:27:56 UTC (rev 405) @@ -61,6 +61,8 @@ //JAN scriptServer->CreateVariable("Command.FreeKickLeft", CmdFreeKickLeft); scriptServer->CreateVariable("Command.FreeKickRight", CmdFreeKickRight); + scriptServer->CreateVariable("Command.DirectFreeKickLeft", CmdDirectFreeKickLeft); + scriptServer->CreateVariable("Command.DirectFreeKickRight", CmdDirectFreeKickRight); scriptServer->CreateVariable("Command.NextCamera", CmdNextCamera); scriptServer->CreateVariable("Command.PreviousCamera", CmdPreviousCamera); @@ -255,6 +257,19 @@ } break; + case CmdDirectFreeKickLeft: + if (input.GetKeyPress()) + { + mGameState->SetPlayMode(PM_DIRECT_FREE_KICK_LEFT); + } + break; + case CmdDirectFreeKickRight: + if (input.GetKeyPress()) + { + mGameState->SetPlayMode(PM_DIRECT_FREE_KICK_RIGHT); + + } + break; case CmdKillAgentLeft: if (input.GetKeyPress()) { Modified: trunk/rcssserver3d/plugin/soccer/internalsoccermonitor/internalsoccerinput.h =================================================================== --- trunk/rcssserver3d/plugin/soccer/internalsoccermonitor/internalsoccerinput.h 2015-09-12 01:48:59 UTC (rev 404) +++ trunk/rcssserver3d/plugin/soccer/internalsoccermonitor/internalsoccerinput.h 2016-05-29 05:27:56 UTC (rev 405) @@ -56,7 +56,9 @@ //JAN CmdFreeKickLeft = CmdCameraRightGoal + 1, CmdFreeKickRight = CmdFreeKickLeft + 1, - CmdKillAgentLeft = CmdFreeKickRight + 1, + CmdDirectFreeKickLeft = CmdFreeKickRight + 1, + CmdDirectFreeKickRight = CmdDirectFreeKickLeft + 1, + CmdKillAgentLeft = CmdDirectFreeKickRight + 1, CmdKillAgentRight = CmdKillAgentLeft + 1, CmdNextCamera = CmdKillAgentRight + 1, Added: trunk/rcssserver3d/plugin/soccer/rvdraw/rvdraw.cpp =================================================================== --- trunk/rcssserver3d/plugin/soccer/rvdraw/rvdraw.cpp (rev 0) +++ trunk/rcssserver3d/plugin/soccer/rvdraw/rvdraw.cpp 2016-05-29 05:27:56 UTC (rev 405) @@ -0,0 +1,719 @@ +/* + * Copyright (C) 2011 Justin Stoecker + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "rvdraw.h" +#include "soccertypes.h" + +long RVSender::uniqueIdNum; + + +/** + * sockfd = -1 on error! + * This creates a socket, which + * is then closed by the + * destructor. Do not close the + * socket! + */ +RVSender::RVSender() +{ + socketCreated = false; + sockfd = -1; + + struct addrinfo hints, *servinfo, *p_ptr; + int rv; + + char *mHost = getenv("RVDRAW_HOST"); + if (mHost == NULL) { + return; + } + + memset(&hints, 0, sizeof hints); + hints.ai_family = AF_UNSPEC; + hints.ai_socktype = SOCK_DGRAM; + + if ((rv = getaddrinfo(mHost, ROBOVIS_PORT, &hints, &servinfo)) != 0) { + fprintf(stderr, "getaddrinfo: %s\n", gai_strerror(rv)); + return; + } + + // loop through all the results and make a socket + for(p_ptr = servinfo; p_ptr != NULL; p_ptr = p_ptr->ai_next) { + if ((sockfd = socket(p_ptr->ai_family, p_ptr->ai_socktype, + p_ptr->ai_protocol)) == -1) { + perror("socket"); + continue; + } + + p = *p_ptr; + + break; + } + + if (p_ptr == NULL) { + fprintf(stderr, "failed to bind socket\n"); + freeaddrinfo(servinfo); + return; + } + + socketCreated = true; + + //freeaddrinfo(servinfo); +} + +/** + * Give a socket and addrinfo. + * Whoever created the socket is + * responsible for closing it! + */ +RVSender::RVSender(int sockfd_, struct addrinfo p_) +{ + socketCreated = false; + p = p_; + sockfd = sockfd_; +} + +RVSender::~RVSender() +{ + if (socketCreated) + close(sockfd); +} + +/* +int RVSender::getSockFD() + { + return sockfd; + } + +struct addrinfo RVSender::getP() + { + return p; + } +*/ + + +char RVSender::getTeamAgent(int uNum, int side) { + return (side == TI_LEFT ? uNum : uNum + 128) - 1; +} + +//drawing colors are uniform & team specific +//this must match the enum in rvdraw.h +void RVSender::getColor(int uNum, float &r, float &g, float &b, bool shade) { + switch(uNum) { + case 1: //red + r = 1; + g = 0; + b = 0; + break; + case 2: //orange + r = 1; + g = 0.5f; + b = 0; + break; + case 3: //yellow + r = 1; + g = 1; + b = 0; + break; + case 4: //green + r = 0; + g = 1; + b = 0; + break; + case 5: //blue-green + r = 0; + g = 1; + b = 0.5f; + break; + case 6: //light blue + r = 0; + g = 1; + b = 1; + break; + case 7: //blue + r = 0; + g = 0.5f; + b = 1; + break; + case 8: //dark blue + r = 0; + g = 0; + b = 1; + break; + case 9: //violet + r = 0.5f; + g = 0; + b = 1; + break; + case 10: //pink + r = 1; + g = 0; + b = 1; + break; + case 11: //magenta + r = 1; + g = 0; + b = 0.5f; + break; + default: + r = 0; + g = 0; + b = 0; + } + + // Get darker color + if (shade) { + r /= 2.0f; + g /= 2.0f; + b /= 2.0f; + } +} + +string RVSender::getMyId() { + return "rcss"; +} + +string RVSender::getDrawingId(const string* name) { + stringstream stream; + stream << getMyId() << '.' << *name; + return stream.str(); +} + +string RVSender::getUniqueId(long unique) { + stringstream stream; + stream << '_' << unique << '.' << getMyId(); + return stream.str(); +} + +string RVSender::getUniqueId() { + return getUniqueId(uniqueIdNum++); +} + +void RVSender::flipPolygon(float *v, int numVerts) { + /* must flip each number, there are three numbers (x, y, z) for each vertex */ + for (int i = 0; i < numVerts * 3; i++) { + v[i] = -v[i]; + } +} + +void RVSender::updateDrawings(string id, string buf) { + drawings[id] = buf; +} + + +// === Public Methods === + +void RVSender::clear() { + for (map<string,string>::iterator it = drawings.begin(); + it != drawings.end(); ++it) { + it->second = ""; + } +} + +void RVSender::refresh() { + string myId(getMyId()); + swapBuffers(&myId); +} + +void RVSender::clearStaticDrawings() { + for (long i = 0; i < uniqueIdNum; i++) { + string uniqueId = getUniqueId(i); + swapBuffers(&uniqueId); + } + uniqueIdNum = 0; +} + +void RVSender::drawCircle(string name, double x, double y, double radius, + RVSender::Color c, bool shade) { + float r, g, b; + getColor(c, r, g, b, shade); + drawCircle(name, x, y, radius, r, g, b); +} + +void RVSender::drawCircle(string name, double x, double y, double radius, float r, float g, float b) { + string id = getDrawingId(&name); + string buf = string(id); + drawCircle(x, y, radius, 3, r, g, b, &buf); + updateDrawings(id, buf); +} + +void RVSender::drawCircle(double x, double y, double radius, RVSender::Color c, bool shade) { + float r, g, b; + getColor(c, r, g, b, shade); + drawCircle(x, y, radius, r, g, b); +} + +void RVSender::drawCircle(double x, double y, double radius, float r, float g, float b) { + string id = getUniqueId(); + string buf = string(id); + drawCircle(x, y, radius, 3, r, g, b, &buf); + swapBuffers(&id); +} + +void RVSender::drawLine(string name, double x1, double y1, double x2, double y2, + RVSender::Color c, bool shade) { + float r, g, b; + getColor(c, r, g, b, shade); + drawLine(name, x1, y1, x2, y2, r, g, b); +} + +void RVSender::drawLine(string name, double x1, double y1, double x2, double y2, + float r, float g, float b) { + string id = getDrawingId(&name); + string buf = string(id); + drawLine(x1, y1, 0, x2, y2, 0, 3, r, g, b, &buf); + updateDrawings(id, buf); +} + +void RVSender::drawLine(double x1, double y1, double x2, double y2, RVSender::Color c, bool shade) { + float r, g, b; + getColor(c, r, g, b, shade); + drawLine(x1, y1, x2, y2, r, g, b); +} + +void RVSender::drawLine(double x1, double y1, double x2, double y2, float r, float g, float b) { + string id = getUniqueId(); + string buf = string(id); + drawLine(x1, y1, 0, x2, y2, 0, 3, r, g, b, &buf); + swapBuffers(&id); +} + +void RVSender::drawText(string name, string text, double x, double y, + RVSender::Color c, bool shade) { + float r, g, b; + getColor(c, r, g, b, shade); + drawText(name, text, x, y, r, g, b); +} + +void RVSender::drawText(string name, string text, double x, double y, + float r, float g, float b) { + string id = getDrawingId(&name); + string buf = string(id); + drawAnnotation(&text, x, y, 0, r, g, b, &buf); + updateDrawings(id, buf); +} + +void RVSender::drawText(string text, double x, double y, + RVSender::Color c, bool shade) { + float r, g, b; + getColor(c, r, g, b, shade); + drawText(text, x, y, r, g, b); +} + +void RVSender::drawText(string text, double x, double y, + float r, float g, float b) { + string id = getUniqueId(); + string buf = string(id); + drawAnnotation(&text, x, y, 0, r, g, b, &buf); + swapBuffers(&id); +} + +void RVSender::drawPoint(string name, double x, double y, double radius, + RVSender::Color c, bool shade) { + float r, g, b; + getColor(c, r, g, b, shade); + drawPoint(name, x, y, radius, r, g, b); +} + +void RVSender::drawPoint(string name, double x, double y, double radius, + float r, float g, float b) { + string id = getDrawingId(&name); + string buf = string(id); + drawPoint(x, y, 0, radius, r, g, b, &buf); + updateDrawings(id, buf); +} + +void RVSender::drawPoint(double x, double y, double radius, + RVSender::Color c, bool shade) { + float r, g, b; + getColor(c, r, g, b, shade); + drawPoint(x, y, radius, r, g, b); +} + +void RVSender::drawPoint(double x, double y, double radius, + float r, float g, float b) { + string id = getUniqueId(); + string buf = string(id); + drawPoint(x, y, 0, radius, r, g, b, &buf); + swapBuffers(&id); +} + +void RVSender::drawSphere(string name, double x, double y, double z, + double radius, RVSender::Color c, bool shade) { + float r, g, b; + getColor(c, r, g, b, shade); + drawSphere(name, x, y, z, radius, r, g, b); +} + +void RVSender::drawSphere(string name, double x, double y, double z, + double radius, float r, float g, float b) { + string id = getDrawingId(&name); + string buf = string(id); + drawSphere(x, y, z, radius, r, g, b, &buf); + updateDrawings(id, buf); +} + +void RVSender::drawSphere(double x, double y, double z, + double radius, RVSender::Color c, bool shade) { + float r, g, b; + getColor(c, r, g, b, shade); + drawSphere(x, y, z, radius, r, g, b); +} + +void RVSender::drawSphere(double x, double y, double z, + double radius, float r, float g, float b) { + string id = getUniqueId(); + string buf = string(id); + drawSphere(x, y, z, radius, r, g, b, &buf); + swapBuffers(&id); +} + +void RVSender::drawPolygon(string name, float *v, int numVerts, + RVSender::Color c, bool shade, float a) { + float r, g, b; + getColor(c, r, g, b, shade); + drawPolygon(name, v, numVerts, r, g, b, a); +} + +void RVSender::drawPolygon(string name, float *v, int numVerts, + float r, float g, float b, float a) { + string id = getDrawingId(&name); + string buf = string(id); + drawPolygon((float*)v, numVerts, r, g, b, a, &buf); + updateDrawings(id, buf); +} + +void RVSender::drawPolygon(float *v, int numVerts, + RVSender::Color c, bool shade, float a) { + float r, g, b; + getColor(c, r, g, b, shade); + drawPolygon(v, numVerts, r, g, b, a); +} + +void RVSender::drawPolygon(float *v, int numVerts, + float r, float g, float b, float a) { + string id = getUniqueId(); + string buf = string(id); + drawPolygon((float*)v, numVerts, r, g, b, a, &buf); + swapBuffers(&id); +} + +void RVSender::drawAgentText(string text, int uNum, int side, RVSender::Color c, bool shade) { + float r, g, b; + getColor(c, r, g, b, shade); + drawAgentText(text, uNum, side, r, g, b); +} + +void RVSender::drawAgentText(string text, int uNum, int side, float r, float g, float b) { + char teamAgent = getTeamAgent(uNum, side); + drawAgentAnnotation(&text, teamAgent, r, g, b); +} + +void RVSender::removeAgentText(int u, int s) { + char teamAgent = getTeamAgent(u, s); + removeAgentAnnotation(teamAgent); +} + +void RVSender::selectAgent(int u, int s) { + char teamAgent = getTeamAgent(u, s); + selectAgent(teamAgent); +} + +void RVSender::swapBuffers(const string* setName) { + int bufSize = -1; + unsigned char* buf = newBufferSwap(setName, &bufSize); + sendto(sockfd, buf, bufSize, 0, p.ai_addr, p.ai_addrlen); + delete[] buf; +} + +void RVSender::drawLine(float x1, float y1, float z1, float x2, float y2, float z2, float thickness, float r, float g, float b, + const string* setName) { + float pa[3] = {x1,y1,z1}; + float pb[3] = {x2,y2,z2}; + float color[3] = {r,g,b}; + + int bufSize = -1; + unsigned char* buf = newLine(pa, pb, thickness, color, setName, &bufSize); + sendto(sockfd, buf, bufSize, 0, p.ai_addr, p.ai_addrlen); + delete[] buf; +} + +void RVSender::drawCircle(float x, float y, float radius, float thickness, float r, float g, float b, const string* setName) { + float center[2] = {x,y}; + float color[3] = {r,g,b}; + + int bufSize = -1; + unsigned char* buf = newCircle(center, radius, thickness, color, setName, &bufSize); + sendto(sockfd, buf, bufSize, 0, p.ai_addr, p.ai_addrlen); + delete[] buf; +} + +void RVSender::drawSphere(float x, float y, float z, float radius, float r, float g, float b, const string* setName) { + float center[3] = {x,y,z}; + float color[3] = {r,g,b}; + + int bufSize = -1; + unsigned char* buf = newSphere(center, radius, color, setName, &bufSize); + sendto(sockfd, buf, bufSize, 0, p.ai_addr, p.ai_addrlen); + delete[] buf; +} + +void RVSender::drawPoint(float x, float y, float z, float size, float r, float g, float b, const string* setName) { + float center[3] = {x,y,z}; + float color[3] = {r,g,b}; + + //printf("Point: (%f, %f, %f)\n", x, y, z); + + int bufSize = -1; + unsigned char* buf = newPoint(center, size, color, setName, &bufSize); + sendto(sockfd, buf, bufSize, 0, p.ai_addr, p.ai_addrlen); + delete[] buf; +} + +void RVSender::drawPolygon(const float* v, int numVerts, float r, float g, float b, float a, + const string* setName) { + float color[4] = {r,g,b,a}; + + int bufSize = -1; + unsigned char* buf = newPolygon(v, numVerts, color, setName, &bufSize); + sendto(sockfd, buf, bufSize, 0, p.ai_addr, p.ai_addrlen); + delete[] buf; +} + +void RVSender::drawAnnotation(const string *txt, float x, float y, float z, + float r, float g, float b, const string *setName) +{ + float color[3] = {r,g,b}; + float point[3] = {x,y,z}; + int bufSize = -1; + unsigned char *buf = newAnnotation(txt, point, color, setName, &bufSize); + sendto(sockfd, buf, bufSize, 0, p.ai_addr, p.ai_addrlen); + delete[] buf; +} + +void RVSender::drawAgentAnnotation(const string *txt, char teamAgent, + float r, float g, float b) +{ + float color[3] = {r,g,b}; + int bufSize = -1; + unsigned char *buf = newAgentAnnotation(txt, teamAgent, color, &bufSize); + sendto(sockfd, buf, bufSize, 0, p.ai_addr, p.ai_addrlen); + delete[] buf; +} + +void RVSender::removeAgentAnnotation(char teamAgent) +{ + int bufSize = -1; + unsigned char *buf = newRemoveAgentAnnotation(teamAgent, &bufSize); + sendto(sockfd, buf, bufSize, 0, p.ai_addr, p.ai_addrlen); + delete[] buf; +} + +void RVSender::selectAgent(char teamAgent) +{ + int bufSize = -1; + unsigned char *buf = newSelectAgent(teamAgent, &bufSize); + sendto(sockfd, buf, bufSize, 0, p.ai_addr, p.ai_addrlen); + delete[] buf; +} + +// The following commands allocate memory, if you use them be sure to deallocate +// the memory later. + +unsigned char* RVSender::newBufferSwap(const string* name, int* bufSize) { + *bufSize = 3 + ((name != NULL) ? name->length() : 0); + unsigned char* buf = new unsigned char[*bufSize]; + + long i = 0; + i += writeCharToBuf(buf+i, 0); + i += writeCharToBuf(buf+i, 0); + i += writeStringToBuf(buf+i, name); + + return buf; +} + +unsigned char* RVSender::newCircle(const float* center, float radius, float thickness, + const float* color, const string* setName, int* bufSize) { + + *bufSize = 30 + ((setName != NULL) ? setName->length() : 0); + unsigned char* buf = new unsigned char[*bufSize]; + + long i = 0; + i += writeCharToBuf(buf+i, 1); + i += writeCharToBuf(buf+i, 0); + i += writeFloatToBuf(buf+i, center[0]); + i += writeFloatToBuf(buf+i, center[1]); + i += writeFloatToBuf(buf+i, radius); + i += writeFloatToBuf(buf+i, thickness); + i += writeColorToBuf(buf+i, color, 3); + i += writeStringToBuf(buf+i, setName); + + return buf; +} + +unsigned char* RVSender::newLine(const float* a, const float* b, float thickness, + const float* color, const string* setName, int* bufSize) { + + *bufSize = 48 + ((setName != NULL) ? setName->length() : 0); + unsigned char* buf = new unsigned char[*bufSize]; + + long i = 0; + i += writeCharToBuf(buf+i, 1); + i += writeCharToBuf(buf+i, 1); + i += writeFloatToBuf(buf+i, a[0]); + i += writeFloatToBuf(buf+i, a[1]); + i += writeFloatToBuf(buf+i, a[2]); + i += writeFloatToBuf(buf+i, b[0]); + i += writeFloatToBuf(buf+i, b[1]); + i += writeFloatToBuf(buf+i, b[2]); + i += writeFloatToBuf(buf+i, thickness); + i += writeColorToBuf(buf+i, color, 3); + i += writeStringToBuf(buf+i, setName); + + return buf; +} + +unsigned char* RVSender::newPoint(const float* p, float size, const float* color, + const string* setName, int* bufSize) { + + *bufSize = 30 + ((setName != NULL) ? setName->length() : 0); + unsigned char* buf = new unsigned char[*bufSize]; + + long i = 0; + i += writeCharToBuf(buf+i, 1); + i += writeCharToBuf(buf+i, 2); + i += writeFloatToBuf(buf+i, p[0]); + i += writeFloatToBuf(buf+i, p[1]); + i += writeFloatToBuf(buf+i, p[2]); + i += writeFloatToBuf(buf+i, size); + i += writeColorToBuf(buf+i, color, 3); + i += writeStringToBuf(buf+i, setName); + + return buf; +} + +unsigned char* RVSender::newSphere(const float* p, float radius, const float* color, + const string* setName, int* bufSize) { + + *bufSize = 30 + ((setName != NULL) ? setName->length() : 0); + unsigned char* buf = new unsigned char[*bufSize]; + + long i = 0; + i += writeCharToBuf(buf+i, 1); + i += writeCharToBuf(buf+i, 3); + i += writeFloatToBuf(buf+i, p[0]); + i += writeFloatToBuf(buf+i, p[1]); + i += writeFloatToBuf(buf+i, p[2]); + i += writeFloatToBuf(buf+i, radius); + i += writeColorToBuf(buf+i, color, 3); + i += writeStringToBuf(buf+i, setName); + + return buf; +} + +unsigned char* RVSender::newPolygon(const float* v, int numVerts, const float* color, + const string* setName, int* bufSize) { + + *bufSize = 18 * numVerts + 8 + ((setName != NULL) ? setName->length() : 0); + unsigned char* buf = new unsigned char[*bufSize]; + + long i = 0; + i += writeCharToBuf(buf+i, 1); + i += writeCharToBuf(buf+i, 4); + i += writeCharToBuf(buf+i, numVerts); + i += writeColorToBuf(buf+i, color, 4); + + for (int j = 0; j < numVerts; j++) { + i += writeFloatToBuf(buf+i, v[j*3+0]); + i += writeFloatToBuf(buf+i, v[j*3+1]); + i += writeFloatToBuf(buf+i, v[j*3+2]); + } + + i += writeStringToBuf(buf+i, setName); + + return buf; +} + +unsigned char* RVSender::newAnnotation(const string *txt, const float *p, const float* color, + const string* setName, int* bufSize) { + + *bufSize = 25 + ((setName != NULL) ? setName->length() : 0) + + ((txt != NULL) ? txt->length(): 0); + unsigned char* buf = new unsigned char[*bufSize]; + + long i = 0; + i += writeCharToBuf(buf+i, 2); + i += writeCharToBuf(buf+i, 0); + i += writeFloatToBuf(buf+i, p[0]); + i += writeFloatToBuf(buf+i, p[1]); + i += writeFloatToBuf(buf+i, p[2]); + i += writeColorToBuf(buf+i, color, 3); + i += writeStringToBuf(buf+i, txt); + i += writeStringToBuf(buf+i, setName); + + return buf; +} + +unsigned char* RVSender::newAgentAnnotation(const string *txt, const char teamAgent, const float* color, int* bufSize) { + + *bufSize = 7 + ((txt != NULL) ? txt->length(): 0); + unsigned char* buf = new unsigned char[*bufSize]; + + long i = 0; + i += writeCharToBuf(buf+i, 2); + i += writeCharToBuf(buf+i, 1); + i += writeCharToBuf(buf+i, teamAgent); + i += writeColorToBuf(buf+i, color, 3); + i += writeStringToBuf(buf+i, txt); + + return buf; +} + +unsigned char* RVSender::newRemoveAgentAnnotation(const char teamAgent, int* bufSize) { + + *bufSize = 3; + unsigned char* buf = new unsigned char[*bufSize]; + + long i = 0; + i += writeCharToBuf(buf+i, 2); + i += writeCharToBuf(buf+i, 2); + i += writeCharToBuf(buf+i, teamAgent); + + return buf; +} + +unsigned char* RVSender::newSelectAgent(const char teamAgent, int* bufSize) { + + *bufSize = 3; + unsigned char* buf = new unsigned char[*bufSize]; + + long i = 0; + i += writeCharToBuf(buf+i, 3); + i += writeCharToBuf(buf+i, 0); + i += writeCharToBuf(buf+i, teamAgent); + + return buf; +} + +/* +int main() + { + RVSender send = RVSender(); + string str = string("thing"); + send.drawPoint(1, 1, 1, 4, 1, 0, 0, &str); + send.swapBuffers(&str); + } +//*/ + Added: trunk/rcssserver3d/plugin/soccer/rvdraw/rvdraw.h =================================================================== --- trunk/rcssserver3d/plugin/soccer/rvdraw/rvdraw.h (rev 0) +++ trunk/rcssserver3d/plugin/soccer/rvdraw/rvdraw.h 2016-05-29 05:27:56 UTC (rev 405) @@ -0,0 +1,301 @@ +#ifndef RVDRAW_H +#define RVDRAW_H + +/* + * Copyright (C) 2011 Justin Stoecker + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +#include <cstdio> +#include <cstring> +#include <stdio.h> +#include <stdlib.h> +#include <unistd.h> +#include <errno.h> +#include <string.h> +#include <sys/types.h> +#include <sys/socket.h> +#include <netinet/in.h> +#include <arpa/inet.h> +#include <netdb.h> +#include <string> +#include <math.h> +#include <map> +#include <boost/lexical_cast.hpp> +#include <sstream> +#include <iomanip> + +#define ROBOVIS_PORT "32769" + +//class RVSender; + +//RVSender* pRVSender; + +using namespace std; + +//extern string mRVDrawHost; + +inline int writeCharToBuf(unsigned char* buf, unsigned char value) { + *buf = value; + return 1; +} + +inline int writeFloatToBuf(unsigned char* buf, float value) { + char temp[20]; + sprintf(temp, "%6f", value); + memcpy(buf, temp, 6); + return 6; +} + +inline int writeColorToBuf(unsigned char* buf, const float* color, int channels) { + int i; + for (i = 0; i < channels; i++) + writeCharToBuf(buf+i, (unsigned char)(color[i]*255)); + return i; +} + +inline int writeStringToBuf(unsigned char* buf, const string* text) { + long i = 0; + if (text != NULL) + i += text->copy((char*)buf+i, text->length(), 0); + i += writeCharToBuf(buf+i, 0); + return i; +} + +//for the drawings map +struct DrawObject { + string id; + string buf; +}; + +class RVSender +{ +private: + static long uniqueIdNum; + map<string, string> drawings; + char getTeamAgent(int uNum, int side); //for AgentAnnotation commands + void getColor(int uNum, float &r, float &g, float &b, bool shade=false); + string getMyId(); + string getDrawingId(const string* name); + string getUniqueId(long unique); + string getUniqueId(); + void flipPolygon(float *v, const int numVerts); //for agents on SIDE_RIGHT + void updateDrawings(string id, string buf); + + int sockfd; + struct addrinfo p; + bool socketCreated; + + unsigned char* newBufferSwap(const string* name, int* bufSize); + unsigned char* newCircle(const float* center, + float radius, float thickness, + const float* color, + const string* setName, + int *bufSize); + unsigned char* newLine(const float* a, + const float* b, + float thickness, + const float* color, + const string* setName, + int* bufSize); + unsigned char* newPoint(const float* p, + float size, + const float* color, + const string* setName, + int* bufSize); + unsigned char* newSphere(const float* p, + float radius, + const float* color, + const string* setName, + int* bufSize); + unsigned char* newPolygon(const float* v, + int numVerts, + const float* color, + const string* setName, + int* bufSize); + unsigned char* newAnnotation(const string *txt, + const float *p, + const float* color, + const string* setName, + int* bufSize); + unsigned char* newAgentAnnotation(const string *txt, + const char teamAgent, + const float* color, + int* bufSize); + unsigned char* newRemoveAgentAnnotation(const char teamAgent, + int* bufSize); + unsigned char* newSelectAgent(const char teamAgent, + int* bufSize); + +public: + RVSender(); + RVSender(int sockfd_, struct addrinfo p); + ~RVSender(); + + inline int getSockFD() { + return sockfd; + } + inline struct addrinfo getP() { + return p; + } + + //this must match the switch in getColor. See rvdraw.cc before changing + enum Color { + RED = 1, ORANGE = 2, YELLOW = 3, GREEN = 4, + BLUEGREEN = 5, LIGHTBLUE = 6, BLUE = 7, DARKBLUE = 8, + VIOLET = 9, PINK = 10, MAGENTA = 11 + }; + + + /* + * These draw commands support animation. + * + * Every time a draw command is called, a map is updated with + * key = string name (the first argument to each of these commands), and + * value = the draw command's buffer (no need to understand that part). + * + * Call refresh() to write these buffers to the screen. + * + * Call clear() to erase what's in the buffers. That allows old shapes to be removed from the + * screen and prevents clutter. It allows you to know what your agents are thinking right now. + * + * It's important to give shapes unique a unique 'string name' argument. + * A shape created with some 'string name' argument will overwrite an older shape with the + * same 'string name' argument. That's how the animation works. + * + * You can use the RVSender::Color enum to specify colors, or specify your own r,g,b values. + */ + + /* draws all elements of drawings map to the screen */ + void refresh(); + + /* erases all elements of drawings map */ + void clear(); + + void drawCircle(string name, double x, double y, double radius, + RVSender::Color c, bool shade=false); + void drawCircle(string name, double x, double y, double radius, float r, float g, float b); + + void drawLine(string name, double x1, double y1, double x2, double y2, + RVSender::Color c, bool shade=false); + void drawLine(string name, double x1, double y1, double x2, double y2, float r, float g, float b); + + void drawText(string name, string text, double x, double y, + RVSender::Color c, bool shade=false); + void drawText(string name, string text, double x, double y, float r, float g, float b); + + void drawPoint(string name, double x, double y, double radius, + RVSender::Color c, bool shade=false); + void drawPoint(string name, double x, double y, double radius, float r, float g, float b); + + void drawSphere(string name, double x, double y, double z, double radius, + RVSender::Color c, bool shade=false); + void drawSphere(string name, double x, double y, double z, double radius, + float r, float g, float b); + + /* format your *v array as {x1, y1, z1, x2, y2, z2, ...} */ + /* the 'a' arguments are for alpha channel (transparency) */ + void drawPolygon(string name, float *v, int numVerts, RVSender::Color c, + bool shade=false, float a=1.0f); + void drawPolygon(string name, float *v, int numVerts, float r, float g, float b, float a=1.0f); + + /* + * These draw commands are for static shapes that remain on the screen indefinitely, + * or until you call clearStaticDrawings() to remove all of them. Use that method on + * a timer to keep only a recent history of drawings on screen. + */ + + /* use this to erase all static shapes. */ + void clearStaticDrawings(); + + void drawCircle(double x, double y, double radius, + RVSender::Color c, bool shade=false); + void drawCircle(double x, double y, double radius, float r, float g, float b); + + void drawLine(double x1, double y1, double x2, double y2, + RVSender::Color c, bool shade=false); + void drawLine(double x1, double y1, double x2, double y2, float r, float g, float b); + + //these two are causing strange errors in roboviz + /*void drawText(string text, double x, double y, + RVSender::Color c, bool shade=false); + void drawText(string text, double x, double y, float r, float g, float b);*/ + + void drawPoint(double x, double y, double radius, + RVSender::Color c, bool shade=false); + void drawPoint(double x, double y, double radius, float r, float g, float b); + + void drawSphere(double x, double y, double z, double radius, + RVSender::Color c, bool shade=false); + void drawSphere(double x, double y, double z, double radius, + float r, float g, float b); + + void drawPolygon(float *v, int numVerts, RVSender::Color c, bool shade=false, float a=1.0f); + void drawPolygon(float *v, int numVerts, float r, float g, float b, float a=1.0f); + + /* + * These agentText commands work differently. No animation involved, you don't need + * the refresh() and clear() commands for these to work. No unique 'string name' either. + */ + + void drawText(string text, double x, double y, + RVSender::Color c, bool shade=false); + void drawText(string text, double x, double y, float r, float g, float b); + + /* draw to player on team "side", with uniform "uNum" */ + void drawAgentText(string text, int uNum, int side, RVSender::Color c, bool shade=false); + void drawAgentText(string text, int uNum, int side, float r, float g, float b); + + /* removes text from a player */ + void removeAgentText(int u, int s); + + void selectAgent(int u, int s); + + + /* old draw commands, don't support the animation */ + void swapBuffers(const string* setName); + void drawLine(float x1, float y1, float z1, + float x2, float y2, float z2, + float thickness, + float r, float g, float b, + const string* setName); + void drawCircle(float x, float y, float radius, + float thickness, + float r, float g, float b, + const string* setName); + void drawSphere(float x, float y, float z, + float radius, + float r, float g, float b, + const string* setName); + void drawPoint(float x, float y, float z, + float size, + float r, float g, float b, + const string *setName); + void drawPolygon(const float *v, int numVerts, + float r, float g, float b, + float a, + const string *setName); + void drawAnnotation(const string *txt, + float x, float y, float z, + float r, float g, float b, + const string *setName); + void drawAgentAnnotation(const string *txt, + char teamAgent, + float r, float g, float b); + void removeAgentAnnotation(char teamAgent); + void selectAgent(char teamAgent); +}; + +#endif // !RVDRAW_H Modified: trunk/rcssserver3d/plugin/soccer/sayeffector/sayeffector.cpp =================================================================== --- trunk/rcssserver3d/plugin/soccer/sayeffector/sayeffector.cpp 2015-09-12 01:48:59 UTC (rev 404) +++ trunk/rcssserver3d/plugin/soccer/sayeffector/sayeffector.cpp 2016-05-29 05:27:56 UTC (rev 405) @@ -25,6 +25,7 @@ #include <agentstate/agentstate.h> #include <soccerbase/soccerbase.h> #include <soccerruleaspect/soccerruleaspect.h> +#include <boost/regex.hpp> using namespace boost; using namespace oxygen; @@ -76,12 +77,24 @@ sayAction->GetMessage(mMessage); ifText=true; - // If " ", "(" or ")" are in mMessage, return false - if (mMessage.find_first_of("() ") != std::string::npos) + // If characters outside allowed value range or " ", "(" or ")" are in mMessage, return false + boost::regex allowedCharacterRange("[\x20-\x7E]*"); + if (!boost::regex_match(mMessage, allowedCharacterRange) + || mMessage.find_first_of("() ") != std::string::npos) { - GetLog()->Debug() + std::string teamName = mAgentState->GetTeamIndex() == TI_RIGHT ? "Right" : "Left"; + + // get the GameStateAspect + boost::shared_ptr<GameStateAspect> mGameState = dynamic_pointer_cast<GameStateAspect> + (SoccerBase::GetControlAspect(*this, "GameStateAspect")); + if (mGameState.get() != 0) + { + teamName = mGameState->GetTeamName(mAgentState->GetTeamIndex()); + } + GetLog()->Error() << "(SayEffector) found illegal character. Ignoring message [" - << mMessage << "]\n"; + << mMessage << "] from " << teamName << " " + << mAgentState->GetUniformNumber() << "\n"; ifText=false; Modified: trunk/rcssserver3d/plugin/soccer/soccerbase/soccerbase.cpp =================================================================== --- trunk/rcssserver3d/plugin/soccer/soccerbase/soccerbase.cpp 2015-09-12 01:48:59 UTC (rev 404) +++ trunk/rcssserver3d/plugin/soccer/soccerbase/soccerbase.cpp 2016-05-29 05:27:56 UTC (rev 405) @@ -608,6 +608,12 @@ case PM_FREE_KICK_RIGHT: return STR_PM_FREE_KICK_RIGHT; + case PM_DIRECT_FREE_KICK_LEFT: + return STR_PM_DIRECT_FREE_KICK_LEFT; + + case PM_DIRECT_FREE_KICK_RIGHT: + return STR_PM_DIRECT_FREE_KICK_RIGHT; + default: return STR_PM_Unknown; }; Modified: trunk/rcssserver3d/plugin/soccer/soccerruleaspect/soccerruleaspect.cpp =================================================================== --- trunk/rcssserver3d/plugin/soccer/soccerruleaspect/soccerruleaspect.cpp 2015-09-12 01:48:59 UTC (rev 404) +++ trunk/rcssserver3d/plugin/soccer/soccerruleaspect/soccerruleaspect.cpp 2016-05-29 05:27:56 UTC (rev 405) @@ -32,6 +32,10 @@ #include <agentstate/agentstate.h> #include <algorithm> +#ifdef RVDRAW +#include <rvdraw/rvdraw.h> +#endif // RVDRAW + using namespace oxygen; using namespace boost; using namespace std; @@ -40,11 +44,15 @@ SoccerRuleAspect::SoccerRuleAspect() : SoccerControlAspect(), mBallRadius(0.111), + mAgentRadius(0.4), mGoalPauseTime(3), mKickInPauseTime(1), mHalfTime(2.25 * 60), + mDropBallTime(15), mFreeKickDist(9.15), mFreeKickMoveDist(15.15), + mRepelPlayersForKick(false), + mKickRepelDist(0.5), mGoalKickDist(1.0), mAutomaticKickOff(false), mWaitBeforeKickOff(1.0), @@ -54,32 +62,69 @@ mAutoKickOffTimeOrigin(1000000.0), mSayMsgSize(20), mAudioCutDist(50.0), - mFirstCollidingAgent(true), - mNotOffside(false), - mLastModeWasPlayOn(false), - mUseOffside(true), - mUseCharging(false), - mChargingMinSpeed(0.2), - mChargingMinBallDist(0.2), - mChargingMaxOppSpeedAngle(90), - mChargingIllInterceptMinMutualSpeedAngel(70), - mDropBallTime(15), mNotStandingMaxTime(1000), // max time player may be sitted or laying down before being repositioned + mGroundMaxTime(1000), // max time player may be on the ground before being repositioned mGoalieNotStandingMaxTime(1000), // max time goalie may be sitted or laying down before being repositioned - mGroundMaxTime(1000), // max time player may be on the ground before being repositioned mGoalieGroundMaxTime(1000), // max time goalie (pl number 1) may be on the ground before being repositioned - mMaxPlayersInsideOwnArea(1000), // maximum number of players of the defending team that may be inside own penalty area mMinOppDistance(0), // min dist for closest Opponent to ball in order to use repositions for 2nd, 3rd player mMin2PlDistance(0), // min dist for second closest of team before being repositioned mMin3PlDistance(0), // min dist for third closest of team before being repositioned + mMaxPlayersInsideOwnArea(1000), // maximum number of players of the defending team that may be inside own penalty area mMaxTouchGroupSize(1000), mMaxFoulTime(0.0), // maximum time allowed for a player to commit a positional foul before being repositioned - mLastKickOffKickTime(0), - mCheckKickOffKickerFoul(false), + mFirstCollidingAgent(true), + mNotOffside(false), + mLastModeWasPlayOn(false), + mUseOffside(true), + mUseCharging(false), + mChargingMinSpeed(0.2), + mChargingMinBallSpeedAngle(15), + mChargingMinDeltaDist(0.2), + mChargingMinDeltaAng(30), + mChargingImmunityTime(1), + mChargingCollisionMinTime(0.2), + mChargingMaxBallRulesDist(100), + mChargingMinCollBallDist(0.1), + mMinCollisionSpeed(0.15), + mFoulHoldTime(0.5), + mLastFreeKickKickTime(0), + mCheckFreeKickKickerFoul(false), mAllowKickOffTeamToScore(true), - mPenaltyShootout(false) + mIndirectKick(false), + mPenaltyShootout(false), + mKeepaway(false), + mKeepawayCenterX(0.0), + mKeepawayCenterY(0.0), + mKeepawayLength(20.0), + mKeepawayWidth(20.0), + mKeepawayLengthReductionRate(4.0), + mKeepawayWidthReductionRate(4.0) { mFreeKickPos = Vector3f(0.0,0.0,mBallRadius); + ResetFoulCounter(TI_LEFT); + ResetFoulCounter(TI_RIGHT); + +#ifdef RVDRAW + // Create connection for sending draw commands to roboviz + mRVSender = boost::shared_ptr<RVSender>(new RVSender()); + if (mRVSender->getSockFD() == -1) + { + mRVSender.reset(); + } +#endif // RVDRAW + + // Initialize values + for (int i = 0; i <= 11; i++) + { + for (int t = 0; t <= 2; t++) + { + playerTimeSinceLastWasMoved[i][t] = 1/.02; + for(int j = 0; j < AVERAGE_VELOCITY_MEASUREMENTS; j++) + { + playerVelocities[i][t][j] = salt::Vector3f(0,0,0); + } + } + } } SoccerRuleAspect::~SoccerRuleAspect() @@ -101,27 +146,71 @@ /* Uses only Ball and Players positions and detects overcrowind near ball and areas and players inappropriate behavior (laying on the ground or not walking for too much time) */ void -SoccerRuleAspect::AutomaticSimpleReferee(TPlayMode playMode) +SoccerRuleAspect::AutomaticSimpleReferee() { + if (mKeepaway) + { + TTime game_time = mGameState->GetTime(); + + float areaMinX = mKeepawayCenterX - mKeepawayLength/2.0 + (mKeepawayLengthReductionRate/2.0*game_time/60.0); + float areaMaxX = mKeepawayCenterX + mKeepawayLength/2.0 - (mKeepawayLengthReductionRate/2.0*game_time/60.0); + float areaMinY = mKeepawayCenterY - mKeepawayWidth/2.0 + (mKeepawayWidthReductionRate/2.0*game_time/60.0); + float areaMaxY = mKeepawayCenterY + mKeepawayWidth/2.0 - (mKeepawayWidthReductionRate/2.0*game_time/60.0); + +#ifdef RVDRAW + if (mRVSender) + { + mRVSender->clear(); + mRVSender->drawLine("KeepawayArea", areaMinX, areaMinY, areaMinX, areaMaxY, RVSender::RED); + mRVSender->drawLine("KeepawayArea", areaMinX, areaMaxY, areaMaxX, areaMaxY, RVSender::RED); + mRVSender->drawLine("KeepawayArea", areaMaxX, areaMaxY, areaMaxX, areaMinY, RVSender::RED); + mRVSender->drawLine("KeepawayArea", areaMaxX, areaMinY, areaMinX, areaMinY, RVSender::RED); + mRVSender->refresh(); + } +#endif // RVDRAW + + if (game_time > 0) + { + bool fBallOutsideKeepawayBox = false; + Vector3f ball_pos = mBallBody->GetPosition(); + if (ball_pos.x() < areaMinX + || ball_pos.x() > areaMaxX + || ball_pos.y() < areaMinY + || ball_pos.y() > areaMaxY) + { + fBallOutsideKeepawayBox = true; + } + + bool fBallCollidedWithTaker = mBallState->GetBallCollidingWithAgentTeam(TI_RIGHT); + + if (fBallOutsideKeepawayBox || fBallCollidedWithTaker) + { + mGameState->SetPlayMode(PM_GameOver); + } + } + } + + if (mPenaltyShootout && mGameState->GetPlayMode() == PM_Goal_Left) { + // Cancel penalty shootout mode now that a goal has been scored + mPenaltyShootout = false; + } + // Reset counters and do not consider players' fouls when game is not - // running + // running (when players can beam) if (mGameState->IsPaused()) { ResetFoulCounter(TI_LEFT); ResetFoulCounter(TI_RIGHT); - - if (mPenaltyShootout && mGameState->GetPlayMode() == PM_Goal_Left) { - // Cancel penalty shootout mode now that a goal has been scored - mPenaltyShootout = false; - } } else { CalculateDistanceArrays(TI_LEFT); // Calculates distance arrays for left team CalculateDistanceArrays(TI_RIGHT); // Calculates distance arrays for right team + UpdateTimesSinceLastBallTouch(); // Resets time since last ball touch for agents currently colliding with ball + AnalyseChargingFouls(); // Analyzes if there are any charging fouls AnalyseFouls(TI_LEFT); // Analyzes simple fouls for the left team AnalyseFouls(TI_RIGHT); // Analyzes simple fouls for the right team - AnalyseTouchGroups(TI_LEFT); // Analyzes how many players are touching for the left team + AnalyseTouchGroups(TI_LEFT); // Analyzes whether too many players are touching for the left team AnalyseTouchGroups(TI_RIGHT); // Analyzes whether too many players are touching for the right team ClearPlayersAutomatic(TI_LEFT); // enforce standing and not overcrowding rules for left team @@ -165,6 +254,9 @@ prevPlayerInsideOwnArea[unum][idx] = 0; playerInsideOwnArea[unum][idx] = 0; playerFoulTime[unum][idx] = 0; + playerTimeSinceLastBallTouch[unum][idx] = mChargingImmunityTime/0.02; + playerChargingTime[unum][idx] = mChargingCollisionMinTime/0.02; + playerLastFoul[unum][idx] = FT_None; } void @@ -176,6 +268,36 @@ } } +// Resets time since last ball touch for agents currently colliding with ball +void +SoccerRuleAspect::UpdateTimesSinceLastBallTouch() +{ + if (mBallState.get() == 0) + return; + + list<boost::shared_ptr<AgentAspect> > agents; + if (mBallState->GetCollidingAgents(agents)) + { + for (list<boost::shared_ptr<AgentAspect> > ::const_iterator agentIt = agents.begin(); + agentIt != agents.end(); + agentIt++) + { + boost::shared_ptr<AgentState> agentState; + if (!SoccerBase::GetAgentState(*agentIt, agentState)) + { + GetLog()->Error() << "ERROR: (SoccerRuleAspect) Cannot get " + "AgentState from an AgentAspect\n"; + } + else + { + int unum = agentState->GetUniformNumber(); + int idx = agentState->GetTeamIndex(); + playerTimeSinceLastBallTouch[unum][idx] = 0; + } + } + } +} + // Process agent state: standing, sitted, laying down, ... void SoccerRuleAspect::ProcessAgentState(salt::Vector3f pos, int unum, TTeamIndex idx) @@ -207,18 +329,32 @@ if (playerStanding[unum][idx] > 0.5 / 0.02) { playerNotStanding[unum][idx] = 0; } + + playerTimeSinceLastBallTouch[unum][idx]++; + playerChargingTime[unum][idx]++; + playerTimeSinceLastWasMoved[unum][idx]++; } // Calculates ordering on a distance vector void SoccerRuleAspect::SimpleOrder(float dArr[][3], int oArr[][3], TTeamIndex idx) { - for(int t1 = 1; t1 <= 10; t1++) - for(int t2 = t1 + 1; t2 <= 11; t2++) + for(int t1 = 1; t1 <= 11; t1++) { + if (HaveEnforceableFoul(t1,idx)) { + // Don't count players who have committed a foul + oArr[t1][idx] = -1; + continue; + } + for(int t2 = t1 + 1; t2 <= 11; t2++) { + if (HaveEnforceableFoul(t2,idx)) { + // Don't count players who have committed a foul + continue; + } if (dArr[t1][idx] >= dArr[t2][idx]) oArr[t1][idx]++; else oArr[t2][idx]++; - + } + } // DEBUG // if (dArr[1][idx]<1000.0) { // cout << "Team: " << idx << " --> "; @@ -279,8 +415,9 @@ prevPlayerInsideOwnArea[unum][idx] = playerInsideOwnArea[unum][idx]; // determine number of players inside area and set inside area state of player - if (idx == TI_LEFT && mLeftPenaltyArea.Contains(Vector2f(agentPos.x(), agentPos.y())) || - idx == TI_RIGHT && mRightPenaltyArea.Contains(Vector2f(agentPos.x(), agentPos.y()))) + if (((idx == TI_LEFT && mLeftPenaltyArea.Contains(Vector2f(agentPos.x(), agentPos.y()))) || + (idx == TI_RIGHT && mRightPenaltyArea.Contains(Vector2f(agentPos.x(), agentPos.y())))) + && !HaveEnforceableFoul(unum,idx)) { numPlInsideOwnArea[idx]++; playerInsideOwnArea[unum][idx] = 1; @@ -304,243 +441,346 @@ SimpleOrder(distGArr, ordGArr, idx); } -void SoccerRuleAspect::AnalyseTouchGroups(TTeamIndex idx) +void SoccerRuleAspect::AnalyseChargingFouls() { - if (idx == TI_NONE || mBallState.get() == 0) + if (!mUseCharging) + { return; + } + + if (mBallState.get() == 0) + return; SoccerBase::TAgentStateList agent_states; - if (! SoccerBase::GetAgentStates(*mBallState.get(), agent_states, idx)) + if (! SoccerBase::GetAgentStates(*mBallState.get(), agent_states, TI_LEFT)) return; - random_shuffle(agent_states.begin(), agent_states.end()); - - // BEGIN FOUL DETECTION - if (mUseCharging) + SoccerBase::TAgentStateList::iterator asIt = agent_states.begin(); + for (; asIt != agent_states.end(); ++asIt) { - - SoccerBase::TAgentStateList::iterator asIt = agent_states.begin(); - for (; asIt != agent_states.end(); ++asIt) + boost::shared_ptr<TouchGroup> touchGroup = (*asIt)->GetTouchGroup(); + if (touchGroup->size() != 2) { - boost::shared_ptr<TouchGroup> touchGroup = (*asIt)->GetTouchGroup(); + continue; + } + + salt::Vector3f agentAvgVel[2]; + salt::Vector3f agentPos[2]; + float s[2]; //agentSpeed + float d[2]; //agentDistToBall + float aVB[2]; //agentAngleOfSpeedVectorToBall + float aVO[2]; //agentAngleOfSpeedVectorToOpponent + int agentUNum[2]; + TTeamIndex agentTeamIndex[2]; + bool isCharging[2]; // Boolean if an agent had co... [truncated message content] |