Metadata-Version: 1.0
Name: PodSixNet
Version: 0.10.0
Summary: Multiplayer networking library for games
Home-page: https://github.com/chr15m/PodSixNet
Author: Chris McCormick
Author-email: chris@mccormick.cx
License: UNKNOWN
Description: PodSixNet - lightweight multiplayer networking library for Python games
        -----------------------------------------------------------------------
        
        PodSixNet is a lightweight network layer designed to make it easy to
        write multiplayer games in Python. It uses Python's built in asyncore
        library and rencode.py (included) to asynchronously serialise network
        events and arbitrary data structures, and deliver them to your high
        level classes through simple callback methods.
        
        Each class within your game client which wants to receive network
        events, subclasses the ConnectionListener class and then implements
        ``Network_*`` methods to catch specific user-defined events from the
        server. You don't have to wait for buffers to fill, or check sockets for
        waiting data or anything like that, just do ``connection.Pump()`` once
        per game loop and the library will handle everything else for you,
        passing off events to all classes that are listening. Sending data back
        to the server is just as easy, using ``connection.Send(mydata)``.
        Likewise on the server side, events are propagated to ``Network_*``
        method callbacks and data is sent back to clients with the
        ``client.Send(mydata)`` method.
        
        The `PodSixNet mailing
        list <http://groups.google.com/group/podsixnet>`__ is good for getting
        help from other users.
        
        For users of the Construct game making environment for Windows, there is
        a tutorial on doing multiplayer networking with PodSixNet,
        `here <http://www.scirra.com/forum/viewtopic.php?f=8&t=6299>`__. Thanks
        to Dave Chabo for contributing this tutorial.
        
        Here is `another tutorial by Julian
        Meyer <http://www.raywenderlich.com/38732/multiplayer-game-programming-for-teens-with-python>`__.
        
        Install
        -------
        
        ``pip install PodSixNet``
        
        or
        
        ``easy_install PodSixNet``
        
        From source
        ~~~~~~~~~~~
        
        First make sure you have `Python <http://python.org/>`__ 2.4 or greater
        installed.
        
        A python3 version of PodSixNet is maintained in the `python3
        branch <https://github.com/chr15m/PodSixNet/tree/python3>`__.
        
        Next you'll want to get the PodSixNet source.
        
        The module is found inside a subdirectory called PodSixNet within the
        top level folder. There's an ``__init__.py`` inside there, so you can
        just copy or symlink the PodSixNet sub-directory into your own project
        and then do ``import PodSixNet``, or else you can run
        ``sudo python setup.py install`` to install PodSixNet into your Python
        path. Use ``sudo python setup.py develop`` if you want to stay up to
        date with the cutting edge and still be able to svn/bzr up every now and
        then.
        
        By default PodSixNet uses a binary encoder to transfer data over the
        network, but it can optionally use the `JSON <http://json.org/>`__
        format or other formats supported by a serialiser which has 'dumps' and
        'loads' methods. If you want to serialise your data using JSON you can
        change the first line of Channel.py to 'from simplejson import dumps,
        loads' or use the built-in json library in Python 2.6 or higher. This
        will allow you to write game clients in languages that can't read the
        'rencode' binary format, such as Javascript.
        
        Examples
        --------
        
        Chat example:
        
        -  ``python examples/ChatServer.py``
        -  and a couple of instances of ``python examples/ChatClient.py``
        
        Whiteboard example:
        
        -  ``python examples/WhiteboardServer.py``
        -  and a couple of instances of ``python examples/WhiteboardClient.py``
        
        LagTime example (measures round-trip time from the server to the
        client):
        
        -  ``python examples/LagTimeServer.py``
        -  and a couple of instances of ``python examples/LagTimeClient.py``
        
        Quick start - Server
        --------------------
        
        You will need to subclass two classes in order to make your own server.
        Each time a client connects, a new Channel based class will be created,
        so you should subclass Channel to make your own
        server-representation-of-a-client class like this:
        
        ::
        
            from PodSixNet.Channel import Channel
        
            class ClientChannel(Channel):
        
                def Network(self, data):
                    print data
                
                def Network_myaction(self, data):
                    print "myaction:", data
        
        Whenever the client does ``connection.Send(mydata)``, the ``Network()``
        method will be called. The method ``Network_myaction()`` will only be
        called if your data has a key called 'action' with a value of
        "myaction". In other words if it looks something like this:
        
        ::
        
            data = {"action": "myaction", "blah": 123, ... }
        
        Next you need to subclass the Server class like this:
        
        ::
        
            from PodSixNet.Server import Server
        
            class MyServer(Server):
                
                channelClass = ClientChannel
                
                def Connected(self, channel, addr):
                    print 'new connection:', channel
        
        Set ``channelClass`` to the channel class that you created above. The
        method ``Connected()`` will be called whenever a new client connects to
        your server. See the example servers for an idea of what you might do
        each time a client connects. You need to call ``Server.Pump()`` every
        now and then, probably once per game loop. For example:
        
        ::
        
            myserver = MyServer()
            while True:
                myserver.Pump()
                sleep(0.0001)
        
        When you want to send data to a specific client/channel, use the Send
        method of the Channel class:
        
        ::
        
            channel.Send({"action": "hello", "message": "hello client!"})
        
        Quick start - Client
        --------------------
        
        To have a client connect to your new server, you should use the
        Connection module. See ``pydoc Connection`` for more details, but here's
        a summary:
        
        ``Connection.connection`` is a singleton Channel which connects to the
        server. You'll only have one of these in your game code, and you'll use
        it to connect to the server and send messages to the server.
        
        ::
        
            from PodSixNet.Connection import connection
        
            # connect to the server - optionally pass hostname and port like: ("mccormick.cx", 31425)
            connection.Connect()
        
            connection.Send({"action": "myaction", "blah": 123, "things": [3, 4, 3, 4, 7]})
        
        You'll also need to put the following code once somewhere in your game
        loop:
        
        ::
        
            connection.Pump()
        
        Any time you have an object in your game which you want to receive
        messages from the server, subclass ``ConnectionListener``. For example:
        
        ::
        
            from PodSixNet.Connection import ConnectionListener
        
            class MyNetworkListener(ConnectionListener):
        
                def Network(self, data):
                    print 'network data:', data
                
                def Network_connected(self, data):
                    print "connected to the server"
                
                def Network_error(self, data):
                    print "error:", data['error'][1]
                
                def Network_disconnected(self, data):
                    print "disconnected from the server"
                
                def Network_myaction(data):
                    print "myaction:", data
        
        Just like in the server case, the network events are received by
        ``Network_*`` callback methods, where you should replace '\*' with the
        value in the 'action' key you want to catch. You can implement as many
        or as few of the above as you like. For example, NetworkGUI would
        probably only want to listen for the ``_connected``, ``_disconnected``,
        and ``_error`` network events. The data for ``_error`` always comes in
        the form of network exceptions, like (111, 'Connection refused') - these
        are passed straight from the socket layer and are standard socket
        errors.
        
        Another class might implement custom methods like
        ``Network_myaction()``, which will receive any data that gets sent from
        the server with an 'action' key that has the name 'myaction'. For
        example, the server might send a message with the number of players
        currently connected like so:
        
        ::
        
            channel.Send({"action": "numplayers", "players": 10})
        
        And the listener would look like this:
        
        ::
        
            from PodSixNet.Connection import ConnectionListener
        
            class MyPlayerListener(ConnectionListener):
        
                def Network_numplayers(data):
                    # update gui element displaying the number of currently connected players
                    print data['players']
        
        You can subclass ``ConnectionListener`` as many times as you like in
        your application, and every class you make which subclasses it will
        receive the network events via named Network callbacks. You should call
        the ``Pump()`` method on each object you instantiate once per game loop:
        
        ::
        
            gui = MyPlayerListener()
            while 1:
                connection.Pump()
                gui.Pump()
        
        License
        -------
        
        Copyright `Chris McCormick <http://mccormick.cx/>`__, 2009-2015.
        
        PodSixNet is licensed under the terms of the LGPL v3.0 or higher. See
        the file called `COPYING <COPYING>`__ for details.
        
        This basically means that you can use it in most types of projects
        (commercial or otherwise), but if you make changes to the PodSixNet code
        you must make the modified code available with the distribution of your
        software. Hopefully you'll tell us about it so we can incorporate your
        changes. I am not a lawyer, so please read the license carefully to
        understand your rights with respect to this code.
        
        Why not use Twisted instead?
        ----------------------------
        
        Twisted is a fantastic library for writing robust network code. I have
        used it in several projects in the past, and it was quite nice to work
        with. That said, Twisted:
        
        -  wants to steal the mainloop
        -  is bloated not KISS (it implements many many different protocols)
        -  has a weird template launching language when Python should do just
           fine
        -  is not written 100% for the specfic use-case of multiplayer games
        
        These are some of the reasons why I decided to write a library that is
        lightweight, has no dependencies except Python, and is dedicated 100% to
        the task of multiplayer game networking.
        
Platform: UNKNOWN
