Skip to content

Commit

Permalink
Merge pull request #67 from alloncm/feature/full_screen
Browse files Browse the repository at this point in the history
Add fullscreen option
  • Loading branch information
alloncm authored Nov 25, 2021
2 parents fd01e3c + cabe5bf commit df43c1f
Show file tree
Hide file tree
Showing 4 changed files with 53 additions and 21 deletions.
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ magenboy [path_to_rom] [other_optional_flags]

* `--log` - Print logs in debug mode to a file
* `--file-audio` - Saves the audio to a file
* `--full-screen` - Full screen mode
* `--no-vsync` - Disable vsync
* `--bootrom [path to bootrom file]` - Specify the path for a bootrom (If not specified the emualtor will look for `dmg_boot.bin` at the cwd)

Expand Down
3 changes: 2 additions & 1 deletion gb/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -23,4 +23,5 @@ cfg-if = "1.0"
default = ["static-sdl"]
sdl-resample = []
push-audio = []
static-sdl = ["sdl2/bundled", "sdl2/static-link"]
static-sdl = ["sdl2/bundled", "sdl2/static-link"]
static-scale = []
8 changes: 4 additions & 4 deletions gb/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ use std::{fs, env, result::Result, vec::Vec};
use log::info;
use sdl2::sys::*;

const SCREEN_SCALE:u8 = 4;
const SCREEN_SCALE:usize = 4;
const TURBO_MUL:u8 = 1;

fn init_logger(debug:bool)->Result<(), fern::InitError>{
Expand All @@ -19,7 +19,7 @@ fn init_logger(debug:bool)->Result<(), fern::InitError>{
.format(|out, message, record| {
out.finish(format_args!(
"{}[{}] {}",
chrono::Local::now().format("[%Y-%m-%d][%H:%M:%S]"),
chrono::Local::now().format("[%Y-%m-%d][%H:%M:%S.%f]"),
record.level(),
message
))
Expand Down Expand Up @@ -65,8 +65,8 @@ fn main() {
Result::Err(error)=>std::panic!("error initing logger: {}", error)
}

let mut sdl_gfx_device = sdl_gfx_device::SdlGfxDevice::new(SCREEN_WIDTH as u32, SCREEN_HEIGHT as u32,
"MagenBoy", SCREEN_SCALE, TURBO_MUL, check_for_terminal_feature_flag(&args, "--no-vsync"));
let mut sdl_gfx_device = sdl_gfx_device::SdlGfxDevice::new("MagenBoy", SCREEN_SCALE, TURBO_MUL,
check_for_terminal_feature_flag(&args, "--no-vsync"), check_for_terminal_feature_flag(&args, "--full-screen"));

let (s,r) = crossbeam_channel::bounded(BUFFERS_NUMBER - 1);
let mpmc_device = MpmcGfxDevice::new(s);
Expand Down
62 changes: 46 additions & 16 deletions gb/src/sdl_gfx_device.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,33 +7,62 @@ pub struct SdlGfxDevice{
_window_name: CString,
renderer: *mut SDL_Renderer,
texture: *mut SDL_Texture,
width:u32,
height:u32,
sacle:u8,
discard:u8,
turbo_mul:u8,
#[cfg(feature = "static-scale")]
screen_scale:usize,
}

impl SdlGfxDevice{
pub fn new(buffer_width:u32, buffer_height:u32, window_name:&str, screen_scale: u8, turbo_mul:u8, disable_vsync:bool)->Self{
pub fn new(window_name:&str, screen_scale: usize, turbo_mul:u8, disable_vsync:bool, full_screen:bool)->Self{
let cs_wnd_name = CString::new(window_name).unwrap();

let (_window, renderer, texture): (*mut SDL_Window, *mut SDL_Renderer, *mut SDL_Texture) = unsafe{
SDL_Init(SDL_INIT_VIDEO);

let window_flags = if full_screen{
#[cfg(feature = "static-scale")]
log::warn!("Please notice that this binary have been compiled with the static-scale feature and you are running with the full screen option.\nThe rendering window might be in wrong scale.");

SDL_WindowFlags::SDL_WINDOW_FULLSCREEN_DESKTOP as u32
}
else{
0
};

let wind:*mut SDL_Window = SDL_CreateWindow(
cs_wnd_name.as_ptr(),
SDL_WINDOWPOS_UNDEFINED_MASK as i32, SDL_WINDOWPOS_UNDEFINED_MASK as i32,
buffer_width as i32 * screen_scale as i32, buffer_height as i32 * screen_scale as i32, 0);
let mut flags = SDL_RendererFlags::SDL_RENDERER_ACCELERATED as u32;
SCREEN_WIDTH as i32 * screen_scale as i32, SCREEN_HEIGHT as i32 * screen_scale as i32,
window_flags);

let mut render_flags = SDL_RendererFlags::SDL_RENDERER_ACCELERATED as u32;
if !disable_vsync{
flags |= SDL_RendererFlags::SDL_RENDERER_PRESENTVSYNC as u32;
render_flags |= SDL_RendererFlags::SDL_RENDERER_PRESENTVSYNC as u32;
}

let rend: *mut SDL_Renderer = SDL_CreateRenderer(wind, -1, flags);
let rend: *mut SDL_Renderer = SDL_CreateRenderer(wind, -1, render_flags);

let texture_width:i32;
let texture_height:i32;

cfg_if::cfg_if!{
if #[cfg(feature = "static-scale")]{
texture_height = SCREEN_HEIGHT as i32 * screen_scale as i32;
texture_width = SCREEN_WIDTH as i32 * screen_scale as i32;
}
else{
if SDL_RenderSetLogicalSize(rend, (SCREEN_WIDTH as u32) as i32, (SCREEN_HEIGHT as u32) as i32) != 0{
std::panic!("Error while setting logical rendering");
}
texture_height = SCREEN_HEIGHT as i32;
texture_width = SCREEN_WIDTH as i32;
}
}

let tex: *mut SDL_Texture = SDL_CreateTexture(rend,
SDL_PixelFormatEnum::SDL_PIXELFORMAT_ARGB8888 as u32, SDL_TextureAccess::SDL_TEXTUREACCESS_STREAMING as i32,
buffer_width as i32 * screen_scale as i32, buffer_height as i32 * screen_scale as i32);
texture_width, texture_height);

(wind, rend, tex)
};
Expand All @@ -42,14 +71,14 @@ impl SdlGfxDevice{
_window_name: cs_wnd_name,
renderer,
texture,
height:buffer_height,
width:buffer_width,
sacle:screen_scale,
discard:0,
turbo_mul
turbo_mul,
#[cfg(feature = "static-scale")]
screen_scale
}
}

#[cfg(feature = "static-scale")]
fn extend_vec(vec:&[u32], scale:usize, w:usize, h:usize)->Vec<u32>{
let mut new_vec = vec![0;vec.len()*scale*scale];
for y in 0..h{
Expand All @@ -74,13 +103,14 @@ impl GfxDevice for SdlGfxDevice{
return;
}

unsafe{
let extended_buffer = Self::extend_vec(buffer, self.sacle as usize, self.width as usize, self.height as usize);
#[cfg(feature = "static-scale")]
let buffer = Self::extend_vec(buffer, self.screen_scale, SCREEN_WIDTH, SCREEN_HEIGHT);

unsafe{
let mut pixels: *mut c_void = std::ptr::null_mut();
let mut length: std::os::raw::c_int = 0;
SDL_LockTexture(self.texture, std::ptr::null(), &mut pixels, &mut length);
std::ptr::copy_nonoverlapping(extended_buffer.as_ptr(),pixels as *mut u32, extended_buffer.len());
std::ptr::copy_nonoverlapping(buffer.as_ptr(),pixels as *mut u32, buffer.len());
SDL_UnlockTexture(self.texture);

//There is no need to call SDL_RenderClear since im replacing the whole buffer
Expand Down

0 comments on commit df43c1f

Please sign in to comment.