mirror of
https://gitlab.com/veloren/veloren.git
synced 2024-08-30 18:12:32 +00:00
Adds arthropod skeleton
This commit is contained in:
parent
59d195b9bc
commit
f67bf2a539
@ -1207,5 +1207,19 @@
|
||||
generic: "Deadwood"
|
||||
),
|
||||
)
|
||||
)
|
||||
),
|
||||
arthropod: (
|
||||
body: (
|
||||
keyword: "arthropod",
|
||||
names_0: [
|
||||
"Shelob"
|
||||
]
|
||||
),
|
||||
species: (
|
||||
tarantula: (
|
||||
keyword: "tarantula",
|
||||
generic: "Tarantula"
|
||||
)
|
||||
)
|
||||
),
|
||||
)
|
||||
|
22
assets/voxygen/voxel/arthropod_central_manifest.ron
Normal file
22
assets/voxygen/voxel/arthropod_central_manifest.ron
Normal file
@ -0,0 +1,22 @@
|
||||
({
|
||||
(Tarantula, Male): (
|
||||
head: (
|
||||
offset: (-4.5, 0.0, -5.0),
|
||||
central: ("npc.tarantula.male.head"),
|
||||
),
|
||||
chest: (
|
||||
offset: (-5.5, -2.0, -3.0),
|
||||
central: ("npc.tarantula.male.chest"),
|
||||
),
|
||||
),
|
||||
(Tarantula, Female): (
|
||||
head: (
|
||||
offset: (-4.5, 0.0, -5.0),
|
||||
central: ("npc.tarantula.male.head"),
|
||||
),
|
||||
chest: (
|
||||
offset: (-5.5, -2.0, -3.0),
|
||||
central: ("npc.tarantula.male.chest"),
|
||||
),
|
||||
),
|
||||
})
|
118
assets/voxygen/voxel/arthropod_lateral_manifest.ron
Normal file
118
assets/voxygen/voxel/arthropod_lateral_manifest.ron
Normal file
@ -0,0 +1,118 @@
|
||||
({
|
||||
(Tarantula, Male): (
|
||||
mandible_l: (
|
||||
offset: (-4.0, -2.0, -9.0),
|
||||
lateral: ("npc.tarantula.male.mandible_l"),
|
||||
),
|
||||
mandible_r: (
|
||||
offset: (0.0, -2.0, -9.0),
|
||||
lateral: ("npc.tarantula.male.mandible_r"),
|
||||
),
|
||||
wing_fl: (
|
||||
offset: (-6.0, -4.5, -8.0),
|
||||
lateral: ("npc.tarantula.male.wing_fl"),
|
||||
),
|
||||
wing_fr: (
|
||||
offset: (0.0, -4.5, -8.0),
|
||||
lateral: ("npc.tarantula.male.wing_fr"),
|
||||
),
|
||||
wing_bl: (
|
||||
offset: (-11.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.wing_bl"),
|
||||
),
|
||||
wing_br: (
|
||||
offset: (-11.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.wing_br"),
|
||||
),
|
||||
leg_fl: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_fl"),
|
||||
),
|
||||
leg_fr: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_fr"),
|
||||
),
|
||||
leg_fcl: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_fbl"),
|
||||
),
|
||||
leg_fcr: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_fbr"),
|
||||
),
|
||||
leg_bcl: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_bcl"),
|
||||
),
|
||||
leg_bcr: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_bcr"),
|
||||
),
|
||||
leg_bl: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_bl"),
|
||||
),
|
||||
leg_br: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_br"),
|
||||
),
|
||||
),
|
||||
(Tarantula, Female): (
|
||||
mandible_l: (
|
||||
offset: (-4.0, -2.0, -9.0),
|
||||
lateral: ("npc.tarantula.male.mandible_l"),
|
||||
),
|
||||
mandible_r: (
|
||||
offset: (0.0, -2.0, -9.0),
|
||||
lateral: ("npc.tarantula.male.mandible_r"),
|
||||
),
|
||||
wing_fl: (
|
||||
offset: (-6.0, -4.5, -8.0),
|
||||
lateral: ("npc.tarantula.male.wing_fl"),
|
||||
),
|
||||
wing_fr: (
|
||||
offset: (0.0, -4.5, -8.0),
|
||||
lateral: ("npc.tarantula.male.wing_fr"),
|
||||
),
|
||||
wing_bl: (
|
||||
offset: (-11.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.wing_bl"),
|
||||
),
|
||||
wing_br: (
|
||||
offset: (-11.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.wing_br"),
|
||||
),
|
||||
leg_fl: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_fl"),
|
||||
),
|
||||
leg_fr: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_fr"),
|
||||
),
|
||||
leg_fcl: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_fbl"),
|
||||
),
|
||||
leg_fcr: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_fbr"),
|
||||
),
|
||||
leg_bcl: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_bcl"),
|
||||
),
|
||||
leg_bcr: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_bcr"),
|
||||
),
|
||||
leg_bl: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_bl"),
|
||||
),
|
||||
leg_br: (
|
||||
offset: (0.0, -1.0, -8.0),
|
||||
lateral: ("npc.tarantula.male.leg_br"),
|
||||
),
|
||||
),
|
||||
})
|
@ -172,6 +172,7 @@ lazy_static! {
|
||||
theropod,
|
||||
dragon,
|
||||
golem,
|
||||
arthropod,
|
||||
);
|
||||
|
||||
souls
|
||||
|
@ -267,6 +267,7 @@ impl<'a> From<&'a Body> for Psyche {
|
||||
Body::Theropod(_) => 0.0,
|
||||
Body::Ship(_) => 0.0,
|
||||
Body::Dragon(_) => 0.0,
|
||||
Body::Arthropod(_) => 1.0,
|
||||
},
|
||||
sight_dist: 40.0,
|
||||
listen_dist: 30.0,
|
||||
|
@ -1,3 +1,4 @@
|
||||
pub mod arthropod;
|
||||
pub mod biped_large;
|
||||
pub mod biped_small;
|
||||
pub mod bird_large;
|
||||
@ -48,6 +49,7 @@ make_case_elim!(
|
||||
Theropod(body: theropod::Body) = 12,
|
||||
QuadrupedLow(body: quadruped_low::Body) = 13,
|
||||
Ship(body: ship::Body) = 14,
|
||||
Arthropod(body: arthropod::Body) = 15,
|
||||
}
|
||||
);
|
||||
|
||||
@ -85,6 +87,7 @@ pub struct AllBodies<BodyMeta, SpeciesMeta> {
|
||||
pub theropod: BodyData<BodyMeta, theropod::AllSpecies<SpeciesMeta>>,
|
||||
pub quadruped_low: BodyData<BodyMeta, quadruped_low::AllSpecies<SpeciesMeta>>,
|
||||
pub ship: BodyData<BodyMeta, ()>,
|
||||
pub arthropod: BodyData<BodyMeta, arthropod::AllSpecies<SpeciesMeta>>,
|
||||
}
|
||||
|
||||
/// Can only retrieve body metadata by direct index.
|
||||
@ -107,6 +110,7 @@ impl<BodyMeta, SpeciesMeta> core::ops::Index<NpcKind> for AllBodies<BodyMeta, Sp
|
||||
NpcKind::Archaeos => &self.theropod.body,
|
||||
NpcKind::Reddragon => &self.dragon.body,
|
||||
NpcKind::Crocodile => &self.quadruped_low.body,
|
||||
NpcKind::Tarantula => &self.arthropod.body,
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -132,6 +136,7 @@ impl<'a, BodyMeta, SpeciesMeta> core::ops::Index<&'a Body> for AllBodies<BodyMet
|
||||
Body::Golem(_) => &self.golem.body,
|
||||
Body::Theropod(_) => &self.theropod.body,
|
||||
Body::QuadrupedLow(_) => &self.quadruped_low.body,
|
||||
Body::Arthropod(_) => &self.arthropod.body,
|
||||
Body::Ship(_) => &self.ship.body,
|
||||
}
|
||||
}
|
||||
@ -290,6 +295,7 @@ impl Body {
|
||||
theropod::Species::Yale => 1_000.0,
|
||||
},
|
||||
Body::Ship(ship) => ship.mass().0,
|
||||
Body::Arthropod(body) => 500.0,
|
||||
};
|
||||
Mass(m)
|
||||
}
|
||||
@ -396,6 +402,7 @@ impl Body {
|
||||
theropod::Species::Woodraptor => Vec3::new(2.0, 3.0, 2.6),
|
||||
theropod::Species::Yale => Vec3::new(1.5, 3.2, 4.0),
|
||||
},
|
||||
Body::Arthropod(body) => Vec3::new(1.0, 1.0, 1.0),
|
||||
}
|
||||
}
|
||||
|
||||
@ -640,6 +647,7 @@ impl Body {
|
||||
quadruped_low::Species::Deadwood => 120,
|
||||
_ => 70,
|
||||
},
|
||||
Body::Arthropod(_) => 100,
|
||||
Body::Ship(_) => 1000,
|
||||
}
|
||||
}
|
||||
|
66
common/src/comp/body/arthropod.rs
Normal file
66
common/src/comp/body/arthropod.rs
Normal file
@ -0,0 +1,66 @@
|
||||
use rand::{seq::SliceRandom, thread_rng};
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash, Serialize, Deserialize)]
|
||||
pub struct Body {
|
||||
pub species: Species,
|
||||
pub body_type: BodyType,
|
||||
}
|
||||
|
||||
impl Body {
|
||||
pub fn random() -> Self {
|
||||
let mut rng = thread_rng();
|
||||
let species = *(&ALL_SPECIES).choose(&mut rng).unwrap();
|
||||
Self::random_with(&mut rng, &species)
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn random_with(rng: &mut impl rand::Rng, &species: &Species) -> Self {
|
||||
let body_type = *(&ALL_BODY_TYPES).choose(rng).unwrap();
|
||||
Self { species, body_type }
|
||||
}
|
||||
}
|
||||
|
||||
impl From<Body> for super::Body {
|
||||
fn from(body: Body) -> Self { super::Body::Arthropod(body) }
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash, Serialize, Deserialize)]
|
||||
#[repr(u32)]
|
||||
pub enum Species {
|
||||
Tarantula = 0,
|
||||
}
|
||||
|
||||
/// Data representing per-species generic data.
|
||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||
pub struct AllSpecies<SpeciesMeta> {
|
||||
pub tarantula: SpeciesMeta,
|
||||
}
|
||||
|
||||
impl<'a, SpeciesMeta> core::ops::Index<&'a Species> for AllSpecies<SpeciesMeta> {
|
||||
type Output = SpeciesMeta;
|
||||
|
||||
#[inline]
|
||||
fn index(&self, &index: &'a Species) -> &Self::Output {
|
||||
match index {
|
||||
Species::Tarantula => &self.tarantula,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub const ALL_SPECIES: [Species; 1] = [Species::Tarantula];
|
||||
|
||||
impl<'a, SpeciesMeta: 'a> IntoIterator for &'a AllSpecies<SpeciesMeta> {
|
||||
type IntoIter = std::iter::Copied<std::slice::Iter<'static, Self::Item>>;
|
||||
type Item = Species;
|
||||
|
||||
fn into_iter(self) -> Self::IntoIter { ALL_SPECIES.iter().copied() }
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash, Serialize, Deserialize)]
|
||||
#[repr(u32)]
|
||||
pub enum BodyType {
|
||||
Female = 0,
|
||||
Male = 1,
|
||||
}
|
||||
pub const ALL_BODY_TYPES: [BodyType; 2] = [BodyType::Female, BodyType::Male];
|
@ -229,7 +229,8 @@ impl Body {
|
||||
Body::Theropod(_)
|
||||
| Body::QuadrupedMedium(_)
|
||||
| Body::QuadrupedSmall(_)
|
||||
| Body::QuadrupedLow(_) => {
|
||||
| Body::QuadrupedLow(_)
|
||||
| Body::Arthropod(_) => {
|
||||
let dim = self.dimensions().map(|a| a * 0.5);
|
||||
let cd: f32 = if matches!(self, Body::QuadrupedLow(_)) {
|
||||
0.7
|
||||
|
@ -3,7 +3,7 @@
|
||||
use crate::{
|
||||
assets::{self, AssetExt},
|
||||
comp::{
|
||||
biped_large, biped_small, bird_large, golem,
|
||||
arthropod, biped_large, biped_small, bird_large, golem,
|
||||
inventory::{
|
||||
loadout::Loadout,
|
||||
slot::{ArmorSlot, EquipSlot},
|
||||
@ -265,6 +265,11 @@ fn default_main_tool(body: &Body) -> Item {
|
||||
"common.items.npc_weapons.unique.theropodbasic",
|
||||
)),
|
||||
},
|
||||
Body::Arthropod(arthropod) => match arthropod.species {
|
||||
_ => Some(Item::new_from_asset_expect(
|
||||
"common.items.npc_weapons.unique.theropodbasic",
|
||||
)),
|
||||
},
|
||||
Body::BipedLarge(biped_large) => match (biped_large.species, biped_large.body_type) {
|
||||
(biped_large::Species::Occultsaurok, _) => Some(Item::new_from_asset_expect(
|
||||
"common.items.npc_weapons.staff.saurok_staff",
|
||||
@ -752,6 +757,7 @@ mod tests {
|
||||
theropod: Theropod,
|
||||
dragon: Dragon,
|
||||
golem: Golem,
|
||||
arthropod: Arthropod,
|
||||
);
|
||||
}
|
||||
|
||||
|
@ -59,9 +59,9 @@ pub use self::{
|
||||
aura::{Aura, AuraChange, AuraKind, Auras},
|
||||
beam::{Beam, BeamSegment},
|
||||
body::{
|
||||
biped_large, biped_small, bird_large, bird_medium, dragon, fish_medium, fish_small, golem,
|
||||
humanoid, object, quadruped_low, quadruped_medium, quadruped_small, ship, theropod,
|
||||
AllBodies, Body, BodyData,
|
||||
arthropod, biped_large, biped_small, bird_large, bird_medium, dragon, fish_medium,
|
||||
fish_small, golem, humanoid, object, quadruped_low, quadruped_medium, quadruped_small,
|
||||
ship, theropod, AllBodies, Body, BodyData,
|
||||
},
|
||||
buff::{
|
||||
Buff, BuffCategory, BuffChange, BuffData, BuffEffect, BuffId, BuffKind, BuffSource, Buffs,
|
||||
|
@ -406,6 +406,7 @@ impl EntityInfo {
|
||||
Body::QuadrupedLow(body) => Some(get_npc_name(&npc_names.quadruped_low, body.species)),
|
||||
Body::Golem(body) => Some(get_npc_name(&npc_names.golem, body.species)),
|
||||
Body::BipedLarge(body) => Some(get_npc_name(&npc_names.biped_large, body.species)),
|
||||
Body::Arthropod(body) => Some(get_npc_name(&npc_names.arthropod, body.species)),
|
||||
_ => None,
|
||||
};
|
||||
self.name = name.map(str::to_owned);
|
||||
|
@ -22,9 +22,10 @@ pub enum NpcKind {
|
||||
StoneGolem,
|
||||
Reddragon,
|
||||
Crocodile,
|
||||
Tarantula,
|
||||
}
|
||||
|
||||
pub const ALL_NPCS: [NpcKind; 13] = [
|
||||
pub const ALL_NPCS: [NpcKind; 14] = [
|
||||
NpcKind::Humanoid,
|
||||
NpcKind::Wolf,
|
||||
NpcKind::Pig,
|
||||
@ -38,6 +39,7 @@ pub const ALL_NPCS: [NpcKind; 13] = [
|
||||
NpcKind::StoneGolem,
|
||||
NpcKind::Reddragon,
|
||||
NpcKind::Crocodile,
|
||||
NpcKind::Tarantula,
|
||||
];
|
||||
|
||||
/// Body-specific NPC name metadata.
|
||||
@ -133,6 +135,7 @@ pub fn kind_to_body(kind: NpcKind) -> Body {
|
||||
NpcKind::StoneGolem => comp::golem::Body::random().into(),
|
||||
NpcKind::Reddragon => comp::dragon::Body::random().into(),
|
||||
NpcKind::Crocodile => comp::quadruped_low::Body::random().into(),
|
||||
NpcKind::Tarantula => comp::arthropod::Body::random().into(),
|
||||
}
|
||||
}
|
||||
|
||||
@ -303,6 +306,14 @@ impl NpcBody {
|
||||
comp::quadruped_low::Body::random_with,
|
||||
)
|
||||
})
|
||||
.or_else(|| {
|
||||
parse(
|
||||
s,
|
||||
NpcKind::Tarantula,
|
||||
&npc_names.arthropod,
|
||||
comp::arthropod::Body::random_with,
|
||||
)
|
||||
})
|
||||
.ok_or(())
|
||||
}
|
||||
}
|
||||
|
@ -2,7 +2,7 @@ use crate::{
|
||||
astar::Astar,
|
||||
combat,
|
||||
comp::{
|
||||
biped_large, biped_small,
|
||||
arthropod, biped_large, biped_small,
|
||||
character_state::OutputEvents,
|
||||
inventory::slot::{EquipSlot, Slot},
|
||||
item::{Hands, ItemKind, Tool, ToolKind},
|
||||
@ -129,6 +129,7 @@ impl Body {
|
||||
quadruped_low::Species::Deadwood => 140.0,
|
||||
},
|
||||
Body::Ship(_) => 0.0,
|
||||
Body::Arthropod(_) => 135.0,
|
||||
}
|
||||
}
|
||||
|
||||
@ -186,6 +187,7 @@ impl Body {
|
||||
},
|
||||
Body::Ship(ship) if ship.has_water_thrust() => 0.1,
|
||||
Body::Ship(_) => 0.035,
|
||||
Body::Arthropod(_) => 3.5,
|
||||
}
|
||||
}
|
||||
|
||||
@ -214,6 +216,7 @@ impl Body {
|
||||
Body::QuadrupedSmall(_) => Some(300.0 * self.mass().0),
|
||||
Body::Ship(ship) if ship.has_water_thrust() => Some(3500.0 * self.mass().0),
|
||||
Body::Ship(_) => None,
|
||||
Body::Arthropod(_) => Some(300.0 * self.mass().0),
|
||||
}
|
||||
}
|
||||
|
||||
@ -242,6 +245,7 @@ impl Body {
|
||||
| theropod::Species::Woodraptor => Some(0.4 * self.mass().0),
|
||||
_ => None,
|
||||
},
|
||||
Body::QuadrupedMedium(_) => Some(3.0 * self.mass().0),
|
||||
_ => Some(0.4 * self.mass().0),
|
||||
}
|
||||
.map(|f| f * GRAVITY)
|
||||
|
@ -1692,6 +1692,7 @@ impl<'a> AgentData<'a> {
|
||||
"Quad Low Quick" => Tactic::QuadLowQuick,
|
||||
"Quad Low Basic" => Tactic::QuadLowBasic,
|
||||
"Theropod Basic" | "Theropod Bird" => Tactic::Theropod,
|
||||
"Arthropod Basic" => Tactic::Arthropod,
|
||||
"Theropod Charge" => Tactic::CircleCharge {
|
||||
radius: 6,
|
||||
circle_time: 1,
|
||||
@ -1968,6 +1969,9 @@ impl<'a> AgentData<'a> {
|
||||
Tactic::Theropod => {
|
||||
self.handle_theropod_attack(agent, controller, &attack_data, tgt_data, read_data)
|
||||
},
|
||||
Tactic::Arthropod => {
|
||||
self.handle_arthropod_attack(agent, controller, &attack_data, tgt_data, read_data)
|
||||
},
|
||||
Tactic::Turret => {
|
||||
self.handle_turret_attack(agent, controller, &attack_data, tgt_data, read_data)
|
||||
},
|
||||
|
70
voxygen/anim/src/arthropod/alpha.rs
Normal file
70
voxygen/anim/src/arthropod/alpha.rs
Normal file
@ -0,0 +1,70 @@
|
||||
use super::{
|
||||
super::{vek::*, Animation},
|
||||
ArthropodSkeleton, SkeletonAttr,
|
||||
};
|
||||
use common::states::utils::StageSection;
|
||||
|
||||
pub struct AlphaAnimation;
|
||||
|
||||
impl Animation for AlphaAnimation {
|
||||
type Dependency<'a> = (f32, f32, Option<StageSection>, f32);
|
||||
type Skeleton = ArthropodSkeleton;
|
||||
|
||||
#[cfg(feature = "use-dyn-lib")]
|
||||
const UPDATE_FN: &'static [u8] = b"arthropod_alpha\0";
|
||||
|
||||
#[cfg_attr(feature = "be-dyn-lib", export_name = "arthropod_alpha")]
|
||||
fn update_skeleton_inner<'a>(
|
||||
skeleton: &Self::Skeleton,
|
||||
(_velocity, global_time, stage_section, timer): Self::Dependency<'a>,
|
||||
anim_time: f32,
|
||||
_rate: &mut f32,
|
||||
s_a: &SkeletonAttr,
|
||||
) -> Self::Skeleton {
|
||||
let mut next = (*skeleton).clone();
|
||||
|
||||
let (movement1base, movement2base, movement3) = match stage_section {
|
||||
Some(StageSection::Buildup) => (anim_time.powi(2), 0.0, 0.0),
|
||||
Some(StageSection::Swing) => (1.0, anim_time.powi(4), 0.0),
|
||||
Some(StageSection::Recover) => (1.0, 1.0, anim_time),
|
||||
_ => (0.0, 0.0, 0.0),
|
||||
};
|
||||
let pullback = 1.0 - movement3;
|
||||
let subtract = global_time - timer;
|
||||
let check = subtract - subtract.trunc();
|
||||
let mirror = (check - 0.5).signum();
|
||||
let movement1 = mirror * movement1base * pullback;
|
||||
let movement2 = mirror * movement2base * pullback;
|
||||
let movement1abs = movement1base * pullback;
|
||||
let movement2abs = movement2base * pullback;
|
||||
|
||||
next.chest.scale = Vec3::one() / s_a.scaler;
|
||||
|
||||
next.head.position = Vec3::new(0.0, s_a.head.0, s_a.head.1);
|
||||
|
||||
next.chest.position = Vec3::new(0.0, s_a.chest.0, s_a.chest.1);
|
||||
|
||||
next.mandible_l.position = Vec3::new(-s_a.mandible_l.0, s_a.mandible_l.1, s_a.mandible_l.2);
|
||||
next.mandible_r.position = Vec3::new(s_a.mandible_r.0, s_a.mandible_r.1, s_a.mandible_r.2);
|
||||
|
||||
next.wing_fl.position = Vec3::new(-s_a.wing_fl.0, s_a.wing_fl.1, s_a.wing_fl.2);
|
||||
next.wing_fr.position = Vec3::new(s_a.wing_fr.0, s_a.wing_fr.1, s_a.wing_fr.2);
|
||||
|
||||
next.wing_bl.position = Vec3::new(-s_a.wing_bl.0, s_a.wing_bl.1, s_a.wing_bl.2);
|
||||
next.wing_br.position = Vec3::new(s_a.wing_br.0, s_a.wing_br.1, s_a.wing_br.2);
|
||||
|
||||
next.leg_fl.position = Vec3::new(-s_a.leg_fl.0, s_a.leg_fl.1, s_a.leg_fl.2);
|
||||
next.leg_fr.position = Vec3::new(s_a.leg_fr.0, s_a.leg_fr.1, s_a.leg_fr.2);
|
||||
|
||||
next.leg_fcl.position = Vec3::new(-s_a.leg_fcl.0, s_a.leg_fcl.1, s_a.leg_fcl.2);
|
||||
next.leg_fcr.position = Vec3::new(s_a.leg_fcr.0, s_a.leg_fcr.1, s_a.leg_fcr.2);
|
||||
|
||||
next.leg_bcl.position = Vec3::new(-s_a.leg_bcl.0, s_a.leg_bcl.1, s_a.leg_bcl.2);
|
||||
next.leg_bcr.position = Vec3::new(s_a.leg_bcr.0, s_a.leg_bcr.1, s_a.leg_bcr.2);
|
||||
|
||||
next.leg_bl.position = Vec3::new(-s_a.leg_bl.0, s_a.leg_bl.1, s_a.leg_bl.2);
|
||||
next.leg_br.position = Vec3::new(s_a.leg_br.0, s_a.leg_br.1, s_a.leg_br.2);
|
||||
|
||||
next
|
||||
}
|
||||
}
|
54
voxygen/anim/src/arthropod/idle.rs
Normal file
54
voxygen/anim/src/arthropod/idle.rs
Normal file
@ -0,0 +1,54 @@
|
||||
use super::{super::Animation, ArthropodSkeleton, SkeletonAttr};
|
||||
//use std::{f32::consts::PI, ops::Mul};
|
||||
use super::super::vek::*;
|
||||
use std::ops::Mul;
|
||||
|
||||
pub struct IdleAnimation;
|
||||
|
||||
impl Animation for IdleAnimation {
|
||||
type Dependency<'a> = f32;
|
||||
type Skeleton = ArthropodSkeleton;
|
||||
|
||||
#[cfg(feature = "use-dyn-lib")]
|
||||
const UPDATE_FN: &'static [u8] = b"arthropod_idle\0";
|
||||
|
||||
#[cfg_attr(feature = "be-dyn-lib", export_name = "arthropod_idle")]
|
||||
fn update_skeleton_inner<'a>(
|
||||
skeleton: &Self::Skeleton,
|
||||
global_time: Self::Dependency<'a>,
|
||||
anim_time: f32,
|
||||
_rate: &mut f32,
|
||||
s_a: &SkeletonAttr,
|
||||
) -> Self::Skeleton {
|
||||
let mut next = (*skeleton).clone();
|
||||
|
||||
next.chest.scale = Vec3::one() / s_a.scaler;
|
||||
|
||||
next.head.position = Vec3::new(0.0, s_a.head.0, s_a.head.1);
|
||||
|
||||
next.chest.position = Vec3::new(0.0, s_a.chest.0, s_a.chest.1);
|
||||
|
||||
next.mandible_l.position = Vec3::new(-s_a.mandible_l.0, s_a.mandible_l.1, s_a.mandible_l.2);
|
||||
next.mandible_r.position = Vec3::new(s_a.mandible_r.0, s_a.mandible_r.1, s_a.mandible_r.2);
|
||||
|
||||
next.wing_fl.position = Vec3::new(-s_a.wing_fl.0, s_a.wing_fl.1, s_a.wing_fl.2);
|
||||
next.wing_fr.position = Vec3::new(s_a.wing_fr.0, s_a.wing_fr.1, s_a.wing_fr.2);
|
||||
|
||||
next.wing_bl.position = Vec3::new(-s_a.wing_bl.0, s_a.wing_bl.1, s_a.wing_bl.2);
|
||||
next.wing_br.position = Vec3::new(s_a.wing_br.0, s_a.wing_br.1, s_a.wing_br.2);
|
||||
|
||||
next.leg_fl.position = Vec3::new(-s_a.leg_fl.0, s_a.leg_fl.1, s_a.leg_fl.2);
|
||||
next.leg_fr.position = Vec3::new(s_a.leg_fr.0, s_a.leg_fr.1, s_a.leg_fr.2);
|
||||
|
||||
next.leg_fcl.position = Vec3::new(-s_a.leg_fcl.0, s_a.leg_fcl.1, s_a.leg_fcl.2);
|
||||
next.leg_fcr.position = Vec3::new(s_a.leg_fcr.0, s_a.leg_fcr.1, s_a.leg_fcr.2);
|
||||
|
||||
next.leg_bcl.position = Vec3::new(-s_a.leg_bcl.0, s_a.leg_bcl.1, s_a.leg_bcl.2);
|
||||
next.leg_bcr.position = Vec3::new(s_a.leg_bcr.0, s_a.leg_bcr.1, s_a.leg_bcr.2);
|
||||
|
||||
next.leg_bl.position = Vec3::new(-s_a.leg_bl.0, s_a.leg_bl.1, s_a.leg_bl.2);
|
||||
next.leg_br.position = Vec3::new(s_a.leg_br.0, s_a.leg_br.1, s_a.leg_br.2);
|
||||
|
||||
next
|
||||
}
|
||||
}
|
53
voxygen/anim/src/arthropod/jump.rs
Normal file
53
voxygen/anim/src/arthropod/jump.rs
Normal file
@ -0,0 +1,53 @@
|
||||
use super::{super::Animation, ArthropodSkeleton, SkeletonAttr};
|
||||
//use std::f32::consts::PI;
|
||||
use super::super::vek::*;
|
||||
|
||||
pub struct JumpAnimation;
|
||||
|
||||
impl Animation for JumpAnimation {
|
||||
type Dependency<'a> = (f32, Vec3<f32>, Vec3<f32>, f32, Vec3<f32>);
|
||||
type Skeleton = ArthropodSkeleton;
|
||||
|
||||
#[cfg(feature = "use-dyn-lib")]
|
||||
const UPDATE_FN: &'static [u8] = b"arthropod_jump\0";
|
||||
|
||||
#[cfg_attr(feature = "be-dyn-lib", export_name = "arthropod_jump")]
|
||||
fn update_skeleton_inner<'a>(
|
||||
skeleton: &Self::Skeleton,
|
||||
(_velocity, _orientation, _last_ori, _global_time, _avg_vel): Self::Dependency<'a>,
|
||||
_anim_time: f32,
|
||||
_rate: &mut f32,
|
||||
s_a: &SkeletonAttr,
|
||||
) -> Self::Skeleton {
|
||||
let mut next = (*skeleton).clone();
|
||||
|
||||
next.chest.scale = Vec3::one() / s_a.scaler;
|
||||
|
||||
next.head.position = Vec3::new(0.0, s_a.head.0, s_a.head.1);
|
||||
|
||||
next.chest.position = Vec3::new(0.0, s_a.chest.0, s_a.chest.1);
|
||||
|
||||
next.mandible_l.position = Vec3::new(-s_a.mandible_l.0, s_a.mandible_l.1, s_a.mandible_l.2);
|
||||
next.mandible_r.position = Vec3::new(s_a.mandible_r.0, s_a.mandible_r.1, s_a.mandible_r.2);
|
||||
|
||||
next.wing_fl.position = Vec3::new(-s_a.wing_fl.0, s_a.wing_fl.1, s_a.wing_fl.2);
|
||||
next.wing_fr.position = Vec3::new(s_a.wing_fr.0, s_a.wing_fr.1, s_a.wing_fr.2);
|
||||
|
||||
next.wing_bl.position = Vec3::new(-s_a.wing_bl.0, s_a.wing_bl.1, s_a.wing_bl.2);
|
||||
next.wing_br.position = Vec3::new(s_a.wing_br.0, s_a.wing_br.1, s_a.wing_br.2);
|
||||
|
||||
next.leg_fl.position = Vec3::new(-s_a.leg_fl.0, s_a.leg_fl.1, s_a.leg_fl.2);
|
||||
next.leg_fr.position = Vec3::new(s_a.leg_fr.0, s_a.leg_fr.1, s_a.leg_fr.2);
|
||||
|
||||
next.leg_fcl.position = Vec3::new(-s_a.leg_fcl.0, s_a.leg_fcl.1, s_a.leg_fcl.2);
|
||||
next.leg_fcr.position = Vec3::new(s_a.leg_fcr.0, s_a.leg_fcr.1, s_a.leg_fcr.2);
|
||||
|
||||
next.leg_bcl.position = Vec3::new(-s_a.leg_bcl.0, s_a.leg_bcl.1, s_a.leg_bcl.2);
|
||||
next.leg_bcr.position = Vec3::new(s_a.leg_bcr.0, s_a.leg_bcr.1, s_a.leg_bcr.2);
|
||||
|
||||
next.leg_bl.position = Vec3::new(-s_a.leg_bl.0, s_a.leg_bl.1, s_a.leg_bl.2);
|
||||
next.leg_br.position = Vec3::new(s_a.leg_br.0, s_a.leg_br.1, s_a.leg_br.2);
|
||||
|
||||
next
|
||||
}
|
||||
}
|
232
voxygen/anim/src/arthropod/mod.rs
Normal file
232
voxygen/anim/src/arthropod/mod.rs
Normal file
@ -0,0 +1,232 @@
|
||||
pub mod alpha;
|
||||
pub mod idle;
|
||||
pub mod jump;
|
||||
pub mod run;
|
||||
|
||||
// Reexports
|
||||
pub use self::{
|
||||
alpha::AlphaAnimation, idle::IdleAnimation, jump::JumpAnimation, run::RunAnimation,
|
||||
};
|
||||
|
||||
use super::{make_bone, vek::*, FigureBoneData, Offsets, Skeleton};
|
||||
use common::comp::{self};
|
||||
use core::convert::TryFrom;
|
||||
|
||||
pub type Body = comp::arthropod::Body;
|
||||
|
||||
skeleton_impls!(struct ArthropodSkeleton {
|
||||
+ head,
|
||||
+ chest,
|
||||
+ mandible_l,
|
||||
+ mandible_r,
|
||||
+ wing_fl,
|
||||
+ wing_fr,
|
||||
+ wing_bl,
|
||||
+ wing_br,
|
||||
+ leg_fl,
|
||||
+ leg_fr,
|
||||
+ leg_fcl,
|
||||
+ leg_fcr,
|
||||
+ leg_bcl,
|
||||
+ leg_bcr,
|
||||
+ leg_bl,
|
||||
+ leg_br,
|
||||
});
|
||||
|
||||
impl Skeleton for ArthropodSkeleton {
|
||||
type Attr = SkeletonAttr;
|
||||
type Body = Body;
|
||||
|
||||
const BONE_COUNT: usize = 16;
|
||||
#[cfg(feature = "use-dyn-lib")]
|
||||
const COMPUTE_FN: &'static [u8] = b"arthropod_compute_s\0";
|
||||
|
||||
#[cfg_attr(feature = "be-dyn-lib", export_name = "arthropod_compute_s")]
|
||||
|
||||
fn compute_matrices_inner(
|
||||
&self,
|
||||
base_mat: Mat4<f32>,
|
||||
buf: &mut [FigureBoneData; super::MAX_BONE_COUNT],
|
||||
body: Self::Body,
|
||||
) -> Offsets {
|
||||
let chest_mat = base_mat * Mat4::<f32>::from(self.chest);
|
||||
let head_mat = chest_mat * Mat4::<f32>::from(self.head);
|
||||
let mandible_l_mat = head_mat * Mat4::<f32>::from(self.mandible_l);
|
||||
let mandible_r_mat = head_mat * Mat4::<f32>::from(self.mandible_r);
|
||||
let wing_fl_mat = chest_mat * Mat4::<f32>::from(self.wing_fl);
|
||||
let wing_fr_mat = chest_mat * Mat4::<f32>::from(self.wing_fr);
|
||||
let wing_bl_mat = chest_mat * Mat4::<f32>::from(self.wing_bl);
|
||||
let wing_br_mat = chest_mat * Mat4::<f32>::from(self.wing_br);
|
||||
let leg_fl_mat = chest_mat * Mat4::<f32>::from(self.leg_fl);
|
||||
let leg_fr_mat = chest_mat * Mat4::<f32>::from(self.leg_fr);
|
||||
let leg_fcl_mat = chest_mat * Mat4::<f32>::from(self.leg_fcl);
|
||||
let leg_fcr_mat = chest_mat * Mat4::<f32>::from(self.leg_fcr);
|
||||
let leg_bcl_mat = chest_mat * Mat4::<f32>::from(self.leg_bcl);
|
||||
let leg_bcr_mat = chest_mat * Mat4::<f32>::from(self.leg_bcr);
|
||||
let leg_bl_mat = chest_mat * Mat4::<f32>::from(self.leg_bl);
|
||||
let leg_br_mat = chest_mat * Mat4::<f32>::from(self.leg_br);
|
||||
|
||||
*(<&mut [_; Self::BONE_COUNT]>::try_from(&mut buf[0..Self::BONE_COUNT]).unwrap()) = [
|
||||
make_bone(head_mat),
|
||||
make_bone(chest_mat),
|
||||
make_bone(mandible_l_mat),
|
||||
make_bone(mandible_r_mat),
|
||||
make_bone(wing_fl_mat),
|
||||
make_bone(wing_fr_mat),
|
||||
make_bone(wing_bl_mat),
|
||||
make_bone(wing_br_mat),
|
||||
make_bone(leg_fl_mat),
|
||||
make_bone(leg_fr_mat),
|
||||
make_bone(leg_fcl_mat),
|
||||
make_bone(leg_fcr_mat),
|
||||
make_bone(leg_bcl_mat),
|
||||
make_bone(leg_bcr_mat),
|
||||
make_bone(leg_bl_mat),
|
||||
make_bone(leg_br_mat),
|
||||
];
|
||||
|
||||
use comp::arthropod::Species::*;
|
||||
let (mount_bone_mat, mount_bone_ori) = match (body.species, body.body_type) {
|
||||
_ => (chest_mat, self.chest.orientation),
|
||||
};
|
||||
// Offset from the mounted bone's origin.
|
||||
// Note: This could be its own bone if we need to animate it independently.
|
||||
let mount_position = (mount_bone_mat * Vec4::from_point(mount_point(&body)))
|
||||
.homogenized()
|
||||
.xyz();
|
||||
// NOTE: We apply the ori from base_mat externally so we don't need to worry
|
||||
// about it here for now.
|
||||
let mount_orientation = mount_bone_ori;
|
||||
|
||||
Offsets {
|
||||
lantern: None,
|
||||
mount_bone: Transform {
|
||||
position: mount_position,
|
||||
orientation: mount_orientation,
|
||||
scale: Vec3::one(),
|
||||
},
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub struct SkeletonAttr {
|
||||
head: (f32, f32),
|
||||
chest: (f32, f32),
|
||||
mandible_l: (f32, f32, f32),
|
||||
mandible_r: (f32, f32, f32),
|
||||
wing_fl: (f32, f32, f32),
|
||||
wing_fr: (f32, f32, f32),
|
||||
wing_bl: (f32, f32, f32),
|
||||
wing_br: (f32, f32, f32),
|
||||
leg_fl: (f32, f32, f32),
|
||||
leg_fr: (f32, f32, f32),
|
||||
leg_fcl: (f32, f32, f32),
|
||||
leg_fcr: (f32, f32, f32),
|
||||
leg_bcl: (f32, f32, f32),
|
||||
leg_bcr: (f32, f32, f32),
|
||||
leg_bl: (f32, f32, f32),
|
||||
leg_br: (f32, f32, f32),
|
||||
scaler: f32,
|
||||
}
|
||||
|
||||
impl<'a> std::convert::TryFrom<&'a comp::Body> for SkeletonAttr {
|
||||
type Error = ();
|
||||
|
||||
fn try_from(body: &'a comp::Body) -> Result<Self, Self::Error> {
|
||||
match body {
|
||||
comp::Body::Arthropod(body) => Ok(SkeletonAttr::from(body)),
|
||||
_ => Err(()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for SkeletonAttr {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
head: (0.0, 0.0),
|
||||
chest: (0.0, 0.0),
|
||||
mandible_l: (0.0, 0.0, 0.0),
|
||||
mandible_r: (0.0, 0.0, 0.0),
|
||||
wing_fl: (0.0, 0.0, 0.0),
|
||||
wing_fr: (0.0, 0.0, 0.0),
|
||||
wing_bl: (0.0, 0.0, 0.0),
|
||||
wing_br: (0.0, 0.0, 0.0),
|
||||
leg_fl: (0.0, 0.0, 0.0),
|
||||
leg_fr: (0.0, 0.0, 0.0),
|
||||
leg_fcl: (0.0, 0.0, 0.0),
|
||||
leg_fcr: (0.0, 0.0, 0.0),
|
||||
leg_bcl: (0.0, 0.0, 0.0),
|
||||
leg_bcr: (0.0, 0.0, 0.0),
|
||||
leg_bl: (0.0, 0.0, 0.0),
|
||||
leg_br: (0.0, 0.0, 0.0),
|
||||
scaler: 0.0,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a> From<&'a Body> for SkeletonAttr {
|
||||
fn from(body: &'a Body) -> Self {
|
||||
use comp::arthropod::Species::*;
|
||||
Self {
|
||||
head: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (8.0, 4.0),
|
||||
},
|
||||
chest: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (1.0, -7.0),
|
||||
},
|
||||
mandible_l: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (3.0, 0.0, -4.0),
|
||||
},
|
||||
mandible_r: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (3.0, 0.0, -4.0),
|
||||
},
|
||||
wing_fl: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (3.0, 0.0, -4.0),
|
||||
},
|
||||
wing_fr: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (3.0, 0.0, -4.0),
|
||||
},
|
||||
wing_bl: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (3.0, 0.0, -4.0),
|
||||
},
|
||||
wing_br: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (3.0, 0.0, -4.0),
|
||||
},
|
||||
leg_fl: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (2.5, -3.0, -4.0),
|
||||
},
|
||||
leg_fr: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (3.0, -0.5, -7.0),
|
||||
},
|
||||
leg_fcl: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (2.5, -3.0, -4.0),
|
||||
},
|
||||
leg_fcr: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (3.0, -0.5, -7.0),
|
||||
},
|
||||
leg_bcl: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (2.5, -3.0, -4.0),
|
||||
},
|
||||
leg_bcr: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (3.0, -0.5, -7.0),
|
||||
},
|
||||
leg_bl: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (2.5, -3.0, -4.0),
|
||||
},
|
||||
leg_br: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (3.0, -0.5, -7.0),
|
||||
},
|
||||
scaler: match (body.species, body.body_type) {
|
||||
(Tarantula, _) => (1.0),
|
||||
},
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn mount_point(body: &Body) -> Vec3<f32> {
|
||||
use comp::arthropod::{BodyType::*, Species::*};
|
||||
match (body.species, body.body_type) {
|
||||
(_, _) => (0.0, -6.0, 6.0),
|
||||
}
|
||||
.into()
|
||||
}
|
94
voxygen/anim/src/arthropod/run.rs
Normal file
94
voxygen/anim/src/arthropod/run.rs
Normal file
@ -0,0 +1,94 @@
|
||||
use super::{super::Animation, ArthropodSkeleton, SkeletonAttr};
|
||||
//use std::{f32::consts::PI, ops::Mul};
|
||||
use super::super::vek::*;
|
||||
use std::f32::consts::{FRAC_PI_2, PI};
|
||||
|
||||
pub struct RunAnimation;
|
||||
|
||||
impl Animation for RunAnimation {
|
||||
type Dependency<'a> = (Vec3<f32>, Vec3<f32>, Vec3<f32>, f32, Vec3<f32>, f32);
|
||||
type Skeleton = ArthropodSkeleton;
|
||||
|
||||
#[cfg(feature = "use-dyn-lib")]
|
||||
const UPDATE_FN: &'static [u8] = b"arthropod_run\0";
|
||||
|
||||
#[cfg_attr(feature = "be-dyn-lib", export_name = "arthropod_run")]
|
||||
fn update_skeleton_inner<'a>(
|
||||
skeleton: &Self::Skeleton,
|
||||
(velocity, orientation, last_ori, _global_time, avg_vel, acc_vel): Self::Dependency<'a>,
|
||||
anim_time: f32,
|
||||
rate: &mut f32,
|
||||
s_a: &SkeletonAttr,
|
||||
) -> Self::Skeleton {
|
||||
let mut next = (*skeleton).clone();
|
||||
let speed = (Vec2::<f32>::from(velocity).magnitude()).min(22.0);
|
||||
*rate = 1.0;
|
||||
|
||||
//let speednorm = speed / 13.0;
|
||||
let speednorm = (speed / 13.0).powf(0.25);
|
||||
let mixed_vel = acc_vel + anim_time * 6.0; //sets run frequency using speed, with anim_time setting a floor
|
||||
|
||||
let speedmult = 1.0;
|
||||
let lab: f32 = 0.6; //6
|
||||
|
||||
let short = ((1.0
|
||||
/ (0.72
|
||||
+ 0.28 * ((mixed_vel * 1.0 * lab * speedmult + PI * -0.15 - 0.5).sin()).powi(2)))
|
||||
.sqrt())
|
||||
* ((mixed_vel * 1.0 * lab * speedmult + PI * -0.15 - 0.5).sin())
|
||||
* speednorm;
|
||||
|
||||
//
|
||||
let shortalt = (mixed_vel * 1.0 * lab * speedmult + PI * 3.0 / 8.0 - 0.5).sin() * speednorm;
|
||||
|
||||
//FL
|
||||
let foot1a = (mixed_vel * 1.0 * lab * speedmult + 0.0 + PI).sin() * speednorm; //1.5
|
||||
let foot1b = (mixed_vel * 1.0 * lab * speedmult + FRAC_PI_2 + PI).sin() * speednorm; //1.9
|
||||
//FR
|
||||
let foot2a = (mixed_vel * 1.0 * lab * speedmult).sin() * speednorm; //1.2
|
||||
let foot2b = (mixed_vel * 1.0 * lab * speedmult + FRAC_PI_2).sin() * speednorm; //1.6
|
||||
let ori: Vec2<f32> = Vec2::from(orientation);
|
||||
let last_ori = Vec2::from(last_ori);
|
||||
let tilt = if ::vek::Vec2::new(ori, last_ori)
|
||||
.map(|o| o.magnitude_squared())
|
||||
.map(|m| m > 0.001 && m.is_finite())
|
||||
.reduce_and()
|
||||
&& ori.angle_between(last_ori).is_finite()
|
||||
{
|
||||
ori.angle_between(last_ori).min(0.2)
|
||||
* last_ori.determine_side(Vec2::zero(), ori).signum()
|
||||
} else {
|
||||
0.0
|
||||
} * 1.3;
|
||||
let x_tilt = avg_vel.z.atan2(avg_vel.xy().magnitude()) * speednorm;
|
||||
|
||||
next.chest.scale = Vec3::one() / s_a.scaler;
|
||||
|
||||
next.head.position = Vec3::new(0.0, s_a.head.0, s_a.head.1);
|
||||
|
||||
next.chest.position = Vec3::new(0.0, s_a.chest.0, s_a.chest.1);
|
||||
|
||||
next.mandible_l.position = Vec3::new(-s_a.mandible_l.0, s_a.mandible_l.1, s_a.mandible_l.2);
|
||||
next.mandible_r.position = Vec3::new(s_a.mandible_r.0, s_a.mandible_r.1, s_a.mandible_r.2);
|
||||
|
||||
next.wing_fl.position = Vec3::new(-s_a.wing_fl.0, s_a.wing_fl.1, s_a.wing_fl.2);
|
||||
next.wing_fr.position = Vec3::new(s_a.wing_fr.0, s_a.wing_fr.1, s_a.wing_fr.2);
|
||||
|
||||
next.wing_bl.position = Vec3::new(-s_a.wing_bl.0, s_a.wing_bl.1, s_a.wing_bl.2);
|
||||
next.wing_br.position = Vec3::new(s_a.wing_br.0, s_a.wing_br.1, s_a.wing_br.2);
|
||||
|
||||
next.leg_fl.position = Vec3::new(-s_a.leg_fl.0, s_a.leg_fl.1, s_a.leg_fl.2);
|
||||
next.leg_fr.position = Vec3::new(s_a.leg_fr.0, s_a.leg_fr.1, s_a.leg_fr.2);
|
||||
|
||||
next.leg_fcl.position = Vec3::new(-s_a.leg_fcl.0, s_a.leg_fcl.1, s_a.leg_fcl.2);
|
||||
next.leg_fcr.position = Vec3::new(s_a.leg_fcr.0, s_a.leg_fcr.1, s_a.leg_fcr.2);
|
||||
|
||||
next.leg_bcl.position = Vec3::new(-s_a.leg_bcl.0, s_a.leg_bcl.1, s_a.leg_bcl.2);
|
||||
next.leg_bcr.position = Vec3::new(s_a.leg_bcr.0, s_a.leg_bcr.1, s_a.leg_bcr.2);
|
||||
|
||||
next.leg_bl.position = Vec3::new(-s_a.leg_bl.0, s_a.leg_bl.1, s_a.leg_bl.2);
|
||||
next.leg_br.position = Vec3::new(s_a.leg_br.0, s_a.leg_br.1, s_a.leg_br.2);
|
||||
|
||||
next
|
||||
}
|
||||
}
|
@ -47,6 +47,7 @@ macro_rules! skeleton_impls {
|
||||
}
|
||||
}
|
||||
|
||||
pub mod arthropod;
|
||||
pub mod biped_large;
|
||||
pub mod biped_small;
|
||||
pub mod bird_large;
|
||||
|
@ -716,6 +716,7 @@ fn body_species(body: &Body) -> String {
|
||||
Body::Golem(body) => format!("{:?}", body.species),
|
||||
Body::Theropod(body) => format!("{:?}", body.species),
|
||||
Body::QuadrupedLow(body) => format!("{:?}", body.species),
|
||||
Body::Arthropod(body) => format!("{:?}", body.species),
|
||||
Body::Ship(body) => format!("{:?}", body),
|
||||
}
|
||||
}
|
||||
|
@ -2,6 +2,7 @@ use super::cache::{FigureKey, ToolKey};
|
||||
use common::{
|
||||
assets::{self, AssetExt, AssetHandle, DotVoxAsset, ReloadWatcher, Ron},
|
||||
comp::{
|
||||
arthropod::{self, BodyType as ABodyType, Species as ASpecies},
|
||||
biped_large::{self, BodyType as BLBodyType, Species as BLSpecies},
|
||||
biped_small,
|
||||
bird_large::{self, BodyType as BLABodyType, Species as BLASpecies},
|
||||
@ -2151,6 +2152,384 @@ impl TheropodLateralSpec {
|
||||
(lateral, Vec3::from(spec.foot_r.offset))
|
||||
}
|
||||
}
|
||||
|
||||
////
|
||||
#[derive(Deserialize)]
|
||||
struct ArthropodCentralSpec(HashMap<(ASpecies, ABodyType), SidedACentralVoxSpec>);
|
||||
|
||||
#[derive(Deserialize)]
|
||||
struct SidedACentralVoxSpec {
|
||||
head: ArthropodCentralSubSpec,
|
||||
chest: ArthropodCentralSubSpec,
|
||||
}
|
||||
#[derive(Deserialize)]
|
||||
struct ArthropodCentralSubSpec {
|
||||
offset: [f32; 3], // Should be relative to initial origin
|
||||
central: VoxSimple,
|
||||
}
|
||||
#[derive(Deserialize)]
|
||||
struct ArthropodLateralSpec(HashMap<(ASpecies, ABodyType), SidedALateralVoxSpec>);
|
||||
|
||||
#[derive(Deserialize)]
|
||||
struct SidedALateralVoxSpec {
|
||||
mandible_l: ArthropodLateralSubSpec,
|
||||
mandible_r: ArthropodLateralSubSpec,
|
||||
wing_fl: ArthropodLateralSubSpec,
|
||||
wing_fr: ArthropodLateralSubSpec,
|
||||
wing_bl: ArthropodLateralSubSpec,
|
||||
wing_br: ArthropodLateralSubSpec,
|
||||
leg_fl: ArthropodLateralSubSpec,
|
||||
leg_fr: ArthropodLateralSubSpec,
|
||||
leg_fcl: ArthropodLateralSubSpec,
|
||||
leg_fcr: ArthropodLateralSubSpec,
|
||||
leg_bcl: ArthropodLateralSubSpec,
|
||||
leg_bcr: ArthropodLateralSubSpec,
|
||||
leg_bl: ArthropodLateralSubSpec,
|
||||
leg_br: ArthropodLateralSubSpec,
|
||||
}
|
||||
#[derive(Deserialize)]
|
||||
struct ArthropodLateralSubSpec {
|
||||
offset: [f32; 3], // Should be relative to initial origin
|
||||
lateral: VoxSimple,
|
||||
}
|
||||
make_vox_spec!(
|
||||
arthropod::Body,
|
||||
struct ArthropodSpec {
|
||||
central: ArthropodCentralSpec = "voxygen.voxel.Arthropod_central_manifest",
|
||||
lateral: ArthropodLateralSpec = "voxygen.voxel.Arthropod_lateral_manifest",
|
||||
},
|
||||
|FigureKey { body, .. }, spec| {
|
||||
[
|
||||
Some(spec.central.read().0.mesh_head(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.central.read().0.mesh_chest(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_mandible_l(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_mandible_r(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_wing_fl(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_wing_fr(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_wing_bl(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_wing_br(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_leg_fl(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_leg_fr(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_leg_fcl(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_leg_fcr(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_leg_bcl(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_leg_bcr(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_leg_bl(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
Some(spec.lateral.read().0.mesh_leg_br(
|
||||
body.species,
|
||||
body.body_type,
|
||||
)),
|
||||
]
|
||||
},
|
||||
);
|
||||
|
||||
impl ArthropodCentralSpec {
|
||||
fn mesh_head(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No head specification exists for the combination of {:?} and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let central = graceful_load_segment(&spec.head.central.0);
|
||||
|
||||
(central, Vec3::from(spec.head.offset))
|
||||
}
|
||||
|
||||
fn mesh_chest(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No chest specification exists for the combination of {:?} and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let central = graceful_load_segment(&spec.chest.central.0);
|
||||
|
||||
(central, Vec3::from(spec.chest.offset))
|
||||
}
|
||||
}
|
||||
impl ArthropodLateralSpec {
|
||||
fn mesh_mandible_l(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No left mandible specification exists for the combination of {:?} and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment_flipped(&spec.mandible_l.lateral.0, true);
|
||||
|
||||
(lateral, Vec3::from(spec.mandible_l.offset))
|
||||
}
|
||||
|
||||
fn mesh_mandible_r(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No right mandible specification exists for the combination of {:?} and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment(&spec.mandible_r.lateral.0);
|
||||
|
||||
(lateral, Vec3::from(spec.mandible_r.offset))
|
||||
}
|
||||
|
||||
fn mesh_wing_fl(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No front left wing specification exists for the combination of {:?} and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment_flipped(&spec.wing_fl.lateral.0, true);
|
||||
|
||||
(lateral, Vec3::from(spec.wing_fl.offset))
|
||||
}
|
||||
|
||||
fn mesh_wing_fr(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No front right wing specification exists for the combination of {:?} and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment(&spec.wing_fr.lateral.0);
|
||||
|
||||
(lateral, Vec3::from(spec.wing_fr.offset))
|
||||
}
|
||||
|
||||
fn mesh_wing_bl(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No back left wing specification exists for the combination of {:?} and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment_flipped(&spec.wing_bl.lateral.0, true);
|
||||
|
||||
(lateral, Vec3::from(spec.wing_bl.offset))
|
||||
}
|
||||
|
||||
fn mesh_wing_br(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No back right wing specification exists for the combination of {:?} and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment(&spec.wing_br.lateral.0);
|
||||
|
||||
(lateral, Vec3::from(spec.wing_br.offset))
|
||||
}
|
||||
|
||||
fn mesh_leg_fl(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No front left leg specification exists for the combination of {:?} and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment_flipped(&spec.leg_fl.lateral.0, true);
|
||||
|
||||
(lateral, Vec3::from(spec.leg_fl.offset))
|
||||
}
|
||||
|
||||
fn mesh_leg_fr(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No front right leg specification exists for the combination of {:?} and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment(&spec.leg_fr.lateral.0);
|
||||
|
||||
(lateral, Vec3::from(spec.leg_fr.offset))
|
||||
}
|
||||
|
||||
fn mesh_leg_fcl(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No front center left leg specification exists for the combination of {:?} \
|
||||
and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment_flipped(&spec.leg_fcl.lateral.0, true);
|
||||
|
||||
(lateral, Vec3::from(spec.leg_fcl.offset))
|
||||
}
|
||||
|
||||
fn mesh_leg_fcr(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No front center right leg specification exists for the combination of {:?} \
|
||||
and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment(&spec.leg_fcr.lateral.0);
|
||||
|
||||
(lateral, Vec3::from(spec.leg_fcr.offset))
|
||||
}
|
||||
|
||||
fn mesh_leg_bcl(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No back center left leg specification exists for the combination of {:?} and \
|
||||
{:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment_flipped(&spec.leg_bcl.lateral.0, true);
|
||||
|
||||
(lateral, Vec3::from(spec.leg_bcl.offset))
|
||||
}
|
||||
|
||||
fn mesh_leg_bcr(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No back center right leg specification exists for the combination of {:?} \
|
||||
and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment(&spec.leg_bcr.lateral.0);
|
||||
|
||||
(lateral, Vec3::from(spec.leg_bcr.offset))
|
||||
}
|
||||
|
||||
fn mesh_leg_bl(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No back left leg specification exists for the combination of {:?} and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment_flipped(&spec.leg_bl.lateral.0, true);
|
||||
|
||||
(lateral, Vec3::from(spec.leg_bl.offset))
|
||||
}
|
||||
|
||||
fn mesh_leg_br(&self, species: ASpecies, body_type: ABodyType) -> BoneMeshes {
|
||||
let spec = match self.0.get(&(species, body_type)) {
|
||||
Some(spec) => spec,
|
||||
None => {
|
||||
error!(
|
||||
"No back right leg specification exists for the combination of {:?} and {:?}",
|
||||
species, body_type
|
||||
);
|
||||
return load_mesh("not_found", Vec3::new(-5.0, -5.0, -2.5));
|
||||
},
|
||||
};
|
||||
let lateral = graceful_load_segment(&spec.leg_br.lateral.0);
|
||||
|
||||
(lateral, Vec3::from(spec.leg_br.offset))
|
||||
}
|
||||
}
|
||||
////
|
||||
#[derive(Deserialize)]
|
||||
struct FishMediumCentralSpec(HashMap<(FMSpecies, FMBodyType), SidedFMCentralVoxSpec>);
|
||||
|
@ -21,7 +21,7 @@ use crate::{
|
||||
},
|
||||
};
|
||||
use anim::{
|
||||
biped_large::BipedLargeSkeleton, biped_small::BipedSmallSkeleton,
|
||||
arthropod::ArthropodSkeleton, biped_large::BipedLargeSkeleton, biped_small::BipedSmallSkeleton,
|
||||
bird_large::BirdLargeSkeleton, bird_medium::BirdMediumSkeleton, character::CharacterSkeleton,
|
||||
dragon::DragonSkeleton, fish_medium::FishMediumSkeleton, fish_small::FishSmallSkeleton,
|
||||
golem::GolemSkeleton, object::ObjectSkeleton, quadruped_low::QuadrupedLowSkeleton,
|
||||
@ -119,6 +119,7 @@ struct FigureMgrStates {
|
||||
object_states: HashMap<EcsEntity, FigureState<ObjectSkeleton>>,
|
||||
ship_states: HashMap<EcsEntity, FigureState<ShipSkeleton>>,
|
||||
volume_states: HashMap<EcsEntity, FigureState<VolumeKey>>,
|
||||
arthropod_states: HashMap<EcsEntity, FigureState<ArthropodSkeleton>>,
|
||||
}
|
||||
|
||||
impl FigureMgrStates {
|
||||
@ -140,6 +141,7 @@ impl FigureMgrStates {
|
||||
object_states: HashMap::new(),
|
||||
ship_states: HashMap::new(),
|
||||
volume_states: HashMap::new(),
|
||||
arthropod_states: HashMap::new(),
|
||||
}
|
||||
}
|
||||
|
||||
@ -207,6 +209,10 @@ impl FigureMgrStates {
|
||||
self.volume_states.get_mut(entity).map(DerefMut::deref_mut)
|
||||
}
|
||||
},
|
||||
Body::Arthropod(_) => self
|
||||
.arthropod_states
|
||||
.get_mut(entity)
|
||||
.map(DerefMut::deref_mut),
|
||||
}
|
||||
}
|
||||
|
||||
@ -237,6 +243,7 @@ impl FigureMgrStates {
|
||||
self.volume_states.remove(entity).map(|e| e.meta)
|
||||
}
|
||||
},
|
||||
Body::Arthropod(_) => self.arthropod_states.remove(entity).map(|e| e.meta),
|
||||
}
|
||||
}
|
||||
|
||||
@ -258,6 +265,7 @@ impl FigureMgrStates {
|
||||
self.object_states.retain(|k, v| f(k, &mut *v));
|
||||
self.ship_states.retain(|k, v| f(k, &mut *v));
|
||||
self.volume_states.retain(|k, v| f(k, &mut *v));
|
||||
self.arthropod_states.retain(|k, v| f(k, &mut *v));
|
||||
}
|
||||
|
||||
fn count(&self) -> usize {
|
||||
@ -278,6 +286,7 @@ impl FigureMgrStates {
|
||||
+ self.object_states.len()
|
||||
+ self.ship_states.len()
|
||||
+ self.volume_states.len()
|
||||
+ self.arthropod_states.len()
|
||||
}
|
||||
|
||||
fn count_visible(&self) -> usize {
|
||||
@ -350,6 +359,11 @@ impl FigureMgrStates {
|
||||
.iter()
|
||||
.filter(|(_, c)| c.visible())
|
||||
.count()
|
||||
+ self
|
||||
.arthropod_states
|
||||
.iter()
|
||||
.filter(|(_, c)| c.visible())
|
||||
.count()
|
||||
+ self.ship_states.iter().filter(|(_, c)| c.visible()).count()
|
||||
+ self
|
||||
.volume_states
|
||||
@ -377,6 +391,7 @@ pub struct FigureMgr {
|
||||
ship_model_cache: FigureModelCache<ShipSkeleton>,
|
||||
golem_model_cache: FigureModelCache<GolemSkeleton>,
|
||||
volume_model_cache: FigureModelCache<VolumeKey>,
|
||||
arthropod_model_cache: FigureModelCache<ArthropodSkeleton>,
|
||||
states: FigureMgrStates,
|
||||
}
|
||||
|
||||
@ -400,6 +415,7 @@ impl FigureMgr {
|
||||
ship_model_cache: FigureModelCache::new(),
|
||||
golem_model_cache: FigureModelCache::new(),
|
||||
volume_model_cache: FigureModelCache::new(),
|
||||
arthropod_model_cache: FigureModelCache::new(),
|
||||
states: FigureMgrStates::default(),
|
||||
}
|
||||
}
|
||||
@ -433,6 +449,7 @@ impl FigureMgr {
|
||||
self.ship_model_cache.clean(&mut self.col_lights, tick);
|
||||
self.golem_model_cache.clean(&mut self.col_lights, tick);
|
||||
self.volume_model_cache.clean(&mut self.col_lights, tick);
|
||||
self.arthropod_model_cache.clean(&mut self.col_lights, tick);
|
||||
}
|
||||
|
||||
pub fn update_lighting(&mut self, scene_data: &SceneData) {
|
||||
@ -3425,6 +3442,152 @@ impl FigureMgr {
|
||||
body,
|
||||
);
|
||||
},
|
||||
Body::Arthropod(body) => {
|
||||
let (model, skeleton_attr) = self.arthropod_model_cache.get_or_create_model(
|
||||
renderer,
|
||||
&mut self.col_lights,
|
||||
body,
|
||||
inventory,
|
||||
tick,
|
||||
player_camera_mode,
|
||||
player_character_state,
|
||||
&slow_jobs,
|
||||
);
|
||||
|
||||
let state = self
|
||||
.states
|
||||
.arthropod_states
|
||||
.entry(entity)
|
||||
.or_insert_with(|| {
|
||||
FigureState::new(renderer, ArthropodSkeleton::default(), body)
|
||||
});
|
||||
|
||||
// Average velocity relative to the current ground
|
||||
let rel_avg_vel = state.avg_vel - physics.ground_vel;
|
||||
|
||||
let (character, last_character) = match (character, last_character) {
|
||||
(Some(c), Some(l)) => (c, l),
|
||||
_ => continue,
|
||||
};
|
||||
|
||||
if !character.same_variant(&last_character.0) {
|
||||
state.state_time = 0.0;
|
||||
}
|
||||
|
||||
let target_base = match (
|
||||
physics.on_ground.is_some(),
|
||||
rel_vel.magnitude_squared() > MOVING_THRESHOLD_SQR, // Moving
|
||||
physics.in_liquid().is_some(), // In water
|
||||
) {
|
||||
// Standing
|
||||
(true, false, false) => anim::arthropod::IdleAnimation::update_skeleton(
|
||||
&ArthropodSkeleton::default(),
|
||||
time,
|
||||
state.state_time,
|
||||
&mut state_animation_rate,
|
||||
skeleton_attr,
|
||||
),
|
||||
// Running
|
||||
(true, true, false) => anim::arthropod::RunAnimation::update_skeleton(
|
||||
&ArthropodSkeleton::default(),
|
||||
(
|
||||
rel_vel,
|
||||
// TODO: Update to use the quaternion.
|
||||
ori * anim::vek::Vec3::<f32>::unit_y(),
|
||||
state.last_ori * anim::vek::Vec3::<f32>::unit_y(),
|
||||
time,
|
||||
rel_avg_vel,
|
||||
state.acc_vel,
|
||||
),
|
||||
state.state_time,
|
||||
&mut state_animation_rate,
|
||||
skeleton_attr,
|
||||
),
|
||||
// In air
|
||||
(false, _, false) => anim::arthropod::JumpAnimation::update_skeleton(
|
||||
&ArthropodSkeleton::default(),
|
||||
(
|
||||
rel_vel.magnitude(),
|
||||
// TODO: Update to use the quaternion.
|
||||
ori * anim::vek::Vec3::<f32>::unit_y(),
|
||||
state.last_ori * anim::vek::Vec3::<f32>::unit_y(),
|
||||
time,
|
||||
rel_avg_vel,
|
||||
),
|
||||
state.state_time,
|
||||
&mut state_animation_rate,
|
||||
skeleton_attr,
|
||||
),
|
||||
_ => anim::arthropod::IdleAnimation::update_skeleton(
|
||||
&ArthropodSkeleton::default(),
|
||||
time,
|
||||
state.state_time,
|
||||
&mut state_animation_rate,
|
||||
skeleton_attr,
|
||||
),
|
||||
};
|
||||
let target_bones = match &character {
|
||||
CharacterState::ComboMelee(s) => {
|
||||
let stage_index = (s.stage - 1) as usize;
|
||||
let stage_time = s.timer.as_secs_f32();
|
||||
let stage_progress =
|
||||
if let Some(stage) = s.static_data.stage_data.get(stage_index) {
|
||||
match s.stage_section {
|
||||
StageSection::Buildup => {
|
||||
stage_time / stage.base_buildup_duration.as_secs_f32()
|
||||
},
|
||||
StageSection::Swing => {
|
||||
stage_time / stage.base_swing_duration.as_secs_f32()
|
||||
},
|
||||
StageSection::Recover => {
|
||||
stage_time / stage.base_recover_duration.as_secs_f32()
|
||||
},
|
||||
_ => 0.0,
|
||||
}
|
||||
} else {
|
||||
0.0
|
||||
};
|
||||
match s.stage {
|
||||
1 => anim::arthropod::AlphaAnimation::update_skeleton(
|
||||
&target_base,
|
||||
(
|
||||
rel_vel.magnitude(),
|
||||
time,
|
||||
Some(s.stage_section),
|
||||
state.state_time,
|
||||
),
|
||||
stage_progress,
|
||||
&mut state_animation_rate,
|
||||
skeleton_attr,
|
||||
),
|
||||
_ => anim::arthropod::AlphaAnimation::update_skeleton(
|
||||
&target_base,
|
||||
(
|
||||
rel_vel.magnitude(),
|
||||
time,
|
||||
Some(s.stage_section),
|
||||
state.state_time,
|
||||
),
|
||||
stage_progress,
|
||||
&mut state_animation_rate,
|
||||
skeleton_attr,
|
||||
),
|
||||
}
|
||||
},
|
||||
// TODO!
|
||||
_ => target_base,
|
||||
};
|
||||
|
||||
state.skeleton = anim::vek::Lerp::lerp(&state.skeleton, &target_bones, dt_lerp);
|
||||
state.update(
|
||||
renderer,
|
||||
&mut update_buf,
|
||||
&common_params,
|
||||
state_animation_rate,
|
||||
model,
|
||||
body,
|
||||
);
|
||||
},
|
||||
Body::BirdLarge(body) => {
|
||||
let (model, skeleton_attr) = self.bird_large_model_cache.get_or_create_model(
|
||||
renderer,
|
||||
@ -5141,7 +5304,11 @@ impl FigureMgr {
|
||||
object_model_cache,
|
||||
ship_model_cache,
|
||||
golem_model_cache,
|
||||
<<<<<<< HEAD
|
||||
volume_model_cache,
|
||||
=======
|
||||
arthropod_model_cache,
|
||||
>>>>>>> 9b36d29d2 (Adds arthropod skeleton)
|
||||
states:
|
||||
FigureMgrStates {
|
||||
character_states,
|
||||
@ -5159,7 +5326,11 @@ impl FigureMgr {
|
||||
golem_states,
|
||||
object_states,
|
||||
ship_states,
|
||||
<<<<<<< HEAD
|
||||
volume_states,
|
||||
=======
|
||||
arthropod_states,
|
||||
>>>>>>> 9b36d29d2 (Adds arthropod skeleton)
|
||||
},
|
||||
} = self;
|
||||
let col_lights = &*col_lights_;
|
||||
@ -5372,6 +5543,22 @@ impl FigureMgr {
|
||||
),
|
||||
)
|
||||
}),
|
||||
Body::Arthropod(body) => arthropod_states
|
||||
.get(&entity)
|
||||
.filter(|state| filter_state(*state))
|
||||
.map(move |state| {
|
||||
(
|
||||
state.bound(),
|
||||
arthropod_model_cache.get_model(
|
||||
col_lights,
|
||||
body,
|
||||
inventory,
|
||||
tick,
|
||||
player_camera_mode,
|
||||
character_state,
|
||||
),
|
||||
)
|
||||
}),
|
||||
Body::Object(body) => object_states
|
||||
.get(&entity)
|
||||
.filter(|state| filter_state(*state))
|
||||
|
Loading…
Reference in New Issue
Block a user