refbox_state_sender.cpp
00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "refbox_state_sender.h"
00024
00025 #include <netcomm/worldinfo/transceiver.h>
00026 #include <core/macros.h>
00027
00028 #include <cstdio>
00029
00030 using namespace fawkes;
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046 RefBoxStateSender::RefBoxStateSender(const char *addr, unsigned short port,
00047 const char *key, const char *iv,
00048 bool debug)
00049 {
00050 __debug = debug;
00051
00052 __transceiver = new WorldInfoTransceiver(WorldInfoTransceiver::MULTICAST, addr, port, key, iv);
00053 __transceiver->set_loop( true );
00054
00055 __game_state = GS_FROZEN;
00056 __state_team = TEAM_BOTH;
00057 __score_cyan = 0;
00058 __score_magenta = 0;
00059 __our_team = TEAM_CYAN;
00060 __our_goal_color = GOAL_BLUE;
00061 __half = HALF_FIRST;
00062 __timeout_thread = NULL;
00063 }
00064
00065
00066
00067
00068 RefBoxStateSender::RefBoxStateSender()
00069 {
00070 __debug = false;
00071 __transceiver = NULL;
00072 __game_state = GS_FROZEN;
00073 __state_team = TEAM_BOTH;
00074 __score_cyan = 0;
00075 __score_magenta = 0;
00076 __our_team = TEAM_CYAN;
00077 __our_goal_color = GOAL_BLUE;
00078 __half = HALF_FIRST;
00079 __timeout_thread = NULL;
00080 }
00081
00082
00083
00084 RefBoxStateSender::~RefBoxStateSender()
00085 {
00086 if ( __timeout_thread ) {
00087 __timeout_thread->cancel();
00088 __timeout_thread->join();
00089 delete __timeout_thread;
00090 }
00091 delete __transceiver;
00092 }
00093
00094
00095
00096
00097
00098
00099 void
00100 RefBoxStateSender::set_gamestate(int game_state,
00101 worldinfo_gamestate_team_t state_team)
00102 {
00103 if ( __debug ) {
00104 printf("Setting gamestate to '%d' for team '%s'\n",
00105 game_state, worldinfo_gamestate_team_tostring(state_team));
00106 }
00107
00108 __game_state = game_state;
00109 __state_team = state_team;
00110 }
00111
00112
00113
00114
00115
00116
00117 void
00118 RefBoxStateSender::set_score(unsigned int score_cyan, unsigned int score_magenta)
00119 {
00120 if ( __debug ) {
00121 printf("Setting score to %u:%u (cyan:magenta)\n", score_cyan, score_magenta);
00122 }
00123 __score_cyan = score_cyan;
00124 __score_magenta = score_magenta;
00125 }
00126
00127
00128
00129
00130
00131
00132 void
00133 RefBoxStateSender::set_team_goal(worldinfo_gamestate_team_t our_team,
00134 worldinfo_gamestate_goalcolor_t goal_color)
00135 {
00136 if ( __debug ) {
00137 printf("Setting team color to '%s' and goal color to '%s'\n",
00138 worldinfo_gamestate_team_tostring(our_team),
00139 worldinfo_gamestate_goalcolor_tostring(goal_color));
00140 }
00141 __our_team = our_team;
00142 __our_goal_color = goal_color;
00143 }
00144
00145
00146
00147
00148
00149 void
00150 RefBoxStateSender::set_half(worldinfo_gamestate_half_t half)
00151 {
00152 if ( __debug ) {
00153 printf("Setting half to '%s'\n",
00154 worldinfo_gamestate_half_tostring(half));
00155 }
00156 __half = half;
00157 }
00158
00159
00160
00161
00162
00163
00164
00165 void
00166 RefBoxStateSender::add_penalty(unsigned int player, unsigned int penalty,
00167 unsigned int seconds_remaining)
00168 {
00169 rss_penalty_t p;
00170 p.player = player;
00171 p.penalty = penalty;
00172 p.seconds_remaining = seconds_remaining;
00173 __penalties[player] = p;
00174 }
00175
00176
00177
00178 void
00179 RefBoxStateSender::send()
00180 {
00181 if ( __debug ) {
00182 printf("Sending worldinfo\n");
00183 }
00184
00185 if ( __timeout_thread ) {
00186 __timeout_thread->cancel();
00187 __timeout_thread->join();
00188 delete __timeout_thread;
00189 }
00190 __timeout_thread = new RefBoxStateSender::TimeoutThread(this);
00191 __timeout_thread->start();
00192 }
00193
00194
00195
00196
00197
00198 void
00199 RefBoxStateSender::execute_send()
00200 {
00201 if (unlikely(! __transceiver)) {
00202 return;
00203 } else {
00204 __transceiver->set_gamestate(__game_state, __state_team);
00205 __transceiver->set_score(__score_cyan, __score_magenta);
00206 __transceiver->set_team_goal(__our_team, __our_goal_color);
00207 __transceiver->set_half(__half);
00208 for (__pit = __penalties.begin(); __pit != __penalties.end(); ++__pit) {
00209 __transceiver->add_penalty(__pit->second.player, __pit->second.penalty,
00210 __pit->second.seconds_remaining);
00211 }
00212 __penalties.clear();
00213 __transceiver->send();
00214 }
00215 }
00216
00217
00218
00219
00220
00221
00222
00223
00224
00225
00226
00227 RefBoxStateSender::TimeoutThread::TimeoutThread(RefBoxStateSender *rss)
00228 : Thread("RefBoxStateSender::TimeoutThread", Thread::OPMODE_CONTINUOUS)
00229 {
00230 __timeout_usec = 0;
00231 __rss = rss;
00232 }
00233
00234
00235
00236 RefBoxStateSender::TimeoutThread::~TimeoutThread()
00237 {
00238 }
00239
00240
00241 void
00242 RefBoxStateSender::TimeoutThread::loop()
00243 {
00244 __rss->execute_send();
00245
00246 switch (__timeout_usec) {
00247 case 0: __timeout_usec = 1; break;
00248 case 1: __timeout_usec = 2; break;
00249 case 2: __timeout_usec = 50000; break;
00250
00251
00252
00253 }
00254
00255 usleep(__timeout_usec);
00256 }