Fix wasm crashing on startup
This commit is contained in:
parent
7aa70cd564
commit
091bdcaa98
6 changed files with 41 additions and 15 deletions
13
index.html
13
index.html
|
@ -7,13 +7,16 @@
|
|||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>wgpu-renderer</title>
|
||||
<style>
|
||||
body {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
background: black;
|
||||
}
|
||||
canvas {
|
||||
background-color: black;
|
||||
display: block;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
min-width: 4px;
|
||||
min-height: 4px;
|
||||
width: 100vw;
|
||||
height: 100vh;
|
||||
}
|
||||
#loading {
|
||||
color: white;
|
||||
|
@ -25,7 +28,7 @@
|
|||
</style>
|
||||
</head>
|
||||
|
||||
<body style="margin: 0; padding: 0">
|
||||
<body>
|
||||
<h1 id="loading">Loading...</h1>
|
||||
<script type="module">
|
||||
import init from "./pkg/wgpu_renderer.js";
|
||||
|
|
|
@ -13,5 +13,5 @@ fn vs_main(
|
|||
);
|
||||
|
||||
let world_position = model_matrix * vec4<f32>(model.position, 1.0);
|
||||
return light.matrices[light_matrix_index] * world_position;
|
||||
return light.matrices[light_matrix_index.value] * world_position;
|
||||
}
|
||||
|
|
|
@ -16,8 +16,15 @@ struct Light {
|
|||
@group(1) @binding(0)
|
||||
var<uniform> light: Light;
|
||||
|
||||
// Needs to be 16 bytes in WebGL
|
||||
struct LightMatrixIndex {
|
||||
value: u32,
|
||||
_padding: u32,
|
||||
_padding1: u32,
|
||||
_padding2: u32,
|
||||
}
|
||||
@group(1) @binding(1)
|
||||
var<uniform> light_matrix_index: u32;
|
||||
var<uniform> light_matrix_index: LightMatrixIndex;
|
||||
|
||||
struct VertexInput {
|
||||
@location(0) position: vec3<f32>,
|
||||
|
|
|
@ -41,6 +41,14 @@ impl LightUniform {
|
|||
}
|
||||
}
|
||||
|
||||
#[repr(C)]
|
||||
#[derive(Debug, Default, Copy, Clone, bytemuck::Pod, bytemuck::Zeroable)]
|
||||
pub struct LightMatrixUniform {
|
||||
pub value: u32,
|
||||
// No DownlevelFlags::BUFFER_BINDINGS_NOT_16_BYTE_ALIGNED in WebGL
|
||||
_padding: [u32; 3],
|
||||
}
|
||||
|
||||
pub trait DrawLight<'a> {
|
||||
fn draw_light_mesh(
|
||||
&mut self,
|
||||
|
|
|
@ -2,11 +2,12 @@ use cgmath::prelude::*;
|
|||
use wgpu::{InstanceDescriptor, Backends, TextureView, TextureViewDescriptor, StoreOp};
|
||||
use std::default::Default;
|
||||
use std::mem;
|
||||
use std::num::NonZeroU32;
|
||||
use std::time::Duration;
|
||||
|
||||
use wgpu::util::DeviceExt;
|
||||
use winit::{event::*, window::Window};
|
||||
use winit::dpi::PhysicalSize;
|
||||
use crate::core::light::LightMatrixUniform;
|
||||
|
||||
use super::camera::{Camera, CameraController, CameraUniform};
|
||||
use super::instance::{Instance, InstanceRaw};
|
||||
|
@ -44,14 +45,17 @@ pub struct State {
|
|||
light_depth_bind_group: wgpu::BindGroup,
|
||||
light_depth_pass: RenderPass,
|
||||
light_depth_texture_target_views: [TextureView; SHADOW_MAP_LAYERS as usize],
|
||||
light_matrix_uniform: u32,
|
||||
light_matrix_uniform: LightMatrixUniform,
|
||||
light_matrix_buffer: wgpu::Buffer,
|
||||
}
|
||||
|
||||
impl State {
|
||||
// Creating some of the wgpu types requires async code
|
||||
pub async fn new(window: &Window) -> Self {
|
||||
let size = window.inner_size();
|
||||
log::info!("Creating surface");
|
||||
let mut size = window.inner_size();
|
||||
size.width = size.width.max(1);
|
||||
size.height = size.height.max(1);
|
||||
let instance = wgpu::Instance::new(InstanceDescriptor { backends: Backends::all(), ..Default::default() });
|
||||
let surface = unsafe { instance.create_surface(window) }.unwrap();
|
||||
|
||||
|
@ -64,7 +68,6 @@ impl State {
|
|||
.await
|
||||
.expect("failed to get adapter");
|
||||
|
||||
// TODO: some feature here doesn't work on WASM
|
||||
let (device, queue) = adapter
|
||||
.request_device(
|
||||
&wgpu::DeviceDescriptor {
|
||||
|
@ -111,6 +114,7 @@ impl State {
|
|||
contents: bytemuck::cast_slice(&[camera_uniform]),
|
||||
usage: wgpu::BufferUsages::UNIFORM | wgpu::BufferUsages::COPY_DST,
|
||||
});
|
||||
let camera_uniform_size = mem::size_of::<CameraUniform>() as u64;
|
||||
let camera_bind_group_layout =
|
||||
device.create_bind_group_layout(&wgpu::BindGroupLayoutDescriptor {
|
||||
entries: &[wgpu::BindGroupLayoutEntry {
|
||||
|
@ -119,7 +123,7 @@ impl State {
|
|||
ty: wgpu::BindingType::Buffer {
|
||||
ty: wgpu::BufferBindingType::Uniform,
|
||||
has_dynamic_offset: false,
|
||||
min_binding_size: None,
|
||||
min_binding_size: wgpu::BufferSize::new(camera_uniform_size),
|
||||
},
|
||||
count: None,
|
||||
}],
|
||||
|
@ -182,7 +186,7 @@ impl State {
|
|||
usage: wgpu::BufferUsages::UNIFORM | wgpu::BufferUsages::COPY_DST,
|
||||
});
|
||||
|
||||
let light_matrix_uniform = 0;
|
||||
let light_matrix_uniform = LightMatrixUniform::default();
|
||||
let light_matrix_buffer = device.create_buffer_init(&wgpu::util::BufferInitDescriptor {
|
||||
label: Some("Light Matrix UB"),
|
||||
contents: bytemuck::cast_slice(&[light_matrix_uniform]),
|
||||
|
@ -190,7 +194,7 @@ impl State {
|
|||
});
|
||||
|
||||
let light_uniform_size = mem::size_of::<LightUniform>() as u64;
|
||||
let light_matrix_uniform_size = mem::size_of::<u32>() as u64;
|
||||
let light_matrix_uniform_size = mem::size_of::<LightMatrixUniform>() as u64;
|
||||
let light_bind_group_layout =
|
||||
device.create_bind_group_layout(&wgpu::BindGroupLayoutDescriptor {
|
||||
entries: &[
|
||||
|
@ -502,7 +506,7 @@ impl State {
|
|||
|
||||
// render light to depth textures
|
||||
for i in 0..SHADOW_MAP_LAYERS as usize {
|
||||
self.light_matrix_uniform = i as u32;
|
||||
self.light_matrix_uniform.value = i as u32;
|
||||
self.queue.write_buffer(
|
||||
&self.light_matrix_buffer,
|
||||
0,
|
||||
|
|
|
@ -8,6 +8,7 @@ use winit::keyboard::{KeyCode, PhysicalKey};
|
|||
|
||||
#[cfg(debug_assertions)]
|
||||
fn create_window(event_loop: &EventLoop<()>) -> winit::window::Window {
|
||||
log::info!("Creating window");
|
||||
use winit::dpi::PhysicalSize;
|
||||
WindowBuilder::new()
|
||||
.with_inner_size(PhysicalSize::new(1280, 720))
|
||||
|
@ -18,6 +19,7 @@ fn create_window(event_loop: &EventLoop<()>) -> winit::window::Window {
|
|||
|
||||
#[cfg(not(debug_assertions))]
|
||||
fn create_window(event_loop: &EventLoop<()>) -> winit::window::Window {
|
||||
log::info!("Creating window");
|
||||
WindowBuilder::new()
|
||||
.with_fullscreen(Some(winit::window::Fullscreen::Borderless(None)))
|
||||
.with_maximized(true)
|
||||
|
@ -31,6 +33,7 @@ pub async fn run() {
|
|||
|
||||
#[cfg(target_arch = "wasm32")]
|
||||
{
|
||||
log::info!("Appending canvas to document");
|
||||
use winit::platform::web::WindowExtWebSys;
|
||||
web_sys::window()
|
||||
.and_then(|win| win.document())
|
||||
|
@ -103,6 +106,7 @@ pub async fn run() {
|
|||
}
|
||||
}
|
||||
WindowEvent::Resized(physical_size) => {
|
||||
log::info!("WindowEvent::Resized {}:{}", physical_size.width, physical_size.height);
|
||||
state.resize(*physical_size);
|
||||
window.request_redraw();
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue