mirror of
https://github.com/Sneed-Group/Poodletooth-iLand
synced 2024-12-26 21:22:27 -06:00
115 lines
3.6 KiB
Python
115 lines
3.6 KiB
Python
|
|
||
|
from cPickle import dumps, loads
|
||
|
|
||
|
from direct.directnotify import DirectNotifyGlobal
|
||
|
from direct.distributed.PyDatagram import PyDatagram
|
||
|
from direct.showbase.Messenger import Messenger
|
||
|
|
||
|
|
||
|
class NetMessenger(Messenger):
|
||
|
"""
|
||
|
This works very much like the Messenger class except that messages
|
||
|
are sent over the network and (possibly) handled (accepted) on a
|
||
|
remote machine (server).
|
||
|
"""
|
||
|
notify = DirectNotifyGlobal.directNotify.newCategory('NetMessenger')
|
||
|
|
||
|
def __init__(self, air, baseChannel=20000, baseMsgType=20000):
|
||
|
"""
|
||
|
air is the AI Repository.
|
||
|
baseChannel is the channel that the first message is sent on.
|
||
|
baseMsgType is the MsgType of the same.
|
||
|
"""
|
||
|
assert self.notify.debugCall()
|
||
|
Messenger.__init__(self)
|
||
|
self.air=air
|
||
|
self.baseChannel = baseChannel
|
||
|
self.baseMsgType = baseMsgType
|
||
|
|
||
|
self.__message2type = {}
|
||
|
self.__type2message = {}
|
||
|
self.__message2channel = {}
|
||
|
|
||
|
def clear(self):
|
||
|
assert self.notify.debugCall()
|
||
|
Messenger.clear(self)
|
||
|
|
||
|
def register(self, code, message):
|
||
|
assert self.notify.debugCall()
|
||
|
channel = self.baseChannel + code
|
||
|
msgType = self.baseMsgType + code
|
||
|
|
||
|
if message in self.__message2type:
|
||
|
self.notify.error('Tried to register message %s twice!' % message)
|
||
|
return
|
||
|
|
||
|
self.__message2type[message] = msgType
|
||
|
self.__type2message[msgType] = message
|
||
|
self.__message2channel[message] = channel
|
||
|
|
||
|
def prepare(self, message, sentArgs=[]):
|
||
|
"""
|
||
|
Prepare the datagram that would get sent in order to send this message
|
||
|
to its designated channel.
|
||
|
"""
|
||
|
assert self.notify.debugCall()
|
||
|
|
||
|
# Make sure the message is registered:
|
||
|
if message not in self.__message2type:
|
||
|
self.notify.error('Tried to send unregistered message %s!' % message)
|
||
|
return
|
||
|
|
||
|
datagram = PyDatagram()
|
||
|
# To:
|
||
|
datagram.addUint8(1)
|
||
|
datagram.addChannel(self.__message2channel[message])
|
||
|
# From:
|
||
|
datagram.addChannel(self.air.ourChannel)
|
||
|
|
||
|
messageType=self.__message2type[message]
|
||
|
datagram.addUint16(messageType)
|
||
|
datagram.addString(str(dumps(sentArgs)))
|
||
|
|
||
|
return datagram
|
||
|
|
||
|
def accept(self, message, *args):
|
||
|
if message not in self.__message2channel:
|
||
|
self.notify.error('Tried to accept unregistered message %s!' % message)
|
||
|
return
|
||
|
|
||
|
anyAccepting = bool(self.whoAccepts(message))
|
||
|
if not anyAccepting:
|
||
|
self.air.registerForChannel(self.__message2channel[message])
|
||
|
|
||
|
Messenger.accept(self, message, *args)
|
||
|
|
||
|
def send(self, message, sentArgs=[]):
|
||
|
"""
|
||
|
Send message to anything that's listening for it.
|
||
|
"""
|
||
|
assert self.notify.debugCall()
|
||
|
|
||
|
datagram = self.prepare(message, sentArgs)
|
||
|
self.air.send(datagram)
|
||
|
Messenger.send(self, message, sentArgs=sentArgs)
|
||
|
|
||
|
def handle(self, msgType, di):
|
||
|
"""
|
||
|
Send data from the net on the local netMessenger.
|
||
|
"""
|
||
|
assert self.notify.debugCall()
|
||
|
|
||
|
if msgType not in self.__type2message:
|
||
|
self.notify.warning('Received unknown message: %d' % msgType)
|
||
|
return
|
||
|
|
||
|
message = self.__type2message[msgType]
|
||
|
sentArgs=loads(di.getString())
|
||
|
|
||
|
if type(sentArgs) != list:
|
||
|
self.notify.warning('Received non-list item in %s message: %r' %
|
||
|
(message, sentArgs))
|
||
|
return
|
||
|
|
||
|
Messenger.send(self, message, sentArgs=sentArgs)
|