Vehicle Lua Reference

Discussion in 'Programming' started by PriusRepellent, May 5, 2019.

  1. PriusRepellent

    PriusRepellent
    Expand Collapse

    Joined:
    Mar 19, 2018
    Messages:
    353
    This is a work in progress thread for documenting how to access various parts of the Vehicle Lua API. Usage of this has been tested in BeamNG.Drive version 0.16 (the latest at the time of this thread's creation).

    I will make the formatting better when I get a chance to.

    Global Tables:
    Code:
    bdebug
    beamstats
    energyStorage
    socket
    drivetrain
    wheel
    beam
    jit
    bit
    powertrain
    color
    settings
    loadingTimes
    core_quickAccess
    ai
    controller
    Light
    Quaternion
    streams
    fire
    IProp
    debug
    thrusters
    backwardsCompatibility
    guihooks
    beamstate
    particlefilter
    partmgmt
    groundModel
    json
    recovery
    display
    collisionData
    sounds
    custom_inputs
    IBody
    particles
    wheelData
    wheels
    HighPerfTimer
    table
    path
    advancedwheeldebug
    cruiseControl
    scenario
    ffi
    midpointT
    motionSim
    mapmgr
    IFlexMesh
    gui
    hydros
    bullettime
    sensors
    electrics
    v
    input
    io
    _G
    float3
    extensions
    os
    debugdrawer
    string
    material
    mime
    props
    Vector3
    damageTracker
    Settings
    coroutine
    node_dynamic_property
    BeamObject
    dbg
    playerInfo
    package
    commands
    math
    

    Global Functions:
    Code:
    stringToVec3
    arrayFindValueIndex
    graphicsStep
    rawget
    beamDeformed
    arrayConcat
    ipairs
    setControllingPlayers
    print
    requestCameraConfig
    tableToFloat3Default
    createCurve
    quatFromEuler
    tableReadOnly
    dumps
    tableIsDict
    bytes_to_string
    load
    tableToColor
    saveCompiledJBeamRecursive
    tableMerge
    round
    tableKeys
    getContrastColorF
    isnan
    setCameraConfig
    sign2
    vehicleDestroy
    detectGlobalWrites
    tableSizeC
    couplerDetached
    isnaninf
    addNode
    vec3toString
    log_jbeam
    processResponseCurve
    tonumber
    vehicleResetted
    vec3
    rawset
    tableFindKey
    unserialize
    dump
    jsonDecode
    isinf
    smoothstep
    getContrastColorStringRGBA
    beamBroken
    split
    newTemporalSmoothing
    executeLuaSandboxed
    jsonEncode
    setfenv
    addHubWheelTSV
    dumpz
    formatTimeStringNow
    saveCompiledJBeam
    rerequire
    require
    debugDraw
    exportPersistentData
    rainbowColor
    tostring
    couplerAttached
    join
    newExponentialSmoothing
    serializePackages
    pcall
    clamp
    tableContains
    dumpsz
    stringHash
    addPressureWheel
    trim
    axisSystemApply
    sign
    torsionbarBroken
    nop
    tableIsEmpty
    init
    xpcall
    getTime
    getContrastColor
    loadstring
    fsign
    catmullRomQuat
    unrequire
    float3ToTable
    graphs
    onSettingsChanged
    smoothmin
    smootherstep
    readFile
    type
    select
    ipairs_safe
    unpack
    startDebugger
    newTemporalSpring
    addRotator
    float3_2_Vector3
    lerp
    PSItoPascal
    createCurveArray
    sendUITextureData
    quatFromDir
    readDictJSONTable
    tableSize
    addMonoHubWheel
    addWheel
    closestLinePoints
    module
    addBeam
    addBeamWithOptions
    addNodeWithOptions
    increaseMax
    newExtensionProxy
    tableMergeRecursive
    importPersistentData
    shallowcopy
    axisSystemCreate
    rpad
    smootheststep
    newTemporalSmoothingNonLinear
    require_optional
    jsonReadFile
    square
    quat
    initSystems
    getfenv
    linePointFromXnorm
    next
    tableFromHeaderTable
    pairs
    addHubWheel
    loadfile
    lookAt
    rawequal
    dumpToFile
    guardZero
    const
    physicsStep
    tableValuesAsLookupDict
    newproxy
    lpad
    tableContainsCaseInsensitive
    nodeCollision
    jsonEncodePretty
    debugPoll
    getContrastColorStringRGB
    writeFile
    tableToFloat3
    ui_message
    deserializePackages
    loadIni
    saveIni
    serialize
    timeprobe
    error
    parseColor
    newValueSampler
    dofile
    newLinearSmoothing
    gcprobe
    addHubWheelTSI
    jsonWriteFile
    newTemporalSigmoidSmoothing
    assert
    tableDepth
    couplerFound
    collectgarbage
    setmetatable
    pairs_safe
    catmullRom
    deepcopy
    getmetatable
    log
    gcinfo
    

    Powertrain reference:
    Code:
    powertrain.getDevices() -- Gets a table of powertrain devices.
    powertrain.getDevice(name) -- Gets a powertrain device by its name (name is a string).
    Code:
    powertrain.getDevices().mainEngine -- Gets the engine table for typical vehicles. This does not work for the eSBR.
    powertrain.getDevice("mainEngine") -- Also gets the engine table for typical vehicles. This might be a better way to access it.
    powertrain.getDevice("mainEngine").dyanmicFriction -- Variable for dynamic friction.
    powertrain.getDevice("mainEngine").friction -- Variable for friction.
    powertrain.getDevice("mainEngine").engineBrakeTorque -- Variable controlling engine braking.
    powertrain.getDevice("mainEngine"):scaleOutputTorque(number) -- multiplies output torque by number.
    powertrain.getDevice("mainEngine"):scaleFriction(number) -- multiplies friction by number
    powertrain.getDevice("mainEngine"):enable() -- enables the engine
    powertrain.getDevice("mainEngine"):disable() -- disables the engine
    WIP
    WIP

    Engine thermals:
    Code:
    powertrain.getDevice("mainEngine").thermals -- Table of thermal related variables and functions.`
    powertrain.getDevice("mainEngine").thermals:reset() -- Reset engine temps.
    powertrain.getDevice("mainEngine").thermals.oilTemperature -- Variable for oil temp.
    powertrain.getDevice("mainEngine").thermals.coolantTemperature -- Variable for coolant temp.
    powertrain.getDevice("mainEngine").thermals.engineBlockTemperature -- Variable for engine block temp.

    Powertrain table dump:
    https://gist.github.com/ChargedCreeper/414aacb8e2785c7d981e130590d4f905
     
    #1 PriusRepellent, May 5, 2019
    Last edited: May 22, 2019
    • Like Like x 10
    • Informative Informative x 2
  2. RobertGracie

    RobertGracie
    Expand Collapse

    Joined:
    Oct 15, 2013
    Messages:
    3,779
    You may want to embolden "Engine Thermals:" but thanks for this thread it should be very useful in the future :)
     
  3. PriusRepellent

    PriusRepellent
    Expand Collapse

    Joined:
    Mar 19, 2018
    Messages:
    353
    It is nowhere near finished. I still have a lot of other functions and tables to document the purpose of. Some I will probably need help to figure out later on too.
     
    • Like Like x 2
  4. fufsgfen

    fufsgfen
    Expand Collapse

    Joined:
    Jan 10, 2017
    Messages:
    6,782
    I think this is very important and valuable project, your time and effort put to this is appreciated very much :)
     
    • Agree Agree x 3
  5. PriusRepellent

    PriusRepellent
    Expand Collapse

    Joined:
    Mar 19, 2018
    Messages:
    353
    Just an update. I have added a raw data dump of the Powertrain table. While it is complete on what there is to access, it may be difficult to find anything useful as quickly. I used Lua to dump the data, so errors or typos are extremely unlikely.

    Using Github gists is becoming needed due to the sheer amount of data. Neither this forum or Pastebin are good for posts approaching or exceeding a full megabyte of text. Gists handles it very well though.
     
    #5 PriusRepellent, May 13, 2019
    Last edited: May 13, 2019
    • Like Like x 1
  6. Arcanox

    Arcanox
    Expand Collapse

    Joined:
    Aug 22, 2018
    Messages:
    290
    You can look in the game's install folder (in Steam's steamapps\common folder, or wherever the non-Steam version installs to) for the Lua source code, which has all the function definitions for everything that powers the game. Visual Studio Code comes in extremely handy for Lua browsing, as it has a very nice third-party Lua extension. You can open the "lua" folder of the game as a workspace and browse through all the files to discover how all the components (powertrain, controllers, etc) fit together.

    There used to be a "lua-doc" folder with HTML documentation on all the Lua code, but it's empty for me now...the source code is fairly easy to navigate though.
     
    • Informative Informative x 1
  7. fufsgfen

    fufsgfen
    Expand Collapse

    Joined:
    Jan 10, 2017
    Messages:
    6,782
    This is valid for 0.16.0.2 game version.

    To get roll of vehicle, you can use obj:getRollPitchYaw()

    So if you have three variables, myRoll, myPitch and myYaw, you can get all three from that single object by doing this:
    myRoll, myPitch, myYaw = obj:getRollPitchYaw()

    To get degrees you need to do this:
    myRoll = Math.Asin(myRoll) * (180 / Math.PI); //C#
    myRoll = Math.asin(myRoll) * (180 / Math.PI) //Lua

    For heading (compass etc) in degrees you need to do this:
    myYaw = (myYaw * 180 / Math.PI + 180); //C#
    myYaw = (myYaw * 180 / Math.PI + 180) //Lua

    G-forces you can get by these:
    gForceY = sensors.gy / 9.81
    gForceX = sensors.gx / 9.81
    gForceZ = sensors.gz / 9.81

    That gives how many G's there is, don't divide by 9.81 if you want just forces game sensors will output.



    Do dump(sensors) and dump(electrics) in console vehicle lua selected to see all possible sensors.


    I have been modifying outsim.lua now and found those from several of ui apps and other lua files, some vehicle lua files etc. it is like finding hidden keys all over the room, there is still few I need to find to get outsim to work, but bit by bit it is getting closer. Then I try to look outgauge and see if I can get unfinished parts of that done too.

    This is really nice with C# and visual studio in figuring out things with outsim and outgauge and as it may be useful for someone else in future, I put link here too:
    https://github.com/alexmcbride/insimdotnet/

    Edit: Fixed errors with my math by math of developers :p
     
    #7 fufsgfen, May 20, 2019
    Last edited: May 20, 2019
    • Informative Informative x 2
  8. fufsgfen

    fufsgfen
    Expand Collapse

    Joined:
    Jan 10, 2017
    Messages:
    6,782
    Also one note, guistreams.lua was great place to find ways to get more data accessed.

    For example obj:getPositionXYZ() I found there, it works like this, you need three variables which you place data from that object:
    myPosX, myPosY, myPosZ = obj:getPositionXYZ() //Lua

    Now as I am playing with outsim here, some data types might be bit different actually in straight lua, for outsim for example position data is integers, which I need to scratch my head a bit to get more sensible data out from them, I might need to multiply and then divide in my program to get all decimals imported too.

    So be wary that some of above might be outsim specific in terms of data types and in lua you might need different math to get some values to be what you need them to be.

    Update: with Outsim issue was when I wanted to read values directly to o.posX etc. using additional variable and then multiplying that before putting value to o.posX did give me 1000 times of value I needed as integer which I then could divide by 1000 and got nice number with fractions.

    For outsim.lua I got this and I surely hope that there is better way to do this:
    local positionX
    local positionY
    local positionZ
    positionX, positionY, positionZ = obj:getPositionXYZ()
    o.posX = positionX * 1000
    o.posY = positionY * 1000
    o.posZ = positionZ * 1000

    However I got coordinate for X show up fine on my program with insane update rate of how much packets outsim is sending, but it is fast at least, yeah my hacks might need few iterations, anyway thought that might be useful for someone visiting this thread.
     
    #8 fufsgfen, May 20, 2019
    Last edited: May 20, 2019
  9. NOCARGO

    NOCARGO
    Expand Collapse

    Joined:
    Apr 1, 2019
    Messages:
    1,514
    Oh yes this is all quite complex but once I'm 'in the zone' I can make most out of this. Very useful info, thx for sharing :)

    btw The value that we get from the G sensors is actually the value that is contained within the
    real life accelerometers. This division by 9.81 has to do something with Earth's gravity.
    I found out when I made my own accelerometer in BeamNG, I was checking the values
    by visiting Wikipedia on accelerometer ( G-meter, wich is the same) and there it is explained.
     
    #9 NOCARGO, May 22, 2019
    Last edited: May 22, 2019
  10. tdev

    tdev
    Expand Collapse
    Developer
    BeamNG Team

    Joined:
    Aug 3, 2012
    Messages:
    3,030
    Oh, nice :)

    We are working on an actual documentation, but it is not finished yet, wanne work with us on that?

    Write me a pm ;)
     
    • Like Like x 1
  11. Tsutarja495

    Tsutarja495
    Expand Collapse

    Joined:
    Mar 16, 2014
    Messages:
    819
    I'll contribute a little:
    Code:
    electrics.values.wheelspeed - Vehicle wheelspeed, average speed of all wheels. Measured in meters per second.
    electrics.values.airspeed - Vehicle speed through the air, more accurate speed measurement but not usually used by cars. Measured in meters per second.
    electrics.values.gearIndex - Manual gear index. Reverse gears have negative values, neutral has a value of 0.
    electrics.values.gear_A - Automatic gear index. Varies by automatic type.  x/y, with x being the "position" of the current gear in the list of available automatic modes, and y being the total amount of automatic modes.
    electrics.values.gear - Current gear in string form, usually sent to UI apps such as Tacho2 or ETK gauges
    electrics.values.steering - Steering amount. Full lock left = -1, full lock right = 1, neutral = 0.
    electrics.values.altitude - Height above ground level, measured in meters.
    electrics.values.esc - Is ESC active?
    electrics.values.tcs - Is TCS active?
    electrics.values.signal_L - Is left signal active and pulsed on?
    electrics.values.signal_R - Is right signal active and pulsed on?
    electrics.values.signal_left_input - Is left signal active, regardless of pulse?
    electrics.values.signal_right_input - is right signal active, regardless of pulse?
    electrics.values.horn - Is the horn active?
    electrics.values.checkengine - Is the engine dead?
    electrics.values.hazard - Are both signals active and pulsed on?
    electrics.values.hazard_enabled -  Are both signals active, regardless of pulse?
    electrics.values.reverse - Is gearIndex less than 0?
    electrics.values.parking - Currently unused, will be used for parking lights later
    electrics.values.rpm - Engine RPM
    electrics.values.rpmspin - Engine RPM for spinning props like pulleys
    electrics.values.rpmTacho - Smoothed engine RPM, less accurate, ideal for older or low quality analog tachometers
    Code:
    controller - Lua file that runs on vehicle spawn and allows to control vehicle parameters and send information to other controllers. Must be called from jbeam.
    controller.getController() - Calls a controller for use by other controllers.
    dt - Game's internal clock. Starts on vehicle reload. Measured in seconds. Must refer to dt within a controller's updateGFX function.
    updateGFX - Function that runs on every frame that is not paused. Every controller has one of these, although some of them do nothing.
    nop - Shorthand for "no operation". Does nothing. Used to cancel out functions and/or avoid potential errors.
    jbeamData - Allows controllers to retrieve data from a vehicle's jbeam.
    Code:
        "controller": [
            ["fileName"],
            ["beamNavigator",{"screenMaterialName": "@etk800_screen", "htmlFilePath": "local://local/vehicles/common/ETK_navi_screen.html", "name":"etk800_navi"}],
        ],
    
    "beamNavigator" - controller name
    things inside brackets - parameters to send to the controller
    Code:
        "etkGauges": { // controller name
            "unitType": "imperial", // parameters to pass on to the controller
        },
    Code:
    local function init(jbeamData)
      local hasESC = controller.getController("esc") ~= nil
      if not hasESC then
        M.updateGFX = nop //do nothing on every frame
      else
        transfercase = powertrain.getDevice("transfercase")
        if transfercase then
          initialSplitA = transfercase.diffTorqueSplitA
          initialSplitB = transfercase.diffTorqueSplitB
          initialViscousCoef = transfercase.viscousCoef
        else
          M.updateGFX = nop //do nothing on every frame
        end
      end
    end
    Code:
    powertrain.getDevice("transfercase") - Calls the transfer case, unless you named it something other than "transfercase".
    diffTorqueSplitA - Percentage of power going to side A. Usually the front wheels.
    diffTorqueSplitB - Percentage of power going to side B. Usually the rear wheels.
    More to be added.
     
    #11 Tsutarja495, May 22, 2019
    Last edited: May 22, 2019
    • Like Like x 6
  12. fufsgfen

    fufsgfen
    Expand Collapse

    Joined:
    Jan 10, 2017
    Messages:
    6,782
    Yes, in here it says that 1g is one gravity, that is 9.81 (or 9.8 in article) https://en.wikipedia.org/wiki/G-force

    Accelerometer sensor, like sensors in BeamNG tell how much 1 gravity is for example, which is ~9.81m/s^2

    Hence to know how many g's car pulls, I need to divide by 9.81.

    Gravity 'g', not grams, not SI unit, actually according to article it should be 9.80665 instead of 9.81 for accuracy.


    There is then gy2, gx2 and gz2 sensors, which I'm not sure what difference they have with gy, gx and gz sensors, haven't had chance to test them enough, it could be that 2 indicates improved sensor or something totally else, but 2 is one that many part of game uses, so might need to use that instead.
     
  13. NOCARGO

    NOCARGO
    Expand Collapse

    Joined:
    Apr 1, 2019
    Messages:
    1,514
    Yep, that's the article :)
    And yes that could be the very case about gy2, gx2 and gz2. They might be improved or alternate or even simplified formulas :)

    @Tsutarja495 Know those already except for one : didn't know 'nop' stands for 'no operation', so that's
    technically something like 'nil' I guess :) thx
     
    #13 NOCARGO, May 22, 2019
    Last edited: May 22, 2019
  14. PriusRepellent

    PriusRepellent
    Expand Collapse

    Joined:
    Mar 19, 2018
    Messages:
    353
    Just updated the thread with more info on global tables and functions.

    This doesn't "call" the transfer case, it returns it. The transfer case (and other parts) isn't represented as a function, but as a table in Lua.
     
    • Like Like x 1
    • Informative Informative x 1
  15. R4NKING

    R4NKING
    Expand Collapse

    Joined:
    Oct 14, 2016
    Messages:
    558
    Is there any Powertrain reference for turbos like to multiply the wastegate?
     
  1. This site uses cookies to help personalise content, tailor your experience and to keep you logged in if you register.
    By continuing to use this site, you are consenting to our use of cookies.
    Dismiss Notice