fix incorrect early uses of get_system_av_info (pre-load_game it is not valid)
This commit is contained in:
parent
a42aa936fe
commit
344d88f26b
|
@ -41,7 +41,9 @@ pub fn main() -> Result<(), Box<dyn std::error::Error>> {
|
|||
|
||||
let mut sdl_context = sdl2::init()?;
|
||||
|
||||
emu.register_component(StderrLogComponent { prefix: "{log} ".to_string() })?;
|
||||
let mut stderr_log = StderrLogComponent::default();
|
||||
stderr_log.prefix = "{log} ".to_string();
|
||||
emu.register_component(stderr_log)?;
|
||||
|
||||
// must register before opengl so it can have priority in queries about what N64 plugin to use
|
||||
// (only supports software-rendered 2D frames currently)
|
||||
|
@ -60,8 +62,7 @@ pub fn main() -> Result<(), Box<dyn std::error::Error>> {
|
|||
|
||||
emu.register_component(SimpleSdl2GamepadComponent::new(&mut sdl_context))?;
|
||||
|
||||
let sleep_fps = SleepFramerateLimitComponent::new(emu.libretro_core());
|
||||
emu.register_component(sleep_fps)?;
|
||||
emu.register_component(SleepFramerateLimitComponent::new())?;
|
||||
|
||||
emu.register_component(PathBufComponent {
|
||||
sys_path: opt.system.clone(),
|
||||
|
|
|
@ -54,25 +54,28 @@ impl RetroCallbacks for SimpleSdl2AudioComponent {
|
|||
}
|
||||
|
||||
impl RetroComponent for SimpleSdl2AudioComponent {
|
||||
fn post_load_game(&mut self, _retro: &mut LibretroWrapper, _rom: &Path) -> Result<(), Box<dyn Error>> {
|
||||
fn post_load_game(&mut self, retro: &mut LibretroWrapper, _rom: &Path) -> Result<(), Box<dyn Error>> {
|
||||
self.src_freq = retro.get_system_av_info().timing.sample_rate;
|
||||
self.queue.resume();
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn post_run(&mut self, _retro: &mut LibretroWrapper) -> ControlFlow {
|
||||
if let Ok(converter) = Self::make_converter(self.src_freq, self.queue.spec()) {
|
||||
let mut samples = std::mem::take(&mut self.audio_buffer);
|
||||
samples = resample(&converter, samples);
|
||||
self.audio_buffer = samples;
|
||||
self.queue.queue(&self.audio_buffer);
|
||||
self.audio_buffer.clear();
|
||||
if !self.audio_buffer.is_empty() {
|
||||
let mut samples = std::mem::take(&mut self.audio_buffer);
|
||||
samples = resample(&converter, samples);
|
||||
self.audio_buffer = samples;
|
||||
self.queue.queue(&self.audio_buffer);
|
||||
self.audio_buffer.clear();
|
||||
}
|
||||
}
|
||||
ControlFlow::Continue
|
||||
}
|
||||
}
|
||||
|
||||
impl SimpleSdl2AudioComponent {
|
||||
pub fn new(sdl_context: &mut Sdl, retro: &LibretroWrapper) -> Result<Self, Box<dyn std::error::Error>> {
|
||||
pub fn new(sdl_context: &mut Sdl, _retro: &LibretroWrapper) -> Result<Self, Box<dyn std::error::Error>> {
|
||||
let audio = sdl_context.audio().unwrap();
|
||||
let desired_spec = AudioSpecDesired {
|
||||
freq: None,
|
||||
|
@ -82,12 +85,8 @@ impl SimpleSdl2AudioComponent {
|
|||
|
||||
let queue = AudioQueue::open_queue(&audio, None, &desired_spec)?;
|
||||
|
||||
let mut src_freq = retro.get_system_av_info().timing.sample_rate;
|
||||
// HACK: some cores don't report this 'til we get an env call to set_system_av_info,
|
||||
// so we can just default to the old libsnes default value.
|
||||
if src_freq == 0.0 {
|
||||
src_freq = 32040.5;
|
||||
}
|
||||
// default to the old libsnes default value until after load_game or set_system_av_info.
|
||||
let src_freq = 32040.5;
|
||||
|
||||
Ok(SimpleSdl2AudioComponent {
|
||||
src_freq,
|
||||
|
|
|
@ -6,6 +6,7 @@ use std::os::raw::c_uint;
|
|||
use sdl2::Sdl;
|
||||
use sdl2::rect::Rect;
|
||||
use sdl2::render::WindowCanvas;
|
||||
use std::path::Path;
|
||||
|
||||
/// Create a root window in SDL2 with an OpenGL context and attaches libretro's
|
||||
/// `hw_get_proc_address` calls to that of the [sdl2::VideoSubsystem].
|
||||
|
@ -34,12 +35,12 @@ impl SimpleSdl2OpenglComponent {
|
|||
unsafe { CStr::from_ptr(sys_info.library_name) }.to_string_lossy()
|
||||
);
|
||||
|
||||
let geometry = retro.get_system_av_info().geometry;
|
||||
let pixel_format = sdl2::pixels::PixelFormatEnum::ARGB1555;
|
||||
|
||||
let video = sdl_context.video()?;
|
||||
// default to old libsnes 256x224 window size until load_game (prereq of get_system_av_info)
|
||||
let window = video
|
||||
.window(title.as_str(), geometry.base_width, geometry.base_height)
|
||||
.window(title.as_str(), 256, 224)
|
||||
.opengl()
|
||||
.build()?;
|
||||
|
||||
|
@ -90,7 +91,13 @@ impl SimpleSdl2OpenglComponent {
|
|||
}
|
||||
}
|
||||
|
||||
impl RetroComponent for SimpleSdl2OpenglComponent {}
|
||||
impl RetroComponent for SimpleSdl2OpenglComponent {
|
||||
fn post_load_game(&mut self, retro: &mut LibretroWrapper, _rom: &Path) -> crate::base::Result<()> {
|
||||
self.set_geometry(&retro.get_system_av_info().geometry);
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
impl RetroCallbacks for SimpleSdl2OpenglComponent {
|
||||
fn video_refresh(&mut self, frame: &VideoFrame) {
|
||||
match frame {
|
||||
|
|
|
@ -2,6 +2,7 @@ use crate::base::ControlFlow;
|
|||
use crate::prelude::*;
|
||||
|
||||
use std::time::{Duration, Instant};
|
||||
use std::path::Path;
|
||||
|
||||
/// Uses [std::thread::sleep] to maintain the target FPS specified by the core.
|
||||
///
|
||||
|
@ -14,6 +15,10 @@ pub struct SleepFramerateLimitComponent {
|
|||
}
|
||||
|
||||
impl RetroComponent for SleepFramerateLimitComponent {
|
||||
fn post_load_game(&mut self, retro: &mut LibretroWrapper, _rom: &Path) -> crate::base::Result<()> {
|
||||
self.fps = retro.get_system_av_info().timing.fps;
|
||||
Ok(())
|
||||
}
|
||||
fn pre_run(&mut self, _retro: &mut LibretroWrapper) -> ControlFlow {
|
||||
self.did_sleep = false;
|
||||
ControlFlow::Continue
|
||||
|
@ -38,11 +43,11 @@ impl RetroCallbacks for SleepFramerateLimitComponent {
|
|||
}
|
||||
|
||||
impl SleepFramerateLimitComponent {
|
||||
pub fn new(retro: &mut LibretroWrapper) -> Self {
|
||||
pub fn new() -> Self {
|
||||
SleepFramerateLimitComponent {
|
||||
did_sleep: false,
|
||||
started_video: false,
|
||||
fps: retro.get_system_av_info().timing.fps,
|
||||
fps: 60.0, // default until load_game
|
||||
frame_begin: Instant::now(),
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,17 +6,29 @@ use std::os::raw::c_uint;
|
|||
use std::path::PathBuf;
|
||||
|
||||
/// Write's the core's own log statements to stderr.
|
||||
#[derive(Default)]
|
||||
pub struct StderrLogComponent {
|
||||
/// May be set to add a prefix to each logged line.
|
||||
pub prefix: String,
|
||||
/// The most verbose log level that should be printed.
|
||||
pub level: ferretro_base::retro::ffi::LogLevel,
|
||||
}
|
||||
|
||||
impl Default for StderrLogComponent {
|
||||
fn default() -> Self {
|
||||
StderrLogComponent {
|
||||
prefix: String::new(),
|
||||
level: ferretro_base::retro::ffi::LogLevel::Info,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl RetroComponent for StderrLogComponent {}
|
||||
|
||||
impl RetroCallbacks for StderrLogComponent {
|
||||
fn log_print(&mut self, level: ferretro_base::retro::ffi::LogLevel, msg: &str) {
|
||||
eprint!("{}[{:?}] {}", self.prefix, level, msg);
|
||||
if level >= self.level {
|
||||
eprint!("{}[{:?}] {}", self.prefix, level, msg);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue