Vehicle
Vehicle is a CoreObject representing a vehicle that can be occupied and driven by a player. Vehicle also implements the Damageable interface.
Properties
Property Name | Return Type | Description | Tags |
---|---|---|---|
driver | Player | The Player currently driving the vehicle, or nil if there is no driver. | Read-Only |
enterTrigger | Trigger | Returns the Trigger a Player uses to occupy the vehicle. | Read-Only |
camera | Camera | Returns the Camera used for the driver while they occupy the vehicle. | Read-Only |
driverAnimationStance | string | Returns the animation stance that will be applied to the driver while they occupy the vehicle. | Read-Only |
mass | number | Returns the mass of the vehicle in kilograms. | Read-Write |
maxSpeed | number | The maximum speed of the vehicle in centimeters per second. | Read-Write |
accelerationRate | number | The approximate acceleration rate of the vehicle in centimeters per second squared. | Read-Write |
brakeStrength | number | The maximum deceleration of the vehicle when stopping. | Read-Write |
coastBrakeStrength | number | The deceleration of the vehicle while coasting (with no forward or backward input). | Read-Write |
tireFriction | number | The amount of friction tires or treads have on the ground. | Read-Write |
gravityScale | number | How much gravity affects this vehicle. Default value is 1.9. | Read-Write |
isAccelerating | boolean | Returns true if the vehicle is currently accelerating. | Read-Only |
isDriverHidden | boolean | Returns true if the driver is made invisible while occupying the vehicle. | Read-Only |
isDriverAttached | boolean | Returns true if the driver is attached to the vehicle while they occupy it. | Read-Only |
isBrakeEngaged | boolean | Returns true if the driver of the vehicle is currently using the brakes. | Read-Only |
isHandbrakeEngaged | boolean | Returns true if the driver of the vehicle is currently using the handbrake. | Read-Only |
hitPoints | number | Current amount of hit points. | Read-Write |
maxHitPoints | number | Maximum amount of hit points. | Read-Write |
isDead | boolean | True if the object is dead, otherwise false. Death occurs when damage is applied which reduces hit points to 0, or when the Die() function is called. | Read-Only |
isImmortal | boolean | When set to true , this object cannot die. | Read-Write |
isInvulnerable | boolean | When set to true , this object does not take damage. | Read-Write |
destroyOnDeath | boolean | When set to true , this object will automatically be destroyed when it dies. | Read-Only |
destroyOnDeathDelay | number | Delay in seconds after death before this object is destroyed, if destroyOnDeath is set to true . Defaults to 0. | Read-Only |
destroyOnDeathClientTemplateId | string | Optional asset ID of a template to be spawned on clients when this object is automatically destroyed on death. | Read-Only |
destroyOnDeathNetworkedTemplateId | string | Optional asset ID of a networked template to be spawned on the server when this object is automatically destroyed on death. | Read-Only |
canExit | boolean | Returns true if the driver of the vehicle is allowed to exit using the Vehicle Exit binding. | Read-Only |
Functions
Function Name | Return Type | Description | Tags |
---|---|---|---|
SetDriver(Player) | None | Sets the given player as the new driver of the vehicle. A nil value will remove the current driver. | None |
RemoveDriver() | None | Removes the current driver from the vehicle. | None |
AddImpulse(Vector3) | None | Adds an impulse force to the vehicle. | None |
GetPhysicsBodyOffset() | Vector3 | Returns the positional offset for the body collision of the vehicle. | None |
GetPhysicsBodyScale() | Vector3 | Returns the scale offset for the body collision of the vehicle. | None |
GetDriverPosition() | Vector3 | Returns the position relative to the vehicle at which the driver is attached while occupying the vehicle. | None |
GetDriverRotation() | Rotation | Returns the rotation with which the driver is attached while occupying the vehicle. | None |
GetCenterOfMassOffset() | Vector3 | Returns the center of mass offset for this vehicle. | None |
SetCenterOfMassOffset(Vector3 offset) | None | Sets the center of mass offset for this vehicle. This resets the vehicle state and may not behave nicely if called repeatedly or while in motion. | None |
ApplyDamage(Damage) | None | Damages the vehicle, unless it is invulnerable. If its hit points reach 0 and it is not immortal, it dies. | Server-Only |
Die([Damage]) | None | Kills the vehicle, unless it is immortal. The optional Damage parameter is a way to communicate cause of death. | Server-Only |
Events
Event Name | Return Type | Description | Tags |
---|---|---|---|
driverEnteredEvent | Event <Vehicle vehicle, Player player> | Fired when a new driver occupies the vehicle. | None |
driverExitedEvent | Event <Vehicle vehicle, Player player> | Fired when a driver exits the vehicle. | None |
damagedEvent | Event <Vehicle vehicle, Damage damage> | Fired when the vehicle takes damage. | Server-Only |
diedEvent | Event <Vehicle vehicle, Damage damage> | Fired when the vehicle dies. | Server-Only |
hitPointsChangedEvent | Event <Vehicle vehicle, number previousHitPoints> | Fired when there's a change in hit points on the vehicle. | Server-Only |
Hooks
Hook Name | Return Type | Description | Tags |
---|---|---|---|
clientMovementHook | Hook <Vehicle vehicle, table parameters> | Hook called when processing the driver's input. The parameters table contains "throttleInput", "steeringInput", and "isHandbrakeEngaged". This is only called on the driver's client. "throttleInput" is a number -1.0, to 1.0, with positive values indicating forward input. "steeringInput" is the same, and positive values indicate turning to the right. "isHandbrakeEngaged" is a boolean. | Client-Only |
serverMovementHook | Hook <Vehicle vehicle, table parameters> | Hook called when on the server for a vehicle with no driver. This has the same parameters as clientMovementHook. | Server-Only |
damageHook | Hook <Vehicle vehicle, Damage damage> | Hook called when applying damage from a call to ApplyDamage() . The incoming damage may be modified or prevented by modifying properties on the damage parameter. | Server-Only |
Examples
Example using:
maxSpeed
tireFriction
accelerationRate
turnRadius
Off road sections are an excellent way to encourage players to stay on the track. In this example, when vehicle with a driver enters a trigger, they will be slowed down and given more traction. Once a vehicle exits the trigger, it will drive at its original speed. Note: Treaded Vehicles do not support turnRadius
.
-- Get the trigger object that will represent the off road area
local propTrigger = script:GetCustomProperty("Trigger"):WaitForObject()
-- This function will be called whenever an object enters the trigger
function OnEnter(trigger, other)
-- Check if a vehicle has entered the trigger and if that vehicle is currently not off road
if(other:IsA("Vehicle") and not other.serverUserData.offRoad) then
-- Set the off road status of the vehicle to "true"
other.serverUserData.offRoad = true
-- Store the original specifications of the vehicle. The "serverUserData" properties
-- are used in the case that other road obstacles are modifying the specifications of the vehicle
other.serverUserData.originalTireFriction = other.serverUserData.originalTireFriction or other.tireFriction
other.serverUserData.originalMaxSpeed = other.serverUserData.originalMaxSpeed or other.maxSpeed
other.serverUserData.originalAccelerationRate = other.serverUserData.originalAccelerationRate or other.accelerationRate
-- turnRadius only supported for FourWheeledVehicle type.
if other:IsA("FourWheeledVehicle") then
other.serverUserData.originalTurnRadius = other.serverUserData.originalTurnRadius or other.turnRadius
end
-- Increase the tire friction of the vehicle by 900%, this will give the vehicle more traction
other.tireFriction = other.tireFriction * 10.0
-- Decrease the maximum speed of the vehicle by 90%
other.maxSpeed = other.maxSpeed * 0.1
-- Decrease the acceleration of the vehicle by 80%
other.accelerationRate = other.accelerationRate * 0.2
-- Shrink the turn radius by 80%, this will allow the vehicle to make tighter turns
-- turnRadius only supported for FourWheeledVehicle type.
if other:IsA("FourWheeledVehicle") then
other.turnRadius = other.tireFriction * 0.2
end
end
end
-- Bind the "OnEnter" function to the "beginOverlapEvent" of the "propTrigger" so that
-- when an object enters the "propTrigger" the "OnEnter" function is executed
propTrigger.beginOverlapEvent:Connect(OnEnter)
-- This function will be called whenever an object enters the trigger
function OnExit(trigger, other)
-- If a vehicle has entered the trigger and the vehicle is off road, then reset
-- the vehicle specifications (maximum speed, acceleration, turning radius)
if(other:IsA("Vehicle") and Object.IsValid(other.driver) and other.serverUserData.offRoad) then
-- Set the off road status of the vehicle to "false"
other.serverUserData.offRoad = false
-- Reset the vehicle specifications to the values before the vehicle
-- had entered the boost pad
other.maxSpeed = other.serverUserData.originalMaxSpeed
-- turnRadius only supported for FourWheeledVehicle type.
if other:IsA("FourWheeledVehicle") then
other.turnRadius = other.serverUserData.originalTurnRadius
end
other.accelerationRate = other.serverUserData.originalAccelerationRate
end
end
-- Bind the "OnExit" function to the "endOverlapEvent" of the "propTrigger" so that
-- when an object exits the "propTrigger" the "OnExit" function is executed
propTrigger.endOverlapEvent:Connect(OnExit)
See also: event:Trigger.beginOverlapEvent | CoreObject.serverUserData
Example using:
tireFriction
maxSpeed
driver
In this example, entering the trigger will act like an oil slick. Any vehicles that enter the trigger will spin out of control.
-- Get the trigger that will represent the oil slick area
local propTrigger = script:GetCustomProperty("Trigger"):WaitForObject()
-- This function will be called whenever an object enters the trigger
function OnEnter(trigger, other)
-- Check if the object entering is a vehicle and if the vehicle is currently not in an oil slick
if(other:IsA("Vehicle") and not other.serverUserData.inOil) then
-- Set the oil slick status of the vehicle to "true" so that any more oil slicks that the vehicle passes
-- over do not affect the vehicle.
other.serverUserData.inOil = true
-- Store the original max speed of the vehicle
local originalMaxSpeed = other.serverUserData.originalMaxSpeed or other.maxSpeed
-- Store the original tire friction of the vehicle
local originalTireFriction = other.serverUserData.originalTireFriction or other.tireFriction
-- Set the maximum speed of the vehicle to 0 to stop it from moving
other.maxSpeed = 1000
-- Set the tire friction of the wheels to 0 so that the car can easily spin
other.tireFriction = 0.5
-- Make the vehicle spin for 2 seconds
other:SetLocalAngularVelocity(Vector3.New(0, 0, 999))
Task.Wait(2)
-- Reset the specifications of the vehicle to the values before the vehicle entered the oil slick
other.maxSpeed = originalMaxSpeed
-- Resetting the "tireFriction" will cause the vehicle to stop spinning
other.tireFriction = originalTireFriction
-- Reset the in oil status of the vehicle so that the vehicle can be affected by another oil slick.
other.serverUserData.inOil = false
end
end
-- Bind the "OnEnter" function to the "beginOverlapEvent" of the "propTrigger" so that
-- when an object enters the "propTrigger" the "OnEnter" function is executed
propTrigger.beginOverlapEvent:Connect(OnEnter)
See also: CoreObject.SetLocalAngularVelocity | event:Trigger.beginOverlapEvent
Example using:
damagedEvent
diedEvent
driver
Vehicles implement the DamageableObject interface. As such, they have all the properties and events from that type. In this example, we add a script to a vehicle that causes it to pass to the driver some of the damage it receives. By default, a vehicle's damageable properties are configured to make them immune-- Change them for this example to work.
local VEHICLE = script:FindAncestorByType("Vehicle")
local CHANCE_TO_PASS_DAMAGE = 0.5
local DAMAGE_REDUCTION = 0.2
local ON_DEATH_DIRECT_DAMAGE_TO_DRIVER = 75
function ApplyDamageToDriver(newAmount, vehicleDamage)
-- Create new damage object for the player
local damage = Damage.New(newAmount)
-- Copy properties from the vehicle's damage object
damage.reason = vehicleDamage.reason
damage.sourceAbility = vehicleDamage.sourceAbility
damage.sourcePlayer = vehicleDamage.sourcePlayer
damage:SetHitResult(vehicleDamage:GetHitResult())
local player = VEHICLE.driver
-- If we think the player will die from this damage, eject them and
-- wait a bit, so they will ragdoll correctly
if player.hitPoints <= damage.amount then
VEHICLE:RemoveDriver()
Task.Wait(0.15)
end
-- Apply it
player:ApplyDamage(damage)
end
function OnDamaged(_, damage)
if damage.amount <= 0 then return end
if not Object.IsValid(VEHICLE.driver) then return end
-- Chance to apply damage to the player or prevent it completely
if math.random() >= CHANCE_TO_PASS_DAMAGE then return end
-- Reduction of the original damage amount
local newAmount = damage.amount * (1 - DAMAGE_REDUCTION)
newAmount = math.ceil(newAmount)
-- Apply reduced damage
ApplyDamageToDriver(newAmount, damage)
end
function OnDied(_, damage)
if not Object.IsValid(VEHICLE.driver) then return end
local player = VEHICLE.driver
-- Apply the on-death damage
ApplyDamageToDriver(ON_DEATH_DIRECT_DAMAGE_TO_DRIVER, damage)
end
VEHICLE.damagedEvent:Connect(OnDamaged)
VEHICLE.diedEvent:Connect(OnDied)
See also: DamageableObject.damagedEvent | CoreObject.FindAncestorByType | Damage.New | Player.ApplyDamage | Object.IsValid
Example using:
driverEnteredEvent
driverExitedEvent
A common situation could be a game that has both weapons and vehicles. In this example, when a player enters the vehicle all their abilities are disabled. When they exit the vehicle their abilities are re-enabled. This script expects to be placed as a child of the vehicle.
local VEHICLE = script.parent
function OnDriverEntered(vehicle, player)
for _,ability in ipairs(player:GetAbilities()) do
ability.isEnabled = false
end
end
function OnDriverExited(vehicle, player)
for _,ability in ipairs(player:GetAbilities()) do
ability.isEnabled = true
end
end
VEHICLE.driverEnteredEvent:Connect(OnDriverEntered)
VEHICLE.driverExitedEvent:Connect(OnDriverExited)
See also: CoreObject.parent | Player.GetAbilities | Ability.isEnabled
Example using:
driverEnteredEvent
driverExitedEvent
accelerationRate
maxSpeed
tireFriction
In this example, when the driver of the vehicle presses the spacebar, the vehicle launches up and forward a slight amount in the direction the vehicle is facing.
The Jump action in the Binding Set will need to be networked for the script to detect input on the server.
local VEHICLE = script:FindAncestorByType("Vehicle")
local actionPressedListener = nil
function OnActionPressed(player, action)
if action == "Jump" then
-- Vector3 (forward, 0, up) rotated into the world space of the vehicle
local impulseVector = VEHICLE:GetWorldRotation() * Vector3.New(1000, 0, 1000)
VEHICLE:AddImpulse(impulseVector * VEHICLE.mass)
end
end
function OnDriverEntered(vehicle, player)
actionPressedListener = Input.actionPressedEvent:Connect(OnActionPressed)
end
function OnDriverExited(vehicle, player)
if actionPressedListener and actionPressedListener.isConnected then
actionPressedListener:Disconnect()
end
end
VEHICLE.driverEnteredEvent:Connect(OnDriverEntered)
VEHICLE.driverExitedEvent:Connect(OnDriverExited)
See also: CoreObject.AddImpulse | Input.actionPressedEvent | EventListener.Disconnect | Vector3.New
Example using:
driverExitedEvent
In this example, players take damage when they exit a vehicle that is in motion. The amount of damage taken is variable, depending on how fast the vehicle is going. This script expects to be placed as a child of the vehicle.
local VEHICLE = script.parent
local MAX_SAFE_SPEED = 400
local LETHAL_SPEED = 4000
function OnDriverExited(vehicle, player)
if MAX_SAFE_SPEED >= LETHAL_SPEED then return end
local speed = vehicle:GetVelocity().size
print("Exit speed = " .. speed)
if not player.isDead and speed > MAX_SAFE_SPEED then
local t = (speed - MAX_SAFE_SPEED) / (LETHAL_SPEED - MAX_SAFE_SPEED)
local amount = CoreMath.Lerp(0, player.maxHitPoints, t)
if amount > 0 then
local damage = Damage.New(amount)
damage.reason = DamageReason.MAP
player:ApplyDamage(damage)
end
end
end
VEHICLE.driverExitedEvent:Connect(OnDriverExited)
See also: CoreObject.GetVelocity | Vector3.size | Player.isDead | CoreMath.Lerp | Damage.New
Example using:
serverMovementHook
This script leverages the movement hook to implement a crude AI that autopilots a vehicle. It avoids obstacles and if it gets stuck, it backs up. It expects to be added as a server script under the vehicle's hierarchy. The script's position inside the vehicle is important, it should be at the front bumper, almost touching the vehicle, and its X-axis should point forward, in the direction the vehicle moves.
local VEHICLE = script:FindAncestorByType("Vehicle")
if not VEHICLE then return end
local reverseClock = 0
local forwardClock = 0
local deltaTime = 0
local averageSpeed = 100
function OnMovementHook(vehicle, params)
-- Disable the handbrake
params.isHandbrakeEngaged = false
-- Pre-process information about the script's position and rotation
local pos = script:GetWorldPosition()
local qRotation = Quaternion.New(script:GetWorldRotation())
local forwardV = qRotation:GetForwardVector()
local rightV = qRotation:GetRightVector() * 120
local speed = VEHICLE:GetVelocity().size
averageSpeed = CoreMath.Lerp(averageSpeed, speed, 0.1)
speed = math.max(speed * 1.2, 120)
local velocity = forwardV * speed
-- Cast 3 rays forward to see if they hit something. The decisions to
-- steer and accelerate are based on the results of these:
local centerHit = World.Raycast(pos, pos + velocity)
local leftHit = World.Raycast(pos - rightV, pos - rightV + velocity)
local rightHit = World.Raycast(pos + rightV, pos + rightV + velocity)
-- Reverse logic in case the vehicle gets stuck
if forwardClock > 0 then
forwardClock = forwardClock - deltaTime
params.throttleInput = 1 -- Press the gas
elseif reverseClock <= 0 and averageSpeed < 30 then
-- Randomize the reverse duration in case multiple cars get stuck on each other
reverseClock = 1 + math.random()
end
if reverseClock > 0 then
reverseClock = reverseClock - deltaTime
params.throttleInput = -1 -- Go in reverse
if reverseClock <= 0 then
forwardClock = 1
end
elseif centerHit then
params.throttleInput = 0 -- Let go of gas
else
params.throttleInput = 1 -- Press the gas
end
-- Steer left/right
if reverseClock > 0 then
params.steeringInput = 1 -- Right (reverse)
elseif rightHit then
params.steeringInput = -1 -- Left
elseif leftHit then
params.steeringInput = 1 -- Right
else
params.steeringInput = 0 -- Don't steer
end
end
function Tick(dt)
deltaTime = dt
end
VEHICLE.serverMovementHook:Connect(OnMovementHook)
See also: CoreObject.GetVelocity | World.Raycast | Quaternion.GetForwardVector | Vector3.size | CoreMath.Lerp
Example using:
AddImpulse
maxSpeed
serverUserData
In this example, when a vehicle enters a trigger, the vehicle will be launched forward for 0.5 seconds.
-- Get the trigger object that will represent the boost pad
local propTrigger = script:GetCustomProperty("Trigger"):WaitForObject()
-- This function will be called whenever an object enters the trigger
function OnEnter(trigger, other)
-- Check if a vehicle has entered the trigger
if(other:IsA("Vehicle")) then
-- Get a vector that represents the direction the boost pad is pointing in
local direction = trigger:GetWorldRotation() * Vector3.RIGHT
-- Apply a force to the vehicle to give the vehicle sudden increase in speed
other:AddImpulse(direction * 2000000)
-- Check if the maximum speed of the vehicle has already been increased
if(not other.serverUserData.isBoosting) then
other.serverUserData.isBoosting = true
-- Store the original maximum speed of the vehicle. The "originalMaxSpeed" property
-- is used in case any other road obstacles are modifying the "maxSpeed" of the vehicle
local originalMaxSpeed = other.serverUserData.originalMaxSpeed or other.maxSpeed
-- Increase the maximum speed of the vehicle by 300%`
other.maxSpeed = originalMaxSpeed * 4.0
-- Wait 0.5 seconds before returning the vehicle to its original speed
Task.Wait(0.5)
-- Return the vehicle to its original speed
other.maxSpeed = originalMaxSpeed
-- Set "isBoosting" to false so that the speed increase of boost pads can be activated
-- when the vehicle passes over another boost pad
other.serverUserData.isBoosting = false
end
end
end
-- Bind the "OnEnter" function to the "beginOverlapEvent" of the "propTrigger" so that
-- when an object enters the "propTrigger" the "OnEnter" function is executed
propTrigger.beginOverlapEvent:Connect(OnEnter)
See also: event:Trigger.beginOverlapEvent | Rotation * Vector3
Example using:
SetDriver
In this example, a vehicle is spawned for each player at the moment they join the game. Also, when they leave the game we destroy the vehicle. For best results, delete the Enter Trigger
that usually comes with vehicles and set the vehicle's Exit Binding
to None
.
local VEHICLE = script:GetCustomProperty("VehicleTemplate")
local playerVehicles = {}
function OnPlayerJoined(player)
local pos = player:GetWorldPosition()
local vehicleInstance = World.SpawnAsset(VEHICLE, {position = pos})
vehicleInstance:SetDriver(player)
playerVehicles[player] = vehicleInstance
end
function OnPlayerLeft(player)
local vehicle = playerVehicles[player]
if Object.IsValid(vehicle) then
vehicle:Destroy()
end
end
Game.playerJoinedEvent:Connect(OnPlayerJoined)
Game.playerLeftEvent:Connect(OnPlayerLeft)
See also: CoreObject.Destroy | Player.GetWorldPosition | World.SpawnAsset | Object.IsValid | Game.playerJoinedEvent
Example using:
SetDriver
driverExitedEvent
In some games it will be important to override the built-in trigger behavior to add more gameplay. In this example, the vehicle belongs to a specific player (Bot1). If another player tries to drive it they will receive a message saying the car doesn't belong to them. This script expects to be placed as a child of the vehicle.
local VEHICLE = script:FindAncestorByType("Vehicle")
local TRIGGER = script:GetCustomProperty("EnterTrigger"):WaitForObject()
local OWNER = "Bot1"
function OnInteracted(trigger, player)
if player.name == OWNER then
VEHICLE:SetDriver(player)
TRIGGER.isEnabled = false
else
Chat.BroadcastMessage("Not your car.", {players = player})
end
end
function OnDriverExited(player)
TRIGGER.isEnabled = true
end
TRIGGER.interactedEvent:Connect(OnInteracted)
VEHICLE.driverExitedEvent:Connect(OnDriverExited)
See also: CoreObject.FindAncestorByType | CoreObjectReference.WaitForObject | Player.name | Chat.BroadcastMessage | Trigger.interactedEvent
Example using:
accelerationRate
maxSpeed
tireFriction
This example takes vehicle stats (acceleration, max speed and tire friction) and normalizes them to rating values between 1 and 5. This could be used, for example, in the UI of a vehicle selection screen to show how vehicles compare to each other in their various stats. When the script runs it searches the game for all vehicles that exist and prints their ratings to the Event Log.
local ACCELE_MIN = 400
local ACCELE_MAX = 4000
local TOP_SPEED_MIN = 2000
local TOP_SPEED_MAX = 20000
local HANDLING_MIN = 0.5
local HANDLING_MAX = 10
local RATING_LEVELS = 5
function RateStat(value, min, max)
if value >= max then
return RATING_LEVELS
end
if value > min and max > min then
local p = (value - min) / (max - min)
local rating = p * RATING_LEVELS
rating = math.floor(rating) + 1
return rating
end
return 1
end
function RateVehicle(vehicle)
local accele = RateStat(vehicle.accelerationRate, ACCELE_MIN, ACCELE_MAX)
local topSpeed = RateStat(vehicle.maxSpeed, TOP_SPEED_MIN, TOP_SPEED_MAX)
local handling = RateStat(vehicle.tireFriction, HANDLING_MIN, HANDLING_MAX)
-- Print vehicle ratings to the Event Log
print(vehicle.name)
print("Acceleration: " .. accele)
print("Top Speed: " .. topSpeed)
print("Handling: " .. handling)
if vehicle:IsA("TreadedVehicle") then
print("Type: Treaded, " .. vehicle.turnSpeed)
-- Check to make sure the vehicle type is four wheeled, because treaded vehicles
-- do not have a turnRadius property.
elseif vehicle:IsA("FourWheeledVehicle") then
print("Type: 4-wheel, " .. vehicle.turnRadius)
else
print("Type: Unknown")
end
print("")
end
-- Search for all vehicles and rate them
for _,vehicle in ipairs(World.FindObjectsByType("Vehicle")) do
RateVehicle(vehicle)
end
See also: TreadedVehicle.turnSpeed | FourWheeledVehicle.turnRadius | World.FindObjectsByType | CoreObject.name