【Unity】用Lerp()实现类杀戮尖塔手牌变化
生活随笔
收集整理的這篇文章主要介紹了
【Unity】用Lerp()实现类杀戮尖塔手牌变化
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
Lerp的種類
- math類里的Lerp函數可以對很多種數據類型進行插值,這里主要用的是Vector3的,因為變換position、scale都要用
- 這里的難點是rotation,我試了用Quaternion.Lerp但是放棄了,因為參數必須也是Quaternion類型的(注意大寫),
所以transform.rotation是不能作為參數的,quaternion.Eular(transform.eularangle)轉換成的歐拉角同樣也是用不了的,所以只能從歐拉角或借助LookRotation函數里加Lerp來變換
Hover時手牌強調動畫
- 強調分三部分:放大、向上移動、取消原有的旋轉,既然是Lerp做平滑,就一定是在update里,但是獲取鼠標懸浮事件又需要OnMouseEnter,我的解決方法是用bool類型控制update中Lerp的開啟或關閉
- 放大和向上移動很簡單,注意transform.position就已經是世界坐標了,OnMouseExit的動畫其實也就是lerp的一二兩個參數對調一下
- 注意旋轉值插值的lerp我放在了lookRotation里面,為什么不直接用歐拉角Lerp呢?畢竟它就是Vector3,理論上可以。因為Lerp對歐拉角的Lerp有坑,例如明明一開始歐拉角是(0,0,-15),要Lerp到(0,0,0),但是過程中會出現(0,0,200),查了半天也不知道怎么會有這種問題,所以最后用的是在(0,0,15)和(0,1,0)間的插值,插值的結果再進入lookRotation,實現卡牌被hover時擺正的效果
- 在lookRotation的使用中,理解起來還挺抽象的,表示三維空間的朝向為什么要兩個三維向量呢?例如希望卡牌歐拉角為(0,0,0),正對攝像機,那么lookRotation就是(Vector3.forward,Vector3.up)。我的理解是,想象卡牌是個人,你想讓它看著你,那就是面對著你(forward),頭頂朝天(up),剛才我的旋轉插值本質上就是在卡牌頭頂正對天和斜對天進行插值
- 比較容易被忽略的是,Lerp的插值插值其實并不能保證變換的程度完全是設置的程度,例如一次縮放結束后,可能和變換前有0.01的誤差,雖然它很小,但積累起來就麻煩了,那怎么辦呢?保險起見我在每次Lerp的最后加了一個直接變換
動態生成數量不同的手牌
基礎位置也就是手牌區正中間我已經定好了,在此基礎上計算每張卡的xy相對位移
private Vector3 CalTargetPos(int cardIndex,int cardTotal){//發的手牌數為奇數if(cardTotal % 2 == 1){var xPos = Vector3.left * (math.ceil(cardTotal / 2)) + Vector3.right * cardIndex;var yPos = Vector3.down * math.abs(math.ceil(cardTotal / 2) - cardIndex);return transform.position + CardXSpace * (xPos) + CardYSpace * (yPos);}//為偶數else{var xPos = Vector3.left * ((cardTotal / 2) - 0.5f) + Vector3.right * cardIndex;var yPos = Vector3.down * math.abs(cardTotal / 2 - cardIndex - 0.5f);return transform.position + CardXSpace * (xPos) + CardYSpace * (yPos);}private quaternion CalTargetQua(int cardIndex,int cardTotal){//發的手牌數為奇數if (System.DelivercardNum % 2 == 1){ return quaternion.LookRotation(Vector3.forward,Vector3.up + CardEular * Vector3.right * (cardIndex - math.ceil(cardTotal / 2)));}//為偶數else{return quaternion.LookRotation(Vector3.forward, Vector3.up + CardEular * Vector3.right * (cardIndex - ((cardTotal / 2) - 0.5f))); ;}}}- 每局發牌的數量多少和奇偶性都會對卡牌位置的計算產生影響,如果是奇數,那就一張卡在中間,旁邊的依次排開,如果是偶數,就是對稱分布,所以要先判斷此局發牌數的奇偶性
- 公式比較好理解,就不細講了
- 注意旋轉的函數,雖然這里可以用rotate,但是為了避免四元數和歐拉角轉換過程中可能的問題,還是用LookRotation
手牌數量減少后的重新布局
本質上還是運用上述的計算公式,在有卡牌被銷毀時重新計算,但是難點在于,在原有的腳本調用順序中,無論如何也只能在卡牌被銷毀之前獲取消息,那么此時關卡中的卡牌總數還未變化(因為還未銷毀),所以計算的結果沒變化,我的解決方案就是
- 把將刪除的卡的tag改了
- 按tag查找不會被銷毀的卡、
- 如果還有卡
- 調用重計算位置的方法
- 否則不調用
當卡牌的運動狀態過多時用枚舉類型避免混亂
現在卡牌已經有了好幾種行為了:放大、縮小、發牌時移動、重布局時移動……,為了避免卡牌移動時被hover可能產生的問題,需要在lerp之前加入判斷,但是都設置個bool值就太麻煩了,這時候就需要枚舉類型,我是在brackey的類寶可夢回合制教程里學會的,這是B站視頻鏈接
最后在Updete里用switch判斷狀態,再調用封裝好的函數,比用bool清晰整潔多了
總結
以上是生活随笔為你收集整理的【Unity】用Lerp()实现类杀戮尖塔手牌变化的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: wordpress会员插件_最好的免费W
- 下一篇: Premiere室内背景场景MG动画PR