mirror of
https://github.com/bevyengine/bevy
synced 2024-11-10 07:04:33 +00:00
Skinned extraction speedup (#4428)
# Objective - While animating 501 https://github.com/KhronosGroup/glTF-Sample-Models/tree/master/2.0/BrainStem, I noticed things were getting a little slow - Looking in tracy, the system `extract_skinned_meshes` is taking a lot of time, with a mean duration of 15.17ms ## Solution - ~~Use `Vec` instead of a `SmallVec`~~ - ~~Don't use an temporary variable~~ - Compute the affine matrix as an `Affine3A` instead - Remove the `temp` vec | |mean| |---|---| |base|15.17ms| |~~vec~~|~~9.31ms~~| |~~no temp variable~~|~~11.31ms~~| |removing the temp vector|8.43ms| |affine|13.21ms| |all together|7.23ms|
This commit is contained in:
parent
c5963b4fd5
commit
9d54f33974
3 changed files with 15 additions and 9 deletions
|
@ -29,4 +29,3 @@ bevy_window = { path = "../bevy_window", version = "0.7.0-dev" }
|
|||
bitflags = "1.2"
|
||||
# direct dependency required for derive macro
|
||||
bytemuck = { version = "1", features = ["derive"] }
|
||||
smallvec = "1.0"
|
||||
|
|
|
@ -26,7 +26,6 @@ use bevy_render::{
|
|||
RenderApp, RenderStage,
|
||||
};
|
||||
use bevy_transform::components::GlobalTransform;
|
||||
use smallvec::SmallVec;
|
||||
use std::num::NonZeroU64;
|
||||
|
||||
#[derive(Default)]
|
||||
|
@ -192,15 +191,16 @@ impl SkinnedMeshJoints {
|
|||
let inverse_bindposes = inverse_bindposes.get(&skin.inverse_bindposes)?;
|
||||
let bindposes = inverse_bindposes.iter();
|
||||
let skin_joints = skin.joints.iter();
|
||||
let mut temp =
|
||||
SmallVec::<[Mat4; MAX_JOINTS]>::with_capacity(bindposes.len().min(MAX_JOINTS));
|
||||
let start = buffer.len();
|
||||
for (inverse_bindpose, joint) in bindposes.zip(skin_joints).take(MAX_JOINTS) {
|
||||
let joint_matrix = joints.get(*joint).ok()?.compute_matrix();
|
||||
temp.push(joint_matrix * *inverse_bindpose);
|
||||
if let Ok(joint) = joints.get(*joint) {
|
||||
buffer.push(joint.compute_affine() * *inverse_bindpose);
|
||||
} else {
|
||||
buffer.truncate(start);
|
||||
return None;
|
||||
}
|
||||
}
|
||||
|
||||
let start = buffer.len();
|
||||
buffer.extend(temp);
|
||||
// Pad to 256 byte alignment
|
||||
while buffer.len() % 4 != 0 {
|
||||
buffer.push(Mat4::ZERO);
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use super::Transform;
|
||||
use bevy_ecs::{component::Component, reflect::ReflectComponent};
|
||||
use bevy_math::{const_vec3, Mat3, Mat4, Quat, Vec3};
|
||||
use bevy_math::{const_vec3, Affine3A, Mat3, Mat4, Quat, Vec3};
|
||||
use bevy_reflect::Reflect;
|
||||
use std::ops::Mul;
|
||||
|
||||
|
@ -128,6 +128,13 @@ impl GlobalTransform {
|
|||
Mat4::from_scale_rotation_translation(self.scale, self.rotation, self.translation)
|
||||
}
|
||||
|
||||
/// Returns the 3d affine transformation from this transforms translation,
|
||||
/// rotation, and scale.
|
||||
#[inline]
|
||||
pub fn compute_affine(&self) -> Affine3A {
|
||||
Affine3A::from_scale_rotation_translation(self.scale, self.rotation, self.translation)
|
||||
}
|
||||
|
||||
/// Get the unit vector in the local x direction
|
||||
#[inline]
|
||||
pub fn local_x(&self) -> Vec3 {
|
||||
|
|
Loading…
Reference in a new issue