start making giant match statement in environment cb wrapper

This commit is contained in:
lif 2019-11-10 23:21:38 -08:00
parent eaab387216
commit 498c874bc7
3 changed files with 208 additions and 263 deletions

View File

@ -1,19 +1,19 @@
use std::convert::{TryFrom, TryInto};
use std::os::raw::{c_uint, c_void};
use std::os::raw::c_uint;
use std::path::PathBuf;
use num_enum::TryFromPrimitive;
use num_enum::{TryFromPrimitive, IntoPrimitive};
use crate::libretro_ffi::*;
#[derive(TryFromPrimitive)]
#[derive(TryFromPrimitive, IntoPrimitive)]
#[repr(u32)]
pub enum Region {
NTSC = RETRO_REGION_NTSC,
PAL = RETRO_REGION_PAL,
}
#[derive(TryFromPrimitive)]
#[derive(TryFromPrimitive, IntoPrimitive)]
#[repr(u32)]
pub enum DeviceType {
None = RETRO_DEVICE_NONE,
@ -25,7 +25,7 @@ pub enum DeviceType {
Pointer = RETRO_DEVICE_POINTER,
}
#[derive(TryFromPrimitive)]
#[derive(TryFromPrimitive, IntoPrimitive)]
#[repr(u32)]
pub enum DeviceIndex {
Left = RETRO_DEVICE_INDEX_ANALOG_LEFT,
@ -33,7 +33,7 @@ pub enum DeviceIndex {
Button = RETRO_DEVICE_INDEX_ANALOG_BUTTON,
}
#[derive(TryFromPrimitive)]
#[derive(TryFromPrimitive, IntoPrimitive)]
#[repr(u32)]
pub enum JoypadButton {
B = RETRO_DEVICE_ID_JOYPAD_B,
@ -54,14 +54,14 @@ pub enum JoypadButton {
R3 = RETRO_DEVICE_ID_JOYPAD_R3,
}
#[derive(TryFromPrimitive)]
#[derive(TryFromPrimitive, IntoPrimitive)]
#[repr(u32)]
pub enum AnalogAxis {
X = RETRO_DEVICE_ID_ANALOG_X,
Y = RETRO_DEVICE_ID_ANALOG_Y,
}
#[derive(TryFromPrimitive)]
#[derive(TryFromPrimitive, IntoPrimitive)]
#[repr(u32)]
pub enum MouseButton {
X = RETRO_DEVICE_ID_MOUSE_X,
@ -77,7 +77,7 @@ pub enum MouseButton {
Button5 = RETRO_DEVICE_ID_MOUSE_BUTTON_5,
}
#[derive(TryFromPrimitive)]
#[derive(TryFromPrimitive, IntoPrimitive)]
#[repr(u32)]
pub enum LightGunButton {
ScreenX = RETRO_DEVICE_ID_LIGHTGUN_SCREEN_X,
@ -99,7 +99,7 @@ pub enum LightGunButton {
Pause = RETRO_DEVICE_ID_LIGHTGUN_PAUSE,
}
#[derive(TryFromPrimitive)]
#[derive(TryFromPrimitive, IntoPrimitive)]
#[repr(u32)]
pub enum PointerStat {
X = RETRO_DEVICE_ID_POINTER_X,
@ -137,7 +137,7 @@ impl<D> TryFrom<(D, c_uint)> for Input
}
}
#[derive(TryFromPrimitive)]
#[derive(TryFromPrimitive, IntoPrimitive)]
#[repr(u32)]
pub enum EnvRotation {
None = 0,
@ -146,7 +146,7 @@ pub enum EnvRotation {
CounterClockwise270 = 3,
}
#[derive(TryFromPrimitive)]
#[derive(TryFromPrimitive, IntoPrimitive)]
#[repr(u32)]
pub enum EnvPixelFormat {
XRGB555 = retro_pixel_format_RETRO_PIXEL_FORMAT_0RGB1555,
@ -162,7 +162,7 @@ pub struct EnvVariable {
value: Option<String>,
}
#[derive(TryFromPrimitive)]
#[derive(TryFromPrimitive, IntoPrimitive)]
#[repr(u32)]
pub enum EnvLanguage {
English = retro_language_RETRO_LANGUAGE_ENGLISH,
@ -186,90 +186,89 @@ pub enum EnvLanguage {
Last = retro_language_RETRO_LANGUAGE_LAST,
}
// TODO: lifetime
// TODO: experimental calls
#[derive(TryFromPrimitive, IntoPrimitive)]
#[repr(u32)]
pub enum EnvironmentCmdData {
SetRotation(EnvRotation),
GetOverscan(&'static mut bool),
GetCanDupe(&'static mut bool),
SetMessage(retro_message), // TODO
Shutdown,
SetPerformanceLevel(c_uint),
GetSystemDirectory(&'static mut PathBuf),
SetPixelFormat(EnvPixelFormat),
SetInputDescriptors(&'static [retro_input_descriptor]), // TODO
SetKeyboardCallback(retro_keyboard_callback), // TODO
SetDiskControlInterface(retro_disk_control_callback), // TODO
SetHwRender(retro_hw_render_callback), // TODO
GetVariable(&'static mut EnvVariable),
SetVariables(&'static [EnvVariable]),
GetVariableUpdate(&'static mut bool),
SetSupportNoGame(bool),
GetLibretroPath(&'static mut PathBuf),
SetFrameTimeCallback(retro_frame_time_callback), // TODO
SetAudioCallback(retro_audio_callback), // TODO
GetRumbleInterface(&'static mut retro_rumble_interface), // TODO
GetInputDeviceCapabilities(&'static mut u64), // TODO
GetSensorInterface(&'static mut retro_sensor_interface), // TODO
GetCameraInterface(&'static mut retro_camera_callback), // TODO
GetLogInterface(&'static mut retro_log_callback), // TODO
GetPerfInterface(&'static mut retro_perf_callback), // TODO
GetLocationInterface(&'static mut retro_location_callback), // TODO
GetCoreAssetsDirectory(&'static mut PathBuf),
GetSaveDirectory(&'static mut PathBuf),
SetSystemAvInfo(retro_system_av_info),
SetProcAddressCallback(retro_get_proc_address_interface), // TODO
SetSubsystemInfo(retro_subsystem_info), // TODO
SetControllerInfo(retro_controller_info), // TODO
SetMemoryMaps(retro_memory_map), // TODO
SetGeometry(retro_game_geometry), // TODO
GetUsername(&'static mut String),
GetLanguage(&'static mut EnvLanguage),
SetSerializationQuirks(&'static mut u64), // TODO
SetRotation = RETRO_ENVIRONMENT_SET_ROTATION,
GetOverscan = RETRO_ENVIRONMENT_GET_OVERSCAN,
GetCanDupe = RETRO_ENVIRONMENT_GET_CAN_DUPE,
SetMessage = RETRO_ENVIRONMENT_SET_MESSAGE,
Shutdown = RETRO_ENVIRONMENT_SHUTDOWN,
SetPerformanceLevel = RETRO_ENVIRONMENT_SET_PERFORMANCE_LEVEL,
GetSystemDirectory = RETRO_ENVIRONMENT_GET_SYSTEM_DIRECTORY,
SetPixelFormat = RETRO_ENVIRONMENT_SET_PIXEL_FORMAT,
SetInputDescriptors = RETRO_ENVIRONMENT_SET_INPUT_DESCRIPTORS,
SetKeyboardCallback = RETRO_ENVIRONMENT_SET_KEYBOARD_CALLBACK,
SetDiskControlInterface = RETRO_ENVIRONMENT_SET_DISK_CONTROL_INTERFACE,
SetHwRender = RETRO_ENVIRONMENT_SET_HW_RENDER,
GetVariable = RETRO_ENVIRONMENT_GET_VARIABLE,
SetVariables = RETRO_ENVIRONMENT_SET_VARIABLES,
GetVariableUpdate = RETRO_ENVIRONMENT_GET_VARIABLE_UPDATE,
SetSupportNoGame = RETRO_ENVIRONMENT_SET_SUPPORT_NO_GAME,
GetLibretroPath = RETRO_ENVIRONMENT_GET_LIBRETRO_PATH,
SetFrameTimeCallback = RETRO_ENVIRONMENT_SET_FRAME_TIME_CALLBACK,
SetAudioCallback = RETRO_ENVIRONMENT_SET_AUDIO_CALLBACK,
GetRumbleInterface = RETRO_ENVIRONMENT_GET_RUMBLE_INTERFACE,
GetInputDeviceCapabilities = RETRO_ENVIRONMENT_GET_INPUT_DEVICE_CAPABILITIES,
GetSensorInterface = RETRO_ENVIRONMENT_GET_SENSOR_INTERFACE,
GetCameraInterface = RETRO_ENVIRONMENT_GET_CAMERA_INTERFACE,
GetLogInterface = RETRO_ENVIRONMENT_GET_LOG_INTERFACE,
GetPerfInterface = RETRO_ENVIRONMENT_GET_PERF_INTERFACE,
GetLocationInterface = RETRO_ENVIRONMENT_GET_LOCATION_INTERFACE,
GetCoreAssetsDirectory = RETRO_ENVIRONMENT_GET_CORE_ASSETS_DIRECTORY,
GetSaveDirectory = RETRO_ENVIRONMENT_GET_SAVE_DIRECTORY,
SetSystemAvInfo = RETRO_ENVIRONMENT_SET_SYSTEM_AV_INFO,
SetProcAddressCallback = RETRO_ENVIRONMENT_SET_PROC_ADDRESS_CALLBACK,
SetSubsystemInfo = RETRO_ENVIRONMENT_SET_SUBSYSTEM_INFO,
SetControllerInfo = RETRO_ENVIRONMENT_SET_CONTROLLER_INFO,
SetMemoryMaps = RETRO_ENVIRONMENT_SET_MEMORY_MAPS,
SetGeometry = RETRO_ENVIRONMENT_SET_GEOMETRY,
GetUsername = RETRO_ENVIRONMENT_GET_USERNAME,
GetLanguage = RETRO_ENVIRONMENT_GET_LANGUAGE,
SetSerializationQuirks = RETRO_ENVIRONMENT_SET_SERIALIZATION_QUIRKS,
}
pub trait HandlesEnvironment: Send + Sync + 'static {
// TODO: wrap cmd+data in enum
fn environment(&mut self, cmd: u32, data: *mut c_void) -> bool;
fn SetRotation(&mut self, rotation: EnvRotation) -> bool;
fn GetOverscan(&mut self, overscan: &mut bool) -> bool;
fn GetCanDupe(&mut self, frame_duping: &mut bool) -> bool;
fn SetMessage(&mut self, message: retro_message) -> bool;
fn Shutdown(&mut self) -> bool;
fn SetPerformanceLevel(&mut self, level: c_uint) -> bool;
fn GetSystemDirectory(&mut self, path: &mut PathBuf) -> bool;
fn SetPixelFormat(&mut self, format: EnvPixelFormat) -> bool;
fn SetInputDescriptors(&mut self, input_descriptors: &[retro_input_descriptor]) -> bool;
fn SetKeyboardCallback(&mut self, keyboard_callback: retro_keyboard_callback) -> bool;
fn SetDiskControlInterface(&mut self, disk_control_callback: retro_disk_control_callback) -> bool;
fn SetHwRender(&mut self, hw_render_callback: retro_hw_render_callback) -> bool;
fn GetVariable(&mut self, variable: &mut EnvVariable) -> bool;
fn SetVariables(&mut self, variables: &[EnvVariable]) -> bool;
fn GetVariableUpdate(&mut self, variables_updated: &mut bool) -> bool;
fn SetSupportNoGame(&mut self, supports_no_game: bool) -> bool;
fn GetLibretroPath(&mut self, path: &mut PathBuf) -> bool;
fn SetFrameTimeCallback(&mut self, frame_time_callback: retro_frame_time_callback) -> bool;
fn SetAudioCallback(&mut self, audio_callback: retro_audio_callback) -> bool;
fn GetRumbleInterface(&mut self, rumble_interface: &mut retro_rumble_interface) -> bool;
fn GetInputDeviceCapabilities(&mut self, input_device_capabilities: &mut u64) -> bool;
fn GetSensorInterface(&mut self, sensor_interface: &mut retro_sensor_interface) -> bool;
fn GetCameraInterface(&mut self, camera_callback: &mut retro_camera_callback) -> bool;
fn GetLogInterface(&mut self, log_callback: &mut retro_log_callback) -> bool;
fn GetPerfInterface(&mut self, perf_callback: &mut retro_perf_callback) -> bool;
fn GetLocationInterface(&mut self, location_callback: &mut retro_location_callback) -> bool;
fn GetCoreAssetsDirectory(&mut self, path: &mut PathBuf) -> bool;
fn GetSaveDirectory(&mut self, path: &mut PathBuf) -> bool;
fn SetSystemAvInfo(&mut self, system_av_info: retro_system_av_info) -> bool;
fn SetProcAddressCallback(&mut self, get_proc_address_interface: retro_get_proc_address_interface) -> bool;
fn SetSubsystemInfo(&mut self, subsystem_info: retro_subsystem_info) -> bool;
fn SetControllerInfo(&mut self, controller_info: retro_controller_info) -> bool;
fn SetMemoryMaps(&mut self, memory_map: retro_memory_map) -> bool;
fn SetGeometry(&mut self, game_geometry: retro_game_geometry) -> bool;
fn GetUsername(&mut self, username: &mut String) -> bool;
fn GetLanguage(&mut self, language: &mut EnvLanguage) -> bool;
fn SetSerializationQuirks(&mut self, quirks: &mut u64) -> bool;
fn set_rotation(&mut self, rotation: EnvRotation) -> bool { false }
fn get_overscan(&mut self) -> Option<bool> { None }
fn get_can_dupe(&mut self) -> Option<bool> { None }
fn set_message(&mut self, message: retro_message) -> bool { false }
fn shutdown(&mut self) -> bool { false }
fn set_performance_level(&mut self, level: c_uint) -> bool { false }
fn get_system_directory(&mut self) -> Option<PathBuf> { None }
fn set_pixel_format(&mut self, format: EnvPixelFormat) -> bool { false }
fn set_input_descriptors(&mut self, input_descriptors: &[retro_input_descriptor]) -> bool { false }
fn set_keyboard_callback(&mut self, cb: retro_keyboard_callback) -> bool { false }
fn set_disk_control_interface(&mut self, cb: retro_disk_control_callback) -> bool { false }
fn set_hw_render(&mut self, hw_render_callback: retro_hw_render_callback) -> bool { false }
fn get_variable(&mut self) -> Option<EnvVariable> { None }
fn set_variables(&mut self, variables: &[EnvVariable]) -> bool { false }
fn get_variable_update(&mut self) -> Option<bool> { None }
fn set_support_no_game(&mut self, supports_no_game: bool) -> bool { false }
fn get_libretro_path(&mut self) -> Option<PathBuf> { None }
fn set_frame_time_callback(&mut self, cb: retro_frame_time_callback) -> bool { false }
fn set_audio_callback(&mut self, audio_callback: retro_audio_callback) -> bool { false }
fn get_rumble_interface(&mut self) -> Option<retro_rumble_interface> { None }
fn get_input_device_capabilities(&mut self) -> Option<u64> { None }
fn get_sensor_interface(&mut self) -> Option<retro_sensor_interface> { None }
fn get_camera_interface(&mut self) -> Option<retro_camera_callback> { None }
fn get_log_interface(&mut self) -> Option<retro_log_callback> { None }
fn get_perf_interface(&mut self) -> Option<retro_perf_callback> { None }
fn get_location_interface(&mut self) -> Option<retro_location_callback> { None }
fn get_core_assets_directory(&mut self) -> Option<PathBuf> { None }
fn get_save_directory(&mut self) -> Option<PathBuf> { None }
fn set_system_av_info(&mut self, system_av_info: retro_system_av_info) -> bool { false }
fn set_proc_address_callback(&mut self, cb: retro_get_proc_address_interface) -> bool { false }
fn set_subsystem_info(&mut self, subsystem_info: retro_subsystem_info) -> bool { false }
fn set_controller_info(&mut self, controller_info: retro_controller_info) -> bool { false }
fn set_memory_maps(&mut self, memory_map: retro_memory_map) -> bool { false }
fn set_geometry(&mut self, game_geometry: retro_game_geometry) -> bool { false }
fn get_username(&mut self) -> Option<String> { None }
fn get_language(&mut self) -> Option<EnvLanguage> { None }
fn set_serialization_quirks(&mut self, quirks: &mut u64) -> bool { false }
}
pub trait HandlesVideoRefresh: Send + Sync + 'static {
fn video_refresh(&mut self, data: &[u8], width: c_uint, height: c_uint, pitch: c_uint);
}

View File

@ -2,10 +2,13 @@ use core::convert::TryInto;
use core::ffi::c_void;
use core::slice::from_raw_parts;
use std::os::raw::c_uint;
use std::ffi::CString;
use std::os::raw::{c_uint, c_char};
use crate::libretro_convert::*;
use crate::libretro_loading::*;
use std::path::Path;
use num_enum::{IntoPrimitive, TryFromPrimitive};
static mut CB_SINGLETON: StaticCallbacks = StaticCallbacks {
environment: None,
@ -29,13 +32,80 @@ struct StaticCallbacks {
unsafe impl Sync for StaticCallbacks {}
impl StaticCallbacks {
extern "C" fn environment_cb(cmd: u32, data: *mut c_void) -> bool {
match unsafe { CB_SINGLETON.environment.as_mut() } {
Some(cb) => cb.environment(cmd, data),
None => false,
}
// helpers for environ cb
fn clone_into_void<T: Clone>(data: *mut c_void, source: &T) -> Option<bool> {
unsafe { (data as *mut T).as_mut() }?.clone_from(source);
Some(true)
}
extern "C" fn video_refresh_cb(data: *const c_void, width: c_uint, height: c_uint, pitch: usize) {
fn string_into_void(data: *mut c_void, source: impl AsRef<str>) -> Option<bool> {
*unsafe { (data as *mut *const c_char).as_mut()? } = CString::new(source.as_ref()).ok()?.into_raw();
Some(true)
}
fn path_into_void(data: *mut c_void, source: impl AsRef<Path>) -> Option<bool> {
Self::string_into_void(data, source.as_ref().to_string_lossy())
}
fn from_void<T>(data: *mut c_void) -> Option<&'static mut T> {
unsafe { (data as *mut T).as_mut() }
}
fn enum_from_void<T>(data: *mut c_void) -> Option<T>
where T: TryFromPrimitive, <T as TryFromPrimitive>::Primitive: 'static
{
let number = Self::from_void(data).cloned()?;
T::try_from_primitive(number).ok()
}
fn environment_cb_inner(cmd: u32, data: *mut c_void) -> Option<bool> {
let mut handler = unsafe { CB_SINGLETON.environment.as_mut() }?;
match cmd.try_into().ok()? {
EnvironmentCmdData::SetRotation => handler.set_rotation(Self::enum_from_void(data)?),
EnvironmentCmdData::GetOverscan => Self::clone_into_void(data, &handler.get_overscan()?)?,
EnvironmentCmdData::GetCanDupe => Self::clone_into_void(data, &handler.get_can_dupe()?)?,
EnvironmentCmdData::SetMessage => handler.set_message(*Self::from_void(data)?),
EnvironmentCmdData::Shutdown => handler.shutdown(),
EnvironmentCmdData::SetPerformanceLevel => handler.set_performance_level(*Self::from_void(data)?),
EnvironmentCmdData::GetSystemDirectory => Self::path_into_void(data, handler.get_system_directory()?)?,
EnvironmentCmdData::SetPixelFormat => handler.set_pixel_format(Self::enum_from_void(data)?),
// TODO EnvironmentCmdData::SetInputDescriptors => {},
// TODO EnvironmentCmdData::SetKeyboardCallback => {},
// TODO EnvironmentCmdData::SetDiskControlInterface => {},
// TODO EnvironmentCmdData::SetHwRender => {},
// TODO EnvironmentCmdData::GetVariable => {}, -- also change to mut parameter?
// TODO EnvironmentCmdData::SetVariables => {},
EnvironmentCmdData::GetVariableUpdate => Self::clone_into_void(data, &handler.get_variable_update()?)?,
EnvironmentCmdData::SetSupportNoGame => handler.set_support_no_game(*Self::from_void(data)?),
EnvironmentCmdData::GetLibretroPath => Self::path_into_void(data, handler.get_libretro_path()?)?,
// TODO EnvironmentCmdData::SetFrameTimeCallback => {},
// TODO EnvironmentCmdData::SetAudioCallback => {},
// TODO EnvironmentCmdData::GetRumbleInterface => {},
EnvironmentCmdData::GetInputDeviceCapabilities => Self::clone_into_void(data, &handler.get_input_device_capabilities()?)?,
// TODO EnvironmentCmdData::GetSensorInterface => {},
// TODO EnvironmentCmdData::GetCameraInterface => {},
// TODO EnvironmentCmdData::GetLogInterface => {},
// TODO EnvironmentCmdData::GetPerfInterface => {},
// TODO EnvironmentCmdData::GetLocationInterface => {},
EnvironmentCmdData::GetCoreAssetsDirectory => Self::path_into_void(data, handler.get_core_assets_directory()?)?,
EnvironmentCmdData::GetSaveDirectory => Self::path_into_void(data, handler.get_save_directory()?)?,
EnvironmentCmdData::SetSystemAvInfo => handler.set_system_av_info(*Self::from_void(data)?),
// TODO EnvironmentCmdData::SetProcAddressCallback => {},
// TODO EnvironmentCmdData::SetSubsystemInfo => {},
// TODO EnvironmentCmdData::SetControllerInfo => {},
// TODO EnvironmentCmdData::SetMemoryMaps => {},
EnvironmentCmdData::SetGeometry => handler.set_geometry(*Self::from_void(data)?),
EnvironmentCmdData::GetUsername => Self::string_into_void(data, handler.get_username()?)?,
EnvironmentCmdData::GetLanguage => Self::clone_into_void(data, &c_uint::from(handler.get_language()?))?,
EnvironmentCmdData::SetSerializationQuirks => handler.set_serialization_quirks(Self::from_void(data)?),
_ => false,
}.into()
}
extern "C" fn environment_cb(cmd: u32, data: *mut c_void) -> bool {
Self::environment_cb_inner(cmd, data).unwrap_or(false)
}
extern "C" fn video_refresh_cb(
data: *const c_void,
width: c_uint,
height: c_uint,
pitch: usize,
) {
if !data.is_null() {
if let Some(cb) = unsafe { CB_SINGLETON.video_refresh.as_mut() } {
let data = data as *const u8;
@ -56,7 +126,7 @@ impl StaticCallbacks {
Some(cb) => match data.is_null() {
true => 0,
false => cb.audio_sample_batch(from_raw_parts(data, frames)),
}
},
None => 0,
}
}
@ -74,22 +144,34 @@ impl StaticCallbacks {
}
}
pub(crate) fn set_environment(cb: &'static mut dyn HandlesEnvironment) {
unsafe { CB_SINGLETON.environment.replace(cb); }
unsafe {
CB_SINGLETON.environment.replace(cb);
}
}
pub(crate) fn set_video_refresh(cb: &'static mut dyn HandlesVideoRefresh) {
unsafe { CB_SINGLETON.video_refresh.replace(cb); }
unsafe {
CB_SINGLETON.video_refresh.replace(cb);
}
}
pub(crate) fn set_audio_sample(cb: &'static mut dyn HandlesAudioSample) {
unsafe { CB_SINGLETON.audio_sample.replace(cb); }
unsafe {
CB_SINGLETON.audio_sample.replace(cb);
}
}
pub(crate) fn set_audio_sample_batch(cb: &'static mut dyn HandlesAudioSampleBatch) {
unsafe { CB_SINGLETON.audio_sample_batch.replace(cb); }
unsafe {
CB_SINGLETON.audio_sample_batch.replace(cb);
}
}
pub(crate) fn set_input_poll(cb: &'static mut dyn HandlesInputPoll) {
unsafe { CB_SINGLETON.input_poll.replace(cb); }
unsafe {
CB_SINGLETON.input_poll.replace(cb);
}
}
pub(crate) fn set_input_state(cb: &'static mut dyn HandlesInputState) {
unsafe { CB_SINGLETON.input_state.replace(cb); }
unsafe {
CB_SINGLETON.input_state.replace(cb);
}
}
pub(crate) fn reset() {
unsafe {
@ -115,9 +197,7 @@ impl<'a> From<LibretroApi<'a>> for LibretroWrapper<'a> {
api.set_audio_sample_batch(Some(StaticCallbacks::audio_sample_batch_cb));
api.set_input_poll(Some(StaticCallbacks::input_poll_cb));
api.set_input_state(Some(StaticCallbacks::input_state_cb));
LibretroWrapper {
api,
}
LibretroWrapper { api }
}
}
@ -148,7 +228,10 @@ impl<'a> LibretroWrapper<'a> {
let ptr: *mut dyn HandlesAudioSample = handler;
StaticCallbacks::set_audio_sample(unsafe { ptr.as_mut() }.unwrap());
}
pub fn register_audio_sample_batch_handler(&self, handler: &'a mut dyn HandlesAudioSampleBatch) {
pub fn register_audio_sample_batch_handler(
&self,
handler: &'a mut dyn HandlesAudioSampleBatch,
) {
let ptr: *mut dyn HandlesAudioSampleBatch = handler;
StaticCallbacks::set_audio_sample_batch(unsafe { ptr.as_mut() }.unwrap());
}
@ -160,4 +243,20 @@ impl<'a> LibretroWrapper<'a> {
let ptr: *mut dyn HandlesInputState = handler;
StaticCallbacks::set_input_state(unsafe { ptr.as_mut() }.unwrap());
}
pub fn register_for_all<T>(&self, handler: &'a mut T)
where
T: HandlesEnvironment
+ HandlesVideoRefresh
+ HandlesAudioSample
+ HandlesAudioSampleBatch
+ HandlesInputPoll
+ HandlesInputState,
{
self.register_environment_handler(handler);
self.register_video_refresh_handler(handler);
self.register_audio_sample_handler(handler);
self.register_audio_sample_batch_handler(handler);
self.register_input_poll_handler(handler);
self.register_input_state_handler(handler);
}
}

View File

@ -7,7 +7,7 @@ mod libretro_loading;
mod libretro_convert;
mod libretro_wrapper;
use std::ffi::{CStr, c_void};
use std::ffi::CStr;
use std::path::PathBuf;
use structopt::StructOpt;
@ -16,159 +16,6 @@ use crate::libretro_convert::{HandlesEnvironment, HandlesVideoRefresh};
struct Foo;
impl HandlesEnvironment for Foo {
fn environment(&mut self, cmd: u32, data: *mut c_void) -> bool {
println!("environment cmd: {}", cmd);
false
}
fn SetRotation(&mut self, rotation: EnvRotation) -> bool {
false
}
fn GetOverscan(&mut self, overscan: &mut bool) -> bool {
false
}
fn GetCanDupe(&mut self, frame_duping: &mut bool) -> bool {
false
}
fn SetMessage(&mut self, message: retro_message) -> bool {
false
}
fn Shutdown(&mut self) -> bool {
false
}
fn SetPerformanceLevel(&mut self, level: c_uint) -> bool {
false
}
fn GetSystemDirectory(&mut self, path: &mut PathBuf) -> bool {
false
}
fn SetPixelFormat(&mut self, format: EnvPixelFormat) -> bool {
false
}
fn SetInputDescriptors(&mut self, input_descriptors: &[retro_input_descriptor]) -> bool {
false
}
fn SetKeyboardCallback(&mut self, keyboard_callback: retro_keyboard_callback) -> bool {
false
}
fn SetDiskControlInterface(&mut self, disk_control_callback: retro_disk_control_callback) -> bool {
false
}
fn SetHwRender(&mut self, hw_render_callback: retro_hw_render_callback) -> bool {
false
}
fn GetVariable(&mut self, variable: &mut EnvVariable) -> bool {
false
}
fn SetVariables(&mut self, variables: &[EnvVariable]) -> bool {
false
}
fn GetVariableUpdate(&mut self, variables_updated: &mut bool) -> bool {
false
}
fn SetSupportNoGame(&mut self, supports_no_game: bool) -> bool {
false
}
fn GetLibretroPath(&mut self, path: &mut PathBuf) -> bool {
false
}
fn SetFrameTimeCallback(&mut self, frame_time_callback: retro_frame_time_callback) -> bool {
false
}
fn SetAudioCallback(&mut self, audio_callback: retro_audio_callback) -> bool {
false
}
fn GetRumbleInterface(&mut self, rumble_interface: &mut retro_rumble_interface) -> bool {
false
}
fn GetInputDeviceCapabilities(&mut self, input_device_capabilities: &mut u64) -> bool {
false
}
fn GetSensorInterface(&mut self, sensor_interface: &mut retro_sensor_interface) -> bool {
false
}
fn GetCameraInterface(&mut self, camera_callback: &mut retro_camera_callback) -> bool {
false
}
fn GetLogInterface(&mut self, log_callback: &mut retro_log_callback) -> bool {
false
}
fn GetPerfInterface(&mut self, perf_callback: &mut retro_perf_callback) -> bool {
false
}
fn GetLocationInterface(&mut self, location_callback: &mut retro_location_callback) -> bool {
false
}
fn GetCoreAssetsDirectory(&mut self, path: &mut PathBuf) -> bool {
false
}
fn GetSaveDirectory(&mut self, path: &mut PathBuf) -> bool {
false
}
fn SetSystemAvInfo(&mut self, system_av_info: retro_system_av_info) -> bool {
false
}
fn SetProcAddressCallback(&mut self, get_proc_address_interface: retro_get_proc_address_interface) -> bool {
false
}
fn SetSubsystemInfo(&mut self, subsystem_info: retro_subsystem_info) -> bool {
false
}
fn SetControllerInfo(&mut self, controller_info: retro_controller_info) -> bool {
false
}
fn SetMemoryMaps(&mut self, memory_map: retro_memory_map) -> bool {
false
}
fn SetGeometry(&mut self, game_geometry: retro_game_geometry) -> bool {
false
}
fn GetUsername(&mut self, username: &mut String) -> bool {
false
}
fn GetLanguage(&mut self, language: &mut EnvLanguage) -> bool {
false
}
fn SetSerializationQuirks(&mut self, quirks: &mut u64) -> bool {
false
}
}
impl HandlesVideoRefresh for Foo {