From 7cf5891323d6665eb117952a3597405e2c4afa47 Mon Sep 17 00:00:00 2001 From: annieversary Date: Wed, 8 Sep 2021 18:36:24 +0200 Subject: [PATCH] subtitled #15 --- Cargo.lock | 8 ++ crates/subtitled15/Cargo.toml | 8 ++ crates/subtitled15/shaders/frag.spv | Bin 0 -> 348 bytes crates/subtitled15/shaders/shader.frag | 13 +++ crates/subtitled15/shaders/shader.vert | 15 +++ crates/subtitled15/shaders/vert.spv | Bin 0 -> 824 bytes crates/subtitled15/src/main.rs | 127 +++++++++++++++++++++++++ 7 files changed, 171 insertions(+) create mode 100644 crates/subtitled15/Cargo.toml create mode 100644 crates/subtitled15/shaders/frag.spv create mode 100644 crates/subtitled15/shaders/shader.frag create mode 100644 crates/subtitled15/shaders/shader.vert create mode 100644 crates/subtitled15/shaders/vert.spv create mode 100644 crates/subtitled15/src/main.rs diff --git a/Cargo.lock b/Cargo.lock index 13e0c08..b84ed65 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2406,6 +2406,14 @@ dependencies = [ "utils", ] +[[package]] +name = "subtitled15" +version = "0.1.0" +dependencies = [ + "nannou", + "utils", +] + [[package]] name = "subtitled2" version = "0.1.0" diff --git a/crates/subtitled15/Cargo.toml b/crates/subtitled15/Cargo.toml new file mode 100644 index 0000000..5e8cd08 --- /dev/null +++ b/crates/subtitled15/Cargo.toml @@ -0,0 +1,8 @@ +[package] +name = "subtitled15" +version = "0.1.0" +edition = "2018" + +[dependencies] +nannou = "0.17" +utils = { path = "../utils" } diff --git a/crates/subtitled15/shaders/frag.spv b/crates/subtitled15/shaders/frag.spv new file mode 100644 index 0000000000000000000000000000000000000000..4e32a1c2f99f29ca6b5a28bc2f158c241863caaa GIT binary patch literal 348 zcmYjN-3kF=6de26AJ%V*JFQ&O=7LQrF85~dJb*+>VG9r7**ujSW#+TWso8U8zBxaw zafUunf{y@oe4`DA3J}7xInCBte7o=C>1-lL1I8NVY0^_>7S7w_MGqCCMUONNXJt4M zc(TEz`tKE&|FGHRr~Hbv;C*U}4m;I5uv1{`E^CikMD*y_4sp$m_zjqKq4Y(;wL{v7 tT;3`HJXSv*S`LiarM?;=k90wG!s~U5_9!&(Ma5-al4*zf-u!EG;saI)5qAIp literal 0 HcmV?d00001 diff --git a/crates/subtitled15/shaders/shader.frag b/crates/subtitled15/shaders/shader.frag new file mode 100644 index 0000000..94d755c --- /dev/null +++ b/crates/subtitled15/shaders/shader.frag @@ -0,0 +1,13 @@ +// NOTE: This shader requires being manually compiled to SPIR-V in order to +// avoid having downstream users require building shaderc and compiling the +// shader themselves. If you update this shader, be sure to also re-compile it +// and update `frag.spv`. You can do so using `glslangValidator` with the +// following command: `glslangValidator -V shader.frag` + +#version 450 + +layout(location = 0) out vec4 f_color; + +void main() { + f_color = vec4(1.0, 0.0, 0.0, 1.0); +} diff --git a/crates/subtitled15/shaders/shader.vert b/crates/subtitled15/shaders/shader.vert new file mode 100644 index 0000000..bdffb60 --- /dev/null +++ b/crates/subtitled15/shaders/shader.vert @@ -0,0 +1,15 @@ +// NOTE: This shader requires being manually compiled to SPIR-V in order to +// avoid having downstream users require building shaderc and compiling the +// shader themselves. If you update this shader, be sure to also re-compile it +// and update `vert.spv`. You can do so using `glslangValidator` with the +// following command: `glslangValidator -V shader.vert` + +#version 450 + +// maybe change for this https://github.com/castor-software/rethread/blob/69a5746b02c260982a812c52da15ee364bc047e8/code/software-evolution/drift_vis/src/shaders/blur.vert + +layout(location = 0) in vec2 position; + +void main() { + gl_Position = vec4(position, 0.0, 1.0); +} diff --git a/crates/subtitled15/shaders/vert.spv b/crates/subtitled15/shaders/vert.spv new file mode 100644 index 0000000000000000000000000000000000000000..45bdcf5ad9d44903c056aa3d08b498372fb001db GIT binary patch literal 824 zcmYk3UrPc}5XEn9>spp(ruGj}dJLq8iXbYYz#e=sgkD2xi3{5*xH{@4@QIDJbCUNpB%xc7%wHlsp=%Q zEPox_n0#HnDfjdh6u(6D#rV(hHM^|dOY}GlXAj{l3Ex!;&2VyhletaoBo-Q^d^A(s z#>vQjgz#JsE%k09JH55@WE?+*iyj-(dyAq)&)0tJiuwB3dFlj}-w9(!%teP~@59Ue z@z95dmgA9wareGDIzJ;e)l6q3veS!#m=wDY`w+^O|=7L#LARvbpF`SLGOcZ78C{&djSRvI98tsJSZ` z=izS2F;_Rz>hp^8JIc{!*Hirm%;nA)__q*W@j@sXbvg6zg)+ODV+sqbm1FEM)MRFF d%i+>vA9lFb4D@&9yaD&Tlqxm+AKl_i{tE@ZG#mf` literal 0 HcmV?d00001 diff --git a/crates/subtitled15/src/main.rs b/crates/subtitled15/src/main.rs new file mode 100644 index 0000000..a0c7054 --- /dev/null +++ b/crates/subtitled15/src/main.rs @@ -0,0 +1,127 @@ +use nannou::prelude::*; + +struct Model { + bind_group: wgpu::BindGroup, + render_pipeline: wgpu::RenderPipeline, + vertex_buffer1: wgpu::Buffer, + vertex_buffer2: wgpu::Buffer, +} + +// The vertex type that we will use to represent a point on our triangle. +#[repr(C)] +#[derive(Clone, Copy)] +struct Vertex { + position: [f32; 2], +} + +// The vertices that make up our triangle. +const VERTICES1: [Vertex; 3] = [ + Vertex { + position: [-1.0, -1.0], + }, + Vertex { + position: [1.0, 1.0], + }, + Vertex { + position: [-1.0, 1.0], + }, +]; +const VERTICES2: [Vertex; 3] = [ + Vertex { + position: [1.0, -1.0], + }, + Vertex { + position: [1.0, 1.0], + }, + Vertex { + position: [-1.0, -1.0], + }, +]; + +fn main() { + nannou::app(model).run(); +} + +fn model(app: &App) -> Model { + let w_id = app.new_window().size(512, 512).view(view).build().unwrap(); + + // The gpu device associated with the window's swapchain + let window = app.window(w_id).unwrap(); + let device = window.swap_chain_device(); + let format = Frame::TEXTURE_FORMAT; + let sample_count = window.msaa_samples(); + + // Load shader modules. + let vs_mod = wgpu::shader_from_spirv_bytes(device, include_bytes!("../shaders/vert.spv")); + let fs_mod = wgpu::shader_from_spirv_bytes(device, include_bytes!("../shaders/frag.spv")); + + // Create the vertex buffer. + let usage = wgpu::BufferUsage::VERTEX; + let vertices_bytes = vertices_as_bytes(&VERTICES1[..]); + let vertex_buffer1 = device.create_buffer_init(&BufferInitDescriptor { + label: None, + contents: vertices_bytes, + usage, + }); + let vertices_bytes = vertices_as_bytes(&VERTICES2[..]); + let vertex_buffer2 = device.create_buffer_init(&BufferInitDescriptor { + label: None, + contents: vertices_bytes, + usage, + }); + + // Create the render pipeline. + let bind_group_layout = wgpu::BindGroupLayoutBuilder::new().build(device); + let bind_group = wgpu::BindGroupBuilder::new().build(device, &bind_group_layout); + let pipeline_layout = wgpu::create_pipeline_layout(device, None, &[&bind_group_layout], &[]); + let render_pipeline = wgpu::RenderPipelineBuilder::from_layout(&pipeline_layout, &vs_mod) + .fragment_shader(&fs_mod) + .color_format(format) + .add_vertex_buffer::(&wgpu::vertex_attr_array![0 => Float32x2]) + .sample_count(sample_count) + .build(device); + + Model { + bind_group, + vertex_buffer1, + vertex_buffer2, + render_pipeline, + } +} + +// Draw the state of your `Model` into the given `Frame` here. +fn view(_app: &App, model: &Model, frame: Frame) { + // Using this we will encode commands that will be submitted to the GPU. + let mut encoder = frame.command_encoder(); + + // The render pass can be thought of a single large command consisting of sub commands. Here we + // begin a render pass that outputs to the frame's texture. Then we add sub-commands for + // setting the bind group, render pipeline, vertex buffers and then finally drawing. + let mut render_pass = wgpu::RenderPassBuilder::new() + .color_attachment(frame.texture_view(), |color| color) + .begin(&mut encoder); + render_pass.set_bind_group(0, &model.bind_group, &[]); + render_pass.set_pipeline(&model.render_pipeline); + render_pass.set_vertex_buffer(0, model.vertex_buffer1.slice(..)); + + // We want to draw the whole range of vertices, and we're only drawing one instance of them. + let vertex_range = 0..VERTICES1.len() as u32; + let instance_range = 0..1; + render_pass.draw(vertex_range, instance_range); + + render_pass.set_bind_group(0, &model.bind_group, &[]); + render_pass.set_pipeline(&model.render_pipeline); + render_pass.set_vertex_buffer(0, model.vertex_buffer2.slice(..)); + + // We want to draw the whole range of vertices, and we're only drawing one instance of them. + let vertex_range = 0..VERTICES2.len() as u32; + let instance_range = 0..1; + render_pass.draw(vertex_range, instance_range); + + // Now we're done! The commands we added will be submitted after `view` completes. +} + +// See the `nannou::wgpu::bytes` documentation for why this is necessary. +fn vertices_as_bytes(data: &[Vertex]) -> &[u8] { + unsafe { wgpu::bytes::from_slice(data) } +}