mirror of
https://gitlab.com/veloren/veloren.git
synced 2024-08-30 18:12:32 +00:00
Changed to one dynamic model per entity.
This commit is contained in:
parent
d9028ec978
commit
05f53a5316
@ -36,7 +36,7 @@ pub use self::{
|
||||
Vertex as SpriteVertex, VERT_PAGE_SIZE as SPRITE_VERT_PAGE_SIZE,
|
||||
},
|
||||
terrain::{Locals as TerrainLocals, TerrainLayout, Vertex as TerrainVertex},
|
||||
trail::{Instance as TrailInstance, Vertex as TrailVertex},
|
||||
trail::Vertex as TrailVertex,
|
||||
ui::{
|
||||
create_quad as create_ui_quad,
|
||||
create_quad_vert_gradient as create_ui_quad_vert_gradient, create_tri as create_ui_tri,
|
||||
|
@ -1,7 +1,6 @@
|
||||
use super::super::{AaMode, GlobalsLayouts, Vertex as VertexTrait};
|
||||
use bytemuck::{Pod, Zeroable};
|
||||
use std::mem;
|
||||
use vek::*;
|
||||
|
||||
#[repr(C)]
|
||||
#[derive(Copy, Clone, Debug, Zeroable, Pod)]
|
||||
@ -26,49 +25,6 @@ impl VertexTrait for Vertex {
|
||||
const STRIDE: wgpu::BufferAddress = mem::size_of::<Self>() as wgpu::BufferAddress;
|
||||
}
|
||||
|
||||
#[repr(C)]
|
||||
#[derive(Copy, Clone, Debug, Zeroable, Pod)]
|
||||
pub struct Instance {
|
||||
// created_at time, so we can calculate time relativity, needed for relative animation.
|
||||
// can save 32 bits per instance, for trails that are not relatively animated.
|
||||
inst_time: f32,
|
||||
|
||||
// The lifespan in seconds of the trail
|
||||
inst_lifespan: f32,
|
||||
|
||||
// The two positions that define where the line of the object making the trail, e.g. sword tip
|
||||
// and sword hilt
|
||||
inner_pos: [f32; 3],
|
||||
outer_pos: [f32; 3],
|
||||
}
|
||||
|
||||
impl Instance {
|
||||
pub fn new(inst_time: f64, lifespan: f32, inner_pos: Vec3<f32>, outer_pos: Vec3<f32>) -> Self {
|
||||
Self {
|
||||
inst_time: inst_time as f32,
|
||||
inst_lifespan: lifespan,
|
||||
inner_pos: inner_pos.into_array(),
|
||||
outer_pos: outer_pos.into_array(),
|
||||
}
|
||||
}
|
||||
|
||||
fn desc<'a>() -> wgpu::VertexBufferLayout<'a> {
|
||||
const ATTRIBUTES: [wgpu::VertexAttribute; 4] =
|
||||
wgpu::vertex_attr_array![2 => Float32, 3 => Float32, 4 => Float32x3, 5 => Float32x3];
|
||||
wgpu::VertexBufferLayout {
|
||||
array_stride: mem::size_of::<Self>() as wgpu::BufferAddress,
|
||||
step_mode: wgpu::InputStepMode::Instance,
|
||||
attributes: &ATTRIBUTES,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn points(&self) -> ([f32; 3], [f32; 3]) { (self.inner_pos, self.outer_pos) }
|
||||
}
|
||||
|
||||
impl Default for Instance {
|
||||
fn default() -> Self { Self::new(0.0, 0.0, Vec3::zero(), Vec3::zero()) }
|
||||
}
|
||||
|
||||
pub struct TrailPipeline {
|
||||
pub pipeline: wgpu::RenderPipeline,
|
||||
}
|
||||
@ -102,7 +58,7 @@ impl TrailPipeline {
|
||||
vertex: wgpu::VertexState {
|
||||
module: vs_module,
|
||||
entry_point: "main",
|
||||
buffers: &[Vertex::desc(), Instance::desc()],
|
||||
buffers: &[Vertex::desc()],
|
||||
},
|
||||
primitive: wgpu::PrimitiveState {
|
||||
topology: wgpu::PrimitiveTopology::TriangleList,
|
||||
|
@ -877,17 +877,11 @@ pub struct TrailDrawer<'pass_ref, 'pass: 'pass_ref> {
|
||||
}
|
||||
|
||||
impl<'pass_ref, 'pass: 'pass_ref> TrailDrawer<'pass_ref, 'pass> {
|
||||
pub fn draw<'data: 'pass>(
|
||||
&mut self,
|
||||
model: &'data DynamicModel<trail::Vertex>,
|
||||
instances: &'data Instances<trail::Instance>,
|
||||
) {
|
||||
pub fn draw<'data: 'pass>(&mut self, model: &'data DynamicModel<trail::Vertex>) {
|
||||
self.render_pass.set_vertex_buffer(0, model.buf().slice(..));
|
||||
self.render_pass
|
||||
.set_vertex_buffer(0, instances.buf().slice(..));
|
||||
self.render_pass
|
||||
// TODO: since we cast to u32 maybe this should returned by the len/count functions?
|
||||
.draw_indexed(0..model.len() as u32 / 4 * 6, 0, 0..instances.count() as u32);
|
||||
.draw_indexed(0..model.len() as u32 / 4 * 6, 0, 0..0);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1,115 +1,31 @@
|
||||
use super::SceneData;
|
||||
use crate::render::{
|
||||
DynamicModel, Instances, Mesh, Quad, Renderer, TrailDrawer, TrailInstance, TrailVertex,
|
||||
};
|
||||
use crate::render::{DynamicModel, Renderer, TrailDrawer, TrailVertex};
|
||||
use common::uid::Uid;
|
||||
use common_base::span;
|
||||
use std::time::Duration;
|
||||
use vek::*;
|
||||
use std::collections::HashMap;
|
||||
|
||||
pub struct TrailMgr {
|
||||
/// keep track of lifespans
|
||||
trails: Vec<Trail>,
|
||||
|
||||
/// GPU Instance Buffer
|
||||
instances: Instances<TrailInstance>,
|
||||
|
||||
/// GPU vertex buffers
|
||||
dynamic_model: DynamicModel<TrailVertex>,
|
||||
dynamic_models: HashMap<Uid, DynamicModel<TrailVertex>>,
|
||||
}
|
||||
|
||||
impl TrailMgr {
|
||||
pub fn new(renderer: &mut Renderer) -> Self {
|
||||
pub fn new(_renderer: &mut Renderer) -> Self {
|
||||
Self {
|
||||
trails: Vec::new(),
|
||||
instances: default_instances(renderer),
|
||||
dynamic_model: renderer.create_dynamic_model(120),
|
||||
dynamic_models: HashMap::new(),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn maintain(&mut self, renderer: &mut Renderer, scene_data: &SceneData) {
|
||||
pub fn maintain(&mut self, _renderer: &mut Renderer, _scene_data: &SceneData) {
|
||||
span!(_guard, "maintain", "TrailMgr::maintain");
|
||||
if scene_data.trails_enabled {
|
||||
// remove dead Trails
|
||||
self.trails
|
||||
.retain(|p| p.alive_until > scene_data.state.get_time());
|
||||
|
||||
// add new Trails
|
||||
|
||||
self.upload_trails(renderer);
|
||||
} else {
|
||||
// remove all trail lifespans
|
||||
if !self.trails.is_empty() {
|
||||
self.trails.clear();
|
||||
self.upload_trails(renderer);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn upload_trails(&mut self, renderer: &mut Renderer) {
|
||||
span!(_guard, "upload_trails", "TrailMgr::upload_trails");
|
||||
let all_cpu_instances = self
|
||||
.trails
|
||||
.iter()
|
||||
.map(|t| t.instance)
|
||||
.collect::<Vec<TrailInstance>>();
|
||||
|
||||
// TODO: optimise buffer writes
|
||||
let gpu_instances = renderer
|
||||
.create_instances(&all_cpu_instances)
|
||||
.expect("Failed to upload trail instances to the GPU!");
|
||||
|
||||
self.instances = gpu_instances;
|
||||
|
||||
for (i, trail) in self.trails.iter().enumerate() {
|
||||
if i > 0 {
|
||||
if let Some((inner1, outer1)) = self.trails.get(i - 1).map(|t| t.instance.points())
|
||||
{
|
||||
let (inner2, outer2) = trail.instance.points();
|
||||
let point = |pos| TrailVertex { pos };
|
||||
let mut mesh = Mesh::new();
|
||||
mesh.push_quad(Quad::new(
|
||||
point(inner1),
|
||||
point(outer1),
|
||||
point(inner2),
|
||||
point(outer2),
|
||||
));
|
||||
renderer.update_model(&self.dynamic_model, &mesh, 4 * i)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn render<'a>(&'a self, drawer: &mut TrailDrawer<'_, 'a>, scene_data: &SceneData) {
|
||||
span!(_guard, "render", "TrailMgr::render");
|
||||
if scene_data.trails_enabled {
|
||||
drawer.draw(&self.dynamic_model, &self.instances);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn trail_count(&self) -> usize { self.instances.count() }
|
||||
|
||||
pub fn trail_count_visible(&self) -> usize { self.instances.count() }
|
||||
}
|
||||
|
||||
fn default_instances(renderer: &mut Renderer) -> Instances<TrailInstance> {
|
||||
let empty_vec = Vec::new();
|
||||
|
||||
renderer
|
||||
.create_instances(&empty_vec)
|
||||
.expect("Failed to upload trail instances to the GPU!")
|
||||
}
|
||||
|
||||
#[derive(Clone, Copy)]
|
||||
struct Trail {
|
||||
alive_until: f64, // created_at + lifespan
|
||||
instance: TrailInstance,
|
||||
}
|
||||
|
||||
impl Trail {
|
||||
fn new(lifespan: Duration, time: f64, inner_pos: Vec3<f32>, outer_pos: Vec3<f32>) -> Self {
|
||||
Trail {
|
||||
alive_until: time + lifespan.as_secs_f64(),
|
||||
instance: TrailInstance::new(time, lifespan.as_secs_f32(), inner_pos, outer_pos),
|
||||
for dynamic_model in self.dynamic_models.values() {
|
||||
drawer.draw(dynamic_model);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user