Multiverse/config/common/proxy.py

From Multiverse

Jump to: navigation, search

Contents

Overview

The common/proxy.py script defines command handlers ("slash commands"). For more information, see Defining Command Handlers.

Code

This section consists of an annotated listing of the code in mv-home/config/common/proxy.py.

Imports and initialization

from java.util import *
from java.lang import *
from multiverse.mars import *
from multiverse.mars.core import *
from multiverse.mars.objects import *
from multiverse.mars.util import *
from multiverse.mars.plugins import *
from multiverse.msgsys import *
from multiverse.server.math import *
from multiverse.server.plugins import *
from multiverse.server.events import *
from multiverse.server.objects import *
from multiverse.server.engine import *
from multiverse.server.util import *

False=0
True=1

AnimationClient.setAnimationEffect("PlayAnimation")
# Register a plugin and create a subscription for it
# myPlugin = EnginePlugin("myPlugin")
# Engine.registerPlugin(myPlugin)
# myPlugin.createSubscription(myHandler(),  MessageType.intern("myMsgType"))

Engine.registerPlugin("multiverse.mars.plugins.MarsProxyPlugin")

proxyPlugin = Engine.getPlugin("Proxy1")

PersistCommand

class PersistCommand (ProxyPlugin.CommandParser):

    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()

        cmd = cmdEvent.getCommand()
        splitCmd = cmd.split(" ")
        objOid = int(splitCmd[1])

        Log.debug("PersistCommand: playerOid=" + str(playerOid) + ", objOid=" + str(objOid))

        # send out a set persist message
        ObjectManagerClient.setPersistenceFlag(objOid,
                                               Boolean.TRUE)
        
        WorldManagerClient.sendObjChatMsg(playerOid, 1, "persisted obj " + str(objOid))
        return None

GenerateCommand

class GenerateCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        # The args are template name
        cmd = cmdEvent.getCommand()
        splitCmd = cmd.split(" ")
        templateName = splitCmd[1]
        Log.debug("GenerateCommand: player=" + str(playerOid) + ", template=" + templateName)
        # get the player's loc
        objInfo = WorldManagerClient.getObjectInfo(playerOid)
        loc = objInfo.loc
        loc.add(1000,0,0)
        Log.debug("GenerateCommand: player=" + str(playerOid) + ", loc=" + loc.toString())
        
        # generate the object
        objOid = ObjectManagerClient.generateObject(templateName, loc)
        Log.debug("GenerateCommand: player=" + str(playerOid) + ", generated obj oid=" + str(objOid))

        # spawn object
        rv = WorldManagerClient.spawn(objOid)
        Log.debug("GenerateCommand: player=" + str(playerOid) + ", spawned obj rv=" + str(rv))
        WorldManagerClient.sendObjChatMsg(playerOid, 1, "generated oid=" + str(objOid))
        return None

ThreadStatsCommand

class ThreadStatsCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
	global proxyPlugin;
        cmd = cmdEvent.getCommand()
        playerOid = cmdEvent.getObjectOid()
        targetOid = cmdEvent.getTarget()
        Log.debug("ThreadStatsCommand: playerOid=" + str(playerOid) + ", " + proxyPlugin.getCurrentThreads().toString())
        InventoryClient.activateObject(targetOid,
                                       playerOid)
        WorldManagerClient.sendObjChatMsg(playerOid, 1, "threadstats=" + proxyPlugin.getCurrentThreads().toString())
        return None

ConcludeCommand

class ConcludeCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        cmd = cmdEvent.getCommand()
        playerOid = cmdEvent.getObjectOid()
        targetOid = cmdEvent.getTarget()

        Log.debug("ConcludeCommand: cmd=" + cmd)

        rv = QuestClient.requestConclude(targetOid,
                                         playerOid)
        return None
        

AddParticleEffectCommand

class AddParticleEffectCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        cmd = cmdEvent.getCommand()
        playerOid = cmdEvent.getObjectOid()
        targetOid = cmdEvent.getTarget()

        Log.debug("AddParticleEffectCommand: cmd=" + cmd)
        splitCmd = cmd.split(" ")
        attachName = splitCmd[1]
        effectName = splitCmd[2]
        vel = 5
        size = 5
        booleans = 0
        if (len(splitCmd) >= 4) :
            vel = float(splitCmd[3])
        if (len(splitCmd) >= 5) :
            size = float(splitCmd[4])
        if (len(splitCmd) >= 6) :
            booleans = int(splitCmd[5])
        r = 255
        g = 255
        b = 255
        if (len(splitCmd) >= 7) :
            r = splitCmd[6]
            if (len(splitCmd) >= 8) :
                g = splitCmd[7]
                if (len(splitCmd) >= 9) :
                    b = splitCmd[8]
        color = Color(int(r), int(g), int(b))
        rv = AnimationClient.addParticleEffect(playerOid,
                                               attachName,
                                               effectName,
                                               Quaternion(0,0,0,1),
                                               vel,
                                               size,
                                               booleans,
                                               color)
        return None

LootCommand

class LootCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        cmd = cmdEvent.getCommand()
        playerOid = cmdEvent.getObjectOid()
        targetOid = cmdEvent.getTarget()

        Log.debug("LootCommand: cmd=" + cmd)

        rv = InventoryClient.lootAll(playerOid,
                                     targetOid)
        WorldManagerClient.sendObjChatMsg(playerOid, 0, "proxy.py:lootAll=" + str(rv))
        return None

SetLocCommand

class SetLocCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        cmd = cmdEvent.getCommand()
        Log.debug("SetLocCommand: cmd=" + cmd)
        splitCmd = cmd.split(" ")
        x = int(splitCmd[1])
        y = int(splitCmd[2])
        z = int(splitCmd[3])
        wnode = BasicWorldNode()
        wnode.setLoc(Point(x,y,z))

        # tell the worldmanager we've moved
        # this should update everyone near me
        WorldManagerClient.updateWorldNode(cmdEvent.getObjectOid(), wnode, True)
        return None
    

GotoCommand

The Goto command moves the player character to the specified waypoint in the world. The user invokes it from the client as follows:

/goto waypointName

where waypointName is a defined waypoint.

class GotoCommand (ProxyPlugin.CommandParser):
   def parse(self, cmdEvent):
       cmd = cmdEvent.getCommand()
       playerOid = cmdEvent.getObjectOid()
       Log.debug("GotoCommand: cmd=" + cmd)
       splitCmd = cmd.split(" ")
       markerName = splitCmd[1]
       Log.debug("GotoCommand: got goto command, to marker=" + markerName)

current = WorldManagerClient.getWorldNode(playerOid) instanceOid = current.getInstanceOid()

       marker = InstanceClient.getMarker(instanceOid, markerName)

if (marker == None):

           WorldManagerClient.sendObjChatMsg(playerOid, 0, "Unknown marker")

return

       Log.debug("GotoCommand: marker " + markerName + "=" + marker.toString())
       wnode = BasicWorldNode()
       wnode.setLoc(marker.getPoint())
       wnode.setOrientation(marker.getOrientation())
       # tell the worldmanager we've moved
       # this should update everyone near me
       WorldManagerClient.updateWorldNode(playerOid, wnode, True)

CreateItemCommand

class CreateItemCommand (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        cmd = cmdEvent.getCommand()

        # the template name is whatever is after the space
        template = cmd[cmd.index(' ')+1:]
        Log.debug("CreateItemSubObjCommand: template=" + template)
        playerOid = cmdEvent.getObjectOid()

        bagOid = WorldManagerClient.getObjectProperty(playerOid, InventoryPlugin.INVENTORY_PROP_BAG_KEY)
        Log.debug("CreateItemSubObjCommand: bagOid=" + str(bagOid))

        # generate the object
        Log.debug("CreateItemSubObjCommand: templ=" + template + ", generating object")
        itemOid = ObjectManagerClient.generateObject(template, Template())

        # add to inventory
        Log.debug("CreateItemSubObjCommand: createitem: oid=" + str(itemOid) + ", bagOid=" + str(bagOid) + ", adding to inventory")
        rv = InventoryClient.addItem(playerOid, playerOid, playerOid, itemOid)
        Log.debug("CommandPlugin: createitem: oid=" + str(itemOid) + ", added, rv=" + str(rv))
        WorldManagerClient.sendObjChatMsg(playerOid, 1, "added item" + str(rv))
        return None
        

SetMeshCommand

class SetMeshCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        cmd = cmdEvent.getCommand()
        playerOid = cmdEvent.getObjectOid()
        mesh = cmd[cmd.index(' ')+1:]
        submeshes = LinkedList()
        Log.debug("/setmesh: oid=" + str(playerOid) + " to: " + mesh)
        WorldManagerClient.modifyDisplayContext(playerOid,
                                                WorldManagerClient.modifyDisplayContextActionReplace,
                                                mesh,
                                                submeshes)
        return None

ReleaseCommand

class ReleaseCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        Log.debug("/release: oid=" + str(playerOid))
        CombatClient.releaseObject(playerOid)
        return None

WhoCommand

class WhoCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        global proxyPlugin;
        playerOid = cmdEvent.getObjectOid()
        playerNames = proxyPlugin.getPlayerNames()
        Log.debug("/who: oid=" + str(playerOid) + ": returning "+str(playerNames.size())+" players")
        response = "players\n------------\n"
        for name in playerNames:
            response = response + name + "\n"
        response = response + str(playerNames.size()) + " players\n"
        WorldManagerClient.sendObjChatMsg(playerOid, 0, response)
        return None

PlayerCountCommand

class PlayerCountCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        global proxyPlugin;
        playerOid = cmdEvent.getObjectOid()
        playerNames = proxyPlugin.getPlayerNames()
        Log.debug("/playercount: oid=" + str(playerOid) + ": returning "+str(playerNames.size())+" players")
        response = str(playerNames.size()) + " players\n"
        ProxyPlugin.sendObjChatMsg(playerOid, 0, response)
        return None

ParmCommand

The "/parm" command accepts a series of name/value pairs, separated by spaces.

class ParmCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        cmd = cmdEvent.getCommand()
        splitCmd = cmd.split(" ")
        count = (len(splitCmd) - 1) / 2
        i = -1
        msg = WorldManagerClient.TargetedExtensionMessage(playerOid)
        msg.setProperty("ext_msg_type", "ClientParameter")
        for s in splitCmd:
            if (i != -1):
                if ((i & 1) == 0):
                    n = s
                else:
                    msg.setProperty(n, s)
            i = i + 1
        Engine.getAgent().sendBroadcast(msg)
        return None

To set a parameter in the client using the command that runs on the server side, type

/parm parameterName parameterValue

For example

/parm CollisionAPI.MinInchesToObstacle 42.0

SysCommand

class SysCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        cmd = cmdEvent.getCommand()
        msg = cmd[cmd.index(' ')+1:]
        Log.debug("SysCommand: msg=" + msg)

        WorldManagerClient.sendSysChatMsg("System: " + msg)
        return None

DirLightCommand

class DirLightCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        global proxyPlugin;
        playerOid = cmdEvent.getObjectOid()
        cmd = cmdEvent.getCommand()
        splitCmd = cmd.split(" ")
        x = Float.valueOf(splitCmd[1])
        y = Float.valueOf(splitCmd[2])
        z = Float.valueOf(splitCmd[3])
        Log.debug("DirLightCommand: playerOid=" + str(playerOid) +
                  ", x=" + str(x) +
                  ", y=" + str(y) +
                  ", z=" + str(z))
        grey = Color(140, 128, 128)
        dirlight = DirectionalLight("dirlight")
        dirlight.setDiffuse(grey)
        dirlight.setSpecular(grey)
        dirlight.setAttenuationRange(1000000)
        dirlight.setAttenuationConstant(1)
        dirlight.setAttenuationLinear(0)
        dirlight.setAttenuationQuadradic(0)
        vector = MVVector(x,y,z)
        dirlight.setLightOrientation(Quaternion.fromAngleAxis(-1, vector))
        lightEvent = NewLightEvent()
        lightEvent.setObjectOid(playerOid)
        lightEvent.setLight(dirlight)
        playerOids = proxyPlugin.getPlayerOids()
        for oid in playerOids:
            conMap = proxyPlugin.getConnectionMap()
            con = conMap.getConnection(oid)
            Log.debug("DirLightCommand: sending light " +
                      dirlight.toString() +
                      " to oid " + str(oid))
            con.send(lightEvent.toBytes())
        return None



FindCommand

class FindCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        cmd = cmdEvent.getCommand()
        itemTemplate = cmd[cmd.index(' ')+1:]
        itemOid = InventoryClient.findItem(playerOid, itemTemplate)
        if (itemOid == None):
            WorldManagerClient.sendObjChatMsg(playerOid, 0, "item not found")
        else:
            WorldManagerClient.sendObjChatMsg(playerOid, 0, itemTemplate + ":" + str(itemOid))

FindWeaponCommand

class FindWeaponCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        itemOid = MarsInventoryClient.findItem(playerOid, MarsEquipSlot.PRIMARYWEAPON)
        if (itemOid == None):
            WorldManagerClient.sendObjChatMsg(playerOid, 0, "item not found")
        else:
            WorldManagerClient.sendObjChatMsg(playerOid, 0, "weapon:" + str(itemOid))

RemoveCommand

class RemoveCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        cmd = cmdEvent.getCommand()
        itemTemplate = cmd[cmd.index(' ')+1:]
        itemOid = InventoryClient.removeItem(playerOid, itemTemplate)
        if (itemOid == None):
            WorldManagerClient.sendObjChatMsg(playerOid, 0, "item not found")
        else:
            WorldManagerClient.sendObjChatMsg(playerOid, 0, itemTemplate + ":" + str(itemOid))

AbilityCommand

class AbilityCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        targetOid = cmdEvent.getTarget()
        cmd = cmdEvent.getCommand()
        abilityName = cmd[cmd.index(' ')+1:]
        CombatClient.startAbility(abilityName, playerOid, targetOid, None)


NoMoveCommand

class NoMoveCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        targetOid = cmdEvent.getTarget()
        cmd = cmdEvent.getCommand()
        nomove = cmd[cmd.index(' ')+1:]
        if nomove == "on":
            WorldManagerClient.setObjectProperty(targetOid, "world.nomove", Boolean(True))
        else:
            WorldManagerClient.setObjectProperty(targetOid, "world.nomove", Boolean(False))

ResetQuestCommand

class ResetQuestCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        QuestClient.resetQuests(playerOid)

DumpStacksCommand

class DumpStacksCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        msg = Message(EnginePlugin.MSG_TYPE_DUMP_ALL_THREAD_STACKS)
        Engine.getAgent().sendBroadcast(msg)

TradeStartCommand

class TradeStartCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        targetOid = cmdEvent.getTarget()
        MarsInventoryClient.tradeStart(playerOid, targetOid)

StuckCommand

Occaisionally, a player can get "stuck" in a collision volume, usually by moving into a new area before the Client loads buildings and other objects with collision volumes. Once the player is in this state, the avatar can't move, because the Multiverse collision system prevents it. If an avatar has been in this situation for five seconds, the chat window will display the message: "Executing /stuck command because player has been in a collision volume for 5000 milliseconds," then the Client will automatically issue the "/stuck" command that calls the server StuckCommand method.

If the world contains a marker named "stuck", then the player is moved to that location. If not, then the player avatar will be moved to the origin (0, 0, 0).

To change the time between getting stuck and executing StuckCommand, set the value of the client parameter InputHandler.MillisecondsStuckBeforeGotoStuck. The default value of this parameter is 5000 milliseconds. To disable "stuck" support, set InputHandler.MillisecondsStuckBeforeGotoStuck to zero (0).

For more information on Client parameters, see Client Parameters.

class StuckCommand (ProxyPlugin.CommandParser):
   def parse(self, cmdEvent):
       wnode = BasicWorldNode()
       playerOid = cmdEvent.getObjectOid()
       current = WorldManagerClient.getWorldNode(playerOid)
       instanceOid = current.getInstanceOid()
       marker = InstanceClient.getMarker(instanceOid, "stuck")
       if (marker != None):
           wnode.setLoc(marker.getPoint())
           wnode.setOrientation(marker.getOrientation())
           Log.debug("StuckCommand: marker stuck = " + marker.toString())
       else:
           wnode.setLoc(Point(0, 0, 0))
           Log.debug("StuckCommand: no marker stuck, so going to (0, 0, 0)")
       # tell the worldmanager we've moved
       WorldManagerClient.updateWorldNode(cmdEvent.getObjectOid(), wnode, True)

TestCommand

# tests should send a chat message back with "test success" or "test failure"
class TestCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        cmd = cmdEvent.getCommand()
        playerOid = cmdEvent.getObjectOid()

        cmd = cmdEvent.getCommand()
        splitCmd = cmd.split(" ")
        testName = splitCmd[1]
        if (testName == "persistKey") :
            # example /test persistKey testKey
            key = splitCmd[2]
            self.testKeywordPersistence(playerOid, key)
        else :
            Log.error("TestCommand: unknown test " + testName)

    def testKeywordPersistence(self, playerOid, key) :
        testNamespace = Namespace.intern("testNamespace")
        saveEntity = Entity("saveEntity")
        saveEntity.setProperty("sample_property", "sample_value")
        if (not ObjectManagerClient.saveObjectData(key,
                                                   saveEntity,
                                                   testNamespace)) :
            Log.error("testKeywordPersistence failed on saving")
            WorldManagerClient.sendObjChatMsg(playerOid, 0, "test failure")
            return
        loadEntity = ObjectManagerClient.loadObjectData(key)
        if (loadEntity == None) :
            Log.error("testKeywordPersistence failed on loading, got null")
            WorldManagerClient.sendObjChatMsg(playerOid, 0, "test failure")
            return
        val = loadEntity.getProperty("sample_property")
        if (val != "sample_value") :
            Log.error("testKeywordPersistence failed, value=" + val)
            WorldManagerClient.sendObjChatMsg(playerOid, 0, "test failure")
            return
        Log.error("testKeywordPersistence: test passed")
        WorldManagerClient.sendObjChatMsg(playerOid, 0, "test success")
        
# Display the server's notion of the orientation of a targeted entity as a chat message

OrientationCommand

class OrientationCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        targetOid = cmdEvent.getTarget()
        targetObj = WorldManagerClient.getObjectInfo(targetOid)
        WorldManagerClient.sendObjChatMsg(playerOid, 0, "Orientation: " + str(targetObj.orient))

DebugOidCommand

Enable debugging for a single OID. If no argument is given, then the targeted object OID is used.

Subject to change - enables some limited arbitrary debugging. May change or be removed in the next release.

class DebugOidCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        cmd = cmdEvent.getCommand().split(" ");
        if len(cmd) > 1:
            cmd = cmd[1]
        else:
            cmd = ""
        objOid = 0
        try:
            if cmd != "":
                objOid = int(cmd)
        except ValueError:
            WorldManagerClient.sendObjChatMsg(playerOid, 0, "Invalid OID");
            return
        except TypeError:
            pass
        if objOid == 0:
            World.DEBUG_OID = cmdEvent.getTarget()
        else:
            World.DEBUG_OID = objOid
        WorldManagerClient.sendObjChatMsg(playerOid, 0, "DEBUG_OID = "+str(World.DEBUG_OID))

UnknownCommand

This command is called if the user enters an unknown slash command. It displays the message "Unknown command" in the chat window.

class UnknownCommand  (ProxyPlugin.CommandParser):
    def parse(self, cmdEvent):
        playerOid = cmdEvent.getObjectOid()
        WorldManagerClient.sendObjChatMsg(playerOid, 0, "Unknown cmd " + cmdEvent.getCommand())

Registrations

This section registers all the commands previously defined, and associates them with the actual slash command that the user must enter.

proxyPlugin.registerCommand("/resetquests", ResetQuestCommand())
proxyPlugin.registerCommand("/nomove", NoMoveCommand())
proxyPlugin.registerCommand("/goto", GotoCommand())
proxyPlugin.registerCommand("/createitem", CreateItemCommand())
proxyPlugin.registerCommand("/setmesh", SetMeshCommand())
proxyPlugin.registerCommand("/setloc", SetLocCommand())
proxyPlugin.registerCommand("/lootall", LootCommand())
proxyPlugin.registerCommand("/addParticle", AddParticleEffectCommand())
proxyPlugin.registerCommand("/release", ReleaseCommand())
proxyPlugin.registerCommand("/conclude", ConcludeCommand())
proxyPlugin.registerCommand("/who", WhoCommand())
proxyPlugin.registerCommand("/playercount", PlayerCountCommand())
proxyPlugin.registerCommand("/parm", ParmCommand())
proxyPlugin.registerCommand("/sys", SysCommand())
proxyPlugin.registerCommand("/dirlight", DirLightCommand())
proxyPlugin.registerCommand("/threadstats", ThreadStatsCommand())
proxyPlugin.registerCommand("/find", FindCommand())
proxyPlugin.registerCommand("/remove", RemoveCommand())
proxyPlugin.registerCommand("/findweapon", FindWeaponCommand())
proxyPlugin.registerCommand("/ability", AbilityCommand())
proxyPlugin.registerCommand("/generate", GenerateCommand())
proxyPlugin.registerCommand("/persist", PersistCommand())
proxyPlugin.registerCommand("/dumpstacks", DumpStacksCommand())
proxyPlugin.registerCommand("/trade", TradeStartCommand())
proxyPlugin.registerCommand("/stuck", StuckCommand())
proxyPlugin.registerCommand("/test", TestCommand())
proxyPlugin.registerCommand("/orientation", OrientationCommand())
proxyPlugin.registerCommand("/debugoid", DebugOidCommand())
proxyPlugin.registerCommand("/unknownCmd", UnknownCommand())
Personal tools