Hello Developers,
I write this article to present you a draft of the Camera API that we are developing (SU5, SU6 no ETA yet). We have read the numerous requests about this topic along those years on DevSupport and tried to answer as many wishes as possible. Before publishing it, we want to be sure that we are not missing any important parts, so feel free to share with us any thoughts about these headers and any future needs you may have (related to this topic) that could help us take this API in the right direction. As always, if you can detail your requests/thoughts with examples and or information, it would help us a lot. The more explicit and concrete you are, the more precisely we can answer.
Flow
A dedicated camera is reserved to addons. This camera can be acquired by SimConnect clients and/or Wasm modules. Once a client possesses the camera, no other addon can steal it from him. That being said, it is not because a client has acquired the camera that it has all rights on the sim’s cameras :
-
The Sim can temporary take back control over the cameras during specific part of the flow (menu, pause screen, RTC…). Passed those situations, the control of cameras will be given back to the addon which had acquired the dedicated camera.
-
The User has all rights over the cameras. Through the camera ingame panel (and maybe others places), he can revoke the acquisition of the addon camera and/or forbid its future acquisition.
All those information will be sent to all clients which have subscribed to this event, even if they haven’t acquired the camera.
Feature
Usable by everyone
CameraAcquire
Try to acquire the camera. Depending on the technology used, the call will look like
SimConnect
HRESULT SimConnect_CameraAcquire(HANDLE hSimConnect);
Send an exception if an internal error occurs. Send a message which contains the same information described in CameraGetStatus (see below) otherwise.
Wasm
bool fsCameraAcquire();
Returns true if the camera has been acquired. Returns false otherwise.
CameraGet
Get the current settings of the camera which are composed of the following data:
-
Position (X, Y, Z). The units of those values will depend of the selected referential (see below)
-
Pbh
-
FOV (double)
-
Referential. One of the following values:
-
Aircraft The position is an offset from the aircraft’s datum (expressed in meter)
-
Eyepoint The position is an offset from the aircraft’s eyepoint (expressed in meter)
-
World The position is a LLA
-
SimConnect
HRESULT SimConnect_CameraGet(HANDLE hSimConnect, DWORD referential);
Send an exception if an internal error occurs. Send a SIMCONNECT_RECV_CAMERA_STATUS (see below) otherwise.
Wasm
bool fsCameraGet(int referential, FsCameraData* pOut);
Fill the structure given in parameter with the data detailled above. Returns false if something went wrong. Returns true otherwise.
Note : It is possible to use a different referential from the one used by the camera. In this case, the position will be converted to the corresponding referential.
CameraGetStatus
Get the status of the shared camera, which is composed of the following data:
-
AcquiredState : One of the following values:
-
NOT_ACQUIRED
-
ACQUIRED
-
ACQUIRED_BY_OTHER
-
USER_DISABLED
-
-
Sim Control State : a boolean
SimConnect
HRESULT SimConnect_CameraGetStatus(HANDLE hSimConnect);
Send an exception if an internal error occurs. Send the same message as the one detailled in above
Wasm
bool fsCameraGetStatus(FsAcquiredState* outAcquiredState, bool* bSimControlled);
Returns false if an internal error occurs. Returns true otherwise
SubscribeToCameraStatusUpdate
Subscribe to this event which will send a message to the client each time the camera status is updated, to avoid using CameraGetStatus each frame
SimConnect
HRESULT SimConnect_SubscribeToCameraStatusUpdate(HANDLE hSimConnect);
Send an exception if an internal error occurs. Send the same message as the one detailled in CameraGetStatus
Wasm
bool fsCameraSubscribeToStatusUpdate(fsCameraWasmCallback callback, void* context);
Callback to call on event with the given context. Return false if an internal error occurs. Returns true otherwise.
UnsubscribeToCameraStatusUpdate
Unregister all callbacks registered for this event.
SimConnect
HRESULT SimConnect_UnsubscribeToCameraStatusUpdate(HANDLE hSimConnect);
Send an exception if an internal error occurs.
Wasm
bool fsCameraUnsubscribeToStatusUpdate();
Return false if an internal error occurs. Returns true otherwise.
EnumerateCameraDefinitions
Enumerate all camera definitions linked to the selected aircraft
SimConnect
HRESULT SimConnect_EnumerateCameraDefinitions(HANDLE hSimConnect);
Sends messages containing the list of all camera definitions name.
Send an exception if an internal error occurs.
Wasm
bool fsCameraEnumerateCameraDefinitions(char** outArrCameraDefinition, int* outArrSize);
Return false if an internal error occurs. Returns true otherwise.
The returned list (char**) must be freed by the user.
Usable if you have acquire the camera
CameraRelease
Release the camera previously acquired. The camera will be available for others to acquire. It is possible to specify the camera definition name towards which the camera switches. By not specify it, it will switch the one set before acquired it.
SimConnect
HRESULT SimConnect_CameraRelease(HANDLE hSimConnect, const char* cameraDefinition);
Send an exception if an internal error occurs or if the client is not the owner of the camera.
Wasm
bool fsCameraRelease(const char* cameraDefinition);
Returns false if an internal error occurs or if the client is not the owner of the camera. Returns true otherwise
CameraSet
Set the settings of the camera which are composed of the following data:
-
Position (X, Y, Z). The units of those values will depend of the selected referential (see below)
-
Pbh
-
FOV (double)
-
Referential. One of the following values:
-
Aircraft The position is an offset from the aircraft’s datum (expressed in meter)
-
Eyepoint The position is an offset from the aircraft’s eyepoint (expressed in meter)
-
World The position is a LLA
-
An additionnal mask must be sent to determine which data is set. This mask is a composition of the following value:
-
POSITION
-
ROTATION
-
FOV
-
REFERENTIAL
SimConnect
HRESULT SimConnect_CameraSet(HANDLE hSimConnect, SIMCONNECT_DATA_CAMERA CameraData, DWORD DataMask);
Send an exception if an internal error occurs or if the client is not the owner of the camera.
Wasm
bool fsCameraSet(FsCameraData* cameraData, int dataMask);
Returns false if an internal error occurs or if the client is not the owner of the camera. Returns true otherwise
CameraEnableFlag
Enable camera specific features. Here is the list of possible values:
-
CAMERA_FLAG_INTERACTION : Are interactions possible using this camera
-
CAMERA_FLAG_ABOVE_GROUND : Name to be determined : Always set the camera altitude above ground and/or buildings
SimConnect
HRESULT SimConnect_CameraEnableFlag(HANDLE hSimConnect, DWORD flag);
Send an exception if an internal error occurs or if the client is not the owner of the camera.
Wasm
bool fsCameraEnableFlag(int flag);
Returns false if an internal error occurs or if the client is not the owner of the camera. Returns true otherwise
CameraDisableFlag
Disable camera specific features. Here is the list of possible values:
-
CAMERA_FLAG_INTERACTION
-
CAMERA_FLAG_ABOVE_GROUND
SimConnect
HRESULT SimConnect_CameraDisableFlag(HANDLE hSimConnect, DWORD flag);
Send an exception if an internal error occurs or if the client is not the owner of the camera.
Wasm
bool fsCameraDisableFlag(int flag);
Returns false if an internal error occurs or if the client is not the owner of the camera. Returns true otherwise
Q&A
What about the previous 6DOF camera?
The 6DOF camera usable through SimConnect is still usable in the same way it was. However, it will now use the same system as the Camera API (using the old 6DOF call will be the same as using the acquire call and set position/rotation in EYEPOINT mode). This implies, that if another addon uses the Camera API and has already acquired the camera, 6DOF call will have no effect.
Wishing you a happy end of the year and all the best for next year!
Best Regards
Maxime & Thibault / Asobo