X-Git-Url: http://git.localhorst.tv/?a=blobdiff_plain;f=src%2Fshared%2Fcli.cpp;h=c144d8677830281318f09585705168f0d9d3ca90;hb=cdd865c1934eccbb1f1d0ffaf041e53f0fdd524b;hp=9663cb2c4efb192e5e7f0ee36768c84b737db437;hpb=20d0a76d2519c71009c3b3babec0df27529f8142;p=blank.git diff --git a/src/shared/cli.cpp b/src/shared/cli.cpp index 9663cb2..c144d86 100644 --- a/src/shared/cli.cpp +++ b/src/shared/cli.cpp @@ -5,6 +5,7 @@ #include "../io/TokenStreamReader.hpp" #include "../world/Entity.hpp" #include "../world/Player.hpp" +#include "../world/World.hpp" #include #include @@ -18,6 +19,7 @@ namespace blank { CLI::CLI(World &world) : world(world) , commands() { + AddCommand("as", new ImpersonateCommand); AddCommand("tp", new TeleportCommand); } @@ -63,14 +65,67 @@ CLI::Command::~Command() { } +CLIContext::CLIContext(Player *p, Entity *e) +: original_player(p) +, effective_player(p) +, original_entity(e) +, effective_entity(e) { + if (!e && p) { + original_entity = effective_entity = &p->GetEntity(); + } +} + +std::string CLIContext::Name() const { + if (HasPlayer()) return GetPlayer().Name(); + if (HasEntity()) return GetEntity().Name(); + return "anonymous"; +} + + +void ImpersonateCommand::Execute(CLI &cli, CLIContext &ctx, TokenStreamReader &args) { + if (!args.HasMore()) { + // no argument => reset + ctx.Reset(); + ctx.Broadcast(ctx.Name() + " returned to their own self"); + return; + } + // TODO: broadcast who (real player name) impersonates who + string old_name = ctx.Name(); + string name(args.GetString()); + + Player *p = cli.GetWorld().FindPlayer(name); + if (p) { + ctx.SetPlayer(*p); + ctx.SetEntity(p->GetEntity()); + ctx.Broadcast(old_name + " now impersonating " + p->Name()); + return; + } + + // not a player, try an entity + Entity *e = cli.GetWorld().FindEntity(name); + if (e) { + ctx.SetEntity(*e); + ctx.Broadcast(old_name + " now impersonating " + e->Name()); + return; + } + + ctx.Error("no player or entity with name " + name); +} + + void TeleportCommand::Execute(CLI &, CLIContext &ctx, TokenStreamReader &args) { + if (!ctx.HasEntity()) { + ctx.Error("teleport needs entity to operate on"); + return; + } + glm::vec3 pos(args.GetFloat(), args.GetFloat(), args.GetFloat()); - EntityState state = ctx.GetPlayer().GetEntity().GetState(); + EntityState state = ctx.GetEntity().GetState(); state.pos = ExactLocation(pos).Sanitize(); - ctx.GetPlayer().GetEntity().SetState(state); + ctx.GetEntity().SetState(state); stringstream msg; - msg << ctx.GetPlayer().Name() << " teleported to " << pos; + msg << ctx.GetEntity().Name() << " teleported to " << pos; ctx.Broadcast(msg.str()); }