processVehicleCameraConfigChanged
Definition
-- @/lua/ge/extensions/core/camera.lua:528
-- TODO trigger this also for global cameras?
local function processVehicleCameraConfigChanged(vid, vdata, focusedCamNamePrevious)
local camerasOld = vdata.cameras or {}
vdata.cameras = {}
local vmvd = extensions.core_vehicle_manager.getVehicleData(vid)
if vmvd then
vmvd = vmvd.vdata
else
return
end
local refNodes = vmvd.refNodes[0]
local vmcd = vmvd.cameraData or {}
local camConfigs = {}
for camMode,constructor in pairs(getConstructors()) do
if tableFindKey(multicams, camMode) then
local jbeamConfigs = vmcd[camMode] or {}
for i,jbeamConfig in pairs(jbeamConfigs) do
table.insert(camConfigs, {name=camMode.."."..jbeamConfig.name, constructor=constructor, jbeamConfig=jbeamConfig})
end
else
local jbeamConfig = vmcd[camMode] or {}
table.insert(camConfigs, {name=camMode, constructor=constructor, jbeamConfig=jbeamConfig})
end
end
for k,v in ipairs(camConfigs) do
if v.name ~= "onboard.driver" and string.lower(v.name) == "onboard.driver" then
log("W", "", "Possibly incorrect camera name '"..v.name.."' (rename to 'onboard.driver'?)")
end
local cam = initCam(camerasOld[v.name], v.jbeamConfig, v.constructor)
if cam then
if cam.setRefNodes then
local refNodes = (vmvd.cameraRefNodes and vmvd.cameraRefNodes[v.name]) or refNodes
cam:setRefNodes(refNodes.ref, refNodes.left, refNodes.back)
end
vdata.cameras[v.name] = cam
end
end
if not arrayFindValueIndex(tableKeys(vdata.cameras), "onboard.driver") then
vdata.cameras.driver = nil -- there's no driver data to feed the driver cam, so remove it
end
-- initial camera config
local initialConfiguration = {
{name="orbit"}
,{name="driver"}
,{name="onboard.hood"}
,{name="external"}
,{name="relative"}
,{name="chase"}
}
local savedConfiguration = settings.getValue('cameraConfig')
if savedConfiguration and savedConfiguration ~= "" then
-- fix INI values that passed through javascript (e.g. when opening Options menu)
savedConfiguration = savedConfiguration:gsub("'",'"')
-- and then deserialize, so we can follow the user settings
savedConfiguration = jsonDecode(savedConfiguration)
-- if user settings version is good, go ahead and use it
if savedConfiguration and (savedConfiguration.version or 0) >= currentVersion then
initialConfiguration = savedConfiguration.data
end
end
-- fill pre-configured cameras (even if it's a disabled/unknown camera)
configuration = {}
for k,v in ipairs(initialConfiguration) do
local enabled = v.enabled
if enabled == nil then
enabled = true
local cam = vdata.cameras[v.name]
if cam then
enabled = cam.disabledByDefault ~= true
end
end
table.insert(configuration, {name=v.name, enabled=enabled})
end
-- append non-configured cameras
local renaminingCamNames = {}
for name, cam in pairs(vdata.cameras) do
local configured = false
for _,v in ipairs(configuration) do
if v.name == name then configured = true end
end
if not configured then
table.insert(renaminingCamNames, name)
end
end
-- now, a bit more complex: order the remaining cameras with their order number (if present) or jbeam order
while #renaminingCamNames > 0 do
local orderMin = 99999
local lowestOrderId = nil
for k, name in ipairs(renaminingCamNames) do
-- locate idx with the minimum order value
local cam = vdata.cameras[name]
if cam.order then
if type(cam.order) == 'number' then
if cam.order < orderMin then
orderMin = cam.order
lowestOrderId = k
end
else
log("E", "", "Incorrectly defined camera, 'order' field is not numeric: "..dumps(type(order)))
end
end
end
if not lowestOrderId then
-- no ordering? simply take first one then
lowestOrderId = 1
end
local name = renaminingCamNames[lowestOrderId]
local enabled = vdata.cameras[name].disabledByDefault ~= true
table.insert(configuration, {name=name, enabled=enabled})
table.remove(renaminingCamNames, lowestOrderId)
end
-- 1st try: we got a saved request, honour it before anything else
local cameraSet = false
if requestedCam[vid] then
cameraSet = _setVehicleCameraByName(vdata, requestedCam[vid].name)
if cameraSet and vdata.cameras[requestedCam[vid].name].setCustomData then
vdata.cameras[requestedCam[vid].name]:setCustomData( requestedCam[vid].customData )
end
requestedCam[vid] = nil
end
-- 2nd try: let's continue using the previous cam (which may have disappeared if we replaced the vehicle)
if not cameraSet and focusedCamNamePrevious then
cameraSet = _setVehicleCameraByName(vdata, focusedCamNamePrevious)
end
-- 3rd try: let's find the first 'enabled' camera and use it (i.e. the default camera)
if not cameraSet then
for k,v in pairs(configuration) do
if v.enabled and vdata.cameras[v.name] and not vdata.cameras[v.name].hidden then
cameraSet = _setVehicleCameraByIndex(vdata, k)
if cameraSet then break end
end
end
end
-- 4th try: let's find the first 'visible' camera and use it
if not cameraSet then
for k,v in pairs(configuration) do
if vdata.cameras[v.name] then
cameraSet = _setVehicleCameraByIndex(vdata, k)
if cameraSet then break end
end
end
end
-- 5th try: panic and don't keep calm
if not cameraSet then
log("E", "", "Unable to find a single usable camera, not even 'orbit' fallback. All bets are off from this point on")
end
saveConfiguration(vdata)
end
Callers
@/lua/ge/extensions/core/camera.lua
local focusedCamNamePrevious = ((vehicleCamerasCache or {})[vid] or {}).focusedCamName
M.processVehicleCameraConfigChanged(vid, vdata, focusedCamNamePrevious)
target[vid] = vdata
for vid, vdata in pairs(getVehicleData()) do
processVehicleCameraConfigChanged(vid, vdata, vdata.focusedCamName)
end