diff options
Diffstat (limited to 'src/core')
-rw-r--r-- | src/core/application.cc | 277 | ||||
-rw-r--r-- | src/core/application.h | 42 | ||||
-rw-r--r-- | src/core/commandbuffer.cc | 129 | ||||
-rw-r--r-- | src/core/commandbuffer.h | 47 | ||||
-rw-r--r-- | src/core/cvar.cc | 119 | ||||
-rw-r--r-- | src/core/cvar.h | 162 | ||||
-rw-r--r-- | src/core/entity.cc | 164 | ||||
-rw-r--r-- | src/core/entity.h | 204 | ||||
-rw-r--r-- | src/core/func.cc | 111 | ||||
-rw-r--r-- | src/core/func.h | 88 | ||||
-rw-r--r-- | src/core/gameinterface.cc | 4 | ||||
-rw-r--r-- | src/core/gameinterface.h | 4 | ||||
-rw-r--r-- | src/core/netclient.cc | 8 | ||||
-rw-r--r-- | src/core/netclient.h | 2 | ||||
-rw-r--r-- | src/core/netconnection.cc | 2 | ||||
-rw-r--r-- | src/core/netserver.cc | 51 | ||||
-rw-r--r-- | src/core/netserver.h | 2 | ||||
-rw-r--r-- | src/core/player.cc | 7 | ||||
-rw-r--r-- | src/core/player.h | 23 |
19 files changed, 804 insertions, 642 deletions
diff --git a/src/core/application.cc b/src/core/application.cc index ce7460f..5d313ad 100644 --- a/src/core/application.cc +++ b/src/core/application.cc @@ -11,25 +11,18 @@ #include <vector> #include <sstream> -#include "math/mathlib.h" #include "sys/sys.h" +#include "math/mathlib.h" #include "filesystem/filesystem.h" #include "core/application.h" -#include "core/core.h" +#include "core/cvar.h" #include "core/entity.h" #include "core/func.h" -#include "core/cvar.h" #include "core/netserver.h" namespace core { -Cvar sv_dedicated; -Cvar sv_private; - -Cvar net_host; -Cvar net_port; - // return the global application object Application *application() { @@ -37,107 +30,88 @@ Application *application() } // --------------- engine functions ------------------------------ -void func_print(std::stringstream &args) +void func_print(std::string const &args) { - char text[MAXCMDSIZE]; - if (args.getline(text, MAXCMDSIZE)) { - // remove the leading space - if (text[0] && text[1]) { - con_print << text+1 << std::endl; - } - } + con_print << args << "\n"; } -void func_help(std::stringstream &args) +void func_help(std::string const &args) { - con_print << "This is the help function" << std::endl; + con_print << "This is the help function\n"; } -void func_quit(std::stringstream &args) +void func_quit(std::string const &args) { - if (Application::instance()) { - Application::instance()->shutdown(); - Application::instance()->quit(0); - } + application()->shutdown(); + application()->quit(0); } -void func_connect(std::stringstream &args) +void func_connect(std::string const &args) { + std::istringstream argstream(args); std::string host; - if (!(args >> host)) + if (!(argstream >> host)) host.clear(); - if (Application::instance()) { - Application::instance()->connect(host); - } -} - -void func_disconnect(std::stringstream &args) -{ - if (Application::instance()) - Application::instance()->disconnect(); -} - -void func_list_func(std::stringstream &args) -{ - func::list(); -} - -void func_list_var(std::stringstream &args) -{ - cvar::list(); + application()->connect(host); } -void func_list_ent(std::stringstream &args) +void func_disconnect(std::string const &args) { - entity::list(); + application()->disconnect(); } -void func_say(std::stringstream &args) +// FIXME this is a game function +void func_say(std::string const &args) { if (application()->netserver) { std::ostringstream osstream; - osstream << "msg public " << localplayer.name << " " << args.str() << "\n"; + osstream << "msg public " << Player::local.name() << " " << args << "\n"; application()->netserver->broadcast(osstream.str()); - con_print << localplayer.name << ": " << args.str() << std::endl; + con_print << Player::local.name() << ": " << args << "\n"; } else if (application()->netconnection.connected()) { std::ostringstream osstream; - osstream << args.str() << std::endl; - application()->netconnection.send(osstream.str()); + osstream << args << "\n"; + application()->netconnection.send(args); } else if (game() && game()->connected) { - con_print << args.str() << std::endl; + con_print << args << "\n"; } else con_print << "Not connected."; } -void func_name(std::stringstream &args) { +void func_name(std::string const &args) { + std::istringstream argstream(args); std::string name; - if (args >> name) { + if (argstream >> name) { if (name.size() > 16) name = name.substr(0,16); } else { - con_print << "name " << localplayer.name << std::endl; + con_print << "name " << Player::local.name() << "\n"; return; } - if (name == localplayer.name) { - con_print << "name " << name << std::endl; + if (name == Player::local.name()) { + con_print << "name " << name << "\n"; return; } if (application()->netserver) { std::ostringstream osstream; - osstream << "msg info " << localplayer.name << " renamed to " << name << "\n"; + osstream << "msg info " << Player::local.name() << " renamed to " << name << "\n"; application()->netserver->broadcast(osstream.str()); - con_print << "msg info " << localplayer.name << " renamed to " << name << std::endl; + + con_print << "msg info " << Player::local.name() << " renamed to " << name << "\n"; } else if (application()->netconnection.connected()) { std::ostringstream osstream; - osstream << args.str() << std::endl; + osstream << "name " << name << "\n"; application()->netconnection.send(osstream.str()); + + con_print << "name " << name << "\n"; } else { - con_print << "name " << name << std::endl; + con_print << "name " << name << "\n"; } - localplayer.name = name; + + Player::local.player_name = name; } // --------------- signal_handler ----------------------------------- @@ -150,17 +124,17 @@ extern "C" void signal_handler(int signum) case SIGQUIT: case SIGTERM: if (Application::instance()) { - con_warn << "Received signal " << signum << ", shutting down..." << std::endl; - Application::instance()->shutdown(); - Application::instance()->quit(0); + con_warn << "Received signal " << signum << ", shutting down...\n"; + application()->shutdown(); + application()->quit(0); } else { - std::cerr << "Received signal " << signum << ", terminated..." << std::endl; - sys::quit(1); + std::cerr << "Received signal " << signum << ", terminated...\n"; + application()->quit(1); } break; default: - std::cerr << "Received signal " << signum << ", terminated..." << std::endl; - sys::quit(1); + std::cerr << "Received signal " << signum << ", terminated...\n"; + application()->quit(1); break; } } @@ -172,7 +146,7 @@ Application *Application::application_instance = 0; Application::Application() { if (application_instance) { - std::cerr << "multiple core::Application instances!" << std::endl; + std::cerr << "multiple core::Application instances!\n"; sys::quit(2); } @@ -209,60 +183,66 @@ bool Application::connected() const void Application::init() { - con_debug << "Debug messages enabled" << std::endl; - con_print << "Initializing core..." << std::endl; + con_debug << "Debug messages enabled\n"; + con_print << "Initializing core...\n"; filesystem::init(); + CommandBuffer::init(); + gameinterface_preload = core::GameInterface::gameinterface_instance; core::GameInterface::gameinterface_instance = 0; if (gameinterface_preload) { - con_print << " preloaded game found: " << gameinterface_preload->name() << std::endl; + con_print << " preloaded game found: " << gameinterface_preload->name() << "\n"; } game_time = 0; - // dedicated server, client should have set this to 0 - core::sv_dedicated = core::cvar::get("sv_dedicated", "1", core::cvar::ReadOnly); + // dedicated server should set this to 1 + Cvar::sv_dedicated = Cvar::get("sv_dedicated", "0", Cvar::ReadOnly); - // private server for the client, server should have set this to 0 - core::sv_private = core::cvar::get("sv_private", "0"); + // client can set this to 1 + Cvar::sv_private = Cvar::get("sv_private", "0"); - if (sv_dedicated->value()) - localplayer.name = "Console"; + if (Cvar::sv_dedicated->value()) + Player::local.player_name = "Console"; else - localplayer.name = "Player0"; + Player::local.player_name = "Player0"; // network settings - core::net_host = core::cvar::get("net_host", "0.0.0.0"); - core::net_port = core::cvar::get("net_port", "8042"); + Cvar::net_host = Cvar::get("net_host", "0.0.0.0"); + Cvar::net_port = Cvar::get("net_port", "8042"); - // register our functions - func::add("print", func_print); - func::add("help", func_help); - func::add("quit", func_quit); + // register our engine functions + Func::add("print", func_print); + Func::add("help", func_help); + Func::add("quit", func_quit); - func::add("connect", func_connect); - func::add("disconnect", func_disconnect); + Func::add("connect", func_connect); + Func::add("disconnect", func_disconnect); - func::add("list_var", func_list_var); - func::add("list_func", func_list_func); - func::add("list_ent", func_list_ent); - - func::add("say", func_say); - func::add("name", func_name); + Func::add("say", func_say); + Func::add("name", func_name); } void Application::shutdown() { - con_print << "Shutting down core..." << std::endl; - - if (game() && game()->connected) + con_print << "Shutting down core...\n"; + + if (connected()) disconnect(); - if (netserver) { - delete netserver; - netserver = 0; - } + // remove our engine functions + Func::remove("print"); + Func::remove("help"); + Func::remove("quit"); + + Func::remove("connect"); + Func::remove("disconnect"); + + Func::remove("say"); + Func::remove("name"); + + CommandBuffer::shutdown(); filesystem::shutdown(); } @@ -272,10 +252,36 @@ void Application::quit(int status) sys::quit(status); } +// clear all game realted objects +void Application::clear() +{ + // remove all entities + for (std::map<unsigned int, Entity*>::iterator it = Entity::registry.begin(); it != Entity::registry.end(); it++) { + delete (*it).second; + } + Entity::registry.clear(); + + // remove all game functions + for (std::map<std::string, Func*>::iterator it = Func::registry.begin(); it != Func::registry.end(); it++) { + if ( ((*it).second->flags() & Func::Game) == Func::Game) { + delete (*it).second; + Func::registry.erase(it); + } + } + + // remove all game cvars + for (std::map<std::string, Cvar*>::iterator it = Cvar::registry.begin(); it != Cvar::registry.end(); it++) { + if ( ((*it).second->flags() & Cvar::Game) == Cvar::Game) { + delete (*it).second; + Cvar::registry.erase(it); + } + } +} + void Application::connect(std::string const &host) { if (game() && game()->connected || netconnection.connected()) { - con_warn << "Connected. Disconnect first." << std::endl; + con_warn << "Connected. Disconnect first.\n"; return; } @@ -285,6 +291,8 @@ void Application::connect(std::string const &host) delete core::GameInterface::gameinterface_instance; } + clear(); + if (host.size()) { // connect to remote core core::GameInterface::gameinterface_instance = 0; @@ -296,38 +304,37 @@ void Application::connect(std::string const &host) if (str >> port) { remotehost.erase(found, std::string::npos); } else { - con_print << "Invalid hostname '" << remotehost << "'" << std::endl; + con_print << "Invalid hostname '" << remotehost << "'\n"; return; } } netconnection.connect(remotehost, port); if (netconnection.connected()) { - con_print << "Connected." << std::endl; + con_print << "Connected.\n"; } else { netconnection.disconnect(); - con_warn << "Could not connect to '" << host << "'" << std::endl; + con_warn << "Could not connect to '" << host << "'\n"; } } else { // use preloaded game core::GameInterface::gameinterface_instance = gameinterface_preload; // reset everything - entity::clear(); game_time = 0; if (game()->connected = game()->init()) { - con_print << "Connected." << std::endl; + con_print << "Connected.\n"; } else { - con_warn << "Could not connect." << std::endl; + con_warn << "Could not connect.\n"; return; } - if (!netserver && (core::sv_dedicated->value() || core::sv_private->value())) { - netserver = new NetServer(net_host->text(), (unsigned int)net_port->value()); + if (!netserver && (Cvar::sv_dedicated->value() || Cvar::sv_private->value())) { + netserver = new NetServer(Cvar::net_host->str(), (unsigned int)Cvar::net_port->value()); if (!netserver->valid()) { delete netserver; - if (core::sv_dedicated->value()) + if (Cvar::sv_dedicated->value()) shutdown(); } } @@ -343,13 +350,13 @@ void Application::disconnect() if (netconnection.connected()) { netconnection.disconnect(); - con_print << "Disconnected." << std::endl; + con_print << "Disconnected.\n"; return; } if (game()) { if (!game()->connected) { - con_warn << "Not connected." << std::endl; + con_warn << "Not connected.\n"; return; } @@ -357,26 +364,9 @@ void Application::disconnect() game()->connected = false; game_time = 0; - // remove all entities - entity::clear(); - - // remove all game functions - for (std::map<std::string, Func>::iterator it = func::registry.begin(); it != func::registry.end(); it++) { - if ( ((*it).second->flags() & func::Game) == func::Game) { - delete (*it).second; - func::registry.erase(it); - } - } - - // remove all game cvars - for (std::map<std::string, Cvar>::iterator it = cvar::registry.begin(); it != cvar::registry.end(); it++) { - if ( ((*it).second->flags() & cvar::Game) == cvar::Game) { - delete (*it).second; - cvar::registry.erase(it); - } - } + clear(); - con_print << "Disconnected." << std::endl; + con_print << "Disconnected.\n"; } } @@ -384,7 +374,22 @@ void Application::frame(float seconds) { if (seconds == 0.0f) return; - + + // execute commands in the buffer + CommandBuffer::exec(); + + // update entities + if (connected()) { + std::map<unsigned int, Entity *>::iterator it; + for (it=Entity::registry.begin(); it != Entity::registry.end(); it++) { + Entity *entity = (*it).second; + if ((entity->type() == Entity::Controlable) || (entity->type() == Entity::Dynamic)) { + entity->frame(seconds); + } + } + } + + // netstuff if (netconnection.connected()) { netconnection.frame(seconds); // TODO this should come from server @@ -396,15 +401,11 @@ void Application::frame(float seconds) } if (game() && game()->connected) { - entity::frame(seconds); game_time += seconds; game()->frame(seconds); } } - - // execute commands in the buffer - commandbuffer::execute(); } } diff --git a/src/core/application.h b/src/core/application.h index 81e6a64..0f4c5fa 100644 --- a/src/core/application.h +++ b/src/core/application.h @@ -7,7 +7,7 @@ #ifndef __INCLUDED_CORE_APPLICATION_H__ #define __INCLUDED_CORE_APPLICATION_H__ -#include "core/cvar.h" +#include "core/commandbuffer.h" #include "core/netserver.h" #include "core/netconnection.h" #include "core/gameinterface.h" @@ -15,15 +15,6 @@ namespace core { -/// cvar to indicate dedicated server status -extern Cvar sv_dedicated; - -/// cvar to indicate private server status -/** - * A private server is a client with server cababilities. - */ -extern Cvar sv_private; - /// core interface for the client and server Application classes class Application { @@ -40,21 +31,9 @@ public: /// shutdown the application virtual void shutdown(); - /// run a core frame - virtual void frame(float seconds); - /// a pointer to the current application instance static Application *instance(); - /// quit the application - virtual void quit(int status); - - /// start the server or connect to remote host - void connect(std::string const &host); - - /// disconnect from the game module - void disconnect(); - /// time the has been connected, in seconds float time() const; @@ -73,10 +52,25 @@ public: /// global application object static Application *application_instance; + /// quit the application without proper shutdown + virtual void quit(int status); + + /// start the server or connect to remote host + void connect(std::string const &host); + + /// disconnect from the game module + void disconnect(); + +protected: + /// clear all game related objects + void clear(); + + /// run a core frame + virtual void frame(float seconds); + private: /// time the core has been running - float game_time; - + float game_time; }; /// pointer to the current ApplicationInterface diff --git a/src/core/commandbuffer.cc b/src/core/commandbuffer.cc index a15708c..8f02f71 100644 --- a/src/core/commandbuffer.cc +++ b/src/core/commandbuffer.cc @@ -4,88 +4,123 @@ the terms of the GNU General Public License version 2 */ -#include "core/commandbuffer.h" -#include "sys/sys.h" - -// C++ headers #include <string> #include <sstream> #include <list> +#include "sys/sys.h" +#include "core/commandbuffer.h" +#include "core/func.h" +#include "core/cvar.h" +#include "core/gameinterface.h" + namespace core { -std::stringstream cmd(std::stringstream::in | std::stringstream::out); +void func_list_func(std::istringstream const &args) +{ + Func::list(); +} + +void func_list_var(std::istringstream const &args) +{ + Cvar::list(); +} + +void func_list_ent(std::istringstream const &args) +{ + Entity::list(); +} + +std::stringstream CommandBuffer::cmdbuf(std::stringstream::in | std::stringstream::out); + +void CommandBuffer::init() +{ + con_debug << "Initializing command buffer...\n"; + + Func::add("list_var", (FuncPtr)func_list_var); + Func::add("list_func", (FuncPtr)func_list_func); + Func::add("list_ent", (FuncPtr)func_list_ent); +} -namespace commandbuffer +void CommandBuffer::shutdown() { + con_debug << "Shutting down command buffer...\n"; -void exec(const char *text) + Func::remove("list_var"); + Func::remove("list_func"); + Func::remove("list_ent"); +} + +void CommandBuffer::exec(std::string const &cmdline) { - std::stringstream cmdstream(text); + if (!cmdline.size()) + return; + + std::istringstream cmdstream(cmdline); std::string command; if (!(cmdstream >> command)) return; + con_debug << "Executing '" << cmdline << "'\n"; + // is it a function - Func f = func::find(command); + Func *f = Func::find(command); if (f) { - // function exists, execute it - if (f->flags() && func::Game) { - // it's a game function + std::string args; + char c; + if (cmdstream >> args) { + while (cmdstream >> c) + args += c; + } + if ((f->flags() & Func::Game)) { if (game() && game()->connected) { - GameFuncPtr function = (GameFuncPtr) f->ptr; - function(localplayer, cmdstream); + f->exec(&Player::local, args); } } else { - // it's a normal function - FuncPtr function = (FuncPtr) f->ptr; - function(cmdstream); + f->exec(args); } return; } // is it a cvar - Cvar cv = cvar::find(command); - if (cv) { + Cvar *cvar = Cvar::find(command); + if (cvar) { // cvar exists - std::string args; - if (((cv->flags() & cvar::ReadOnly) == 0) && (cmdstream >> args)) { + std::string value; + if (((cvar->flags() & Cvar::ReadOnly) == 0) && (cmdstream >> value)) { // we're setting a new value char c; while (cmdstream >> c) - args += c; - (*cv) = args; + value += c; + (*cvar) = value; } - con_print << command << " " << cv->text() << std::endl; + con_print << command << " " << cvar->str() << "\n"; return; } - con_print << "Unknown command '" << command << "'" << std::endl; + // TODO this must get forwarded to the server + + con_print << "Unknown command '" << command << "'\n"; } -void execute() +void CommandBuffer::exec() { - if (core::cmd.eof()) + if (cmdbuf.eof()) return; char line[MAXCMDSIZE]; - while (core::cmd.getline(line, MAXCMDSIZE-1)) { - exec(line); + + while (core::cmd().getline(line, MAXCMDSIZE-1)) { + exec(std::string(line)); } - cmd.clear(); + cmdbuf.clear(); } -void clear() -{ - char line[MAXCMDSIZE]; - while (core::cmd.getline(line, MAXCMDSIZE-1)); -} - -void complete(std::string &input, size_t &pos) +void CommandBuffer::complete(std::string &input, size_t &pos) { std::list<std::string> match; @@ -94,20 +129,20 @@ void complete(std::string &input, size_t &pos) return; // search function registry for matches - std::map<std::string, Func>::iterator f; - for (f = func::registry.begin(); f != func::registry.end(); f++) { + std::map<std::string, Func *>::iterator f; + for (f = Func::registry.begin(); f != Func::registry.end(); f++) { if (partial == (*f).first.substr(0, partial.size())) { match.push_back((*f).first); - //con_print << " " << (*f).first << std::endl; + //con_print << " " << (*f).first << "\n"; } } // search cvar registry for matches - std::map<std::string, Cvar>::iterator c; - for (c = cvar::registry.begin(); c != cvar::registry.end(); c++) { + std::map<std::string, Cvar *>::iterator c; + for (c = Cvar::registry.begin(); c != Cvar::registry.end(); c++) { if (partial == (*c).first.substr(0, partial.size())) { match.push_back((*c).first); - //con_print << " " << (*c).first << std::endl; + //con_print << " " << (*c).first << "\n"; } } @@ -127,9 +162,9 @@ void complete(std::string &input, size_t &pos) if (i < maxmatch.size()) maxmatch.erase(i); } - con_print << " " << (*l) << std::endl; + con_print << " " << (*l) << "\n"; } - con_print << match.size() << " matches" << std::endl; + con_print << match.size() << " matches\n"; } @@ -141,7 +176,5 @@ void complete(std::string &input, size_t &pos) } -} // namespace commandbuffer - -} // namespace core +} diff --git a/src/core/commandbuffer.h b/src/core/commandbuffer.h index 22f53d2..8970d89 100644 --- a/src/core/commandbuffer.h +++ b/src/core/commandbuffer.h @@ -4,35 +4,46 @@ the terms of the GNU General Public License version 2 */ -#ifndef __INCLUDED_COMMANDBUFFER_H__ -#define __INCLUDED_COMMANDBUFFER_H__ +#ifndef __INCLUDED_CORE_COMMANDBUFFER_H__ +#define __INCLUDED_CORE_COMMANDBUFFER_H__ -// project headers -#include "core/core.h" - -// C++ headers +#include <string> #include <sstream> namespace core { -/// global buffer to hold the command stream -extern std::stringstream cmd; - -namespace commandbuffer +class CommandBuffer { +public: + /// register command buffer functions + static void init(); -/// execute the commands in the buffer -void execute(); + /// remove command buffer functions + static void shutdown(); -/// flush the command buffer -void clear(); + /// execute the commands in the buffer + static void exec(); -/// tab completion -void complete(std::string &input, size_t &pos); + /// clear the command buffer + static void clear(); -} + /// global buffer to hold the command stream + static std::stringstream cmd; + + /// input command completion + static void complete(std::string &input, size_t &pos); + + /// the global command buffer + static std::stringstream cmdbuf; + +private: + static void exec(std::string const & cmdline); +}; + +/// the global command buffer +inline std::stringstream & cmd() { return CommandBuffer::cmdbuf; } } -#endif // COMMANDBUFFER +#endif // __INCLUDED_CORE_COMMANDBUFFER_H__ diff --git a/src/core/cvar.cc b/src/core/cvar.cc index 531e0ad..dbe1d30 100644 --- a/src/core/cvar.cc +++ b/src/core/cvar.cc @@ -17,159 +17,154 @@ namespace core { -Cvar_t::Cvar_t(unsigned int cvarflags) +Cvar *Cvar::sv_dedicated = 0; +Cvar *Cvar::sv_private = 0; +Cvar *Cvar::net_host = 0; +Cvar *Cvar::net_port = 0; + +std::map<std::string, Cvar*> Cvar::registry; + +Cvar::Cvar(const char *name, unsigned int flags) { - cvar_flags = cvarflags; + cvar_flags = flags; + if (name) + cvar_name.assign(name); } -Cvar_t & Cvar_t::operator=(const std::string &other) +Cvar & Cvar::operator=(const std::string &other) { - cvar_text = other; - std::stringstream s(cvar_text); + cvar_str = other; + std::stringstream s(cvar_str); if (!(s >> cvar_value)) - cvar_value = cvar_text.size(); + cvar_value = cvar_str.size(); return (*this); } -Cvar_t & Cvar_t::operator=(const char *other) +Cvar & Cvar::operator=(const char *other) { return ((*this) = std::string(other)); } -Cvar_t & Cvar_t::operator=(float other) +Cvar & Cvar::operator=(float other) { std::stringstream s; s << other; - s >> cvar_text; + s >> cvar_str; cvar_value = other; return (*this); } -unsigned int Cvar_t::flags() const -{ - return(cvar_flags); -} - -float Cvar_t::value() const +Cvar* Cvar::get(const char *name, const char *value, unsigned int flags) { - return(cvar_value); -} - -const std::string &Cvar_t::text() const -{ - return(cvar_text); -} - -namespace cvar -{ - -std::map<std::string, Cvar> registry; - -Cvar get(const char *name, const char *value, int flags) -{ - Cvar c = find(name); + Cvar *c = find(name); if (c) { - //con_debug << "cvar::get " << name << " already exist with value " << cvar->text() << std::endl; + //con_debug << "get " << name << " already exist with value " << cvar->str() << std::endl; } else { - //con_debug << "cvar::get " << name << " " << value << std::endl; - c = new Cvar_t(flags); + //con_debug << "get " << name << " " << value << std::endl; + c = new Cvar(name, flags); registry[std::string(name)] = c; (*c) = value; } + c->cvar_flags = flags; return c; } -Cvar get(const char *name, float value, int flags) +Cvar* Cvar::get(const char *name, float value, unsigned int flags) { - Cvar c = find(name); + Cvar *c = find(name); if (c) { - //con_debug << "cvar::get " << name << " already exist with value " << cvar->text() << std::endl; + //con_debug << "get " << name << " already exist with value " << cvar->str() << std::endl; } else { - //con_debug << "cvar::get " << name << " " << value << std::endl; - c = new Cvar_t(flags); + //con_debug << "get " << name << " " << value << std::endl; + c = new Cvar(name, flags); registry[std::string(name)] = c; (*c) = value; } + c->cvar_flags = flags; return c; } -Cvar set(const char *name, const char *value, int flags) +Cvar* Cvar::set(const char *name, const char *value, unsigned int flags) { - Cvar c = find(name); + Cvar *c = find(name); if (!c) { - c = new Cvar_t(flags); + c = new Cvar(name, flags); registry[std::string(name)] = c; } (*c) = value; - //con_debug << "cvar::set " << name << " " << cvar->text() << std::endl; + c->cvar_flags = flags; + + //con_debug << "set " << name << " " << cvar->str() << std::endl; return c; } -Cvar set(const char *name, float value, int flags) +Cvar* Cvar::set(const char *name, float value, unsigned int flags) { - Cvar c = find(name); + Cvar *c = find(name); if (!c) { - c = new Cvar_t(flags); + c = new Cvar(name, flags); registry[std::string(name)] = c; } (*c) = value; - //con_debug << "cvar::set " << name << " " << cvar->text() << std::endl; + c->cvar_flags = flags; + + //con_debug << "set " << name << " " << cvar->str() << std::endl; return c; } -void unset(const std::string &name) +void Cvar::unset(std::string const &name) { - Cvar c = find(name); + Cvar *c = find(name); if (c) { - con_debug << "cvar::unset " << name << std::endl; + con_debug << "unset " << name << std::endl; registry.erase(name); delete c; } } -void unset(const char *name) +void Cvar::unset(const char *name) { unset(std::string(name)); } -Cvar find(const std::string &name) +Cvar *Cvar::find(std::string const &name) { - std::map<std::string, Cvar>::iterator it = registry.find(name); + std::map<std::string, Cvar*>::iterator it = registry.find(name); if (it == registry.end()) return 0; else return (*it).second; } -Cvar find(const char *name) +Cvar *Cvar::find(const char *name) { return(find(std::string(name))); } -void list() +void Cvar::list() { - std::map<std::string, Cvar>::iterator it; + std::map<std::string, Cvar*>::iterator it; for (it = registry.begin(); it != registry.end(); it++) { std::string typeindicator; - if ((*it).second->flags() & cvar::Archive) + if (((*it).second->flags() & Archive) == Archive) typeindicator += 'A'; else typeindicator += ' '; - if ((*it).second->flags() & cvar::ReadOnly) + if (((*it).second->flags() & ReadOnly) == ReadOnly) typeindicator += 'R'; else typeindicator += ' '; - if ((*it).second->flags() & cvar::Game) + if (((*it).second->flags() & Game) == Game) typeindicator += 'G'; else typeindicator += ' '; - con_print << typeindicator << " " << (*it).first << " " << (*it).second->text() << std::endl; + con_print << std::setw(4) << (*it).second->flags() << " " << typeindicator << + " " << (*it).first << " " << (*it).second->str() << std::endl; } con_print << registry.size() << " registered variables" << std::endl; } -} // namespace cvar +} -} // namespace core diff --git a/src/core/cvar.h b/src/core/cvar.h index bca3d8a..7350eee 100644 --- a/src/core/cvar.h +++ b/src/core/cvar.h @@ -13,82 +13,106 @@ namespace core { -/// the cvar container class -class Cvar_t +/// a variable encapsulation class +class Cvar { public: - - Cvar_t(unsigned int cvflags = 0); - - Cvar_t &operator=(const char *other); - Cvar_t &operator=(const std::string &other); - Cvar_t &operator=(float other); + /// Cvar flags + /** + * Archive a cvar with this flag will be saved to the configuration file + * ReadOnly the value of cvar with this flag can not be altered from the commandline + * Game a cvar with this flag is only valid when a game is loaded + */ + enum Flags {Archive=1, ReadOnly=2, Game=4}; - unsigned int flags() const; - float value() const; - const std::string &text() const; + /// create a new variable + Cvar(const char *name = 0, unsigned int flags = 0); + +/*----- inspectors ------------------------------------------------ */ + + /// returns the name of the variable + inline std::string const &name() { return cvar_name; } + + /// returns the flags of the variable + inline unsigned int flags() const { return cvar_flags; } + + /// returns the float value of the variable + inline float value() const { return cvar_value; } + + /// returns the string value of the variable + inline const std::string &str() const { return cvar_str; } + +/*----- mutators -------------------------------------------------- */ + + /// char * assignment operator + Cvar &operator=(const char *other); + + /// std::string assignment operator + Cvar &operator=(const std::string &other); + + /// float assignment operator + Cvar &operator=(float other); + +/* ---- Static functions for the Cvar registry -------------------- */ -private: - std::string cvar_text; - float cvar_value; - unsigned int cvar_flags; -}; + /// get a cvar value from the registry + /** If the a cvar with the given name already exists in the registry, + * its value will not be changed. If the cvar does not exist, + * it will be created + */ + static Cvar *get(const char *name, const char *value, unsigned int flags=0); + + /// get a cvar value from the registry + /** If the a cvar with the given name already exists in the registry, + * its value will not be changed. If the cvar does not exist, + * it will be created + */ + static Cvar *get(const char *name, float value, unsigned int flags=0); + + /// set a cvar value + /** If the a cvar with the given name already exists in the registry, + * its value will be replaced + */ + static Cvar *set(const char *name, const char *value, unsigned int flags=0); + + /// set a cvar value + /** If the a cvar with the given name already exists in the registry, + * its value will be replaced + */ + static Cvar *set(const char *name, float value, unsigned int flags=0); + + /// delete a cvar from the registry + static void unset(const char *name); + + /// delete a cvar from the registry + static void unset(std::string const &name); + + /// search for a named cvar, returns 0 if not found + static Cvar *find(std::string const &name); + + /// search for a named cvar, returns 0 if not found + static Cvar *find(const char *name); + + /// list the cvar registry + static void list(); + + /// the Cvar registry + static std::map<std::string, Cvar*> registry; + + static Cvar *sv_dedicated; // dedicated server + static Cvar *sv_private; // client with private server + static Cvar *net_host; // network server ip (default binds to all interfaces) + static Cvar *net_port; // network port -/// general cvar type -typedef Cvar_t *Cvar; +private: + std::string cvar_name; + std::string cvar_str; + unsigned int cvar_flags; + float cvar_value; -/// the cvar registry -namespace cvar -{ +}; -/// cvar flags -enum Flags {Archive=1, ReadOnly=2, Game=4}; - -/// get a cvar value from the registry -/** If the a cvar with the given name already exists in the registry, - * its value will not be changed. If the cvar does not exist, - * it will be created - */ -Cvar get(const char *name, const char *value, int flags=0); -/// get a cvar value from the registry -/** If the a cvar with the given name already exists in the registry, - * its value will not be changed. If the cvar does not exist, - * it will be created - */ -Cvar get(const char *name, float value, int flags=0); - -/// set a cvar value -/** If the a cvar with the given name already exists in the registry, - * its value will be replaced - */ -Cvar set(const char *name, const char *value, int flags=0); -/// set a cvar value -/** If the a cvar with the given name already exists in the registry, - * its value will be replaced - */ -Cvar set(const char *name, float value, int flags=0); - -/// delete a cvar from the registry -void unset(const char *name); - -/// delete a cvar from the registry -void unset(const std::string &name); - -/// search for a named cvar, returns 0 if not found -Cvar find(const std::string &name); - -/// search for a named cvar, returns 0 if not found -Cvar find(const char *name); - -/// list the cvar registry -void list(); - -/// the Cvar registry -extern std::map<std::string, Cvar> registry; - -} // namespace cvar - -} // namespace core +} #endif // __INCLUDED_CORE_CVAR_H__ diff --git a/src/core/entity.cc b/src/core/entity.cc index 6115e71..229fb52 100644 --- a/src/core/entity.cc +++ b/src/core/entity.cc @@ -4,121 +4,141 @@ the terms of the GNU General Public License version 2. */ +#include <vector> +#include <iomanip> + #include "sys/sys.h" #include "core/entity.h" -#include <iomanip> - namespace core { -// --- Entity ----------------------------------------------------- +using math::Color; +using math::Vector3f; -Entity::Entity(unsigned int entity_flags) -{ - flags = entity_flags; - - core_shape = entity::Diamond; - core_color = math::Color(1.0f, 1.0f, 1.0f); - core_radius = 1.0f; +/* ---- Static functions for the Entity registry ------------------- */ - core::entity::add(this); - type = 0; - - direction = 0; -} +std::map<unsigned int, Entity *> Entity::registry; -Entity::~Entity() -{} +void Entity::add(Entity *ent) +{ + std::map<unsigned int, Entity*>::iterator it; + unsigned int id = 1; + for (it = registry.begin(); it != registry.end() && id == (*it).second->id(); it++) { + id++; + } + ent->entity_id = id; + registry[id] = ent; +} -// --- EntityDynamic ------------------------------------------ +Entity *Entity::find(unsigned int id) +{ + std::map<unsigned int, Entity *>::iterator it = registry.find(id); + if (it == registry.end()) + return 0; + else + return (*it).second; +} -EntityDynamic::EntityDynamic(unsigned int entity_flags) : - Entity(entity_flags) +void Entity::remove(unsigned int id) { - speed = 0.0f; + std::map<unsigned int, Entity *>::iterator it = registry.find(id); + if (it != registry.end()) { + delete((*it).second); + registry.erase(it); + } } -EntityDynamic::~EntityDynamic() +void Entity::list() { + std::map<unsigned int, Entity *>::iterator it; + for (it = registry.begin(); it != registry.end(); it++) { + std::string typeindicator; + Entity *entity = (*it).second; + con_print << " id " << std::setw(4) << entity->id() + << " type " << std::setw(4) << entity->type() + << ":" << std::setw(4) << entity->moduletype() + << " " << entity->name() << std::endl; + } + con_print << registry.size() << " registered entities" << std::endl; } -// --- EntityControlable ------------------------------------------ +/*----- Entity ----------------------------------------------------- */ -EntityControlable::EntityControlable(unsigned int entity_flags) : - EntityDynamic(entity_flags) +Entity::Entity(unsigned int flags) : + entity_location(0.0f, 0.0f, 0.0f), + entity_color(1.0f, 1.0f, 1.0f, 1.0f) { - owner = 0; - target_direction = 0.0f; - target_thrust = 0.0f; + entity_id = 0; + entity_flags = flags; + entity_moduletypeid = 0; + + entity_radius = 1.0f; + entity_direction = 0; + entity_shape = Diamond; + + add(this); } -EntityControlable::~EntityControlable() +Entity::~Entity() +{ +} + +void Entity::frame(float seconds) { } -// --- namespace entity ------------------------------------------- +/* ---- EntityDynamic ---------------------------------------------- */ -namespace entity +EntityDynamic::EntityDynamic(unsigned int flags) : + Entity(flags) { + entity_speed = 0.0f; +} -std::vector<Entity*> registry; +EntityDynamic::~EntityDynamic() +{ +} -void add(Entity *ent) +void EntityDynamic::frame(float seconds) { - std::vector<Entity *>::iterator it; - unsigned int entity_id = 1; - for (it=registry.begin(); it != registry.end() && entity_id == (*it)->id; it++) { - entity_id++; - } - ent->id = entity_id; - registry.push_back(ent); + // location avoid sin/cos calculations + entity_location.x += cosf(entity_direction * M_PI / 180) * entity_speed * seconds; + entity_location.z -= sinf(entity_direction * M_PI / 180) * entity_speed * seconds; } -void remove(unsigned int entity_id) +/*----- EntityControlable ------------------------------------------ */ + +EntityControlable::EntityControlable(Player *player, unsigned int flags) : + EntityDynamic(flags) { - std::vector<Entity *>::iterator it; - for (it=registry.begin(); it != registry.end(); it++) { - if (entity_id == (*it)->id) { - delete((*it)); - registry.erase(it); - return; - } - } + entity_owner = 0; + entity_thrust = 0; + + target_direction = 0.0f; + target_thrust = 0.0f; } -void clear() +EntityControlable::~EntityControlable() { - std::vector<Entity *>::iterator it; - for (it=registry.begin(); it != registry.end(); it++) { - delete(*it); - (*it) = 0; - } - registry.clear(); } -void list() +void EntityControlable::frame(float seconds) { - std::vector<Entity *>::iterator it; - for (it=registry.begin(); it != registry.end(); it++) { - con_print << " id " << std::setw(4) << (*it)->id - << " type " << std::setw(4) << (*it)->core_type() - << ":" << std::setw(4) << (*it)->type - << " " << (*it)->label << std::endl; - } - con_print << registry.size() << " registered entities" << std::endl; + entity_direction = target_direction; + entity_thrust = target_thrust; + + EntityDynamic::frame(seconds); } -void frame(float seconds) +void EntityControlable::set_thrust(float thrust) { - std::vector<Entity *>::iterator it; - for (it=registry.begin(); it != registry.end(); it++) { - if ((*it)->core_type() == entity::Controlable) { - static_cast<EntityControlable *>(*it)->frame(seconds); - } - } + target_thrust = thrust; } +void EntityControlable::set_direction(float direction) +{ + target_direction = direction; } } diff --git a/src/core/entity.h b/src/core/entity.h index b3dd7ef..7b3f200 100644 --- a/src/core/entity.h +++ b/src/core/entity.h @@ -15,136 +15,182 @@ class EntityControlable; #include "core/player.h" #include "math/mathlib.h" -#include <vector> +#include <string> +#include <map> namespace core { -namespace entity -{ - -/// Entity flags -enum Flags {Static=1, Solid=2}; - -/// Entity type constants -enum Type {Default = 0, Dynamic = 1, Controlable = 2}; - -/// Entity shape constants -enum Shape {Diamond=0, Sphere=1, Cube=2}; - -} - /// The base world entity. All gameworld entities must derive from this class. class Entity { public: + /// Entity flags + enum Flags {Static=1, Solid=2}; + + /// Entity type constants + enum Type {Default = 0, Dynamic = 1, Controlable = 2}; + + /// Entity shape constants + enum Shape {Diamond=0, Sphere=1, Cube=2}; + /// create a new entity and add it to the registry - Entity(unsigned int entity_flags = 0); + Entity(unsigned int flags = 0); + + /// destroy an entity virtual ~Entity(); + +/*----- inspectors ------------------------------------------------ */ + /// entity id + inline unsigned int id() const { return entity_id; } + + /// module type id + inline unsigned int moduletype() const { return entity_moduletypeid; } + /// core type id - virtual inline unsigned int core_type() { return entity::Default; } + virtual inline unsigned int type() { return Default; } - /// unique instance identifier, automaticly set - unsigned int id; + /// entity flags + inline unsigned int flags() const { return entity_flags; } - /// core shape id - entity::Shape core_shape; + /// entity name + inline std::string const & name() { return entity_name; } - /// core color - math::Color core_color; + /// entity location + inline math::Vector3f const & location() const { return entity_location; } - /// core radius, in game units - float core_radius; - - /// the entities label - std::string label; + /// direction the entity is facing, in degrees. + inline float direction() const { return entity_direction; } + + /// base color of the entity + inline math::Color const & color() const { return entity_color; } - /// custom game type id of this entity - unsigned int type; + /// base shape of the entity + inline Shape shape() const { return entity_shape; } - /// flags - /// @see core::entity::Flags - unsigned int flags; + /// base radius of the entity + inline float radius() const { return entity_radius; } - /* updateable by game */ +/*----- mutators -------------------------------------------------- */ - /// location of the entity - math::Vector3f location; + /// runs one game frame for the entity + /** + * The default implementation does nothing + */ + virtual void frame(float seconds); - /// direction the entity is facing, in degrees - /// A direction of 0 degrees means the entity is looking - /// along the positive X-axis. - float direction; +/*----- static ---------------------------------------------------- */ + + /// the entity registry + static std::map<unsigned int, Entity*> registry; + + /// find an entity in the registry + static Entity *find(unsigned int id); + + /// remove one entity from the registry and deletes it + static void remove(unsigned int entity_id); + + /// list the entity registry + static void list(); + + /* entity_ variables can be set by the module */ + float entity_radius; + std::string entity_name; + Shape entity_shape; + math::Vector3f entity_location; + math::Color entity_color; + /* + * A direction of 0 degrees means the entity is looking + * along the positive X-axis. Positive angle is along the negative Z-axis. + */ + float entity_direction; + unsigned int entity_moduletypeid; + unsigned int entity_flags; + +private: + /// add an entity to the registry + static void add(Entity *ent); + + /// the id is set by add() + unsigned int entity_id; }; /// an entity that can move around in the game world class EntityDynamic : public Entity { public: - EntityDynamic(unsigned int entity_flags = 0); + EntityDynamic(unsigned int flags = 0); virtual ~EntityDynamic(); +/*----- inspectors ------------------------------------------------ */ /// core type id - virtual inline unsigned int core_type() { return entity::Dynamic; } - - /* updateable by game */ + virtual inline unsigned int type() { return Entity::Dynamic; } /// current speed of the entity in game units per second - float speed; + inline float speed() const { return entity_speed; } + +/*----- mutators -------------------------------------------------- */ + + /// runs one game frame for the entity + /** + * The default implementation will update the position() of the entity, + * determined by its speed() and direction() + */ + virtual void frame(float seconds); + + /// speed of the entity + float entity_speed; }; /// an entity that can be controlled by a player class EntityControlable : public EntityDynamic { public: - EntityControlable(unsigned int entity_flags = 0); + /// create + EntityControlable(Player *player, unsigned int flags = 0); virtual ~EntityControlable(); - /// core type id - virtual inline unsigned int core_type() { return entity::Controlable; } - - /// runs one game frame for the entity, to be implemented by game - virtual void frame(float seconds) = 0; - - /* updateable by game */ +/*----- inspectors ------------------------------------------------ */ - /// owner of this controllable entity - Player *owner; - - /* updatable by client */ + /// core type id + virtual inline unsigned int type() { return Entity::Controlable; } - /// the direction the client wants to travel the entity to - /// @see direction - float target_direction; + /// owner of this entity + inline Player *owner() const { return entity_owner; } - /// engine thrust as set by the client, 0.0f - 1.0f - float target_thrust; -}; + /// thrust + inline float thrust() const { return entity_thrust; } +/*----- mutators -------------------------------------------------- */ -namespace entity -{ + /// set the target thrust + void set_thrust(float t); -/// the entity registry -extern std::vector<Entity*> registry; + /// set the target direction + void set_direction(float t); -/// add an entity to the registry -void add(Entity *ent); + /// runs one game frame for the entity + /** + * The default implementation will set direction() and thrust() to the desired targets + * and calls its parent frame() funcion. + */ + virtual void frame(float seconds); -/// remove one entity from the registry -void remove(unsigned int entity_id); + /* entity_ variables can be set by the module */ -/// clear the entity registry -void clear(); + /// owner of the entity + Player *entity_owner; + /// current thrust + float entity_thrust; -/// list the entity registry -void list(); + /* target_ variables can be set by the client */ -/// run a game frame on each entity in the registry -void frame(float seconds); - -} + /// target thrust as set by the client + float target_thrust; + /// target direction as set by the client + float target_direction; +}; } diff --git a/src/core/func.cc b/src/core/func.cc index 06aa5b6..0215ddf 100644 --- a/src/core/func.cc +++ b/src/core/func.cc @@ -4,100 +4,125 @@ the terms of the GNU General Public License version 2 */ -#include "core/func.h" #include <map> #include <string> +#include <iomanip> -namespace core -{ - -Func_t::Func_t(unsigned int funcflags) -{ - func_flags = funcflags; -} +#include "sys/sys.h" +#include "core/func.h" -unsigned int Func_t::flags() +namespace core { - return func_flags; -} -namespace func -{ +/* ---- Static functions for the Func registry -------------------- */ -std::map<std::string, Func> registry; +std::map<std::string, Func*> Func::registry; -void add(const char * functionname, FuncPtr functionptr, unsigned int flags) +void Func::add(const char *name, FuncPtr functionptr, unsigned int flags) { - std::map<std::string, Func>::iterator it = registry.find(functionname); + std::map<std::string, Func*>::iterator it = registry.find(name); if (it == registry.end()) { - // function does not yet exist in the registry - Func f = new Func_t(flags); - //f->name = functionname; - f->ptr = (void *)functionptr; - registry[std::string(functionname)] = f; + registry[std::string(name)] = new Func(name, (void *)functionptr, flags & ~Func::Game); } else { - con_warn << "Function '" << functionname << "' already registered!" << std::endl; + con_warn << "Function '" << name << "' already registered!" << std::endl; } } -void add(const char * functionname, GameFuncPtr gamefunctionptr, unsigned int flags) +void Func::add(const char *name, GameFuncPtr gamefunctionptr, unsigned int flags) { - std::map<std::string, Func>::iterator it = registry.find(functionname); + std::map<std::string, Func*>::iterator it = registry.find(name); if (it == registry.end()) { - // function does not yet exist in the registry - Func f = new Func_t(flags & func::Game); - //f->name = functionname; - f->ptr = (void *)gamefunctionptr; - registry[std::string(functionname)] = f; + registry[std::string(name)] = new Func(name, (void *)gamefunctionptr, flags | Func::Game); + con_debug << "Function '" << name << "' registered." << std::endl; } else { - con_warn << "Function '" << functionname << "' already registered!" << std::endl; + con_warn << "Function '" << name << "' already registered!" << std::endl; } } -void remove(const char *functionname) +void Func::remove(const char *name) { - std::map<std::string, Func>::iterator it = registry.find(functionname); + std::map<std::string, Func *>::iterator it = registry.find(std::string(name)); if (it != registry.end()) { delete (*it).second; - registry.erase(std::string(functionname)); + registry.erase(it); + con_debug << "Function '" << name << "' unregistered." << std::endl; } } -void remove(const std::string &functionname) +void Func::remove(const std::string &name) { - std::map<std::string, Func>::iterator it = registry.find(functionname); + std::map<std::string, Func *>::iterator it = registry.find(name); if (it != registry.end()) { delete (*it).second; - registry.erase(std::string(functionname)); + registry.erase(it); + con_debug << "Function '" << name << "' unregistered." << std::endl; } } -Func find(const std::string &functionname) +Func *Func::find(const std::string &name) { - std::map<std::string, Func>::iterator it = registry.find(functionname); + std::map<std::string, Func *>::iterator it = registry.find(name); if (it == registry.end()) return 0; else return (*it).second; } -void list() +void Func::list() { - std::map<std::string, Func>::iterator it; + std::map<std::string, Func*>::iterator it; for (it = registry.begin(); it != registry.end(); it++) { std::string typeindicator; - if ((*it).second->flags() & func::Game) + if (((*it).second->flags() & Game) == Game) typeindicator += 'G'; else typeindicator += ' '; - con_print << " " << typeindicator << " " << (*it).first << std::endl; + con_print << std::setw(4) << (*it).second->flags() << " " << typeindicator << + " " << (*it).second->name() << std::endl; } con_print << registry.size() << " registered functions" << std::endl; } -} // namespace func +/* ---- Func ------------------------------------------------------ */ + +Func::Func(char const * funcname, void *ptr, unsigned int funcflags) +{ + if (funcname) + func_name.assign(funcname); + else + func_name.clear(); + + func_flags = funcflags; + func_ptr = ptr; +} + +Func::~Func() +{ + func_name.clear(); + func_ptr = 0; + func_flags = 0; +} + + +void Func::exec(std::string const &args) +{ + if ((flags() & Game)) + return; + + FuncPtr function = (FuncPtr) func_ptr; + function(args); +} + +void Func::exec(Player *player, std::string const &args) +{ + if (!(flags() & Game)) + return; + + GameFuncPtr gamefunction = (GameFuncPtr) func_ptr; + gamefunction(player, args); +} } // namespace core diff --git a/src/core/func.h b/src/core/func.h index 3d91ab1..e34e32d 100644 --- a/src/core/func.h +++ b/src/core/func.h @@ -7,7 +7,6 @@ #ifndef __INCLUDED_CORE_FUNC_H__ #define __INCLUDED_CORE_FUNC_H__ -#include "sys/sys.h" #include "core/player.h" #include <sstream> @@ -17,65 +16,70 @@ namespace core { -class Func_t +/// function pointer type for local functions +typedef void(* FuncPtr)(std::string const &args); + +/// fuction pointer for game functions +typedef void(* GameFuncPtr)(Player *player, std::string const &args); + +/// a function pointer encapsulation class +class Func { public: - Func_t(unsigned int fflags = 0); - - /// flags - unsigned int flags(); + /// function flags + enum Flags {Game=1}; + /// create a new function + Func(char const * funcname, void *ptr, unsigned int funcflags = 0); - /// pointer to the function - void *ptr; + ~Func(); -private: - unsigned int func_flags; -}; +/*----- inspectors ------------------------------------------------ */ -/// function type -typedef Func_t *Func; + /// returns the fucuntion flags + inline unsigned int flags() const { return func_flags; } -/// function pointer type for local functions -typedef void(* FuncPtr)(std::stringstream &args); + /// returns the name of the function + inline std::string const &name() const { return func_name; } -/// fuction pointer for game functions -typedef void(* GameFuncPtr)(Player &player, std::stringstream &args); +/*----- mutators -------------------------------------------------- */ + + /// execute the function if the Game flag is not set + void exec(std::string const &args); + + /// execute the function if the Game flag is set + void exec(Player *player, std::string const &args); -/// the function registry -namespace func -{ +/* ---- Static functions for the Func registry -------------------- */ -/// function flags -enum Flags {Game=1}; + /// add a function to the registry + static void add(const char *name, FuncPtr functionptr, unsigned int flags=0); -/// add a function to the registry -void add(const char *functionname, FuncPtr functionptr, unsigned int flags=0); + /// add a game function to the registry and set the Game flag + static void add(const char *name, GameFuncPtr functionptr, unsigned int flags=0); -/** - * @brief add a game function to the registry - * the flag core::func::Game will automaticly be set - */ -void add(const char *functionname, GameFuncPtr gamefunctionptr, unsigned int flags=0); + /// remove a function from the registry + static void remove(const char *name); -/// remove a function from the registry -void remove(const char *functionname); -void remove(const std::string &functionname); + /// remove a function from the registry + static void remove(std::string const &name); -/// find a fuction pointer -/** Returns 0 if the function pointer could not be found - */ -Func find(const std::string &functionname); + /// find a fuction pointer, return 0 if it could not be found + static Func *find(std::string const &name); -/// list the function registry -void list(); + /// list the function registry + static void list(); -/// the function registry -extern std::map<std::string, Func> registry; + /// the function registry + static std::map<std::string, Func*> registry; -} // namespace func +private: + std::string func_name; + unsigned int func_flags; + void *func_ptr; +}; -} // namespace core +} #endif // __INCLUDED_CORE_FUNC_H__ diff --git a/src/core/gameinterface.cc b/src/core/gameinterface.cc index d07f804..38ea6fe 100644 --- a/src/core/gameinterface.cc +++ b/src/core/gameinterface.cc @@ -64,10 +64,10 @@ void message_broadcast(std::string const & message, int ignoreplayer) } } -void message_send(Player const &player, const char *protohdr, std::string message) +void message_send(Player const *player, const char *protohdr, std::string message) { // send to console - if (&player == &localplayer) { + if (player == &Player::local) { con_print << message << std::endl; } diff --git a/src/core/gameinterface.h b/src/core/gameinterface.h index 457df86..9eb6880 100644 --- a/src/core/gameinterface.h +++ b/src/core/gameinterface.h @@ -44,10 +44,10 @@ public: virtual void shutdown() = 0; /// is called when a player connects - virtual void player_connect(Player &player) = 0; + virtual void player_connect(Player *player) = 0; /// is called when a player disconnects - virtual void player_disconnect(Player &player) = 0; + virtual void player_disconnect(Player *player) = 0; static GameInterface *gameinterface_instance; diff --git a/src/core/netclient.cc b/src/core/netclient.cc index e2a9b7e..61a3e64 100644 --- a/src/core/netclient.cc +++ b/src/core/netclient.cc @@ -21,8 +21,8 @@ NetClient::NetClient(int clientfd, std::string host, int port) : std::ostringstream osstream; //osstream << "host << ":" << port; osstream << "Player" << clientfd; - client_player.name = osstream.str(); - client_player.id = (unsigned int) clientfd; + client_player.player_name = osstream.str(); + client_player.player_id = (unsigned int) clientfd; client_host = host; client_port = port; @@ -43,9 +43,9 @@ int NetClient::port() const return client_port; } -Player &NetClient::player() +Player *NetClient::player() { - return client_player; + return &client_player; } bool NetClient::has_messages() const { diff --git a/src/core/netclient.h b/src/core/netclient.h index dcffb3c..04234da 100644 --- a/src/core/netclient.h +++ b/src/core/netclient.h @@ -31,7 +31,7 @@ public: int port() const; /// the player info associated with this client - Player & player(); + Player *player(); /// return true if there are incoming messages bool has_messages() const; diff --git a/src/core/netconnection.cc b/src/core/netconnection.cc index 85c0534..60b4ff8 100644 --- a/src/core/netconnection.cc +++ b/src/core/netconnection.cc @@ -31,7 +31,7 @@ void NetConnection::connect(std::string const &to_host, int to_port) } std::ostringstream osstream; - osstream << "name " << localplayer.name << std::endl; + osstream << "name " << Player::local.name() << std::endl; send(osstream.str()); } diff --git a/src/core/netserver.cc b/src/core/netserver.cc index 08863df..39548dd 100644 --- a/src/core/netserver.cc +++ b/src/core/netserver.cc @@ -37,7 +37,7 @@ NetServer::~NetServer() // notify the game if (game() && game()->connected) { core::game()->player_disconnect((*it)->player()); - con_print << (*it)->player().name << " disconnected."<< std::endl; + con_print << (*it)->player()->name() << " disconnected."<< std::endl; } delete (*it); } @@ -58,11 +58,11 @@ void NetServer::client_connect(int const clientfd, std::string const host, int c FD_SET(client->fd(), &serverset); // TODO send infos - con_print << client->host() << ":" << client->port() << " " << client->player().name << " connected."<< std::endl; + con_print << client->host() << ":" << client->port() << " " << client->player()->name() << " connected."<< std::endl; // BROADCAST connect message std::ostringstream osstream; - osstream << "msg info " << client->player().name << " connected."<< std::endl; + osstream << "msg info " << client->player()->name() << " connected."<< std::endl; broadcast(osstream.str(), clientfd); // notify the game @@ -84,14 +84,14 @@ void NetServer::reap() // BROADCAST disconnect message std::ostringstream osstream; - osstream << "msg info " << client->player().name << " disconnected."<< std::endl; + osstream << "msg info " << client->player()->name() << " disconnected."<< std::endl; broadcast(osstream.str()); // notify the game if (core::game()) core::game()->player_disconnect(client->player()); - con_print << client->player().name << " disconnected."<< std::endl; + con_print << client->player()->name() << " disconnected."<< std::endl; // remove the client clients.erase(it); @@ -163,10 +163,10 @@ void NetServer::broadcast(std::string const & message, int ignorefd) } // find the client corresponding to a player id -NetClient *NetServer::find_client(Player const &player) +NetClient *NetServer::find_client(Player const *player) { for (std::list<NetClient *>::iterator it = clients.begin(); it != clients.end(); it++) { - if ((*it)->fd() == (int) player.id) { + if ((*it)->fd() == (int) player->id()) { return (*it); } } @@ -201,9 +201,9 @@ void NetServer::parse_incoming_message(NetClient *client, const std::string & me if (command == "say") { if (message.size() > command.size()+1) { std::ostringstream osstream; - osstream << "msg public " << client->player().name << " " << message.substr(command.size()+1) << "\n"; + osstream << "msg public " << client->player()->name() << " " << message.substr(command.size()+1) << "\n"; broadcast(osstream.str()); - con_print << client->player().name << " " << message.substr(command.size()+1) << std::endl; + con_print << client->player()->name() << " " << message.substr(command.size()+1) << std::endl; } return; } @@ -214,12 +214,12 @@ void NetServer::parse_incoming_message(NetClient *client, const std::string & me if (msgstream >> name) { if (name.size() > 16) name = name.substr(0,16); - if (name != client->player().name) { + if (name != client->player()->name()) { std::ostringstream osstream; - osstream << "msg info " << client->player().name << " renamed to " << name << "\n"; + osstream << "msg info " << client->player()->name() << " renamed to " << name << "\n"; broadcast(osstream.str()); - con_print << client->player().name << " renamed to " << name << std::endl; - client->player().name = name; + con_print << client->player()->name() << " renamed to " << name << std::endl; + client->player()->player_name = name; } } return; @@ -228,7 +228,7 @@ void NetServer::parse_incoming_message(NetClient *client, const std::string & me if (command == "list_players") { std::ostringstream osstream; for (std::list<NetClient *>::iterator it = clients.begin(); it != clients.end(); it++) { - osstream << "msg info " << (*it)->player().name << " " << (*it)->host() << ":" << (*it)->port() << "\n"; + osstream << "msg info " << (*it)->player()->name() << " " << (*it)->host() << ":" << (*it)->port() << "\n"; } osstream << "msg info " << clients.size() << " connected players\n" << std::endl; send(client, osstream.str()); @@ -245,15 +245,18 @@ void NetServer::parse_incoming_message(NetClient *client, const std::string & me // execute game functions if (game() && game()->connected) { - Func f = func::find(command); - if (f) { - if (f->flags() && func::Game) { - GameFuncPtr function = (GameFuncPtr) f->ptr; - function(client->player(), msgstream); + Func *function = Func::find(command); + if (function ) { + std::string args; + char c; + if (msgstream >> args) + while (msgstream >> c) + args += c; + if (function ->flags() && Func::Game) { + function->exec(client->player(), args); } else { // instant rcon - //FuncPtr function = (FuncPtr) f->ptr; - //function(msgstream); + //function->exec(args); } } } @@ -267,10 +270,10 @@ void NetServer::parse_client_variable(NetClient * client, const std::string varn std::ostringstream osstream; if (name.size() > 16) name = name.substr(0,16); - if (name != client->player().name) { - osstream << "msg info " << client->player().name << " renamed to " << name << "\n"; + if (name != client->player()->name()) { + osstream << "msg info " << client->player()->name() << " renamed to " << name << "\n"; broadcast(osstream.str()); - client->player().name = name; + client->player()->player_name = name; } } return; diff --git a/src/core/netserver.h b/src/core/netserver.h index 8ebd83d..8c3da65 100644 --- a/src/core/netserver.h +++ b/src/core/netserver.h @@ -35,7 +35,7 @@ public: void send(NetClient * client, std::string const & message); /// find the client corresponding to a player - NetClient *find_client(Player const &player); + NetClient *find_client(Player const *player); protected: /// called by accept() when a new client connects diff --git a/src/core/player.cc b/src/core/player.cc index 6bd79ec..b54bf9e 100644 --- a/src/core/player.cc +++ b/src/core/player.cc @@ -9,14 +9,13 @@ namespace core { -Player localplayer; +Player Player::local; Player::Player() { - id = 0; - name.clear(); + player_id = 0; + player_name.clear(); dirty = false; - control = 0; } diff --git a/src/core/player.h b/src/core/player.h index aa20d20..e19b8ae 100644 --- a/src/core/player.h +++ b/src/core/player.h @@ -27,21 +27,28 @@ public: ~Player(); /// name of the player - std::string name; - - /// core id of the player - unsigned int id; - + inline std::string const &name() const { return player_name; } + + /// id of the player + inline unsigned int id() const { return player_id; } + + /// id of the player + unsigned int player_id; + + /// name of the player + std::string player_name; + + /// dirty state bool dirty; /// the entity the Player is currently controling EntityControlable *control; + + /// the local player + static Player local; }; -/// the local player, always has id 0 -extern Player localplayer; - } #endif // __INCLUDED_CORE_PLAYER_H__ |