use anyhow::Result;
use gpui_engine::GpuRenderer;
use gpui_platform::{DevicePixels, GpuSpecs, PlatformRenderer, RendererTarget, Size};
#[cfg(target_os = "windows")]
use gpui_platform::{WinSceneRenderer, WindowBackgroundAppearance};
use raw_window_handle::{
DisplayHandle, HandleError, HasDisplayHandle, HasWindowHandle, RawDisplayHandle,
RawWindowHandle, WindowHandle,
};
use crate::WgpuRenderer;
impl PlatformRenderer for WgpuRenderer {
fn update_drawable_size(&mut self, size: Size<DevicePixels>) {
WgpuRenderer::update_drawable_size(self, size);
}
fn max_texture_size(&self) -> u32 {
WgpuRenderer::max_texture_size(self)
}
fn gpu_specs(&self) -> Option<GpuSpecs> {
WgpuRenderer::gpu_specs(self)
}
fn set_subpixel_layout(&mut self, is_bgr: bool) {
WgpuRenderer::set_subpixel_layout(self, is_bgr);
}
fn update_transparency(&mut self, transparent: bool) {
WgpuRenderer::update_transparency(self, transparent);
}
fn destroy(&mut self) {
WgpuRenderer::destroy(self);
}
fn device_lost(&self) -> bool {
WgpuRenderer::device_lost(self)
}
fn needs_redraw(&mut self) -> bool {
WgpuRenderer::needs_redraw(self)
}
fn recover(&mut self, target: RendererTarget<'_>) -> Result<()> {
let window = RawWindowHandles::from_target(&target)?;
WgpuRenderer::recover(self, &window)
}
}
impl GpuRenderer for WgpuRenderer {
type Device = (std::sync::Arc<wgpu::Device>, std::sync::Arc<wgpu::Queue>);
fn device(&self) -> Option<Self::Device> {
let context = WgpuRenderer::gpu_context(self)?;
let context = context.borrow();
let context = context.as_ref()?;
Some((context.device.clone(), context.queue.clone()))
}
}
#[cfg(target_os = "windows")]
impl WinSceneRenderer for WgpuRenderer {
fn set_background_appearance(&mut self, _appearance: WindowBackgroundAppearance) {}
fn resize(&mut self, size: Size<DevicePixels>) -> Result<()> {
WgpuRenderer::update_drawable_size(self, size);
Ok(())
}
}
#[derive(Debug, Clone, Copy)]
struct RawWindowHandles {
window: RawWindowHandle,
display: RawDisplayHandle,
}
unsafe impl Send for RawWindowHandles {}
unsafe impl Sync for RawWindowHandles {}
impl RawWindowHandles {
fn from_target(target: &RendererTarget<'_>) -> Result<Self> {
Ok(Self {
window: target
.window_handle
.ok_or_else(|| anyhow::anyhow!("renderer target has no window handle"))?,
display: target
.display_handle
.ok_or_else(|| anyhow::anyhow!("renderer target has no display handle"))?,
})
}
}
impl HasWindowHandle for RawWindowHandles {
fn window_handle(&self) -> std::result::Result<WindowHandle<'_>, HandleError> {
Ok(unsafe { WindowHandle::borrow_raw(self.window) })
}
}
impl HasDisplayHandle for RawWindowHandles {
fn display_handle(&self) -> std::result::Result<DisplayHandle<'_>, HandleError> {
Ok(unsafe { DisplayHandle::borrow_raw(self.display) })
}
}