#![allow(clippy::too_many_arguments, clippy::missing_safety_doc)]
#![allow(non_upper_case_globals)]
#![allow(non_camel_case_types)]
#![allow(non_snake_case)]
use std::ffi::CString;
use std::mem::transmute_copy;
use std::ptr;
include!(concat!(env!("OUT_DIR"), "/bindings.rs"));
#[derive(Debug)]
pub enum DispatchResult<'a> {
Null,
Exception(&'a SIMCONNECT_RECV_EXCEPTION),
Open(&'a SIMCONNECT_RECV_OPEN),
Quit(&'a SIMCONNECT_RECV_QUIT),
Event(&'a SIMCONNECT_RECV_EVENT),
EventObjectAddRemove(&'a SIMCONNECT_RECV_EVENT_OBJECT_ADDREMOVE),
EventFilename(&'a SIMCONNECT_RECV_EVENT_FILENAME),
EventFrame(&'a SIMCONNECT_RECV_EVENT_FRAME),
SimObjectData(&'a SIMCONNECT_RECV_SIMOBJECT_DATA),
SimObjectDataByType(&'a SIMCONNECT_RECV_SIMOBJECT_DATA_BYTYPE),
WeatherObservation(&'a SIMCONNECT_RECV_WEATHER_OBSERVATION),
CloudState(&'a SIMCONNECT_RECV_CLOUD_STATE),
AssignedObjectId(&'a SIMCONNECT_RECV_ASSIGNED_OBJECT_ID),
ReservedKey(&'a SIMCONNECT_RECV_RESERVED_KEY),
CustomAction(&'a SIMCONNECT_RECV_CUSTOM_ACTION),
SystemState(&'a SIMCONNECT_RECV_SYSTEM_STATE),
ClientData(&'a SIMCONNECT_RECV_CLIENT_DATA),
EventWeatherMode(&'a SIMCONNECT_RECV_EVENT_WEATHER_MODE),
AirportList(&'a SIMCONNECT_RECV_AIRPORT_LIST),
VorList(&'a SIMCONNECT_RECV_VOR_LIST),
NdbList(&'a SIMCONNECT_RECV_NDB_LIST),
WaypointList(&'a SIMCONNECT_RECV_WAYPOINT_LIST),
EventMultiplayerServerStarted(&'a SIMCONNECT_RECV_EVENT_MULTIPLAYER_SERVER_STARTED),
EventMultiplayerClientStarted(&'a SIMCONNECT_RECV_EVENT_MULTIPLAYER_CLIENT_STARTED),
EventMultiplayerSessionEnded(&'a SIMCONNECT_RECV_EVENT_MULTIPLAYER_SESSION_ENDED),
EventRaceEnd(&'a SIMCONNECT_RECV_EVENT_RACE_END),
EventRaceLap(&'a SIMCONNECT_RECV_EVENT_RACE_LAP),
EventEx1(&'a SIMCONNECT_RECV_EVENT_EX1),
FacilityData(&'a SIMCONNECT_RECV_FACILITY_DATA),
FacilityDataEnd(&'a SIMCONNECT_RECV_FACILITY_DATA_END),
FacilityMinimalList(&'a SIMCONNECT_RECV_FACILITY_MINIMAL_LIST),
JetwayData(&'a SIMCONNECT_RECV_JETWAY_DATA),
ActionCallback(&'a SIMCONNECT_RECV_ACTION_CALLBACK),
EnumerateInputEvents(&'a SIMCONNECT_RECV_ENUMERATE_INPUT_EVENTS),
GetInputEvent(&'a SIMCONNECT_RECV_GET_INPUT_EVENT),
SubscribeInputEvent(&'a SIMCONNECT_RECV_SUBSCRIBE_INPUT_EVENT),
EnumerateInputEventParams(&'a SIMCONNECT_RECV_ENUMERATE_INPUT_EVENT_PARAMS),
ControllersList(&'a SIMCONNECT_RECV_CONTROLLERS_LIST),
}
#[derive(Debug)]
pub struct SimConnector {
sim_connect_handle: HANDLE,
}
impl Default for SimConnector {
fn default() -> Self {
Self {
sim_connect_handle: std::ptr::null_mut(),
}
}
}
impl SimConnector {
pub fn new() -> Self {
Self::default()
}
pub fn connect(&mut self, program_name: &str) -> bool {
unsafe {
let temp_1 = ptr::null_mut();
let temp_2 = ptr::null_mut();
let program_name = CString::new(program_name).unwrap();
SimConnect_Open(
&mut self.sim_connect_handle,
program_name.as_ptr(),
temp_1,
0,
temp_2,
0,
);
!self.sim_connect_handle.is_null()
}
}
pub fn add_data_definition(
&self,
define_id: SIMCONNECT_DATA_DEFINITION_ID,
datum_name: &str,
units_name: &str,
datum_type: SIMCONNECT_DATATYPE,
datum_id: DWORD,
epsilon: f32,
) -> bool {
let datum_name = CString::new(datum_name).unwrap();
let units_name = CString::new(units_name).unwrap();
unsafe {
SimConnect_AddToDataDefinition(
self.sim_connect_handle,
define_id,
datum_name.as_ptr(),
units_name.as_ptr(),
datum_type,
epsilon,
datum_id,
) == 0
}
}
pub fn set_system_event_state(
&self,
event_id: SIMCONNECT_CLIENT_EVENT_ID,
state: SIMCONNECT_STATE,
) -> bool {
unsafe { SimConnect_SetSystemEventState(self.sim_connect_handle, event_id, state) == 0 }
}
pub fn remove_client_event(
&self,
group_id: SIMCONNECT_NOTIFICATION_GROUP_ID,
event_id: SIMCONNECT_CLIENT_EVENT_ID,
) -> bool {
unsafe { SimConnect_RemoveClientEvent(self.sim_connect_handle, group_id, event_id) == 0 }
}
pub fn clear_notification_group(&self, group_id: SIMCONNECT_NOTIFICATION_GROUP_ID) -> bool {
unsafe { SimConnect_ClearNotificationGroup(self.sim_connect_handle, group_id) == 0 }
}
pub fn request_notification_group(
&self,
group_id: SIMCONNECT_NOTIFICATION_GROUP_ID,
reserved: DWORD,
flags: DWORD,
) -> bool {
unsafe {
SimConnect_RequestNotificationGroup(self.sim_connect_handle, group_id, reserved, flags)
== 0
}
}
pub fn clear_data_definition(&self, define_id: SIMCONNECT_DATA_DEFINITION_ID) -> bool {
unsafe { SimConnect_ClearDataDefinition(self.sim_connect_handle, define_id) == 0 }
}
pub fn create_client_data(
&self,
data_id: SIMCONNECT_CLIENT_DATA_ID,
size: DWORD,
flags: SIMCONNECT_CREATE_CLIENT_DATA_FLAG,
) -> bool {
unsafe { SimConnect_CreateClientData(self.sim_connect_handle, data_id, size, flags) == 0 }
}
pub fn request_data_on_sim_object_type(
&self,
request_id: SIMCONNECT_DATA_REQUEST_ID,
define_id: SIMCONNECT_DATA_DEFINITION_ID,
radius_in_meters: DWORD,
object_type: SIMCONNECT_SIMOBJECT_TYPE,
) -> bool {
unsafe {
SimConnect_RequestDataOnSimObjectType(
self.sim_connect_handle,
request_id,
define_id,
radius_in_meters,
object_type,
) == 0
}
}
pub fn remove_input_event(
&self,
group_id: SIMCONNECT_INPUT_GROUP_ID,
input_definition: &str,
) -> bool {
let input_definition = CString::new(input_definition).unwrap();
unsafe {
SimConnect_RemoveInputEvent(
self.sim_connect_handle,
group_id,
input_definition.as_ptr(),
) == 0
}
}
pub fn clear_input_group(&self, group_id: SIMCONNECT_INPUT_GROUP_ID) -> bool {
unsafe { SimConnect_ClearInputGroup(self.sim_connect_handle, group_id) == 0 }
}
pub fn request_reserved_key(
&self,
event_id: SIMCONNECT_CLIENT_EVENT_ID,
key_choice_1: &str,
key_choice_2: &str,
key_choice_3: &str,
) -> bool {
let key_choice_1 = CString::new(key_choice_1).unwrap();
let key_choice_2 = CString::new(key_choice_2).unwrap();
let key_choice_3 = CString::new(key_choice_3).unwrap();
unsafe {
SimConnect_RequestReservedKey(
self.sim_connect_handle,
event_id,
key_choice_1.as_ptr(),
key_choice_2.as_ptr(),
key_choice_3.as_ptr(),
) == 0
}
}
pub fn unsubscribe_from_system_event(&self, event_id: SIMCONNECT_CLIENT_EVENT_ID) -> bool {
unsafe { SimConnect_UnsubscribeFromSystemEvent(self.sim_connect_handle, event_id) == 0 }
}
pub fn ai_create_parked_atc_aircraft(
&self,
container_title: &str,
tail_number: &str,
airport_id: &str,
request_id: SIMCONNECT_DATA_REQUEST_ID,
) -> bool {
let container_title = CString::new(container_title).unwrap();
let tail_number = CString::new(tail_number).unwrap();
let airport_id = CString::new(airport_id).unwrap();
unsafe {
SimConnect_AICreateParkedATCAircraft(
self.sim_connect_handle,
container_title.as_ptr(),
tail_number.as_ptr(),
airport_id.as_ptr(),
request_id,
) == 0
}
}
pub fn ai_create_enroute_atc_aircraft(
&self,
container_title: &str,
tail_number: &str,
flight_number: i32,
flight_plan_path: &str,
flight_plan_position: f64,
touch_and_go: bool,
request_id: SIMCONNECT_DATA_REQUEST_ID,
) -> bool {
let container_title = CString::new(container_title).unwrap();
let tail_number = CString::new(tail_number).unwrap();
let flight_plan_path = CString::new(flight_plan_path).unwrap();
unsafe {
SimConnect_AICreateEnrouteATCAircraft(
self.sim_connect_handle,
container_title.as_ptr(),
tail_number.as_ptr(),
flight_number,
flight_plan_path.as_ptr(),
flight_plan_position,
touch_and_go as i32,
request_id,
) == 0
}
}
pub fn ai_create_non_atc_aircraft(
&self,
container_title: &str,
tail_number: &str,
init_pos: SIMCONNECT_DATA_INITPOSITION,
request_id: SIMCONNECT_DATA_REQUEST_ID,
) -> bool {
let container_title = CString::new(container_title).unwrap();
let tail_number = CString::new(tail_number).unwrap();
unsafe {
SimConnect_AICreateNonATCAircraft(
self.sim_connect_handle,
container_title.as_ptr(),
tail_number.as_ptr(),
init_pos,
request_id,
) == 0
}
}
pub fn ai_create_simulated_object(
&self,
container_title: &str,
init_pos: SIMCONNECT_DATA_INITPOSITION,
request_id: SIMCONNECT_DATA_REQUEST_ID,
) -> bool {
let container_title = CString::new(container_title).unwrap();
unsafe {
SimConnect_AICreateSimulatedObject(
self.sim_connect_handle,
container_title.as_ptr(),
init_pos,
request_id,
) == 0
}
}
pub fn ai_release_control(
&self,
object_id: SIMCONNECT_OBJECT_ID,
request_id: SIMCONNECT_DATA_REQUEST_ID,
) -> bool {
unsafe { SimConnect_AIReleaseControl(self.sim_connect_handle, object_id, request_id) == 0 }
}
pub fn ai_remove_object(
&self,
object_id: SIMCONNECT_OBJECT_ID,
request_id: SIMCONNECT_DATA_REQUEST_ID,
) -> bool {
unsafe { SimConnect_AIRemoveObject(self.sim_connect_handle, object_id, request_id) == 0 }
}
pub fn ai_set_aircraft_flight_plan(
&self,
object_id: SIMCONNECT_OBJECT_ID,
flight_plan_path: &str,
request_id: SIMCONNECT_DATA_REQUEST_ID,
) -> bool {
let flight_plan_path = CString::new(flight_plan_path).unwrap();
unsafe {
SimConnect_AISetAircraftFlightPlan(
self.sim_connect_handle,
object_id,
flight_plan_path.as_ptr(),
request_id,
) == 0
}
}
pub fn execute_mission_action(&self, instance_id: GUID) -> bool {
unsafe { SimConnect_ExecuteMissionAction(self.sim_connect_handle, instance_id) == 0 }
}
pub fn complete_custom_mission_action(&self, instance_id: GUID) -> bool {
unsafe { SimConnect_CompleteCustomMissionAction(self.sim_connect_handle, instance_id) == 0 }
}
pub fn close(&self) -> bool {
unsafe { SimConnect_Close(self.sim_connect_handle) == 0 }
}
pub unsafe fn get_last_sent_packet_id(&self, error: *mut DWORD) -> bool {
unsafe { SimConnect_GetLastSentPacketID(self.sim_connect_handle, error) == 0 }
}
pub unsafe fn call_dispatch(
&self,
dispatch_callback: DispatchProc,
context: *mut std::os::raw::c_void,
) -> bool {
unsafe { SimConnect_CallDispatch(self.sim_connect_handle, dispatch_callback, context) == 0 }
}
pub unsafe fn request_response_times(&self, count: DWORD, elapsed_seconds: *mut f32) -> bool {
unsafe {
SimConnect_RequestResponseTimes(self.sim_connect_handle, count, elapsed_seconds) == 0
}
}
pub fn camera_set_relative_6dof(
&self,
delta_x: f32,
delta_y: f32,
delta_z: f32,
pitch: f32,
bank: f32,
heading: f32,
) -> bool {
unsafe {
SimConnect_CameraSetRelative6DOF(
self.sim_connect_handle,
delta_x,
delta_y,
delta_z,
pitch,
bank,
heading,
) == 0
}
}
pub fn menu_add_item(
&self,
menu_item: &str,
event_id: SIMCONNECT_CLIENT_EVENT_ID,
data: DWORD,
) -> bool {
let menu_item = CString::new(menu_item).unwrap();
unsafe {
SimConnect_MenuAddItem(self.sim_connect_handle, menu_item.as_ptr(), event_id, data) == 0
}
}
pub fn menu_delete_item(&self, event_id: SIMCONNECT_CLIENT_EVENT_ID) -> bool {
unsafe { SimConnect_MenuDeleteItem(self.sim_connect_handle, event_id) == 0 }
}
pub fn menu_delete_sub_item(
&self,
event_id: SIMCONNECT_CLIENT_EVENT_ID,
sub_event_id: SIMCONNECT_CLIENT_EVENT_ID,
) -> bool {
unsafe {
SimConnect_MenuDeleteSubItem(self.sim_connect_handle, event_id, sub_event_id) == 0
}
}
pub fn request_system_state(
&self,
request_id: SIMCONNECT_DATA_REQUEST_ID,
state: &str,
) -> bool {
let state = CString::new(state).unwrap();
unsafe {
SimConnect_RequestSystemState(self.sim_connect_handle, request_id, state.as_ptr()) == 0
}
}
pub fn map_client_data_name_to_id(
&self,
client_data_name: &str,
data_id: SIMCONNECT_CLIENT_DATA_ID,
) -> bool {
let client_data_name = CString::new(client_data_name).unwrap();
unsafe {
SimConnect_MapClientDataNameToID(
self.sim_connect_handle,
client_data_name.as_ptr(),
data_id,
) == 0
}
}
pub fn add_to_client_data_definition(
&self,
define_id: SIMCONNECT_DATA_DEFINITION_ID,
offset: DWORD,
size_or_type: DWORD,
epsilon: f32,
datum_id: DWORD,
) -> bool {
unsafe {
SimConnect_AddToClientDataDefinition(
self.sim_connect_handle,
define_id,
offset,
size_or_type,
epsilon,
datum_id,
) == 0
}
}
pub fn clear_client_data_definition(&self, define_id: SIMCONNECT_DATA_DEFINITION_ID) -> bool {
unsafe { SimConnect_ClearClientDataDefinition(self.sim_connect_handle, define_id) == 0 }
}
pub fn request_client_data(
&self,
data_id: SIMCONNECT_CLIENT_DATA_ID,
request_id: SIMCONNECT_DATA_REQUEST_ID,
define_id: SIMCONNECT_DATA_DEFINITION_ID,
period: SIMCONNECT_CLIENT_DATA_PERIOD,
flags: SIMCONNECT_CLIENT_DATA_REQUEST_FLAG,
origin: DWORD,
interval: DWORD,
limit: DWORD,
) -> bool {
unsafe {
SimConnect_RequestClientData(
self.sim_connect_handle,
data_id,
request_id,
define_id,
period,
flags,
origin,
interval,
limit,
) == 0
}
}
pub unsafe fn set_client_data(
&self,
data_id: SIMCONNECT_CLIENT_DATA_ID,
define_id: SIMCONNECT_DATA_DEFINITION_ID,
flags: DWORD,
reserved: DWORD,
unit_size: DWORD,
data_set: *mut std::os::raw::c_void,
) -> bool {
unsafe {
SimConnect_SetClientData(
self.sim_connect_handle,
data_id,
define_id,
flags,
reserved,
unit_size,
data_set,
) == 0
}
}
pub fn flight_load(&self, file_name: &str) -> bool {
let file_name = CString::new(file_name).unwrap();
unsafe { SimConnect_FlightLoad(self.sim_connect_handle, file_name.as_ptr()) == 0 }
}
pub unsafe fn text(
&self,
text_type: SIMCONNECT_TEXT_TYPE,
time_in_seconds: f32,
event_id: SIMCONNECT_CLIENT_EVENT_ID,
unit_size: DWORD,
data_set: *mut std::os::raw::c_void,
) -> bool {
unsafe {
SimConnect_Text(
self.sim_connect_handle,
text_type,
time_in_seconds,
event_id,
unit_size,
data_set,
) == 0
}
}
pub fn subscribe_to_facilities(
&self,
list_type: SIMCONNECT_FACILITY_LIST_TYPE,
request_id: SIMCONNECT_DATA_REQUEST_ID,
) -> bool {
unsafe {
SimConnect_SubscribeToFacilities(self.sim_connect_handle, list_type, request_id) == 0
}
}
pub fn unsubscribe_to_facilities(&self, list_type: SIMCONNECT_FACILITY_LIST_TYPE) -> bool {
unsafe { SimConnect_UnsubscribeToFacilities(self.sim_connect_handle, list_type) == 0 }
}
pub fn request_facilities_list(
&self,
list_type: SIMCONNECT_FACILITY_LIST_TYPE,
request_id: SIMCONNECT_DATA_REQUEST_ID,
) -> bool {
unsafe {
SimConnect_RequestFacilitiesList(self.sim_connect_handle, list_type, request_id) == 0
}
}
pub fn request_data_on_sim_object(
&self,
request_id: SIMCONNECT_DATA_REQUEST_ID,
define_id: SIMCONNECT_DATA_DEFINITION_ID,
object_id: SIMCONNECT_OBJECT_ID,
period: SIMCONNECT_CLIENT_DATA_PERIOD,
flags: SIMCONNECT_DATA_REQUEST_FLAG,
origin: DWORD,
interval: DWORD,
limit: DWORD,
) -> bool {
unsafe {
SimConnect_RequestDataOnSimObject(
self.sim_connect_handle,
request_id,
define_id,
object_id,
period,
flags,
origin,
interval,
limit,
) == 0
}
}
pub unsafe fn set_data_on_sim_object(
&self,
define_id: SIMCONNECT_DATA_DEFINITION_ID,
object_id: SIMCONNECT_OBJECT_ID,
flags: SIMCONNECT_DATA_SET_FLAG,
array_count: DWORD,
size: DWORD,
pntr: *mut ::std::os::raw::c_void,
) -> bool {
unsafe {
SimConnect_SetDataOnSimObject(
self.sim_connect_handle,
define_id,
object_id,
flags,
array_count,
size,
pntr,
) == 0
}
}
pub fn subscribe_to_system_event(
&self,
event_id: SIMCONNECT_CLIENT_EVENT_ID,
event_name: &str,
) -> bool {
let event_name = CString::new(event_name).unwrap();
unsafe {
SimConnect_SubscribeToSystemEvent(
self.sim_connect_handle,
event_id,
event_name.as_ptr(),
) == 0
}
}
pub fn map_client_event_to_sim_event(
&self,
event_id: SIMCONNECT_CLIENT_EVENT_ID,
event_name: &str,
) -> bool {
let event_name = CString::new(event_name).unwrap();
unsafe {
SimConnect_MapClientEventToSimEvent(
self.sim_connect_handle,
event_id,
event_name.as_ptr(),
) == 0
}
}
pub fn transmit_client_event(
&self,
object_id: SIMCONNECT_OBJECT_ID,
event_id: SIMCONNECT_CLIENT_EVENT_ID,
dw_data: DWORD,
group_id: SIMCONNECT_NOTIFICATION_GROUP_ID,
flags: SIMCONNECT_EVENT_FLAG,
) -> bool {
unsafe {
SimConnect_TransmitClientEvent(
self.sim_connect_handle,
object_id,
event_id,
dw_data,
group_id,
flags,
) == 0
}
}
pub fn add_client_event_to_notification_group(
&self,
group_id: SIMCONNECT_NOTIFICATION_GROUP_ID,
event_id: SIMCONNECT_CLIENT_EVENT_ID,
maskable: bool,
) -> bool {
unsafe {
SimConnect_AddClientEventToNotificationGroup(
self.sim_connect_handle,
group_id,
event_id,
maskable as i32,
) == 0
}
}
pub fn set_notification_group_priority(
&self,
group_id: SIMCONNECT_NOTIFICATION_GROUP_ID,
priority: DWORD,
) -> bool {
unsafe {
SimConnect_SetNotificationGroupPriority(self.sim_connect_handle, group_id, priority)
== 0
}
}
pub fn map_input_event_to_client_event(
&self,
group_id: SIMCONNECT_INPUT_GROUP_ID,
input_definition: &str,
down_event: SIMCONNECT_CLIENT_EVENT_ID,
down_return_value: DWORD,
up_event: SIMCONNECT_CLIENT_EVENT_ID,
up_return_value: DWORD,
maskable: bool,
) -> bool {
let input_definition = CString::new(input_definition).unwrap();
unsafe {
SimConnect_MapInputEventToClientEvent(
self.sim_connect_handle,
group_id,
input_definition.as_ptr(),
down_event,
down_return_value,
up_event,
up_return_value,
maskable as i32,
) == 0
}
}
pub fn set_input_group_state(&self, group_id: SIMCONNECT_INPUT_GROUP_ID, state: DWORD) -> bool {
unsafe { SimConnect_SetInputGroupState(self.sim_connect_handle, group_id, state) == 0 }
}
pub fn set_input_priority(&self, group_id: SIMCONNECT_INPUT_GROUP_ID, priority: DWORD) -> bool {
unsafe {
SimConnect_SetInputGroupPriority(self.sim_connect_handle, group_id, priority) == 0
}
}
pub fn transmit_client_event_ex1(
&self,
object_id: SIMCONNECT_OBJECT_ID,
event_id: SIMCONNECT_CLIENT_EVENT_ID,
group_id: SIMCONNECT_NOTIFICATION_GROUP_ID,
flags: SIMCONNECT_EVENT_FLAG,
data0: DWORD,
data1: DWORD,
data2: DWORD,
data3: DWORD,
data4: DWORD,
) -> bool {
unsafe {
SimConnect_TransmitClientEvent_EX1(
self.sim_connect_handle,
object_id,
event_id,
group_id,
flags,
data0,
data1,
data2,
data3,
data4,
) == 0
}
}
pub fn add_to_facility_definition(
&self,
define_id: SIMCONNECT_DATA_DEFINITION_ID,
field_name: &str,
) -> bool {
let field_name = CString::new(field_name).unwrap();
unsafe {
SimConnect_AddToFacilityDefinition(
self.sim_connect_handle,
define_id,
field_name.as_ptr(),
) == 0
}
}
pub fn request_facility_data(
&self,
define_id: SIMCONNECT_DATA_DEFINITION_ID,
request_id: SIMCONNECT_DATA_REQUEST_ID,
icao: &str,
region: Option<&str>,
) -> bool {
let icao = CString::new(icao).unwrap();
let region = region.map(|s| CString::new(s).unwrap());
unsafe {
SimConnect_RequestFacilityData(
self.sim_connect_handle,
define_id,
request_id,
icao.as_ptr(),
region.as_ref().map_or(ptr::null(), |s| s.as_ptr()),
) == 0
}
}
pub fn subscribe_to_facilities_ex1(
&self,
list_type: SIMCONNECT_FACILITY_LIST_TYPE,
new_in_range_request_id: SIMCONNECT_DATA_REQUEST_ID,
old_out_of_range_request_id: SIMCONNECT_DATA_REQUEST_ID,
) -> bool {
unsafe {
SimConnect_SubscribeToFacilities_EX1(
self.sim_connect_handle,
list_type,
new_in_range_request_id,
old_out_of_range_request_id,
) == 0
}
}
pub fn unsubscribe_to_facilities_ex1(
&self,
list_type: SIMCONNECT_FACILITY_LIST_TYPE,
unsubscribe_new_in_range: bool,
unsubscribe_old_out_of_range: bool,
) -> bool {
unsafe {
SimConnect_UnsubscribeToFacilities_EX1(
self.sim_connect_handle,
list_type,
unsubscribe_new_in_range,
unsubscribe_old_out_of_range,
) == 0
}
}
pub fn request_facilities_list_ex1(
&self,
list_type: SIMCONNECT_FACILITY_LIST_TYPE,
request_id: SIMCONNECT_DATA_REQUEST_ID,
) -> bool {
unsafe {
SimConnect_RequestFacilitiesList_EX1(self.sim_connect_handle, list_type, request_id)
== 0
}
}
pub fn request_facility_data_ex1(
&self,
define_id: SIMCONNECT_DATA_DEFINITION_ID,
request_id: SIMCONNECT_DATA_REQUEST_ID,
icao: &str,
region: Option<&str>,
type_: Option<i8>,
) -> bool {
let icao = CString::new(icao).unwrap();
let region = region.map(|s| CString::new(s).unwrap());
unsafe {
SimConnect_RequestFacilityData_EX1(
self.sim_connect_handle,
define_id,
request_id,
icao.as_ptr(),
region.as_ref().map_or(ptr::null(), |s| s.as_ptr()),
type_.unwrap_or(0) as ::std::os::raw::c_char,
) == 0
}
}
pub unsafe fn request_jetway_data(
&self,
airport_icao: &str,
array_count: DWORD,
indexes: *mut i32,
) -> bool {
let airport_icao = CString::new(airport_icao).unwrap();
unsafe {
SimConnect_RequestJetwayData(
self.sim_connect_handle,
airport_icao.as_ptr(),
array_count,
indexes,
) == 0
}
}
pub fn enumerate_controllers(&self) -> bool {
unsafe { SimConnect_EnumerateControllers(self.sim_connect_handle) == 0 }
}
pub fn map_input_event_to_client_event_ex1(
&self,
group_id: SIMCONNECT_INPUT_GROUP_ID,
input_definition: &str,
down_event: SIMCONNECT_CLIENT_EVENT_ID,
down_return_value: DWORD,
up_event: SIMCONNECT_CLIENT_EVENT_ID,
up_return_value: DWORD,
maskable: bool,
) -> bool {
let input_definition = CString::new(input_definition).unwrap();
unsafe {
SimConnect_MapInputEventToClientEvent_EX1(
self.sim_connect_handle,
group_id,
input_definition.as_ptr(),
down_event,
down_return_value,
up_event,
up_return_value,
maskable as i32,
) == 0
}
}
pub unsafe fn execute_action(
&self,
request_id: DWORD,
action_id: &str,
unit_size: DWORD,
param_values: *mut std::os::raw::c_void,
) -> bool {
let action_id = CString::new(action_id).unwrap();
unsafe {
SimConnect_ExecuteAction(
self.sim_connect_handle,
request_id,
action_id.as_ptr(),
unit_size,
param_values,
) == 0
}
}
pub fn enumerate_input_events(&self, request_id: SIMCONNECT_DATA_REQUEST_ID) -> bool {
unsafe { SimConnect_EnumerateInputEvents(self.sim_connect_handle, request_id) == 0 }
}
pub fn get_input_event(&self, request_id: SIMCONNECT_DATA_REQUEST_ID, hash: u64) -> bool {
unsafe { SimConnect_GetInputEvent(self.sim_connect_handle, request_id, hash) == 0 }
}
pub unsafe fn set_input_event(
&self,
hash: u64,
unit_size: DWORD,
value: *mut std::os::raw::c_void,
) -> bool {
unsafe { SimConnect_SetInputEvent(self.sim_connect_handle, hash, unit_size, value) == 0 }
}
pub fn subscribe_input_event(&self, hash: u64) -> bool {
unsafe { SimConnect_SubscribeInputEvent(self.sim_connect_handle, hash) == 0 }
}
pub fn unsubscribe_input_event(&self, hash: u64) -> bool {
unsafe { SimConnect_UnsubscribeInputEvent(self.sim_connect_handle, hash) == 0 }
}
pub fn enumerate_input_event_params(&self, hash: u64) -> bool {
unsafe { SimConnect_EnumerateInputEventParams(self.sim_connect_handle, hash) == 0 }
}
pub fn add_facility_data_definition_filter(
&self,
define_id: SIMCONNECT_DATA_DEFINITION_ID,
filter_path: &str,
filter_data: *const std::os::raw::c_void,
cb_unit_size: DWORD,
) -> bool {
let filter_path = CString::new(filter_path).unwrap();
unsafe {
SimConnect_AddFacilityDataDefinitionFilter(
self.sim_connect_handle,
define_id,
filter_path.as_ptr(),
cb_unit_size,
filter_data as *mut _,
) == 0
}
}
pub fn clear_all_facility_data_definition_filters(
&self,
define_id: SIMCONNECT_DATA_DEFINITION_ID,
) -> bool {
unsafe {
SimConnect_ClearAllFacilityDataDefinitionFilters(self.sim_connect_handle, define_id)
== 0
}
}
pub fn get_next_message(&self) -> Result<DispatchResult<'_>, &str> {
let mut data_buf: *mut SIMCONNECT_RECV = ptr::null_mut();
let mut size_buf: DWORD = 0;
let size_buf_pointer: *mut DWORD = &mut size_buf;
unsafe {
let result = SimConnect_GetNextDispatch(
self.sim_connect_handle,
&mut data_buf,
size_buf_pointer,
);
if result != 0 {
return Err("Failed getting data!");
}
if data_buf.is_null() {
return Ok(DispatchResult::Null);
}
match (*data_buf).dwID as SIMCONNECT_RECV_ID {
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_NULL => Ok(DispatchResult::Null),
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_EXCEPTION => Ok(DispatchResult::Exception(
transmute_copy(&(data_buf as *const SIMCONNECT_RECV_EXCEPTION)),
)),
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_OPEN => Ok(DispatchResult::Open(
transmute_copy(&(data_buf as *const SIMCONNECT_RECV_OPEN)),
)),
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_QUIT => Ok(DispatchResult::Quit(
transmute_copy(&(data_buf as *const SIMCONNECT_RECV_QUIT)),
)),
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_EVENT => Ok(DispatchResult::Event(
transmute_copy(&(data_buf as *const SIMCONNECT_RECV_EVENT)),
)),
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_EVENT_OBJECT_ADDREMOVE => {
Ok(DispatchResult::EventObjectAddRemove(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_EVENT_OBJECT_ADDREMOVE),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_EVENT_FILENAME => {
Ok(DispatchResult::EventFilename(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_EVENT_FILENAME),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_EVENT_FRAME => {
Ok(DispatchResult::EventFrame(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_EVENT_FRAME),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_SIMOBJECT_DATA => {
Ok(DispatchResult::SimObjectData(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_SIMOBJECT_DATA),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_SIMOBJECT_DATA_BYTYPE => {
Ok(DispatchResult::SimObjectDataByType(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_SIMOBJECT_DATA_BYTYPE),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_WEATHER_OBSERVATION => {
Ok(DispatchResult::WeatherObservation(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_WEATHER_OBSERVATION),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_CLOUD_STATE => {
Ok(DispatchResult::CloudState(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_CLOUD_STATE),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_ASSIGNED_OBJECT_ID => {
Ok(DispatchResult::AssignedObjectId(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_ASSIGNED_OBJECT_ID),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_RESERVED_KEY => {
Ok(DispatchResult::ReservedKey(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_RESERVED_KEY),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_CUSTOM_ACTION => {
Ok(DispatchResult::CustomAction(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_CUSTOM_ACTION),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_SYSTEM_STATE => {
Ok(DispatchResult::SystemState(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_SYSTEM_STATE),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_CLIENT_DATA => {
Ok(DispatchResult::ClientData(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_CLIENT_DATA),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_EVENT_WEATHER_MODE => {
Ok(DispatchResult::EventWeatherMode(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_EVENT_WEATHER_MODE),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_AIRPORT_LIST => {
Ok(DispatchResult::AirportList(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_AIRPORT_LIST),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_VOR_LIST => Ok(DispatchResult::VorList(
transmute_copy(&(data_buf as *const SIMCONNECT_RECV_VOR_LIST)),
)),
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_NDB_LIST => Ok(DispatchResult::NdbList(
transmute_copy(&(data_buf as *const SIMCONNECT_RECV_NDB_LIST)),
)),
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_WAYPOINT_LIST => {
Ok(DispatchResult::WaypointList(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_WAYPOINT_LIST),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_EVENT_MULTIPLAYER_SERVER_STARTED => Ok(
DispatchResult::EventMultiplayerServerStarted(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_EVENT_MULTIPLAYER_SERVER_STARTED),
)),
),
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_EVENT_MULTIPLAYER_CLIENT_STARTED => Ok(
DispatchResult::EventMultiplayerClientStarted(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_EVENT_MULTIPLAYER_CLIENT_STARTED),
)),
),
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_EVENT_MULTIPLAYER_SESSION_ENDED => Ok(
DispatchResult::EventMultiplayerSessionEnded(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_EVENT_MULTIPLAYER_SESSION_ENDED),
)),
),
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_EVENT_RACE_END => {
Ok(DispatchResult::EventRaceEnd(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_EVENT_RACE_END),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_EVENT_RACE_LAP => {
Ok(DispatchResult::EventRaceLap(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_EVENT_RACE_LAP),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_EVENT_EX1 => Ok(DispatchResult::EventEx1(
transmute_copy(&(data_buf as *const SIMCONNECT_RECV_EVENT_EX1)),
)),
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_FACILITY_DATA => {
Ok(DispatchResult::FacilityData(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_FACILITY_DATA),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_FACILITY_DATA_END => {
Ok(DispatchResult::FacilityDataEnd(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_FACILITY_DATA_END),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_FACILITY_MINIMAL_LIST => {
Ok(DispatchResult::FacilityMinimalList(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_FACILITY_MINIMAL_LIST),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_JETWAY_DATA => {
Ok(DispatchResult::JetwayData(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_JETWAY_DATA),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_CONTROLLERS_LIST => {
Ok(DispatchResult::ControllersList(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_CONTROLLERS_LIST),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_ACTION_CALLBACK => {
Ok(DispatchResult::ActionCallback(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_ACTION_CALLBACK),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_ENUMERATE_INPUT_EVENTS => {
Ok(DispatchResult::EnumerateInputEvents(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_ENUMERATE_INPUT_EVENTS),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_GET_INPUT_EVENT => {
Ok(DispatchResult::GetInputEvent(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_GET_INPUT_EVENT),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_SUBSCRIBE_INPUT_EVENT => {
Ok(DispatchResult::SubscribeInputEvent(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_SUBSCRIBE_INPUT_EVENT),
)))
}
SIMCONNECT_RECV_ID_SIMCONNECT_RECV_ID_ENUMERATE_INPUT_EVENT_PARAMS => {
Ok(DispatchResult::EnumerateInputEventParams(transmute_copy(
&(data_buf as *const SIMCONNECT_RECV_ENUMERATE_INPUT_EVENT_PARAMS),
)))
}
_ => Err("Unhandled RECV_ID"),
}
}
}
}
impl Drop for SimConnector {
fn drop(&mut self) {
if !self.sim_connect_handle.is_null() {
self.close();
}
}
}