Skip to content
Closed
Show file tree
Hide file tree
Changes from 4 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,10 @@

## [Unreleased] - ReleaseDate

### Changed

- [#48] Allowed for multiple window to co-exist in the same application.

## [0.6.0] - 2023-11-26

### Changed
Expand Down
87 changes: 67 additions & 20 deletions src/window/sdl_window.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,24 @@ use sdl2::{

use crate::{OutputImage, OutputSettings, SimulatorDisplay};

struct SdlContext {
video_subsystem: sdl2::VideoSubsystem,
event_pump: EventPump,
}

thread_local! {
static SDL_CONTEXT: std::cell::RefCell<SdlContext> = {
let sdl_context = sdl2::init().unwrap();
let video_subsystem = sdl_context.video().unwrap();
let event_pump = sdl_context.event_pump().unwrap();

std::cell::RefCell::new(SdlContext {
video_subsystem,
event_pump,
})
};
}

/// A derivation of [`sdl2::event::Event`] mapped to embedded-graphics coordinates
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
pub enum SimulatorEvent {
Expand Down Expand Up @@ -67,7 +85,6 @@ pub enum SimulatorEvent {

pub struct SdlWindow {
canvas: Canvas<sdl2::video::Window>,
event_pump: EventPump,
window_texture: SdlWindowTexture,
size: Size,
}
Expand All @@ -81,19 +98,18 @@ impl SdlWindow {
where
C: PixelColor + Into<Rgb888>,
{
let sdl_context = sdl2::init().unwrap();
let video_subsystem = sdl_context.video().unwrap();

let size = output_settings.framebuffer_size(display);

let window = video_subsystem
.window(title, size.width, size.height)
.position_centered()
.build()
.unwrap();
let window = SDL_CONTEXT.with(|ctx| {
ctx.borrow_mut()
.video_subsystem
.window(title, size.width, size.height)
.position_centered()
.build()
.unwrap()
});

let canvas = window.into_canvas().build().unwrap();
let event_pump = sdl_context.event_pump().unwrap();

let window_texture = SdlWindowTextureBuilder {
texture_creator: canvas.texture_creator(),
Expand All @@ -107,7 +123,6 @@ impl SdlWindow {

Self {
canvas,
event_pump,
window_texture,
size,
}
Expand Down Expand Up @@ -138,8 +153,12 @@ impl SdlWindow {
output_settings: &OutputSettings,
) -> impl Iterator<Item = SimulatorEvent> + '_ {
let output_settings = output_settings.clone();
self.event_pump
.poll_iter()
let events: Vec<Event> =
SDL_CONTEXT.with(|ctx| ctx.borrow_mut().event_pump.poll_iter().collect());
let window_id = self.canvas.window().id();
events
.into_iter()
.filter(move |e| e.get_window_id() == Some(window_id) || e.get_window_id().is_none())
.filter_map(move |event| match event {
Event::Quit { .. }
| Event::KeyDown {
Expand Down Expand Up @@ -179,24 +198,52 @@ impl SdlWindow {
}
}
Event::MouseButtonUp {
x, y, mouse_btn, ..
x,
y,
mouse_btn,
window_id,
..
} => {
if window_id != window_id {
return None;
}
let point = output_settings.output_to_display(Point::new(x, y));
Some(SimulatorEvent::MouseButtonUp { point, mouse_btn })
}
Event::MouseButtonDown {
x, y, mouse_btn, ..
x,
y,
mouse_btn,
window_id,
..
} => {
if window_id != window_id {
return None;
}
let point = output_settings.output_to_display(Point::new(x, y));
Some(SimulatorEvent::MouseButtonDown { point, mouse_btn })
}
Event::MouseWheel {
x, y, direction, ..
} => Some(SimulatorEvent::MouseWheel {
scroll_delta: Point::new(x, y),
x,
y,
direction,
}),
Event::MouseMotion { x, y, .. } => {
window_id,
..
} => {
if window_id != window_id {
return None;
}
Some(SimulatorEvent::MouseWheel {
scroll_delta: Point::new(x, y),
direction,
})
}
Event::MouseMotion {
x, y, window_id, ..
} => {
if window_id != window_id {
return None;
}
let point = output_settings.output_to_display(Point::new(x, y));
Some(SimulatorEvent::MouseMove { point })
}
Expand Down