Renderer/src/main/java/electrosphere/renderer/anim/AnimChannel.java
2021-05-26 22:16:28 -04:00

185 lines
7.3 KiB
Java

package electrosphere.renderer.anim;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.ListIterator;
import org.joml.Matrix4f;
import org.joml.Quaternionf;
import org.joml.Vector3f;
/**
*
* @author amaterasu
*/
public class AnimChannel {
double timeCurrent;
double timeTotal;
public String nodeID;
public Vector3f startingPosition;
public ArrayList<Keyframe> positionFrame;
public ListIterator<Keyframe> positionFrameIterator;
Keyframe positionFrameCurrent;
Keyframe positionFrameNext;
double nextPositionTime;
public Quaternionf startingRotation;
public ArrayList<Keyframe> rotationFrame;
public ListIterator<Keyframe> rotationFrameIterator;
Keyframe rotationFrameCurrent;
Keyframe rotationFrameNext;
double nextRotationTime;
public ArrayList<Keyframe> scaleFrame;
public ListIterator<Keyframe> scaleFrameIterator;
Keyframe scaleFrameCurrent;
Keyframe scaleFrameNext;
double nextScaleTime;
public AnimChannel(double maxTime){
timeTotal = maxTime;
}
public Vector3f getCurrentPosition(){
Vector3f rVal = new Vector3f();
if(positionFrameCurrent != null){
if(positionFrameNext != null){
double percent_Next = ((timeCurrent - positionFrameCurrent.time) / (positionFrameNext.time - positionFrameCurrent.time));
rVal = new Vector3f().add(new Vector3f().add(positionFrameCurrent.position).mul((float)(1.0 - percent_Next))).add(new Vector3f().add(positionFrameNext.position).mul((float)(percent_Next)));
} else {
rVal = new Vector3f().add(positionFrameCurrent.position);
}
// rVal.add(new Vector3f().add(positionFrameCurrent.position).mul(()/(positionFrameNext.time - positionFrameCurrent.time)));
}
// rVal = rVal.sub(startingPosition);
return rVal;
}
public Quaternionf getCurrentRotation(){
Quaternionf rVal = new Quaternionf();
if(rotationFrameCurrent != null){
if(rotationFrameNext != null){
double percent_Next = ((timeCurrent - rotationFrameCurrent.time) / (rotationFrameNext.time - rotationFrameCurrent.time));
// rVal = new Quaternionf(rotationFrameCurrent.rotation).normalize();//.add(rotationFrameCurrent.rotation);
rVal = new Quaternionf(rotationFrameCurrent.rotation).slerp(rotationFrameNext.rotation, (float)percent_Next);
// rVal = new Quaternionf(rotationFrameCurrent.rotation).normalize().slerp(new Quaternionf(rotationFrameNext.rotation).normalize(), (float)(percent_Next)).rotateAxis((float)(-Math.PI/2), new Vector3f(1,0,0));
} else {
rVal = new Quaternionf(rotationFrameCurrent.rotation);//.add(rotationFrameCurrent.rotation);
}
}
// rVal = rVal.mul(new Quaternionf(startingRotation).invert());
return rVal;
}
public Vector3f getCurrentScale(){
Vector3f rVal = new Vector3f();
if(scaleFrameCurrent != null){
if(scaleFrameNext != null){
double percent_Next = ((timeCurrent - scaleFrameCurrent.time) / (scaleFrameNext.time - scaleFrameCurrent.time));
rVal = new Vector3f().add(new Vector3f().add(scaleFrameCurrent.scale).mul((float)(1.0 - percent_Next))).add(new Vector3f().add(scaleFrameNext.scale).mul((float)(percent_Next)));
} else {
rVal = new Vector3f().add(scaleFrameCurrent.scale);
}
// rVal.add(new Vector3f().add(positionFrameCurrent.position).mul(()/(positionFrameNext.time - positionFrameCurrent.time)));
}
return rVal;
}
public void incrementTime(double incrementValue){
timeCurrent = timeCurrent + incrementValue;
while(positionFrameNext != null && timeCurrent > positionFrameNext.time){
positionFrameCurrent = positionFrameNext;
if(positionFrameIterator.hasNext()){
positionFrameNext = positionFrameIterator.next();
} else {
positionFrameNext = null;
}
}
while(rotationFrameNext != null && timeCurrent > rotationFrameNext.time){
rotationFrameCurrent = rotationFrameNext;
if(rotationFrameIterator.hasNext()){
rotationFrameNext = rotationFrameIterator.next();
} else {
rotationFrameNext = null;
}
}
while(scaleFrameNext != null && timeCurrent > scaleFrameNext.time){
scaleFrameCurrent = scaleFrameNext;
if(scaleFrameIterator.hasNext()){
scaleFrameNext = scaleFrameIterator.next();
} else {
scaleFrameNext = null;
}
}
}
public void rewind(){
timeCurrent = 0;
//TODO: Make sure has at least two frames
positionFrameIterator = positionFrame.listIterator();
if(positionFrameIterator.hasNext()){
positionFrameCurrent = positionFrameIterator.next();
if(positionFrameIterator.hasNext()){
positionFrameNext = positionFrameIterator.next();
nextPositionTime = positionFrameNext.time;
} else {
positionFrameNext = null;
}
}
rotationFrameIterator = rotationFrame.listIterator();
if(rotationFrameIterator.hasNext()){
rotationFrameCurrent = rotationFrameIterator.next();
if(rotationFrameIterator.hasNext()){
rotationFrameNext = rotationFrameIterator.next();
} else {
rotationFrameNext = null;
}
}
scaleFrameIterator = scaleFrame.listIterator();
if(scaleFrameIterator.hasNext()){
scaleFrameCurrent = scaleFrameIterator.next();
if(scaleFrameIterator.hasNext()){
scaleFrameNext = scaleFrameIterator.next();
} else {
scaleFrameNext = null;
}
}
}
public void describeChannel(){
System.out.println("Target object: " + nodeID);
System.out.println("Time: " + timeCurrent + "/" + timeTotal);
System.out.println(positionFrame.size() + " position Frames");
System.out.println(rotationFrame.size() + " rotation Frames");
System.out.println(scaleFrame.size() + " scale Frames");
}
public void fullDescribeChannel(){
System.out.println("Target object: " + nodeID);
System.out.println("Time: " + timeCurrent + "/" + timeTotal);
System.out.println(positionFrame.size() + " position Frames");
Iterator<Keyframe> frameIterator = positionFrame.iterator();
while(frameIterator.hasNext()){
System.out.println(frameIterator.next());
}
System.out.println(rotationFrame.size() + " rotation Frames");
frameIterator = rotationFrame.iterator();
while(frameIterator.hasNext()){
System.out.println(frameIterator.next());
}
System.out.println(scaleFrame.size() + " scale Frames");
frameIterator = scaleFrame.iterator();
while(frameIterator.hasNext()){
System.out.println(frameIterator.next());
}
}
}