Skip to content
Alex McBride edited this page Sep 24, 2023 · 5 revisions

Pyinsim Tutorial

Here are several examples of using the library.

InSim

The simplest pyinsim program. We initialize InSim and send the message 'Hello, InSim!' to the game chat.

# Import the pyinsim module.
import pyinsim

# Initialize InSim on the specified host and port.
insim = pyinsim.insim('127.0.0.1', 29999, Admin='')

# Send message 'Hello, InSim!' to the host.
insim.sendm('Hello, InSim!')

# Run the pyinsim system.
pyinsim.run()

Note that we are calling sendm(msg) to send the message, this is a convenience method that pyinsim provides. We could also have written this code in a slightly more verbose way.

import pyinsim

insim = pyinsim.insim('127.0.0.1', 29999, Admin='')

# Create new MST message packet with the Msg 'Hello, InSim!'
mst = pyinsim.IS_MST(Msg='Hello, InSim!')

# Send the packet to InSim.
insim.sendp(mst)

pyinsim.run()

We create a packet object which we then send to InSim. This also demonstrates that packets in pyinsim are just normal Python objects, there is nothing special about them. As this pattern of sending packets is so common, pyinsim contains another convenience method for doing so.

import pyinsim

insim = pyinsim.insim('127.0.0.1', 29999, Admin='')

# Send message packet to InSim.
insim.send(pyinsim.ISP_MST, Msg='Hello, InSim!')

pyinsim.run()

Events

We have seen how to send simple packets, but what about receiving them? pyinsim uses a simple event system for handling incoming packets.

import pyinsim

# Function to handle MSO packet event.
def message_out(insim, mso):
     # Print the MSO message to the stdout.
    print mso.Msg

insim = pyinsim.insim('127.0.0.1', 29999, Admin='')

# Bind event for MSO packet.
insim.bind(pyinsim.ISP_MSO, message_out)

pyinsim.run()

Each time a MSO packet is received the event will be raised. The first event parameter is a reference to the object that raised the event, the second parameter is the packet object itself. There are also several other high-level events which pyinsim can raise, these are:

  • EVT_INIT - InSim is initialized
  • EVT_CLOSE - InSim has closed
  • EVT_ERROR - An error has occurred
  • EVT_ALL - Special event to bind all packets
  • EVT_OUTSIM - Bind an OutSim packet
  • EVT_OUTGAUGE - Bind an OutGauge packet
  • EVT_TIMEOUT - A UDP connection with LFS has timed out Here is an example of using these events.
import pyinsim

# Function called for INIT event.
def init(insim):
    print 'InSim is initialized!'

# Function called for CLOSE event.
def closed(insim):
    print 'InSim has closed!'

insim = pyinsim.insim('127.0.0.1', 29999, Admin='')

# Bind events
insim.bind(pyinsim.EVT_INIT, init)
insim.bind(pyinsim.EVT_CLOSE, closed)

pyinsim.run()

InSim Relay

pyinsim has full InSim Relay support, which allows you to connect to the LFS Relay Server and request data about any online hosts.

import pyinsim

def new_connection(relay, ncn):
    # Print out connection name.
    print 'Connection:', ncn.UName

# Initialize InSim relay and select the specified host.
relay = pyinsim.relay(HName='My Host Name')

# Bind events.
relay.bind(pyinsim.ISP_NCN, new_connection)

# Request connection list from host.
relay.send(pyinsim.ISP_TINY, ReqI=255, SubT=pyinsim.TINY_NCN)

# Run pyinsim.
pyinsim.run()

OutSim and OutGauge

pyinsim makes it easy to deal with OutSim or OutGauge packets by requiring very little code. While InSim uses TCP to handle its connection, OutSim and OutGauge instead use UDP. This means that they are stateless and you must define a timeout period. The timeout is the number of seconds that pyinsim will wait after a packet has been received before timing out.

Before you can use OutSim or OutGauge you must initialize their respective systems within LFS. The various settings can be set in the LFS\cfg.txt file, where you will see sections resembling the following:

OutSim Mode 0        : 0-off 1-driving 2-driving+replay
OutSim Delay 1       : minimum delay between packets (100ths of a sec)
OutSim IP 0.0.0.0    : IP address to send the UDP packet
OutSim Port 0        : IP port
OutSim ID 0          : if not zero, adds an identifier to the packet
OutGauge Mode 0        : 0-off 1-driving 2-driving+replay
OutGauge Delay 1       : minimum delay between packets (100ths of a sec)
OutGauge IP 0.0.0.0    : IP address to send the UDP packet
OutGauge Port 0        : IP port
OutGauge ID 0          : if not zero, adds an identifier to the packet

An important note to remember is that both OutSim and OutGauge only work if you are using cockpit view in the game. When viewing a car from an external view no packets are sent.

OutSim Example

In the example we initialize OutSim and use Pythons build-in vars() function to dump the content of each packet to the standard output.

import pyinsim

# Function to handle OutInSim packets
def outsim_handler(outsim, packet):
    print vars(packet)

# Initialize OutSim. Set timeout to 30 seconds.
pyinsim.outsim('127.0.0.1', 30000, outinsim_handler, 30.0)

pyinsim.run()

OutGauge Example

Using OutGauge is almost identical.

import pyinsim

# Function to handle OutGauge packet
def outgauge_handler(outgauge, packet):
    print vars(packet)

# Initialize OutGauge. Set timeout to 30 seconds.
pyinsim.outgauge('127.0.0.1', 30000, outgauge_handler, 30.0)

pyinsim.run()

Using OutSim and OutGauge with InSim.

It is possible to receive OutSim and OutGauge packets while using InSim by specifying a separate UDP port when initializing the InSim connection. This example shows you how to enable OutGauge packets by sending a SMALL_SSG packet to InSim.

import pyinsim

def outgauge_handler(insim, og):
    print vars(og)
    
# Initialize InSim with UDP port of 30000
insim = pyinsim.insim('127.0.0.1', 29999, UDPPort=30000, Admin='password')

# Bind OutGauge event.
insim.bind(pyinsim.EVT_OUTGAUGE, outgauge_handler)

# Request OutGauge packets to be sent with a delay of 100 milliseconds between updates (10 per second)
insim.send(pyinsim.ISP_SMALL, ReqI=255, SubT=pyinsim.SMALL_SSG, UVal=100)

pyinsim.run()