diff --git a/render/wgpu/src/backend.rs b/render/wgpu/src/backend.rs index 68c8a11c8..29964205f 100644 --- a/render/wgpu/src/backend.rs +++ b/render/wgpu/src/backend.rs @@ -1,5 +1,3 @@ -use crate::commands::CommandRenderer; -use crate::frame::Frame; use crate::surface::Surface; use crate::target::RenderTargetFrame; use crate::target::TextureTarget; @@ -7,8 +5,7 @@ use crate::uniform_buffer::BufferStorage; use crate::{ create_buffer_with_data, format_list, get_backend_names, BufferDimensions, Descriptors, Draw, DrawType, Error, Globals, GradientStorage, GradientUniforms, Mesh, RegistryData, RenderTarget, - SwapChainTarget, Texture, TextureOffscreen, TextureTransforms, Transforms, UniformBuffer, - Vertex, + SwapChainTarget, Texture, TextureOffscreen, TextureTransforms, Transforms, Vertex, }; use fnv::FnvHashMap; use ruffle_render::backend::{RenderBackend, ShapeHandle, ViewportDimensions}; @@ -544,83 +541,23 @@ impl RenderBackend for WgpuRenderBackend { } }; - let label = create_debug_label!("Draw encoder"); - let mut draw_encoder = - self.descriptors - .device - .create_command_encoder(&wgpu::CommandEncoderDescriptor { - label: label.as_deref(), - }); - - let uniform_encoder_label = create_debug_label!("Uniform upload command encoder"); - let mut uniform_encoder = - self.descriptors - .device - .create_command_encoder(&wgpu::CommandEncoderDescriptor { - label: uniform_encoder_label.as_deref(), - }); - - self.globals - .update_uniform(&self.descriptors.device, &mut draw_encoder); - - let mut render_pass = draw_encoder.begin_render_pass(&wgpu::RenderPassDescriptor { - color_attachments: &[Some(wgpu::RenderPassColorAttachment { - view: self.surface.view(frame_output.view()), - ops: wgpu::Operations { - load: wgpu::LoadOp::Clear(wgpu::Color { - r: f64::from(clear.r) / 255.0, - g: f64::from(clear.g) / 255.0, - b: f64::from(clear.b) / 255.0, - a: f64::from(clear.a) / 255.0, - }), - store: true, - }, - resolve_target: self.surface.resolve_target(frame_output.view()), - })], - depth_stencil_attachment: Some(wgpu::RenderPassDepthStencilAttachment { - view: self.surface.depth(), - depth_ops: Some(wgpu::Operations { - load: wgpu::LoadOp::Clear(0.0), - store: false, - }), - stencil_ops: Some(wgpu::Operations { - load: wgpu::LoadOp::Clear(0), - store: true, - }), - }), - label: None, - }); - render_pass.set_bind_group(0, self.globals.bind_group(), &[]); - self.uniform_buffers_storage.recall(); - let mut frame = Frame::new( - &self.descriptors.onscreen.pipelines, + let command_buffers = self.surface.draw_commands( + frame_output.view(), + wgpu::Color { + r: f64::from(clear.r) / 255.0, + g: f64::from(clear.g) / 255.0, + b: f64::from(clear.b) / 255.0, + a: f64::from(clear.a) / 255.0, + }, &self.descriptors, - UniformBuffer::new(&mut self.uniform_buffers_storage), - render_pass, - &mut uniform_encoder, - ); - commands.execute(&mut CommandRenderer::new( - &mut frame, + &mut self.globals, + &self.descriptors.onscreen.pipelines, + &mut self.uniform_buffers_storage, &self.meshes, &self.bitmap_registry, - self.descriptors.quad.vertices.slice(..), - self.descriptors.quad.indices.slice(..), - )); - frame.finish(); - - let copy_encoder = self.surface.copy_srgb( - &frame_output, - &self.descriptors, - &self.globals, - &mut self.uniform_buffers_storage, - &mut uniform_encoder, + commands, ); - let mut command_buffers = vec![uniform_encoder.finish(), draw_encoder.finish()]; - if let Some(copy_encoder) = copy_encoder { - command_buffers.push(copy_encoder); - } - self.target.submit( &self.descriptors.device, &self.descriptors.queue, @@ -851,83 +788,32 @@ impl RenderBackend for WgpuRenderBackend { }; let (old_width, old_height) = self.globals.resolution(); + self.globals.set_resolution(width, height); let frame_output = target .get_next_texture() .expect("TextureTargetFrame.get_next_texture is infallible"); - let label = create_debug_label!("Draw encoder"); - let mut draw_encoder = - self.descriptors - .device - .create_command_encoder(&wgpu::CommandEncoderDescriptor { - label: label.as_deref(), - }); - - let uniform_encoder_label = create_debug_label!("Uniform upload command encoder"); - let mut uniform_encoder = - self.descriptors - .device - .create_command_encoder(&wgpu::CommandEncoderDescriptor { - label: uniform_encoder_label.as_deref(), - }); - - self.globals.set_resolution(width, height); - self.globals - .update_uniform(&self.descriptors.device, &mut draw_encoder); - - let mut render_pass = draw_encoder.begin_render_pass(&wgpu::RenderPassDescriptor { - color_attachments: &[Some(wgpu::RenderPassColorAttachment { - view: texture_offscreen.surface.view(frame_output.view()), - ops: wgpu::Operations { - load: wgpu::LoadOp::Clear(wgpu::Color { - r: f64::from(clear_color.r) / 255.0, - g: f64::from(clear_color.g) / 255.0, - b: f64::from(clear_color.b) / 255.0, - a: f64::from(clear_color.a) / 255.0, - }), - store: true, - }, - resolve_target: texture_offscreen - .surface - .resolve_target(frame_output.view()), - })], - depth_stencil_attachment: Some(wgpu::RenderPassDepthStencilAttachment { - view: texture_offscreen.surface.depth(), - depth_ops: Some(wgpu::Operations { - load: wgpu::LoadOp::Clear(0.0), - store: false, - }), - stencil_ops: Some(wgpu::Operations { - load: wgpu::LoadOp::Clear(0), - store: true, - }), - }), - label: None, - }); - render_pass.set_bind_group(0, self.globals.bind_group(), &[]); - - self.uniform_buffers_storage.recall(); - let mut frame = Frame::new( - &self.descriptors.offscreen.pipelines, + let command_buffers = texture_offscreen.surface.draw_commands( + frame_output.view(), + wgpu::Color { + r: f64::from(clear_color.r) / 255.0, + g: f64::from(clear_color.g) / 255.0, + b: f64::from(clear_color.b) / 255.0, + a: f64::from(clear_color.a) / 255.0, + }, &self.descriptors, - UniformBuffer::new(&mut self.uniform_buffers_storage), - render_pass, - &mut uniform_encoder, - ); - commands.execute(&mut CommandRenderer::new( - &mut frame, + &mut self.globals, + &self.descriptors.offscreen.pipelines, + &mut self.uniform_buffers_storage, &self.meshes, &self.bitmap_registry, - self.descriptors.quad.vertices.slice(..), - self.descriptors.quad.indices.slice(..), - )); - frame.finish(); - + commands, + ); target.submit( &self.descriptors.device, &self.descriptors.queue, - vec![uniform_encoder.finish(), draw_encoder.finish()], + command_buffers, frame_output, ); diff --git a/render/wgpu/src/surface.rs b/render/wgpu/src/surface.rs index 471555784..2775ced6c 100644 --- a/render/wgpu/src/surface.rs +++ b/render/wgpu/src/surface.rs @@ -1,13 +1,16 @@ +use crate::commands::CommandRenderer; use crate::descriptors::Quad; use crate::frame::Frame; use crate::layouts::BindLayouts; use crate::surface::Surface::{Direct, DirectSrgb, Resolve, ResolveSrgb}; -use crate::target::RenderTargetFrame; use crate::uniform_buffer::BufferStorage; use crate::{ - create_buffer_with_data, ColorAdjustments, Descriptors, Globals, TextureTransforms, Transforms, - UniformBuffer, + create_buffer_with_data, ColorAdjustments, Descriptors, Globals, Mesh, Pipelines, RegistryData, + TextureTransforms, Transforms, UniformBuffer, }; +use fnv::FnvHashMap; +use ruffle_render::bitmap::BitmapHandle; +use ruffle_render::commands::CommandList; #[derive(Debug)] pub struct FrameBuffer { @@ -309,9 +312,9 @@ impl Surface { } } - pub fn copy_srgb( + pub fn copy_srgb( &self, - frame: &T, + frame: &wgpu::TextureView, descriptors: &Descriptors, globals: &Globals, uniform_buffers_storage: &mut BufferStorage, @@ -320,7 +323,7 @@ impl Surface { match self { Direct { .. } => None, DirectSrgb { srgb, .. } => Some(srgb.copy_srgb( - frame.view(), + frame, descriptors, globals, uniform_buffers_storage, @@ -328,7 +331,7 @@ impl Surface { )), Resolve { .. } => None, ResolveSrgb { srgb, .. } => Some(srgb.copy_srgb( - frame.view(), + frame, descriptors, globals, uniform_buffers_storage, @@ -336,4 +339,92 @@ impl Surface { )), } } + + #[allow(clippy::too_many_arguments)] + pub fn draw_commands( + &self, + frame_view: &wgpu::TextureView, + clear_color: wgpu::Color, + descriptors: &Descriptors, + globals: &mut Globals, + pipelines: &Pipelines, + uniform_buffers_storage: &mut BufferStorage, + meshes: &Vec, + bitmap_registry: &FnvHashMap, + commands: CommandList, + ) -> Vec { + let label = create_debug_label!("Draw encoder"); + let mut draw_encoder = + descriptors + .device + .create_command_encoder(&wgpu::CommandEncoderDescriptor { + label: label.as_deref(), + }); + + let uniform_encoder_label = create_debug_label!("Uniform upload command encoder"); + let mut uniform_encoder = + descriptors + .device + .create_command_encoder(&wgpu::CommandEncoderDescriptor { + label: uniform_encoder_label.as_deref(), + }); + + globals.update_uniform(&descriptors.device, &mut draw_encoder); + + let mut render_pass = draw_encoder.begin_render_pass(&wgpu::RenderPassDescriptor { + color_attachments: &[Some(wgpu::RenderPassColorAttachment { + view: self.view(frame_view), + ops: wgpu::Operations { + load: wgpu::LoadOp::Clear(clear_color), + store: true, + }, + resolve_target: self.resolve_target(frame_view), + })], + depth_stencil_attachment: Some(wgpu::RenderPassDepthStencilAttachment { + view: self.depth(), + depth_ops: Some(wgpu::Operations { + load: wgpu::LoadOp::Clear(0.0), + store: false, + }), + stencil_ops: Some(wgpu::Operations { + load: wgpu::LoadOp::Clear(0), + store: true, + }), + }), + label: None, + }); + render_pass.set_bind_group(0, globals.bind_group(), &[]); + + uniform_buffers_storage.recall(); + let mut frame = Frame::new( + &pipelines, + &descriptors, + UniformBuffer::new(uniform_buffers_storage), + render_pass, + &mut uniform_encoder, + ); + commands.execute(&mut CommandRenderer::new( + &mut frame, + meshes, + bitmap_registry, + descriptors.quad.vertices.slice(..), + descriptors.quad.indices.slice(..), + )); + frame.finish(); + + let copy_encoder = self.copy_srgb( + &frame_view, + &descriptors, + &globals, + uniform_buffers_storage, + &mut uniform_encoder, + ); + + let mut command_buffers = vec![uniform_encoder.finish(), draw_encoder.finish()]; + if let Some(copy_encoder) = copy_encoder { + command_buffers.push(copy_encoder); + } + + command_buffers + } }