Spaces:
Sleeping
Sleeping
| export interface Keyframe { | |
| id: string; | |
| time: number; | |
| position: [number, number, number]; | |
| rotation: [number, number, number]; | |
| scale: [number, number, number]; | |
| easing: 'linear' | 'ease-in' | 'ease-out' | 'ease-in-out'; | |
| } | |
| export interface Track { | |
| objectId: string; | |
| keyframes: Keyframe[]; | |
| } | |
| export function interpolateKF( | |
| a: Keyframe, | |
| b: Keyframe, | |
| t: number | |
| ): { position: [number,number,number]; rotation: [number,number,number]; scale: [number,number,number] } { | |
| const ease = (x: number, type: Keyframe['easing']): number => { | |
| switch (type) { | |
| case 'ease-in': return x * x; | |
| case 'ease-out': return 1 - (1 - x) * (1 - x); | |
| case 'ease-in-out': return x < 0.5 ? 2*x*x : 1 - Math.pow(-2*x+2, 2)/2; | |
| default: return x; | |
| } | |
| }; | |
| const et = ease(t, b.easing); | |
| const lerp = (a: number, b: number) => a + (b - a) * et; | |
| const lerpV3 = ( | |
| a: [number,number,number], | |
| b: [number,number,number] | |
| ): [number,number,number] => [ | |
| lerp(a[0], b[0]), | |
| lerp(a[1], b[1]), | |
| lerp(a[2], b[2]), | |
| ]; | |
| return { | |
| position: lerpV3(a.position, b.position), | |
| rotation: lerpV3(a.rotation, b.rotation), | |
| scale: lerpV3(a.scale, b.scale), | |
| }; | |
| } | |
| export function getFramesAtTime(keyframes: Keyframe[], time: number) { | |
| const sorted = [...keyframes].sort((a, b) => a.time - b.time); | |
| if (!sorted.length) return null; | |
| if (time <= sorted[0].time) return { a: sorted[0], b: sorted[0], t: 0 }; | |
| const last = sorted[sorted.length - 1]; | |
| if (time >= last.time) return { a: last, b: last, t: 0 }; | |
| for (let i = 0; i < sorted.length - 1; i++) { | |
| if (time >= sorted[i].time && time <= sorted[i+1].time) { | |
| const span = sorted[i+1].time - sorted[i].time; | |
| const t = span === 0 ? 0 : (time - sorted[i].time) / span; | |
| return { a: sorted[i], b: sorted[i+1], t }; | |
| } | |
| } | |
| return null; | |
| } |