
I made algorithm a tinnnny bit faster by getting rid of Endtime - Starttime and just saving the Duration as a global var
saves a simple subtraction every tick.
Rama
Simulated Function tick( Float DeltaTime ) { //rotates this actor to face the player camera Self.SetRotation(RInterpTo(Self.Rotation, PlayerController.Rotation, deltatime, 0.7)); }
var float StartTime, EndTime, A, B; function Go( float inA, float inB, float Duration ) { A = inA; B = inB; StartTime = WorldInfo.TimeSeconds; EndTime = StartTime + Duration; } event Tick() { float t; t = ( EndTime - StartTime ) / ( WorldInfo.TimeSeconds - StartTime ); if ( t >= 1 ) { result = B; // TODO: stop the interpolation } else { result = Lerp( Start, End, t ); } }
// ========= SpoofInterp Vars ========= var Rotator startValue; var Rotator endValue; var Rotator currentValue; var float StartTime, EndTime, DurationTime; var bool SpoofInterpRunning; //spoof's RLerp using quaternions static function Rotator RLerpQuat( Rotator A, Rotator B, float Alpha, bool bShortestPath ) { return QuatToRotator( QuatSlerp( QuatFromRotator( A ), QuatFromRotator( B ), Alpha, bShortestPath ) ); } function startSpoofInterp( rotator inA, rotator inB, float Duration ) { //restarts spoof Interpolater //if run again before SpoofInterp gets to t == 1 DurationTime = Duration; startValue = inA; EndValue = inB; StartTime = WorldInfo.TimeSeconds; EndTime = StartTime + Duration; SetTimer(0.01, true, 'SpoofInterp'); SpoofInterpRunning = true; //could use isTimerActive('SpoofInterp') instead //to always know if SpoofInterp is running } function SpoofInterp() { local float t; //for debugging, lets you know when the actor is in the process //of rotating, and spoofInterp is running successfully `log("time"$WorldInfo.TimeSeconds); //based on current time, decide where the actor should be on //scale of 0 to 1 toward 1 = final destination t = ( WorldInfo.TimeSeconds - StartTime ) / ( DurationTime ); //so if the interp was told to run at gameTime 10 for 2 seconds //and 1 second has elapsed, that means we are halfway to goal //so the interpolation should be at 1/2 = 0.5 using equation above //>= 1 means we are at or beyond the desired duration for this interpolation, so finish if ( t >= 1 ) { currentValue = endValue; ClearTimer('SpoofInterp'); SpoofInterpRunning = false; //not needed if use isTimerActive } else { //replace with other interp func as needed currentValue =RLerpQuat( startValue, EndValue, t ); } //My Contribution //makes effect more smooth visually to exclude fringe values //adjust this depending on the precision required //This is how I removed the flicker I was getting even using RLerp if (Vsize(Vector(Self.Rotation) - Vector(currentValue)) < 0.016) { return; } //update Actor's Rotation/Position SetRotation(currentValue); } function tick(float deltatime) { local Rotator angletoCamera; //if you are extending a class that has tick() contents you need super.tick(deltatime); //get angle between this actor location and the player camera location angletoCamera = Rotator(playercontroller.Location - Self.Location); //if this actor is not facing the camera if(Self.Rotation != angletoCamera){ //start the SpoofInterpolator if(!SpoofInterpRunning){ startSpoofInterp(Self.Rotation, angletoCamera, 1.2); } //the joy of the Spoof Interpolator //is that you can determine exactly how long //you want the interpolation to take //here it is set to take 1.2 seconds; } }
if(!SpoofInterpRunning){
ForEach WorldInfo.AllControllers(class'PlayerController', PlayerController) { LocalPlayer = LocalPlayer(PlayerController.Player); }
Leave a comment: