您好,登錄后才能下訂單哦!
這篇文章主要介紹了怎么用Unity實現掘地求升游戲的相關知識,內容詳細易懂,操作簡單快捷,具有一定借鑒價值,相信大家閱讀完這篇怎么用Unity實現掘地求升游戲文章都會有所收獲,下面我們一起來看看吧。
1.場景搭建
說干就干,我們來實際操作一下。
新建一個場景,用簡易的3D物體來組裝成猛男和錘子,掛上不同的材質用顏色區分一下。
然后分別掛上Rigibody,因為我們想的是讓2D平面運行,因此在Rigibody上分別鎖了Z軸的移動和X,Y軸的旋轉,順便把錘子上的重力去掉,因為待會要用代碼去控制錘子的位置。
2.控制錘頭
新建一個腳本掛載在父節點上,分別獲取身體和錘子。
我們想要的效果是錘子能一直跟隨鼠標移動且錘頭一直指向鼠標,思路是在錘頭添加一個空的子節點作為錘頭的錨點,然后讓整個錘子圍繞著這個錨點的Z軸旋轉讓錘柄指向身體的方向。
public GameObject body;public GameObject hammer;Rigidbody body_rig;Rigidbody hammer_rig;Transform hammer_anchor;void Start(){ body_rig = body.GetComponent<Rigidbody>(); hammer_rig = hammer.GetComponent<Rigidbody>(); hammer_anchor = hammer.transform.GetChild(2);}//物理相關的操作一般最好放在FixedUpdate里進行,與系統的物理計算保持同步 private void FixedUpdate() { HammerControl(); }void HammerControl(){ //獲取鼠標在屏幕上的坐標并轉換為世界坐標 Vector2 MousePosition = Camera.main.ScreenToWorldPoint(Input.mousePosition); //通過修改錘子身上剛體的速度讓錘子移動,向量的起點用錘頭的坐標 //注意這里要讓錘頭的錨點與錘子本身的坐標的Z值相等,為了讓旋轉軸與世界坐標的Z軸平行,同理鼠標坐標的Z值也直接使用錘子的坐標的Z值 hammer_rig.velocity = (new Vector3(MousePosition.x, MousePosition.y, hammer.transform.position.z) - hammer_anchor.position) * 10; //獲取身體到鼠標的方向 Vector3 direction = (new Vector3(MousePosition.x, MousePosition.y, hammer_anchor.position.z) - new Vector3(body.transform.position.x, body.transform.position.y, hammer_anchor.position.z)).normalized; //讓錘子沿著錘頭錨點轉向身體的方向 hammer.transform.RotateAround(hammer_anchor.position, Vector3.Cross(hammer_anchor.up, direction), Vector3.Angle(hammer_anchor.up, direction)); }
效果如圖:
但是現在問題來了,因為只是簡單模擬功能的效果,所以猛男并沒有手,但是最終我們是希望錘子活動的范圍離猛男有一個最大距離的限制,這樣看起來好像是有一只無形的手來操作錘子一樣,該如何計算這個范圍呢?
由圖可見這個問題的思路是,當錘頭錨點在最大活動范圍里面時是跟著鼠標的坐標走,當處于最大活動范圍外的時候是跟著錘頭錨點與身體坐標的向量和最大移動范圍形成的圓的交點走。這個思路用于代碼上就是當鼠標移動到最大距離范圍之外時得到當前身體到鼠標位置的方向向量,然后讓這個向量的長度等于最大距離的長度。
那么,我們在此基礎上修改一下代碼。
public float MaxDistance; float RelativeDistance;//單獨抽出一個函數獲取最大距離以外的轉換后的鼠標坐標 Vector2 GetConfinedPosition(Vector2 mouseposition) { Vector2 Confined_MousePosition; //去掉body坐標的Z值,避免計算距離時的影響 Vector2 body_position = new Vector2(body.transform.position.x, body.transform.position.y); //計算當前鼠標位置和身體位置的相對距離 RelativeDistance = Vector2.Distance(mouseposition, body_position); if (RelativeDistance > MaxDistance) { //當相對距離大于自己設置的最大距離時,獲取轉換以后的目標坐標 //這里的思路需要稍稍轉一個彎,一開始是獲取的是長度為最大距離,方向為身體到鼠標方向的向量。 //在這個基礎上加上身體的當前坐標,其等于是將這個向量的起始點設置為身體的坐標。 //最后向量與坐標點可以直接相互轉換,此時轉換后的目標坐標就等于這個向量。 Confined_MousePosition = (mouseposition - body_position).normalized * MaxDistance + body_position; } else { //若相對距離小于最大距離那么鼠標當前坐標就是目標坐標 Confined_MousePosition = mouseposition; } return Confined_MousePosition; }
然后把HammerControl()函數內的MousePosition的賦值修改一下:
//獲取鼠標在屏幕上的坐標并轉換為世界坐標,若相對距離大于最大距離則獲得轉換后的坐標 Vector2 MousePosition = GetConfinedPosition(Camera.main.ScreenToWorldPoint(Input.mousePosition));
最后調整MaxDistance到一個合適的值,效果如下:
3.控制身體的逆向運動
現在離實現就差最后一步了,前面思考實現方式的時候說過,錘頭的移動方向與理論上身體移動的方向剛好是相反的,并且同為以身體重心為原點,錘子的最大移動距離為半徑的圓的切線。那么我們順著這個思路去做。
首先還有一個先決條件,錘子不能憑空受力,必須是杵在地上或者掛在障礙物上才行。
我們先在錘頭上加一個碰撞盒子并在錘子上添加一個新建腳本,用幾句簡單的代碼用來檢測錘頭是否碰撞到東西。
public class CollisionDetection : MonoBehaviour { public bool IsCollision; private void OnCollisionEnter(Collision collision) { IsCollision = true; } private void OnCollisionExit(Collision collision) { IsCollision = false; } }
這里要注意的是錘子是錘頭的父物體,所以即便碰撞盒子不在錘子上,作為父物體的錘子依然能檢測到子物體上的碰撞信息,反過來由于錘頭上并沒有剛體組件,所以腳本掛在錘頭上是檢測不到碰撞信息的。
然后當檢測到碰撞時給予身體一個相反的速度值。
void HammerControl() { //在給hammer_rig.velocity賦值后添加下面的代碼 if(hammer.GetComponent<CollisionDetection>().IsCollision) { BodyControl(hammer_rig.velocity); } } void BodyControl(Vector3 velociy) { body_rig.velocity = -velociy; }
最后效果如下:
關于“怎么用Unity實現掘地求升游戲”這篇文章的內容就介紹到這里,感謝各位的閱讀!相信大家對“怎么用Unity實現掘地求升游戲”知識都有一定的了解,大家如果還想學習更多知識,歡迎關注億速云行業資訊頻道。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。