diff options
| author | 2023-06-29 08:09:45 +0200 | |
|---|---|---|
| committer | 2023-06-29 08:09:45 +0200 | |
| commit | c6b583113da7c9d9ceaeb5a3bf676ae62d8931e1 (patch) | |
| tree | ed833fab41f64c57a7522fea400ea42eec788e9f /wgpu | |
| parent | 8d65e40a1174ecb8225ce9973575bced36e7aeb5 (diff) | |
| parent | 6921564c9f66e8103e19ec658099c5f5c32e8cc5 (diff) | |
| download | iced-c6b583113da7c9d9ceaeb5a3bf676ae62d8931e1.tar.gz iced-c6b583113da7c9d9ceaeb5a3bf676ae62d8931e1.tar.bz2 iced-c6b583113da7c9d9ceaeb5a3bf676ae62d8931e1.zip | |
Merge pull request #1932 from iced-rs/generic-graphics-primitive
Backend-specific primitives
Diffstat (limited to 'wgpu')
| -rw-r--r-- | wgpu/src/backend.rs | 7 | ||||
| -rw-r--r-- | wgpu/src/geometry.rs | 66 | ||||
| -rw-r--r-- | wgpu/src/layer.rs | 93 | ||||
| -rw-r--r-- | wgpu/src/layer/mesh.rs | 6 | ||||
| -rw-r--r-- | wgpu/src/lib.rs | 2 | ||||
| -rw-r--r-- | wgpu/src/primitive.rs | 21 | ||||
| -rw-r--r-- | wgpu/src/triangle.rs | 75 | ||||
| -rw-r--r-- | wgpu/src/window/compositor.rs | 4 | 
8 files changed, 159 insertions, 115 deletions
| diff --git a/wgpu/src/backend.rs b/wgpu/src/backend.rs index f8829e47..596d43c5 100644 --- a/wgpu/src/backend.rs +++ b/wgpu/src/backend.rs @@ -2,7 +2,8 @@ use crate::core;  use crate::core::{Color, Font, Point, Size};  use crate::graphics::backend;  use crate::graphics::color; -use crate::graphics::{Primitive, Transformation, Viewport}; +use crate::graphics::{Transformation, Viewport}; +use crate::primitive::{self, Primitive};  use crate::quad;  use crate::text;  use crate::triangle; @@ -334,6 +335,10 @@ impl Backend {      }  } +impl crate::graphics::Backend for Backend { +    type Primitive = primitive::Custom; +} +  impl backend::Text for Backend {      const ICON_FONT: Font = Font::with_name("Iced-Icons");      const CHECKMARK_ICON: char = '\u{f00c}'; diff --git a/wgpu/src/geometry.rs b/wgpu/src/geometry.rs index f81b5b2f..e421e0b0 100644 --- a/wgpu/src/geometry.rs +++ b/wgpu/src/geometry.rs @@ -5,10 +5,10 @@ use crate::graphics::geometry::fill::{self, Fill};  use crate::graphics::geometry::{      LineCap, LineDash, LineJoin, Path, Stroke, Style, Text,  }; -use crate::graphics::primitive::{self, Primitive}; -use crate::graphics::Gradient; +use crate::graphics::gradient::{self, Gradient}; +use crate::graphics::mesh::{self, Mesh}; +use crate::primitive::{self, Primitive}; -use iced_graphics::gradient;  use lyon::geom::euclid;  use lyon::tessellation;  use std::borrow::Cow; @@ -25,8 +25,8 @@ pub struct Frame {  }  enum Buffer { -    Solid(tessellation::VertexBuffers<primitive::ColoredVertex2D, u32>), -    Gradient(tessellation::VertexBuffers<primitive::GradientVertex2D, u32>), +    Solid(tessellation::VertexBuffers<mesh::SolidVertex2D, u32>), +    Gradient(tessellation::VertexBuffers<mesh::GradientVertex2D, u32>),  }  struct BufferStack { @@ -464,24 +464,28 @@ impl Frame {              match buffer {                  Buffer::Solid(buffer) => {                      if !buffer.indices.is_empty() { -                        self.primitives.push(Primitive::SolidMesh { -                            buffers: primitive::Mesh2D { -                                vertices: buffer.vertices, -                                indices: buffer.indices, -                            }, -                            size: self.size, -                        }) +                        self.primitives.push(Primitive::Custom( +                            primitive::Custom::Mesh(Mesh::Solid { +                                buffers: mesh::Indexed { +                                    vertices: buffer.vertices, +                                    indices: buffer.indices, +                                }, +                                size: self.size, +                            }), +                        ))                      }                  }                  Buffer::Gradient(buffer) => {                      if !buffer.indices.is_empty() { -                        self.primitives.push(Primitive::GradientMesh { -                            buffers: primitive::Mesh2D { -                                vertices: buffer.vertices, -                                indices: buffer.indices, -                            }, -                            size: self.size, -                        }) +                        self.primitives.push(Primitive::Custom( +                            primitive::Custom::Mesh(Mesh::Gradient { +                                buffers: mesh::Indexed { +                                    vertices: buffer.vertices, +                                    indices: buffer.indices, +                                }, +                                size: self.size, +                            }), +                        ))                      }                  }              } @@ -495,32 +499,32 @@ struct GradientVertex2DBuilder {      gradient: gradient::Packed,  } -impl tessellation::FillVertexConstructor<primitive::GradientVertex2D> +impl tessellation::FillVertexConstructor<mesh::GradientVertex2D>      for GradientVertex2DBuilder  {      fn new_vertex(          &mut self,          vertex: tessellation::FillVertex<'_>, -    ) -> primitive::GradientVertex2D { +    ) -> mesh::GradientVertex2D {          let position = vertex.position(); -        primitive::GradientVertex2D { +        mesh::GradientVertex2D {              position: [position.x, position.y],              gradient: self.gradient,          }      }  } -impl tessellation::StrokeVertexConstructor<primitive::GradientVertex2D> +impl tessellation::StrokeVertexConstructor<mesh::GradientVertex2D>      for GradientVertex2DBuilder  {      fn new_vertex(          &mut self,          vertex: tessellation::StrokeVertex<'_, '_>, -    ) -> primitive::GradientVertex2D { +    ) -> mesh::GradientVertex2D {          let position = vertex.position(); -        primitive::GradientVertex2D { +        mesh::GradientVertex2D {              position: [position.x, position.y],              gradient: self.gradient,          } @@ -529,32 +533,32 @@ impl tessellation::StrokeVertexConstructor<primitive::GradientVertex2D>  struct TriangleVertex2DBuilder(color::Packed); -impl tessellation::FillVertexConstructor<primitive::ColoredVertex2D> +impl tessellation::FillVertexConstructor<mesh::SolidVertex2D>      for TriangleVertex2DBuilder  {      fn new_vertex(          &mut self,          vertex: tessellation::FillVertex<'_>, -    ) -> primitive::ColoredVertex2D { +    ) -> mesh::SolidVertex2D {          let position = vertex.position(); -        primitive::ColoredVertex2D { +        mesh::SolidVertex2D {              position: [position.x, position.y],              color: self.0,          }      }  } -impl tessellation::StrokeVertexConstructor<primitive::ColoredVertex2D> +impl tessellation::StrokeVertexConstructor<mesh::SolidVertex2D>      for TriangleVertex2DBuilder  {      fn new_vertex(          &mut self,          vertex: tessellation::StrokeVertex<'_, '_>, -    ) -> primitive::ColoredVertex2D { +    ) -> mesh::SolidVertex2D {          let position = vertex.position(); -        primitive::ColoredVertex2D { +        mesh::SolidVertex2D {              position: [position.x, position.y],              color: self.0,          } diff --git a/wgpu/src/layer.rs b/wgpu/src/layer.rs index 71570e3d..b8f32db1 100644 --- a/wgpu/src/layer.rs +++ b/wgpu/src/layer.rs @@ -11,8 +11,10 @@ pub use text::Text;  use crate::core;  use crate::core::alignment;  use crate::core::{Color, Font, Point, Rectangle, Size, Vector}; +use crate::graphics;  use crate::graphics::color; -use crate::graphics::{Primitive, Viewport}; +use crate::graphics::Viewport; +use crate::primitive::{self, Primitive};  use crate::quad::{self, Quad};  /// A group of primitives that should be clipped together. @@ -179,40 +181,6 @@ impl<'a> Layer<'a> {                      bounds: *bounds + translation,                  });              } -            Primitive::SolidMesh { buffers, size } => { -                let layer = &mut layers[current_layer]; - -                let bounds = Rectangle::new( -                    Point::new(translation.x, translation.y), -                    *size, -                ); - -                // Only draw visible content -                if let Some(clip_bounds) = layer.bounds.intersection(&bounds) { -                    layer.meshes.push(Mesh::Solid { -                        origin: Point::new(translation.x, translation.y), -                        buffers, -                        clip_bounds, -                    }); -                } -            } -            Primitive::GradientMesh { buffers, size } => { -                let layer = &mut layers[current_layer]; - -                let bounds = Rectangle::new( -                    Point::new(translation.x, translation.y), -                    *size, -                ); - -                // Only draw visible content -                if let Some(clip_bounds) = layer.bounds.intersection(&bounds) { -                    layer.meshes.push(Mesh::Gradient { -                        origin: Point::new(translation.x, translation.y), -                        buffers, -                        clip_bounds, -                    }); -                } -            }              Primitive::Group { primitives } => {                  // TODO: Inspect a bit and regroup (?)                  for primitive in primitives { @@ -262,13 +230,54 @@ impl<'a> Layer<'a> {                      current_layer,                  );              } -            _ => { -                // Not supported! -                log::warn!( -                    "Unsupported primitive in `iced_wgpu`: {:?}", -                    primitive -                ); -            } +            Primitive::Custom(custom) => match custom { +                primitive::Custom::Mesh(mesh) => match mesh { +                    graphics::Mesh::Solid { buffers, size } => { +                        let layer = &mut layers[current_layer]; + +                        let bounds = Rectangle::new( +                            Point::new(translation.x, translation.y), +                            *size, +                        ); + +                        // Only draw visible content +                        if let Some(clip_bounds) = +                            layer.bounds.intersection(&bounds) +                        { +                            layer.meshes.push(Mesh::Solid { +                                origin: Point::new( +                                    translation.x, +                                    translation.y, +                                ), +                                buffers, +                                clip_bounds, +                            }); +                        } +                    } +                    graphics::Mesh::Gradient { buffers, size } => { +                        let layer = &mut layers[current_layer]; + +                        let bounds = Rectangle::new( +                            Point::new(translation.x, translation.y), +                            *size, +                        ); + +                        // Only draw visible content +                        if let Some(clip_bounds) = +                            layer.bounds.intersection(&bounds) +                        { +                            layer.meshes.push(Mesh::Gradient { +                                origin: Point::new( +                                    translation.x, +                                    translation.y, +                                ), +                                buffers, +                                clip_bounds, +                            }); +                        } +                    } +                }, +            },          }      }  } diff --git a/wgpu/src/layer/mesh.rs b/wgpu/src/layer/mesh.rs index b7dd9a0b..7c6206cd 100644 --- a/wgpu/src/layer/mesh.rs +++ b/wgpu/src/layer/mesh.rs @@ -1,6 +1,6 @@  //! A collection of triangle primitives.  use crate::core::{Point, Rectangle}; -use crate::graphics::primitive; +use crate::graphics::mesh;  /// A mesh of triangles.  #[derive(Debug, Clone, Copy)] @@ -11,7 +11,7 @@ pub enum Mesh<'a> {          origin: Point,          /// The vertex and index buffers of the [`Mesh`]. -        buffers: &'a primitive::Mesh2D<primitive::ColoredVertex2D>, +        buffers: &'a mesh::Indexed<mesh::SolidVertex2D>,          /// The clipping bounds of the [`Mesh`].          clip_bounds: Rectangle<f32>, @@ -22,7 +22,7 @@ pub enum Mesh<'a> {          origin: Point,          /// The vertex and index buffers of the [`Mesh`]. -        buffers: &'a primitive::Mesh2D<primitive::GradientVertex2D>, +        buffers: &'a mesh::Indexed<mesh::GradientVertex2D>,          /// The clipping bounds of the [`Mesh`].          clip_bounds: Rectangle<f32>, diff --git a/wgpu/src/lib.rs b/wgpu/src/lib.rs index 86a962a5..deb223ef 100644 --- a/wgpu/src/lib.rs +++ b/wgpu/src/lib.rs @@ -38,6 +38,7 @@  #![allow(clippy::inherent_to_string, clippy::type_complexity)]  #![cfg_attr(docsrs, feature(doc_auto_cfg))]  pub mod layer; +pub mod primitive;  pub mod settings;  pub mod window; @@ -60,6 +61,7 @@ pub use wgpu;  pub use backend::Backend;  pub use layer::Layer; +pub use primitive::Primitive;  pub use settings::Settings;  #[cfg(any(feature = "image", feature = "svg"))] diff --git a/wgpu/src/primitive.rs b/wgpu/src/primitive.rs new file mode 100644 index 00000000..8dbf3008 --- /dev/null +++ b/wgpu/src/primitive.rs @@ -0,0 +1,21 @@ +//! Draw using different graphical primitives. +use crate::core::Rectangle; +use crate::graphics::{Damage, Mesh}; + +/// The graphical primitives supported by `iced_wgpu`. +pub type Primitive = crate::graphics::Primitive<Custom>; + +/// The custom primitives supported by `iced_wgpu`. +#[derive(Debug, Clone, PartialEq)] +pub enum Custom { +    /// A mesh primitive. +    Mesh(Mesh), +} + +impl Damage for Custom { +    fn bounds(&self) -> Rectangle { +        match self { +            Self::Mesh(mesh) => mesh.bounds(), +        } +    } +} diff --git a/wgpu/src/triangle.rs b/wgpu/src/triangle.rs index 3f3635cf..d8b23dfe 100644 --- a/wgpu/src/triangle.rs +++ b/wgpu/src/triangle.rs @@ -393,7 +393,7 @@ impl Uniforms {  }  mod solid { -    use crate::graphics::primitive; +    use crate::graphics::mesh;      use crate::graphics::Antialiasing;      use crate::triangle;      use crate::Buffer; @@ -406,7 +406,7 @@ mod solid {      #[derive(Debug)]      pub struct Layer { -        pub vertices: Buffer<primitive::ColoredVertex2D>, +        pub vertices: Buffer<mesh::SolidVertex2D>,          pub uniforms: Buffer<triangle::Uniforms>,          pub constants: wgpu::BindGroup,      } @@ -493,38 +493,40 @@ mod solid {                      ),                  }); -            let pipeline = device.create_render_pipeline( -                &wgpu::RenderPipelineDescriptor { -                    label: Some("iced_wgpu::triangle::solid pipeline"), -                    layout: Some(&layout), -                    vertex: wgpu::VertexState { -                        module: &shader, -                        entry_point: "solid_vs_main", -                        buffers: &[wgpu::VertexBufferLayout { -                            array_stride: std::mem::size_of::< -                                primitive::ColoredVertex2D, -                            >() -                                as u64, -                            step_mode: wgpu::VertexStepMode::Vertex, -                            attributes: &wgpu::vertex_attr_array!( -                                // Position -                                0 => Float32x2, -                                // Color -                                1 => Float32x4, -                            ), -                        }], +            let pipeline = +                device.create_render_pipeline( +                    &wgpu::RenderPipelineDescriptor { +                        label: Some("iced_wgpu::triangle::solid pipeline"), +                        layout: Some(&layout), +                        vertex: wgpu::VertexState { +                            module: &shader, +                            entry_point: "solid_vs_main", +                            buffers: &[wgpu::VertexBufferLayout { +                                array_stride: std::mem::size_of::< +                                    mesh::SolidVertex2D, +                                >( +                                ) +                                    as u64, +                                step_mode: wgpu::VertexStepMode::Vertex, +                                attributes: &wgpu::vertex_attr_array!( +                                    // Position +                                    0 => Float32x2, +                                    // Color +                                    1 => Float32x4, +                                ), +                            }], +                        }, +                        fragment: Some(wgpu::FragmentState { +                            module: &shader, +                            entry_point: "solid_fs_main", +                            targets: &[triangle::fragment_target(format)], +                        }), +                        primitive: triangle::primitive_state(), +                        depth_stencil: None, +                        multisample: triangle::multisample_state(antialiasing), +                        multiview: None,                      }, -                    fragment: Some(wgpu::FragmentState { -                        module: &shader, -                        entry_point: "solid_fs_main", -                        targets: &[triangle::fragment_target(format)], -                    }), -                    primitive: triangle::primitive_state(), -                    depth_stencil: None, -                    multisample: triangle::multisample_state(antialiasing), -                    multiview: None, -                }, -            ); +                );              Self {                  pipeline, @@ -535,7 +537,8 @@ mod solid {  }  mod gradient { -    use crate::graphics::{primitive, Antialiasing}; +    use crate::graphics::mesh; +    use crate::graphics::Antialiasing;      use crate::triangle;      use crate::Buffer; @@ -547,7 +550,7 @@ mod gradient {      #[derive(Debug)]      pub struct Layer { -        pub vertices: Buffer<primitive::GradientVertex2D>, +        pub vertices: Buffer<mesh::GradientVertex2D>,          pub uniforms: Buffer<triangle::Uniforms>,          pub constants: wgpu::BindGroup,      } @@ -645,7 +648,7 @@ mod gradient {                          entry_point: "gradient_vs_main",                          buffers: &[wgpu::VertexBufferLayout {                              array_stride: std::mem::size_of::< -                                primitive::GradientVertex2D, +                                mesh::GradientVertex2D,                              >()                                  as u64,                              step_mode: wgpu::VertexStepMode::Vertex, diff --git a/wgpu/src/window/compositor.rs b/wgpu/src/window/compositor.rs index 1cfd7b67..cd5b20cc 100644 --- a/wgpu/src/window/compositor.rs +++ b/wgpu/src/window/compositor.rs @@ -3,8 +3,8 @@ use crate::core::{Color, Size};  use crate::graphics;  use crate::graphics::color;  use crate::graphics::compositor; -use crate::graphics::{Error, Primitive, Viewport}; -use crate::{Backend, Renderer, Settings}; +use crate::graphics::{Error, Viewport}; +use crate::{Backend, Primitive, Renderer, Settings};  use futures::stream::{self, StreamExt}; | 
