veloren_voxygen_anim/quadruped_low/
combomelee.rs1use super::{
2 super::{Animation, vek::*},
3 QuadrupedLowSkeleton, SkeletonAttr, quadruped_low_alpha, quadruped_low_beta,
4};
5use common::states::utils::StageSection;
6
7pub struct ComboAnimation;
8impl Animation for ComboAnimation {
9 type Dependency<'a> = (Option<&'a str>, StageSection, usize, f32, f32);
10 type Skeleton = QuadrupedLowSkeleton;
11
12 #[cfg(feature = "use-dyn-lib")]
13 const UPDATE_FN: &'static [u8] = b"quadruped_low_combo\0";
14
15 #[cfg_attr(feature = "be-dyn-lib", export_name = "quadruped_low_combo")]
16 fn update_skeleton_inner(
17 skeleton: &Self::Skeleton,
18 (ability_id, stage_section, current_strike, global_time, timer): Self::Dependency<'_>,
19 anim_time: f32,
20 rate: &mut f32,
21 s_a: &SkeletonAttr,
22 ) -> Self::Skeleton {
23 *rate = 1.0;
24 let mut next = (*skeleton).clone();
25
26 let _multi_strike_pullback = 1.0
27 - if matches!(stage_section, StageSection::Recover) {
28 anim_time.powi(4)
29 } else {
30 0.0
31 };
32
33 for strike in 0..=current_strike {
34 match ability_id {
35 Some("common.abilities.custom.hydra.multi_bite") => {
36 let (movement1base, movement2base, movement3) = match stage_section {
37 StageSection::Buildup => (anim_time.sqrt(), 0.0, 0.0),
38 StageSection::Action => (1.0, anim_time.powi(4), 0.0),
39 StageSection::Recover => (1.0, 1.0, anim_time),
40 _ => (0.0, 0.0, 0.0),
41 };
42 let pullback = 1.0 - movement3;
43 let subtract = global_time - timer;
44 let check = subtract - subtract.trunc();
45 let mirror = (check - 0.5).signum();
46 let twitch3 = (mirror * movement3 * 9.0).sin();
47 let movement1 = mirror * movement1base * pullback;
48 let movement2 = mirror * movement2base * pullback;
49 let movement1abs = movement1base * pullback;
50 let movement2abs = movement2base * pullback;
51
52 match strike {
53 2 => {
54 next.head_l_upper.orientation = Quaternion::rotation_z(twitch3 * -0.7);
55
56 next.head_l_lower.orientation =
57 Quaternion::rotation_z(movement1abs * 0.5 + movement2abs * 0.2)
58 * Quaternion::rotation_y(
59 movement1abs * -0.4 + movement2abs * -0.2,
60 )
61 * Quaternion::rotation_x(
62 movement1abs * 0.35 + movement2abs * -0.9,
63 );
64
65 next.jaw_l.orientation =
66 Quaternion::rotation_x(movement1abs * -0.5 + movement2abs * 0.5);
67
68 next.head_c_upper.orientation = Quaternion::rotation_z(twitch3 * -0.7);
69
70 next.head_c_lower.orientation =
71 Quaternion::rotation_x(movement1abs * 0.35 + movement2abs * -0.9);
72
73 next.jaw_c.orientation =
74 Quaternion::rotation_x(movement1abs * -0.5 + movement2abs * 0.5);
75
76 next.head_r_upper.orientation = Quaternion::rotation_z(twitch3 * -0.7);
77
78 next.head_r_lower.orientation =
79 Quaternion::rotation_z(movement1abs * -0.5 + movement2abs * -0.2)
80 * Quaternion::rotation_y(
81 movement1abs * 0.4 + movement2abs * 0.2,
82 )
83 * Quaternion::rotation_x(
84 movement1abs * 0.35 + movement2abs * -0.9,
85 );
86
87 next.jaw_r.orientation =
88 Quaternion::rotation_x(movement1abs * -0.5 + movement2abs * 0.5);
89
90 next.chest.orientation =
91 Quaternion::rotation_z(movement1 * -0.2 + movement2 * 0.6);
92
93 next.tail_front.orientation = Quaternion::rotation_x(0.25)
94 * Quaternion::rotation_z(movement1 * -1.0 + movement2 * 2.2);
95
96 next.tail_rear.orientation = Quaternion::rotation_x(-0.12)
97 * Quaternion::rotation_z(movement1 * -0.6 + movement2 * 0.6);
98 },
99 0 | 1 => {
100 let dir = match strike {
101 0 => 1.0,
102 _ => -1.0,
103 };
104 next.head_l_upper.orientation = Quaternion::rotation_z(twitch3 * 0.2);
105
106 next.head_l_lower.orientation =
107 Quaternion::rotation_x(movement1abs * 0.4 + movement2abs * -1.2);
108
109 next.jaw_l.orientation =
110 Quaternion::rotation_x(movement1abs * -0.9 + movement2abs * 0.9);
111
112 next.head_c_upper.orientation = Quaternion::rotation_z(twitch3 * 0.2);
113
114 next.head_c_lower.orientation =
115 Quaternion::rotation_x(movement1abs * 0.5 + movement2abs * -1.5);
116
117 next.jaw_c.orientation =
118 Quaternion::rotation_x(movement1abs * -0.9 + movement2abs * 0.9);
119
120 next.head_r_upper.orientation = Quaternion::rotation_z(twitch3 * 0.2);
121
122 next.head_r_lower.orientation =
123 Quaternion::rotation_x(movement1abs * 0.4 + movement2abs * -1.2);
124
125 next.jaw_r.orientation =
126 Quaternion::rotation_x(movement1abs * -0.9 + movement2abs * 0.9);
127
128 next.chest.orientation = Quaternion::rotation_z(
129 movement1 * 0.2 * dir + movement2 * -0.3 * dir,
130 );
131
132 next.tail_front.orientation = Quaternion::rotation_x(0.15)
133 * Quaternion::rotation_z(movement1 * 0.4 + movement2 * 0.2);
134
135 next.tail_rear.orientation = Quaternion::rotation_x(-0.12)
136 * Quaternion::rotation_z(movement1 * 0.4 + movement2 * 0.2);
137 },
138 _ => {},
139 }
140 },
141 Some(
142 "common.abilities.custom.icedrake.multi_bite"
143 | "common.abilities.custom.icedrake.icy_bite"
144 | "common.abilities.custom.driggle.bite",
145 ) => {
146 let (movement1base, movement2base, movement3) = match stage_section {
147 StageSection::Buildup => (anim_time.sqrt(), 0.0, 0.0),
148 StageSection::Action => (1.0, anim_time.powi(4), 0.0),
149 StageSection::Recover => (1.0, 1.0, anim_time),
150 _ => (0.0, 0.0, 0.0),
151 };
152 let pullback = 1.0 - movement3;
153 let subtract = global_time - timer;
154 let check = subtract - subtract.trunc();
155 let mirror = (check - 0.5).signum();
156 let twitch3 = (mirror * movement3 * 9.0).sin();
157 let movement1 = mirror * movement1base * pullback;
158 let movement2 = mirror * movement2base * pullback;
159 let movement1abs = movement1base * pullback;
160 let movement2abs = movement2base * pullback;
161
162 match strike {
163 0 | 2 => {
164 next.head_c_upper.orientation = Quaternion::rotation_z(twitch3 * -0.7);
165
166 next.head_c_lower.orientation =
167 Quaternion::rotation_x(movement1abs * 0.35 + movement2abs * -0.9)
168 * Quaternion::rotation_y(movement1 * 0.7 + movement2 * -1.0);
169
170 next.jaw_c.orientation =
171 Quaternion::rotation_x(movement1abs * -0.5 + movement2abs * 0.5);
172 next.chest.orientation =
173 Quaternion::rotation_y(movement1 * -0.08 + movement2 * 0.15)
174 * Quaternion::rotation_z(movement1 * -0.2 + movement2 * 0.6);
175
176 next.tail_front.orientation = Quaternion::rotation_x(0.15)
177 * Quaternion::rotation_z(movement1 * -0.4 + movement2 * -0.2);
178
179 next.tail_rear.orientation = Quaternion::rotation_x(-0.12)
180 * Quaternion::rotation_z(movement1 * -0.4 + movement2 * -0.2);
181 },
182 1 => {
183 next.head_c_upper.orientation = Quaternion::rotation_z(twitch3 * 0.2);
184
185 next.head_c_lower.orientation =
186 Quaternion::rotation_x(movement1abs * 0.15 + movement2abs * -0.6)
187 * Quaternion::rotation_y(movement1 * -0.1 + movement2 * 0.15);
188
189 next.jaw_c.orientation =
190 Quaternion::rotation_x(movement1abs * -0.9 + movement2abs * 0.9);
191 next.chest.orientation =
192 Quaternion::rotation_y(movement1 * 0.08 + movement2 * -0.15)
193 * Quaternion::rotation_z(movement1 * 0.2 + movement2 * -0.3);
194
195 next.tail_front.orientation = Quaternion::rotation_x(0.15)
196 * Quaternion::rotation_z(movement1 * 0.4 + movement2 * 0.2);
197
198 next.tail_rear.orientation = Quaternion::rotation_x(-0.12)
199 * Quaternion::rotation_z(movement1 * 0.4 + movement2 * 0.2);
200 },
201 _ => {},
202 }
203 },
204 Some(
205 "common.abilities.custom.asp.singlestrike"
206 | "common.abilities.custom.maneater.singlestrike"
207 | "common.abilities.custom.quadlowbasic.singlestrike",
208 ) => {
209 quadruped_low_alpha(
210 &mut next,
211 s_a,
212 stage_section,
213 anim_time,
214 global_time,
215 timer,
216 );
217 },
218 Some(
219 "common.abilities.custom.basilisk.triplestrike"
220 | "common.abilities.custom.quadlowbasic.triplestrike"
221 | "common.abilities.custom.quadlowbreathe.triplestrike"
222 | "common.abilities.custom.quadlowtail.triplestrike"
223 | "common.abilities.custom.rocksnapper.triplestrike",
224 ) => match strike {
225 0 | 2 => {
226 quadruped_low_alpha(
227 &mut next,
228 s_a,
229 stage_section,
230 anim_time,
231 global_time,
232 timer,
233 );
234 },
235 1 => {
236 quadruped_low_beta(
237 &mut next,
238 s_a,
239 stage_section,
240 anim_time,
241 global_time,
242 timer,
243 );
244 },
245 _ => {},
246 },
247 Some("common.abilities.custom.quadlowquick.quadstrike") => match strike {
248 0 | 2 | 3 => {
249 quadruped_low_alpha(
250 &mut next,
251 s_a,
252 stage_section,
253 anim_time,
254 global_time,
255 timer,
256 );
257 },
258 1 => {
259 quadruped_low_beta(
260 &mut next,
261 s_a,
262 stage_section,
263 anim_time,
264 global_time,
265 timer,
266 );
267 },
268 _ => {},
269 },
270 Some("common.abilities.custom.dwarves.snaretongue.tongue") => {
271 let (movement1base, movement2base, movement3) = match stage_section {
272 StageSection::Buildup => (anim_time.sqrt(), 0.0, 0.0),
273 StageSection::Action => (1.0, anim_time.powi(4), 0.0),
274 StageSection::Recover => (1.0, 1.0, anim_time),
275 _ => (0.0, 0.0, 0.0),
276 };
277 let pullback = 1.0 - movement3;
278 let subtract = global_time - timer;
279 let check = subtract - subtract.trunc();
280 let mirror = (check - 0.5).signum();
281 let twitch3 = (mirror * movement3 * 9.0).sin();
282 let movement1 = mirror * movement1base * pullback;
283 let movement2 = mirror * movement2base * pullback;
284 let movement1abs = movement1base * pullback;
285 let movement2abs = movement2base * pullback;
286
287 next.head_c_upper.orientation = Quaternion::rotation_z(twitch3 * -0.7);
288 next.head_c_lower.orientation =
289 Quaternion::rotation_x(movement1abs * 0.35 + movement2abs * -0.4)
290 * Quaternion::rotation_y(movement1 * 0.7 + movement2 * -0.7);
291
292 next.jaw_c.orientation =
293 Quaternion::rotation_x(movement2abs * -0.8 + movement3 * -0.6);
294 next.chest.orientation =
295 Quaternion::rotation_y(movement1 * -0.08 + movement2 * 0.15)
296 * Quaternion::rotation_z(movement1 * -0.2 + movement2 * 0.6);
297
298 next.tail_front.position = Vec3::new(
299 0.0,
300 s_a.tail_front.0 + (4.0 * s_a.tail_front.0 * movement2abs),
301 s_a.tail_front.1,
302 );
303 next.tail_rear.position =
304 Vec3::new(0.0, 3.0 * s_a.tail_rear.0 * movement2abs, s_a.tail_rear.1);
305 next.tail_front.orientation = Quaternion::rotation_x(movement3 * 0.15);
306 },
307 _ => {},
308 }
309 }
310 next
311 }
312}