[Libretro] Implement SET_SYSTEM_AV_INFO and SET_GEOMETRY
This commit is contained in:
parent
799dc4a2f0
commit
0d3c7b7e0c
Binary file not shown.
Binary file not shown.
|
@ -17,6 +17,10 @@ public:
|
|||
: supportsNoGame(false)
|
||||
, retroMessageString()
|
||||
, retroMessageTime(0)
|
||||
, geoInfoDirty(false)
|
||||
, geoInfo()
|
||||
, timingInfoDirty(false)
|
||||
, timingInfo()
|
||||
, variablesDirty(false)
|
||||
, variableCount(0)
|
||||
, variableKeys()
|
||||
|
@ -238,8 +242,15 @@ public:
|
|||
*static_cast<const char**>(data) = saveDirectory.c_str();
|
||||
return true;
|
||||
case RETRO_ENVIRONMENT::SET_SYSTEM_AV_INFO:
|
||||
RetroLog(RETRO_LOG::WARN, "NEED RETRO_ENVIRONMENT::SET_SYSTEM_AV_INFO");
|
||||
return false;
|
||||
{
|
||||
const retro_system_av_info* av = static_cast<const retro_system_av_info*>(data);
|
||||
std::memcpy(&geoInfo, &av->geometry, sizeof (retro_game_geometry));
|
||||
SetVideoSize(geoInfo.max_width * geoInfo.max_height);
|
||||
geoInfoDirty = true;
|
||||
std::memcpy(&timingInfo, &av->timing, sizeof (retro_system_timing));
|
||||
timingInfoDirty = true;
|
||||
return true;
|
||||
}
|
||||
case RETRO_ENVIRONMENT::SET_PROC_ADDRESS_CALLBACK:
|
||||
//this is some way to get symbols for API extensions
|
||||
//of which none exist
|
||||
|
@ -252,9 +263,13 @@ public:
|
|||
//TODO medium priority probably
|
||||
return false;
|
||||
case RETRO_ENVIRONMENT::SET_GEOMETRY:
|
||||
//TODO medium priority probably
|
||||
//this is essentially just set system av info, except only for video
|
||||
return false;
|
||||
{
|
||||
const retro_game_geometry* geo = static_cast<const retro_game_geometry*>(data);
|
||||
std::memcpy(&geoInfo, geo, sizeof (retro_game_geometry));
|
||||
SetVideoSize(geoInfo.max_width * geoInfo.max_height);
|
||||
geoInfoDirty = true;
|
||||
return true;
|
||||
}
|
||||
case RETRO_ENVIRONMENT::GET_USERNAME:
|
||||
//we definitely want to return false here so the core will do something deterministic
|
||||
return false;
|
||||
|
@ -461,6 +476,26 @@ public:
|
|||
}
|
||||
}
|
||||
|
||||
bool GetRetroGeometryInfo(retro_game_geometry* geo) {
|
||||
if (!geoInfoDirty) {
|
||||
return false;
|
||||
}
|
||||
|
||||
std::memcpy(geo, &geoInfo, sizeof (retro_game_geometry));
|
||||
geoInfoDirty = false;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool GetRetroTimingInfo(retro_system_timing* timing) {
|
||||
if (!timingInfoDirty) {
|
||||
return false;
|
||||
}
|
||||
|
||||
std::memcpy(timing, &timingInfo, sizeof (retro_system_timing));
|
||||
timingInfoDirty = false;
|
||||
return true;
|
||||
}
|
||||
|
||||
// need some way to communicate with retro variables later
|
||||
|
||||
void SetDirectories(const char* systemDirectory, const char* saveDirectory, const char* coreDirectory, const char* coreAssetsDirectory) {
|
||||
|
@ -528,6 +563,12 @@ private:
|
|||
std::string retroMessageString;
|
||||
u32 retroMessageTime;
|
||||
|
||||
bool geoInfoDirty;
|
||||
retro_game_geometry geoInfo;
|
||||
|
||||
bool timingInfoDirty;
|
||||
retro_system_timing timingInfo;
|
||||
|
||||
bool variablesDirty;
|
||||
u32 variableCount;
|
||||
std::unique_ptr<std::string[]> variableKeys;
|
||||
|
@ -593,6 +634,20 @@ EXPORT void LibretroBridge_GetRetroMessage(CallbackHandler* cbHandler, retro_mes
|
|||
cbHandler->GetRetroMessage(m);
|
||||
}
|
||||
|
||||
// get current retro_game_geometry set by the core
|
||||
// returns false if no changes are needed for geometry info
|
||||
// geo is only valid if true is returned
|
||||
EXPORT bool LibretroBridge_GetRetroGeometryInfo(CallbackHandler* cbHandler, retro_game_geometry* geo) {
|
||||
return cbHandler->GetRetroGeometryInfo(geo);
|
||||
}
|
||||
|
||||
// get current retro_system_timing set by the core
|
||||
// returns false if no changes are needed for timing info
|
||||
// timing is only valid if true is returned
|
||||
EXPORT bool LibretroBridge_GetRetroTimingInfo(CallbackHandler* cbHandler, retro_system_timing* timing) {
|
||||
return cbHandler->GetRetroTimingInfo(timing);
|
||||
}
|
||||
|
||||
// set directories for the core
|
||||
EXPORT void LibretroBridge_SetDirectories(CallbackHandler* cbHandler, const char* systemDirectory, const char* saveDirectory, const char* coreDirectory, const char* coreAssetsDirectory) {
|
||||
cbHandler->SetDirectories(systemDirectory, saveDirectory, coreDirectory, coreAssetsDirectory);
|
||||
|
|
|
@ -11,6 +11,9 @@ typedef std::uint16_t u16;
|
|||
typedef std::uint32_t u32;
|
||||
typedef std::uint64_t u64;
|
||||
|
||||
typedef float f32;
|
||||
typedef double f64;
|
||||
|
||||
typedef u8 boolean;
|
||||
|
||||
#define EXPORT extern "C" __attribute__((visibility("default")))
|
||||
|
@ -355,6 +358,24 @@ enum class RETRO_LOG {
|
|||
DUMMY = INT_MAX,
|
||||
};
|
||||
|
||||
struct retro_game_geometry {
|
||||
u32 base_width;
|
||||
u32 base_height;
|
||||
u32 max_width;
|
||||
u32 max_height;
|
||||
f32 aspect_ratio;
|
||||
};
|
||||
|
||||
struct retro_system_timing {
|
||||
f64 fps;
|
||||
f64 sample_rate;
|
||||
};
|
||||
|
||||
struct retro_system_av_info {
|
||||
retro_game_geometry geometry;
|
||||
retro_system_timing timing;
|
||||
};
|
||||
|
||||
struct retro_variable {
|
||||
const char* key;
|
||||
const char* value;
|
||||
|
|
|
@ -326,20 +326,29 @@ namespace BizHawk.Emulation.Cores.Libretro
|
|||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct retro_system_av_info
|
||||
public struct retro_game_geometry
|
||||
{
|
||||
// struct retro_game_geometry
|
||||
public uint base_width;
|
||||
public uint base_height;
|
||||
public uint max_width;
|
||||
public uint max_height;
|
||||
public float aspect_ratio;
|
||||
}
|
||||
|
||||
// struct retro_system_timing
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct retro_system_timing
|
||||
{
|
||||
public double fps;
|
||||
public double sample_rate;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct retro_system_av_info
|
||||
{
|
||||
public retro_game_geometry geometry;
|
||||
public retro_system_timing timing;
|
||||
}
|
||||
|
||||
[BizImport(cc)]
|
||||
public abstract void retro_init();
|
||||
|
||||
|
@ -432,6 +441,12 @@ namespace BizHawk.Emulation.Cores.Libretro
|
|||
[BizImport(cc)]
|
||||
public abstract bool LibretroBridge_GetSupportsNoGame(IntPtr cbHandler);
|
||||
|
||||
[BizImport(cc)]
|
||||
public abstract bool LibretroBridge_GetRetroGeometryInfo(IntPtr cbHandler, ref LibretroApi.retro_game_geometry g);
|
||||
|
||||
[BizImport(cc)]
|
||||
public abstract bool LibretroBridge_GetRetroTimingInfo(IntPtr cbHandler, ref LibretroApi.retro_system_timing t);
|
||||
|
||||
[BizImport(cc)]
|
||||
public abstract void LibretroBridge_GetRetroMessage(IntPtr cbHandler, ref LibretroApi.retro_message m);
|
||||
|
||||
|
|
|
@ -210,13 +210,13 @@ namespace BizHawk.Emulation.Cores.Libretro
|
|||
//this stuff can only happen after the game is loaded
|
||||
|
||||
//allocate a video buffer which will definitely be large enough
|
||||
InitVideoBuffer((int)av.base_width, (int)av.base_height, (int)(av.max_width * av.max_height));
|
||||
InitVideoBuffer((int)av.geometry.base_width, (int)av.geometry.base_height, (int)(av.geometry.max_width * av.geometry.max_height));
|
||||
|
||||
// TODO: more precise
|
||||
VsyncNumerator = (int)(10000000 * av.fps);
|
||||
VsyncNumerator = (int)(10000000 * av.timing.fps);
|
||||
VsyncDenominator = 10000000;
|
||||
|
||||
SetupResampler(av.fps, av.sample_rate);
|
||||
SetupResampler(av.timing.fps, av.timing.sample_rate);
|
||||
|
||||
InitMemoryDomains(); // im going to assume this should happen when a game is loaded
|
||||
|
||||
|
@ -236,6 +236,18 @@ namespace BizHawk.Emulation.Cores.Libretro
|
|||
|
||||
private void FrameAdvancePost(bool render, bool renderSound)
|
||||
{
|
||||
if (bridge.LibretroBridge_GetRetroGeometryInfo(cbHandler, ref av_info.geometry))
|
||||
{
|
||||
vidBuffer = new int[av_info.geometry.max_width * av_info.geometry.max_height];
|
||||
}
|
||||
|
||||
if (bridge.LibretroBridge_GetRetroTimingInfo(cbHandler, ref av_info.timing))
|
||||
{
|
||||
VsyncNumerator = (int)(10000000 * av_info.timing.fps);
|
||||
_blipL.SetRates(av_info.timing.sample_rate, 44100);
|
||||
_blipR.SetRates(av_info.timing.sample_rate, 44100);
|
||||
}
|
||||
|
||||
if (render)
|
||||
{
|
||||
UpdateVideoBuffer();
|
||||
|
|
|
@ -27,7 +27,7 @@ namespace BizHawk.Emulation.Cores.Libretro
|
|||
{
|
||||
get
|
||||
{
|
||||
var dar = av_info.aspect_ratio;
|
||||
var dar = av_info.geometry.aspect_ratio;
|
||||
if (dar <= 0)
|
||||
{
|
||||
return vidWidth;
|
||||
|
@ -44,7 +44,7 @@ namespace BizHawk.Emulation.Cores.Libretro
|
|||
{
|
||||
get
|
||||
{
|
||||
var dar = av_info.aspect_ratio;
|
||||
var dar = av_info.geometry.aspect_ratio;
|
||||
if (dar <= 0)
|
||||
{
|
||||
return vidHeight;
|
||||
|
|
Loading…
Reference in New Issue