Lan game communication?
I'm building a game (probably just like many others in this forum :) and I was wondering how I could implement a LAN multiplayer. I know that there is a module out there called socket, but I am not exactly sure how to use it. And it seems ( correct me if I'm wrong) that it cannot find other players who are up for a LAN game.
THanks in advance,
socketmodule allows you to send binary strings over the network. Here is a short client example:
import socket s = socket.socket() s.connect(("localhost", 8888)) s.send(b"some data") response = s.recv(1024) print(response) s.close()
import socket s = socket.socket() s.bind(("localhost", 8888)) s.listen(1) while True: conn, addr = s.accept() print("got connection from: ", addr) data = conn.recv(1024) print("received: ", data) conn.send(b"server received: " + data) conn.close()
Both of these code snippets are only minimal and untested.
When developing multiplayer for a game, the largest part is actually the creation and handling of these messages.
What do you want to be sent between server and client? The simplest way is to only send the actions each player chooses (e.g. move north) to the server, where the real game runs, and send the changes (player moves north) to all the client.
It is more complicated if you want one client to also be the server of the game.
The most simple way is to structure the whole gamecode arround the netcode (in my experience). This means seperating the game logic from the user interface. For example, you could always start a server in the background and make every singleplayer game connect to this private server instead of writing a seperate server.
In this case the client only needs to handle the menu, graphics and user input.
If you want your clients to automatically find other games in the LAN, take a look at UDP broadcasting.
For a simple way to convert a python object into a string, use the
pickle module(but be aware that this is quite a security risk, so you may want to use other modules for this).
Also, take a look at
threading(running multiple functions in paralell) or asynchronous network programming if you want to handle multiple clients at the same time. In python2, there is a
SocketServermodule for easily handling multple clients in parallel (using the
ThreadingMixInclass or how it was named). This module was renamed in py3.
if it is ios and macOS only then you could also use the native apple multipeer connectivity API for iOS and macOs.
Here is a very nice pythonista wrapper which was done by @mikael
Especially looking up and finding nearby users is very easy with Apples Multipeer Connectivity.
@bennr01 Should the last line of your server code be deeneted? Do you really want to close the socket inside the loop?
@ccc the last line does not close the server socket itself. It only closes the just accepted connection. The client also closes immediately after sending "some data". So no reason to not close the connection on server side.
Anyway @bennr01 did only write this as some short demonstration ... In real world you would probably hold the connection open over the whole game session ....
@mithrendal this sounds great, I didn't even know that this existed. I'm just looking into it now
@Drizzel it depends on what you are planning to develop. If you want local multiplayer then forget about the socket stuff and go with multipeer API. If you want multiplayer over the internet then you go the socket way.
Either way, whish you happy time with sending and receiving data ... it's fun ;-)
@mithrendal Haha it definitely is fun :)
And it's exactly what I need for my local multiplayer. That it works over Bluetooth as well is a nice add on
@Drizzel MultipeerConnectivity defines two modes:
see here the definition taken from apple developer website:
Use this message type for application-critical data.
this message type should be used for data that ceases to be relevant if delayed, such as real-time gaming data.
@mikael uses in his wrapper the first one which might not be perfectly suited for gaming, where you simply want no lag at all. But you can patch the wrapper so it sends in MCSessionSendDataUnreliable mode. just look out for the send data method mikael uses for mode a 0 value. Replace it with a 1 value should do. (https://developer.apple.com/documentation/multipeerconnectivity/mcsessionsenddatamode/1407029-unreliable)
in mikaels multipeer.py file, find the following line and change the 0 to 1
self.session.sendData_toPeers_withMode_error_(json.dumps(message).encode(), peers, 0, None)
@mithrendal great thanks a lot. Hopefully decreases the lag :)
This may be off topic , but is your name inspired by Gandalf's mithrandir in the hobbit/ lord of the rings?
@Drizzel I tried my very best to hide my real name but you now uncovered it. Yes I am the son of an uncle of a cousin of gandalf the white! :-)
PS: hope that they don't throw us out of this forum now. Sorry for the off topic ness nature of this post to anyone who's disturbed by it. :-)
event and rpc based realtime comms