如何解决Unity 按钮滚动 3D 骰子,在按钮上寻找刚体而不是骰子对象
我是 Unity 的新手,一直在尝试掷骰子。我遇到了一组教程,这些教程允许我创建一个 3d 模具(该模具使用 Rigidbody 和 Mesh Collider)并编写脚本使其在按下空格键时滚动,如下所示:
Dice.cs:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Dice : MonoBehaviour
{
Rigidbody rb;
bool hasLanded;
bool thrown;
Vector3 initPosition;
public int diceValue;
public DiceSide[] diceSides;
// Start is called before the first frame update
void Start()
{
rb = GetComponent<Rigidbody>();
initPosition = transform.position;
rb.useGravity = false;
}
// Update is called once per frame
void Update()
{
if (Input.GetKeyDown(KeyCode.Space)){
RollDice();
}
if (rb.IsSleeping() && !hasLanded && thrown)
{
hasLanded = true;
rb.useGravity = false;
rb.isKinematic = true;
SideValueCheck();
}
else if (rb.IsSleeping() && hasLanded && diceValue == 0)
{
RollAgain();
}
}
void RollDice()
{
if (!thrown && !hasLanded)
{
thrown = true;
rb.useGravity = true;
rb.AddTorque(Random.Range(0,500),Random.Range(0,500));
}
else if (thrown && hasLanded)
{
Reset();
}
}
void Reset()
{
transform.position = initPosition;
thrown = false;
hasLanded = false;
rb.useGravity = false;
rb.isKinematic = false;
}
void RollAgain()
{
Reset();
thrown = true;
rb.useGravity = true;
rb.AddTorque(Random.Range(0,500));
}
void SideValueCheck()
{
diceValue = 0;
foreach (DiceSide side in diceSides)
{
if (side.OnGround())
{
diceValue = side.sideValue;
Debug.Log(diceValue + " has been rolled!");
}
}
}
}
DiceSide.cs:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class DiceSide : MonoBehaviour
{
// Start is called before the first frame update
void Start()
{
}
// Update is called once per frame
void Update()
{
}
bool onGround;
public int sideValue;
private void OnTriggerStay(Collider col)
{
if(col.tag == "Ground")
{
onGround = true;
}
}
private void OnTriggerExit(Collider col)
{
if(col.tag == "Ground")
{
onGround = true;
}
}
public bool OnGround()
{
return onGround;
}
}
骰子的每一面都有一个球体,DiceSide.cs 附着在球体上,其中包含与给定面相反的侧面值,而 Dice.cs 附着在主骰子本身上。
以上所有工作都很好。
我面临的问题是,我想在点击按钮后掷骰子,而不是按一个键(在这种情况下,空格键)。
为此,我修改了 Dice.cs 代码如下:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Dice : MonoBehaviour
{
Rigidbody rb;
bool hasLanded;
bool thrown;
Vector3 initPosition;
public int diceValue;
public DiceSide[] diceSides;
// Start is called before the first frame update
void Start()
{
rb = GetComponent<Rigidbody>();
initPosition = transform.position;
rb.useGravity = false;
}
// Update is called once per frame
void Update()
{
if (rb.IsSleeping() && !hasLanded && thrown)
{
hasLanded = true;
rb.useGravity = false;
rb.isKinematic = true;
SideValueCheck();
}
else if (rb.IsSleeping() && hasLanded && diceValue == 0)
{
RollAgain();
}
}
public void RollDice()
{
if (!thrown && !hasLanded)
{
thrown = true;
rb.useGravity = true;
rb.AddTorque(Random.Range(0,500));
}
void SideValueCheck()
{
diceValue = 0;
foreach (DiceSide side in diceSides)
{
if (side.OnGround())
{
diceValue = side.sideValue;
Debug.Log(diceValue + " has been rolled!");
}
}
}
}
我收到来自 Unity 的错误提示
MissingComponentException:没有“Rigidbody”附加到“Button-RollDice”游戏对象,但脚本正试图访问它。 您可能需要向游戏对象“Button-RollDice”添加一个刚体。或者您的脚本需要在使用组件之前检查它是否已附加。 Dice.Update ()(在 Assets/Dice.cs:35)
我足够了解代码正在寻找按钮上的 Rigidbody 而不是模具,但我不知道如何修改我的代码以使其按预期在模具上运行。
谢谢。
解决方法
骰子脚本仍然需要在骰子对象上。您需要一个带有 OnClick 事件的中间脚本来分配给按钮,并引用 Dice 脚本,然后该脚本可以调用 RollDice。
类似于:
public class ButtonHandler : MonoBehavior
{
// Assign dice game object to script in editor
public GameObject DiceGameObject;
private Dice dice;
void Awake()
{
// Retrieve the script from the gameobject
dice = diceGameObject.GetComponent<Dice>();
}
public void RollDiceOnClick()
{
// Call the roll dice method
dice.RollDice();
}
}
您可以将 RollDiceOnClick() 方法分配给按钮的 OnClick 事件(而不是 RollDice)。
然后你将骰子游戏对象拖到 DiceGameObject 属性上,一切都应该链接起来
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。