2016-09-09 31 views
0

我想沿着Z軸前後lerp前後數量相同以避免旋轉(因爲我的sprite不是圓形的)。要做到這一點,我計劃隨機使用forward angle,存儲它,lerp然後lerp返回相同的金額。然而,這會給出一些奇怪的爆裂,因爲當向後旋轉開始時,開始角度不會是相同的,但是它是。當我打電話給它時,我同時插入它。有些代碼:Quaternion lerp來回

IEnumerator LerpQuat(QuatLerpInput rotThis, float time, float leftBoundary, float rightBoundary) 
{ 
    /* 
    * we want to rotate forward, then backward the same amount 
    * to avoid spinning. we store the given value to both of these. 
    */ 

    Transform stuffToRot = rotThis.godRayGO.transform; 

    float lastTime = Time.realtimeSinceStartup; 
    float timer = 0.0f; 
    switch (rotThis.rotState) 
    { 
     case (QuatLerpInput.RotationStates.rotAway): 
      rotThis.deltaRot = Random.Range(leftBoundary, rightBoundary); 
      while (timer < time) 
      { 
       stuffToRot.rotation = Quaternion.Euler(stuffToRot.rotation.x, stuffToRot.rotation.y, 
        Mathf.LerpAngle(rotThis.idleRot, rotThis.idleRot + rotThis.deltaRot, timer/time)); 
       timer += (Time.realtimeSinceStartup - lastTime); 
       lastTime = Time.realtimeSinceStartup; 
       yield return null; 
      } 
      rotThis.rotState = QuatLerpInput.RotationStates.setBack; 
      break; 
     case (QuatLerpInput.RotationStates.setBack): 
      while (timer < time) 
      { 
       stuffToRot.rotation = Quaternion.Euler(stuffToRot.rotation.x, stuffToRot.rotation.y, 
        Mathf.LerpAngle(rotThis.idleRot + rotThis.deltaRot, rotThis.idleRot, timer/time)); 
       timer += (Time.realtimeSinceStartup - lastTime); 
       lastTime = Time.realtimeSinceStartup; 
       yield return null; 
      } 
      rotThis.rotState = QuatLerpInput.RotationStates.rotAway; 
      break; 
    } 

} 
public class QuatLerpInput 
{ 
    public GameObject godRayGO; 
    public float deltaRot; 
    public float idleRot; 
    public enum RotationStates 
    { 
     rotAway, setBack 
    } 
    public RotationStates rotState = RotationStates.rotAway; 
    public QuatLerpInput(GameObject godRayGO) 
    { 
     this.godRayGO = godRayGO; 
     deltaRot = godRayGO.transform.rotation.z; 
     idleRot = godRayGO.transform.rotation.z; 
    } 
} 

編輯switch與四元數:

switch (rotThis.rotState) 
    { 
     case (QuatLerpInput.RotationStates.rotAway): 
      rotThis.deltaRot = Random.Range(leftBoundary, rightBoundary); 
      Quaternion destination = new Quaternion(rotThis.idleQuat.x, rotThis.idleQuat.y, rotThis.idleQuat.z + rotThis.deltaRot, 1.0f); 
      rotThis.deltaQuat = destination; 
      while (timer < time) 
      { 
       stuffToRot.rotation = Quaternion.Slerp(rotThis.idleQuat, rotThis.deltaQuat, timer/time); 
       //stuffToRot.rotation = Quaternion.Euler(stuffToRot.rotation.x, stuffToRot.rotation.y, 
       // Mathf.LerpAngle(rotThis.idleRot, rotThis.idleRot + rotThis.deltaRot, timer/time)); 
       timer += (Time.realtimeSinceStartup - lastTime); 
       lastTime = Time.realtimeSinceStartup; 

       yield return null; 
      } 
      rotThis.rotState = QuatLerpInput.RotationStates.setBack; 
      break; 
     case (QuatLerpInput.RotationStates.setBack): 
      while (timer < time) 
      { 
       stuffToRot.rotation = Quaternion.Slerp(rotThis.deltaQuat, rotThis.idleQuat, timer/time); 
       //stuffToRot.rotation = Quaternion.Euler(stuffToRot.rotation.x, stuffToRot.rotation.y, 
       // Mathf.LerpAngle(rotThis.idleRot + rotThis.deltaRot, rotThis.idleRot, timer/time)); 
       timer += (Time.realtimeSinceStartup - lastTime); 
       lastTime = Time.realtimeSinceStartup; 

       yield return null; 
      } 
      rotThis.rotState = QuatLerpInput.RotationStates.rotAway; 
      break; 
    } 
+0

如果有人偶然發現並無法幫助,請隨時要求澄清。我竭盡全力,但我可能已經表達了自己的不清楚,並且在我的最後仍然沒有找到答案。 – agiro

回答

0

對於任何人看到這個,我找到了一個解決方案。

void LerpQuat(QuatLerpInput rotThis, float time, float leftBoundary, float rightBoundary) 
{ 
    /* 
    * we want to rotate forward, then backward the same amount 
    * to avoid spinning. we store the given value to both of these. 
    */ 

    Transform stuffToRot = rotThis.godRayGO.transform; 

    float lastTime = Time.realtimeSinceStartup; 
    float timer = 0.0f; 

    switch (rotThis.rotState) 
    { 
     case (QuatLerpInput.RotationStates.rotAway): 
      rotThis.deltaRot = Random.Range(leftBoundary, rightBoundary); 
      Quaternion destination = new Quaternion(rotThis.idleQuat.x, rotThis.idleQuat.y, rotThis.deltaRot, 1.0f); 
      rotThis.deltaQuat = destination; 
      rotThis.deltaEulerAngle = Vector3.forward * rotThis.deltaRot;    
      StartCoroutine(RotateMe(rotThis, rotThis.idleQuat, rotThis.deltaEulerAngle, initiateAlphaSwap)); 
      break; 
     case (QuatLerpInput.RotationStates.setBack): 
      StartCoroutine(RotateMe(rotThis, rotThis.deltaQuat,-1.0f * rotThis.deltaEulerAngle, initiateAlphaSwap)); 
      break; 
    } 
} 
IEnumerator RotateMe(QuatLerpInput whatToRotate,Quaternion fromWhere,Vector3 byAngles, float inTime) 
{ 
    Quaternion fromAngle = fromWhere; 
    Quaternion toAngle = Quaternion.Euler(whatToRotate.godRayGO.transform.eulerAngles + byAngles); 
    toAngle = new Quaternion(toAngle.x, toAngle.y, toAngle.z, 1.0f); 

    if(whatToRotate.rotState == QuatLerpInput.RotationStates.setBack) 
    { 
     fromAngle = new Quaternion(whatToRotate.RotEndPos.x, whatToRotate.RotEndPos.y, whatToRotate.RotEndPos.z, 1.0f); 
     toAngle = new Quaternion(0.0f, 0.0f, 0.0f, 1.0f); 
    } 

    for (float t = 0.0f; t < 1.0f; t += Time.deltaTime/inTime) 
    { 
     whatToRotate.godRayGO.transform.rotation = Quaternion.Lerp(fromAngle, toAngle, t); 
     yield return null; 
    } 
    if(whatToRotate.rotState == QuatLerpInput.RotationStates.rotAway) 
    { 
     whatToRotate.rotState = QuatLerpInput.RotationStates.setBack; 
     whatToRotate.RotEndPos = new Vector3(toAngle.x, toAngle.y, toAngle.z); 
    } 
    else 
    { 
     whatToRotate.rotState = QuatLerpInput.RotationStates.rotAway; 
    } 

} 

的解決方法是使用Quaternion.Lerp時間可持續的loop並設置狀態循環完成後。這樣它就做我想做的事情。

0

lerping角度相反的,你應該計算目標四元數和使用Quaternion.Slerp插值到隨機四元數和背部。

+0

感謝您的努力。所以我應該給他們完全相同的X和Y以及不同的Z? – agiro

+0

我使用帶有Quaternion的代碼編輯我的問題。依然不起作用,而且運動性非常強。 – agiro

+0

爲了記錄,它與'Slerp'完全相同的彈出 – agiro