Implmenting indices, and textures
This commit is contained in:
parent
e5b6a24ae6
commit
5434c11f4a
Binary file not shown.
After Width: | Height: | Size: 28 KiB |
|
@ -2,27 +2,32 @@
|
||||||
|
|
||||||
struct VertexInput {
|
struct VertexInput {
|
||||||
@location(0) position: vec3<f32>,
|
@location(0) position: vec3<f32>,
|
||||||
@location(1) color: vec3<f32>,
|
@location(1) tex_coords: vec2<f32>,
|
||||||
};
|
}
|
||||||
|
|
||||||
struct VertexOutput {
|
struct VertexOutput {
|
||||||
@builtin(position) clip_position: vec4<f32>,
|
@builtin(position) clip_position: vec4<f32>,
|
||||||
@location(0) color: vec3<f32>,
|
@location(0) tex_coords: vec2<f32>,
|
||||||
};
|
}
|
||||||
|
|
||||||
@vertex
|
@vertex
|
||||||
fn vs_main(
|
fn vs_main(
|
||||||
model: VertexInput,
|
model: VertexInput,
|
||||||
) -> VertexOutput {
|
) -> VertexOutput {
|
||||||
var out: VertexOutput;
|
var out: VertexOutput;
|
||||||
out.color = model.color;
|
out.tex_coords = model.tex_coords;
|
||||||
out.clip_position = vec4<f32>(model.position, 1.0);
|
out.clip_position = vec4<f32>(model.position, 1.0);
|
||||||
return out;
|
return out;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Fragment shader
|
// Fragment shader
|
||||||
|
|
||||||
|
@group(0) @binding(0)
|
||||||
|
var t_diffuse: texture_2d<f32>;
|
||||||
|
@group(0)@binding(1)
|
||||||
|
var s_diffuse: sampler;
|
||||||
|
|
||||||
@fragment
|
@fragment
|
||||||
fn fs_main(in: VertexOutput) -> @location(0) vec4<f32> {
|
fn fs_main(in: VertexOutput) -> @location(0) vec4<f32> {
|
||||||
return vec4<f32>(in.color, 1.0);
|
return textureSample(t_diffuse, s_diffuse, in.tex_coords);
|
||||||
}
|
}
|
||||||
|
|
|
@ -160,7 +160,7 @@ impl<'a, 'b> Game<'static, 'static> {
|
||||||
let filter = FilterFn::new(|metadata| {
|
let filter = FilterFn::new(|metadata| {
|
||||||
metadata.module_path()
|
metadata.module_path()
|
||||||
.unwrap_or_else(|| metadata.target())
|
.unwrap_or_else(|| metadata.target())
|
||||||
.starts_with("lyra_engine") && (LevelFilter::INFO >= metadata.level().to_owned())
|
.starts_with("lyra_engine") && (LevelFilter::DEBUG >= metadata.level().to_owned())
|
||||||
});
|
});
|
||||||
|
|
||||||
let layer = tracing_subscriber::fmt::layer();
|
let layer = tracing_subscriber::fmt::layer();
|
||||||
|
|
|
@ -0,0 +1,29 @@
|
||||||
|
use wgpu::{BindGroup, BindGroupLayout};
|
||||||
|
|
||||||
|
use super::{vertex::Vertex, render_buffer::{BufferStorage}};
|
||||||
|
|
||||||
|
pub struct Mesh {
|
||||||
|
//material
|
||||||
|
//texture: Option<Texture>,
|
||||||
|
pub vertices: Vec<Vertex>,
|
||||||
|
pub indices: Option<Vec<u16>>,
|
||||||
|
|
||||||
|
pub buffer_vertex: BufferStorage,
|
||||||
|
pub buffer_indices: Option<BufferStorage>, // TOOD: make optional
|
||||||
|
|
||||||
|
pub texture_bindgroup: Option<BindGroup>,
|
||||||
|
pub texture_layout: Option<BindGroupLayout>
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Mesh {
|
||||||
|
pub fn new(vertices: Vec<Vertex>, indices: Option<Vec<u16>>, buffer_vertex: BufferStorage, buffer_indices: Option<BufferStorage>, texture_bindgroup: Option<BindGroup>, texture_layout: Option<BindGroupLayout>) -> Self {
|
||||||
|
Self {
|
||||||
|
vertices,
|
||||||
|
indices,
|
||||||
|
buffer_vertex,
|
||||||
|
buffer_indices,
|
||||||
|
texture_bindgroup,
|
||||||
|
texture_layout,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -2,4 +2,7 @@ pub mod renderer;
|
||||||
pub mod render_pipeline;
|
pub mod render_pipeline;
|
||||||
pub mod vertex;
|
pub mod vertex;
|
||||||
pub mod desc_buf_lay;
|
pub mod desc_buf_lay;
|
||||||
pub mod render_buffer;
|
pub mod render_buffer;
|
||||||
|
pub mod render_job;
|
||||||
|
pub mod mesh;
|
||||||
|
pub mod texture;
|
|
@ -1,15 +1,18 @@
|
||||||
use super::{desc_buf_lay::DescVertexBufferLayout, vertex::Vertex};
|
use super::{desc_buf_lay::DescVertexBufferLayout, vertex::Vertex};
|
||||||
|
|
||||||
|
#[allow(dead_code)]
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub enum RenderBuffer {
|
pub enum RenderBuffer {
|
||||||
VertexBuffer(BufferStorage),
|
VertexBuffer(BufferStorage),
|
||||||
|
VertexIndexBufferPair((BufferStorage, BufferStorage)),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[allow(dead_code)]
|
||||||
impl RenderBuffer {
|
impl RenderBuffer {
|
||||||
pub fn desc<'a>(&self) -> wgpu::VertexBufferLayout<'a> {
|
pub fn desc<'a>(&self) -> Option<wgpu::VertexBufferLayout<'a>> {
|
||||||
match self {
|
match self {
|
||||||
RenderBuffer::VertexBuffer(b) => Vertex::desc(),
|
RenderBuffer::VertexBuffer(_) => Some(Vertex::desc()),
|
||||||
_ => panic!("Cannot create a VertexBufferLayout for {:?}!", *self)
|
RenderBuffer::VertexIndexBufferPair(_) => Some(Vertex::desc()),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -18,13 +21,16 @@ impl RenderBuffer {
|
||||||
pub struct BufferStorage {
|
pub struct BufferStorage {
|
||||||
buffer: wgpu::Buffer,
|
buffer: wgpu::Buffer,
|
||||||
slot: u32,
|
slot: u32,
|
||||||
|
count: Option<u32>
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[allow(dead_code)]
|
||||||
impl BufferStorage {
|
impl BufferStorage {
|
||||||
pub fn new(buffer: wgpu::Buffer, slot: u32) -> Self {
|
pub fn new(buffer: wgpu::Buffer, slot: u32, count: Option<u32>) -> Self {
|
||||||
Self {
|
Self {
|
||||||
buffer,
|
buffer,
|
||||||
slot,
|
slot,
|
||||||
|
count,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -39,4 +45,8 @@ impl BufferStorage {
|
||||||
pub fn slot(&self) -> u32 {
|
pub fn slot(&self) -> u32 {
|
||||||
self.slot
|
self.slot
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn count(&self) -> Option<u32> {
|
||||||
|
self.count
|
||||||
|
}
|
||||||
}
|
}
|
|
@ -0,0 +1,17 @@
|
||||||
|
use super::{mesh::Mesh};
|
||||||
|
|
||||||
|
pub struct RenderJob {
|
||||||
|
mesh: Mesh
|
||||||
|
}
|
||||||
|
|
||||||
|
impl RenderJob {
|
||||||
|
pub fn new(mesh: Mesh) -> Self {
|
||||||
|
Self {
|
||||||
|
mesh,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn mesh(&self)-> &Mesh {
|
||||||
|
&self.mesh
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,25 +1,33 @@
|
||||||
use std::ops::Range;
|
use std::ops::Range;
|
||||||
|
|
||||||
use wgpu::{TextureFormat, PipelineLayout, RenderPipeline, VertexBufferLayout, RenderPass};
|
use wgpu::{PipelineLayout, RenderPipeline, RenderPass};
|
||||||
|
|
||||||
use super::render_buffer::RenderBuffer;
|
use super::{render_job::RenderJob, vertex::Vertex, desc_buf_lay::DescVertexBufferLayout};
|
||||||
|
|
||||||
pub struct FullRenderPipeline {
|
pub struct FullRenderPipeline {
|
||||||
layout: PipelineLayout,
|
layout: PipelineLayout,
|
||||||
wgpu_pipeline: RenderPipeline,
|
wgpu_pipeline: RenderPipeline,
|
||||||
buffers: Vec<RenderBuffer>,
|
jobs: Vec<RenderJob>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl FullRenderPipeline {
|
impl FullRenderPipeline {
|
||||||
pub fn new(device: &wgpu::Device, config: &wgpu::SurfaceConfiguration, shader: &wgpu::ShaderModule, buffers: Vec<RenderBuffer>) -> Self {
|
pub fn new(device: &wgpu::Device, config: &wgpu::SurfaceConfiguration, shader: &wgpu::ShaderModule, jobs: Vec<RenderJob>) -> Self {
|
||||||
let buffer_layouts: Vec<VertexBufferLayout> = buffers.iter().map(|b| match b {
|
// Extract the layouts from all the jobs
|
||||||
RenderBuffer::VertexBuffer(_) => b.desc()
|
let mut buffer_layouts = vec![];
|
||||||
}).collect();
|
let mut bind_group_layouts = vec![];
|
||||||
|
for job in jobs.iter() {
|
||||||
|
// Push layout for the vertex buffer, index buffer doesn't need one
|
||||||
|
buffer_layouts.push(Vertex::desc());
|
||||||
|
|
||||||
|
if let Some(layout) = job.mesh().texture_layout.as_ref() {
|
||||||
|
bind_group_layouts.push(layout);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
let render_pipeline_layout =
|
let render_pipeline_layout =
|
||||||
device.create_pipeline_layout(&wgpu::PipelineLayoutDescriptor {
|
device.create_pipeline_layout(&wgpu::PipelineLayoutDescriptor {
|
||||||
label: Some("Render Pipeline Layout"),
|
label: Some("Render Pipeline Layout"),
|
||||||
bind_group_layouts: &[],
|
bind_group_layouts: &bind_group_layouts,
|
||||||
push_constant_ranges: &[],
|
push_constant_ranges: &[],
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -64,14 +72,16 @@ impl FullRenderPipeline {
|
||||||
Self {
|
Self {
|
||||||
layout: render_pipeline_layout,
|
layout: render_pipeline_layout,
|
||||||
wgpu_pipeline: render_pipeline,
|
wgpu_pipeline: render_pipeline,
|
||||||
buffers,
|
jobs,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[allow(dead_code)]
|
||||||
pub fn get_layout(&self) -> &PipelineLayout {
|
pub fn get_layout(&self) -> &PipelineLayout {
|
||||||
&self.layout
|
&self.layout
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[allow(dead_code)]
|
||||||
pub fn get_wgpu_pipeline(&self) -> &RenderPipeline {
|
pub fn get_wgpu_pipeline(&self) -> &RenderPipeline {
|
||||||
&self.wgpu_pipeline
|
&self.wgpu_pipeline
|
||||||
}
|
}
|
||||||
|
@ -79,15 +89,23 @@ impl FullRenderPipeline {
|
||||||
pub fn render<'a>(&'a self, pass: &mut RenderPass<'a>, vertices: Range<u32>, instances: Range<u32>) {
|
pub fn render<'a>(&'a self, pass: &mut RenderPass<'a>, vertices: Range<u32>, instances: Range<u32>) {
|
||||||
pass.set_pipeline(&self.wgpu_pipeline);
|
pass.set_pipeline(&self.wgpu_pipeline);
|
||||||
|
|
||||||
for buffer in self.buffers.iter() {
|
for job in self.jobs.iter() {
|
||||||
match buffer {
|
let mesh = job.mesh();
|
||||||
RenderBuffer::VertexBuffer(b) => {
|
|
||||||
pass.set_vertex_buffer(b.slot(), b.buffer().slice(..));
|
if let Some(tex) = mesh.texture_bindgroup.as_ref() {
|
||||||
},
|
pass.set_bind_group(0, &tex, &[]);
|
||||||
_ => {}
|
}
|
||||||
|
|
||||||
|
if let Some(indices) = mesh.buffer_indices.as_ref() {
|
||||||
|
let indices_len = indices.count().unwrap(); // index buffers will have count, if not thats a bug
|
||||||
|
|
||||||
|
pass.set_vertex_buffer(mesh.buffer_vertex.slot(), mesh.buffer_vertex.buffer().slice(..));
|
||||||
|
pass.set_index_buffer(indices.buffer().slice(..), wgpu::IndexFormat::Uint16);
|
||||||
|
pass.draw_indexed(0..indices_len, 0, instances.clone());
|
||||||
|
} else {
|
||||||
|
pass.set_vertex_buffer(mesh.buffer_vertex.slot(), mesh.buffer_vertex.buffer().slice(..));
|
||||||
|
pass.draw(vertices.clone(), instances.clone());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pass.draw(vertices, instances);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -4,13 +4,12 @@ use std::borrow::Cow;
|
||||||
use async_trait::async_trait;
|
use async_trait::async_trait;
|
||||||
|
|
||||||
use wgpu::util::DeviceExt;
|
use wgpu::util::DeviceExt;
|
||||||
//use winit::{window::Window, event::WindowEvent};
|
use winit::window::Window;
|
||||||
//use winit::window::Window;
|
|
||||||
use winit::{window::Window, event::WindowEvent};
|
|
||||||
|
|
||||||
use crate::resources;
|
use crate::resources;
|
||||||
|
|
||||||
use super::{render_pipeline::FullRenderPipeline, vertex::{Vertex, VERTICES}, desc_buf_lay::DescVertexBufferLayout, render_buffer::{BufferStorage, RenderBuffer}};
|
use super::texture::Texture;
|
||||||
|
use super::{render_pipeline::FullRenderPipeline, vertex::{VERTICES}, render_buffer::BufferStorage, render_job::RenderJob, mesh::Mesh};
|
||||||
|
|
||||||
#[async_trait]
|
#[async_trait]
|
||||||
pub trait Renderer {
|
pub trait Renderer {
|
||||||
|
@ -90,6 +89,51 @@ impl BasicRenderer {
|
||||||
surface.configure(&device, &config);
|
surface.configure(&device, &config);
|
||||||
|
|
||||||
|
|
||||||
|
let diffuse_bytes = include_bytes!("../../res/happy-tree.png");
|
||||||
|
let diffuse_texture = Texture::from_bytes(&device, &queue, diffuse_bytes, "happy-tree.png").unwrap();
|
||||||
|
|
||||||
|
let texture_bind_group_layout =
|
||||||
|
device.create_bind_group_layout(&wgpu::BindGroupLayoutDescriptor {
|
||||||
|
entries: &[
|
||||||
|
wgpu::BindGroupLayoutEntry {
|
||||||
|
binding: 0,
|
||||||
|
visibility: wgpu::ShaderStages::FRAGMENT,
|
||||||
|
ty: wgpu::BindingType::Texture {
|
||||||
|
multisampled: false,
|
||||||
|
view_dimension: wgpu::TextureViewDimension::D2,
|
||||||
|
sample_type: wgpu::TextureSampleType::Float { filterable: true },
|
||||||
|
},
|
||||||
|
count: None,
|
||||||
|
},
|
||||||
|
wgpu::BindGroupLayoutEntry {
|
||||||
|
binding: 1,
|
||||||
|
visibility: wgpu::ShaderStages::FRAGMENT,
|
||||||
|
// This should match the filterable field of the
|
||||||
|
// corresponding Texture entry above.
|
||||||
|
ty: wgpu::BindingType::Sampler(wgpu::SamplerBindingType::Filtering),
|
||||||
|
count: None,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
label: Some("texture_bind_group_layout"),
|
||||||
|
});
|
||||||
|
|
||||||
|
let diffuse_bind_group = device.create_bind_group(
|
||||||
|
&wgpu::BindGroupDescriptor {
|
||||||
|
layout: &texture_bind_group_layout,
|
||||||
|
entries: &[
|
||||||
|
wgpu::BindGroupEntry {
|
||||||
|
binding: 0,
|
||||||
|
resource: wgpu::BindingResource::TextureView(diffuse_texture.view()),
|
||||||
|
},
|
||||||
|
wgpu::BindGroupEntry {
|
||||||
|
binding: 1,
|
||||||
|
resource: wgpu::BindingResource::Sampler(diffuse_texture.sampler()),
|
||||||
|
}
|
||||||
|
],
|
||||||
|
label: Some("diffuse_bind_group"),
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
|
||||||
let shader_src = resources::load_string("shader.wgsl").await.expect("Failed to load shader!");
|
let shader_src = resources::load_string("shader.wgsl").await.expect("Failed to load shader!");
|
||||||
let shader = device.create_shader_module(wgpu::ShaderModuleDescriptor {
|
let shader = device.create_shader_module(wgpu::ShaderModuleDescriptor {
|
||||||
|
@ -105,9 +149,24 @@ impl BasicRenderer {
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|
||||||
|
let index_buffer = device.create_buffer_init(
|
||||||
|
&wgpu::util::BufferInitDescriptor {
|
||||||
|
label: Some("Index Buffer"),
|
||||||
|
contents: bytemuck::cast_slice(super::vertex::INDICES),
|
||||||
|
usage: wgpu::BufferUsages::INDEX,
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
let job = RenderJob::new(Mesh::new(
|
||||||
|
super::vertex::VERTICES.to_vec(), Some(super::vertex::INDICES.to_vec()),
|
||||||
|
BufferStorage::new(vertex_buffer, 0, None),
|
||||||
|
Some(BufferStorage::new(index_buffer, 0, Some(super::vertex::INDICES.len() as u32))),
|
||||||
|
Some(diffuse_bind_group), Some(texture_bind_group_layout)
|
||||||
|
));
|
||||||
|
|
||||||
let pipelines = vec![
|
let pipelines = vec![
|
||||||
FullRenderPipeline::new(&device, &config, &shader,
|
FullRenderPipeline::new(&device, &config, &shader,
|
||||||
vec![RenderBuffer::VertexBuffer(BufferStorage::new(vertex_buffer, 0))])
|
vec![job,])
|
||||||
];
|
];
|
||||||
|
|
||||||
Self {
|
Self {
|
||||||
|
|
|
@ -0,0 +1,81 @@
|
||||||
|
use image::GenericImageView;
|
||||||
|
|
||||||
|
#[allow(dead_code)]
|
||||||
|
pub struct Texture {
|
||||||
|
texture: wgpu::Texture,
|
||||||
|
view: wgpu::TextureView,
|
||||||
|
sampler: wgpu::Sampler,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Texture {
|
||||||
|
pub fn from_bytes(device: &wgpu::Device, queue: &wgpu::Queue, bytes: &[u8], label: &str) -> anyhow::Result<Self> {
|
||||||
|
let img = image::load_from_memory(bytes)?;
|
||||||
|
Self::from_image(device, queue, &img, Some(label))
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn from_image(device: &wgpu::Device, queue: &wgpu::Queue, img: &image::DynamicImage, label: Option<&str> ) -> anyhow::Result<Self> {
|
||||||
|
let rgba = img.to_rgba8();
|
||||||
|
let dimensions = img.dimensions();
|
||||||
|
|
||||||
|
let size = wgpu::Extent3d {
|
||||||
|
width: dimensions.0,
|
||||||
|
height: dimensions.1,
|
||||||
|
depth_or_array_layers: 1,
|
||||||
|
};
|
||||||
|
let texture = device.create_texture(
|
||||||
|
&wgpu::TextureDescriptor {
|
||||||
|
label,
|
||||||
|
size,
|
||||||
|
mip_level_count: 1,
|
||||||
|
sample_count: 1,
|
||||||
|
dimension: wgpu::TextureDimension::D2,
|
||||||
|
format: wgpu::TextureFormat::Rgba8UnormSrgb,
|
||||||
|
usage: wgpu::TextureUsages::TEXTURE_BINDING | wgpu::TextureUsages::COPY_DST,
|
||||||
|
view_formats: &[],
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
queue.write_texture(
|
||||||
|
wgpu::ImageCopyTexture {
|
||||||
|
aspect: wgpu::TextureAspect::All,
|
||||||
|
texture: &texture,
|
||||||
|
mip_level: 0,
|
||||||
|
origin: wgpu::Origin3d::ZERO,
|
||||||
|
},
|
||||||
|
&rgba,
|
||||||
|
wgpu::ImageDataLayout {
|
||||||
|
offset: 0,
|
||||||
|
bytes_per_row: std::num::NonZeroU32::new(4 * dimensions.0),
|
||||||
|
rows_per_image: std::num::NonZeroU32::new(dimensions.1),
|
||||||
|
},
|
||||||
|
size,
|
||||||
|
);
|
||||||
|
|
||||||
|
let view = texture.create_view(&wgpu::TextureViewDescriptor::default());
|
||||||
|
let sampler = device.create_sampler(
|
||||||
|
&wgpu::SamplerDescriptor {
|
||||||
|
address_mode_u: wgpu::AddressMode::ClampToEdge,
|
||||||
|
address_mode_v: wgpu::AddressMode::ClampToEdge,
|
||||||
|
address_mode_w: wgpu::AddressMode::ClampToEdge,
|
||||||
|
mag_filter: wgpu::FilterMode::Linear,
|
||||||
|
min_filter: wgpu::FilterMode::Nearest,
|
||||||
|
mipmap_filter: wgpu::FilterMode::Nearest,
|
||||||
|
..Default::default()
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
Ok(Self { texture, view, sampler })
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn texture(&self) -> &wgpu::Texture {
|
||||||
|
&self.texture
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn view(&self) -> &wgpu::TextureView {
|
||||||
|
&self.view
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn sampler(&self) -> &wgpu::Sampler {
|
||||||
|
&self.sampler
|
||||||
|
}
|
||||||
|
}
|
|
@ -4,13 +4,22 @@ use super::desc_buf_lay::DescVertexBufferLayout;
|
||||||
#[derive(Copy, Clone, Debug, bytemuck::Pod, bytemuck::Zeroable)]
|
#[derive(Copy, Clone, Debug, bytemuck::Pod, bytemuck::Zeroable)]
|
||||||
pub struct Vertex {
|
pub struct Vertex {
|
||||||
pub position: [f32; 3],
|
pub position: [f32; 3],
|
||||||
pub color: [f32; 3],
|
//pub color: [f32; 3], // TODO: add color again
|
||||||
|
tex_coords: [f32; 2]
|
||||||
}
|
}
|
||||||
|
|
||||||
pub const VERTICES: &[Vertex] = &[
|
pub const VERTICES: &[Vertex] = &[
|
||||||
Vertex { position: [0.0, 0.5, 0.0], color: [1.0, 0.0, 0.0] },
|
Vertex { position: [-0.0868241, 0.49240386, 0.0], tex_coords: [0.4131759, 0.00759614], }, // A
|
||||||
Vertex { position: [-0.5, -0.5, 0.0], color: [0.0, 1.0, 0.0] },
|
Vertex { position: [-0.49513406, 0.06958647, 0.0], tex_coords: [0.0048659444, 0.43041354], }, // B
|
||||||
Vertex { position: [0.5, -0.5, 0.0], color: [0.0, 0.0, 1.0] },
|
Vertex { position: [-0.21918549, -0.44939706, 0.0], tex_coords: [0.28081453, 0.949397], }, // C
|
||||||
|
Vertex { position: [0.35966998, -0.3473291, 0.0], tex_coords: [0.85967, 0.84732914], }, // D
|
||||||
|
Vertex { position: [0.44147372, 0.2347359, 0.0], tex_coords: [0.9414737, 0.2652641], }, // E
|
||||||
|
];
|
||||||
|
|
||||||
|
pub const INDICES: &[u16] = &[
|
||||||
|
0, 1, 4,
|
||||||
|
1, 2, 4,
|
||||||
|
2, 3, 4,
|
||||||
];
|
];
|
||||||
|
|
||||||
impl DescVertexBufferLayout for Vertex {
|
impl DescVertexBufferLayout for Vertex {
|
||||||
|
@ -27,7 +36,7 @@ impl DescVertexBufferLayout for Vertex {
|
||||||
wgpu::VertexAttribute {
|
wgpu::VertexAttribute {
|
||||||
offset: std::mem::size_of::<[f32; 3]>() as wgpu::BufferAddress,
|
offset: std::mem::size_of::<[f32; 3]>() as wgpu::BufferAddress,
|
||||||
shader_location: 1,
|
shader_location: 1,
|
||||||
format: wgpu::VertexFormat::Float32x3,
|
format: wgpu::VertexFormat::Float32x2,
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue