我正在通过统一网站(here)上的'太空射击'教程,我遇到以下代码的问题。我试图对船只Rigidbody
施加限制,使其无法离开可见的游戏区域。但是,我收到以下错误,我不明白为什么(这是我第一次使用C#,所以很抱歉,如果它真的很明显是什么问题):
错误:
NullReferenceException: Object reference not set to an instance of an object
PlayerController.FixedUpdate () (at Assets/Scripts/PlayerController.cs:28)
我在下面标记了第28行(在错误中提到)
脚本:
using UnityEngine;
using System.Collections;
public class Boundary
{
public float xMin, xMax, zMin, zMax;
}
public class PlayerController : MonoBehaviour
{
public float speed;
public Boundary b;
public Rigidbody rb;
void Start ()
{
rb = GetComponent<Rigidbody>();
}
void FixedUpdate () {
float moveHorizontal = Input.GetAxis ("Horizontal");
float moveVertical = Input.GetAxis ("Vertical");
Vector3 movement = new Vector3 (moveHorizontal, 0.0f, moveVertical);
rb.velocity = movement * speed;
rb.position = new Vector3( \\ *** line 28 ***
Mathf.Clamp (rb.position.x, b.xMin, b.xMax),
0.0f,
Mathf.Clamp (rb.position.z, b.zMin, b.zMax)
);
}
}
非常感谢任何有关解决此错误的帮助,教程中的脚本本身与unity5不兼容,但我只是看不出这个错误是对的。
答案 0 :(得分:1)
在您的代码中,Boundary
是一种引用类型,这意味着如果您没有为其提供值,则为空。在您的代码中,我无法看到您曾为b
分配了一个值。这就是NullReferenceException
出现的原因 - b
为空!也许你可以在start方法中做到这一点:
b = new Boundary ();
b.xMin = 1;
b.xMax = 2;
b.zMin = 3;
b.zMax = 4;
//The numbers are just examples. Change it however you want
这应该使b
不为空。或者,您可以在Boundary
类中添加构造函数:
public Boundary (int xMin, int xMax, int zMin, int zMax) {
this.xMin = xMin;
this.xMax = xMax;
this.zMin = zMin;
this.zMax = zMax;
}
答案 1 :(得分:1)
正如您在评论中提到的那样,您并未在任何地方初始化b
,因此默认情况下为null
。阅读默认值和内容here,还可以查看值类型和引用类型之间的区别,例如,有一种方法可以使Boundary
成为值类型。
您可能还想在Boundary
中添加构造函数,以便更容易创建构造函数。
public class Boundary
{
public float xMin, xMax, zMin, zMax;
public Boundary(float xMin, float xMax, ...)
{
// Set your fields.
}
}
更好的是,使用Unity的Vector2
类型来存储您的边界信息。
public class Boundary
{
public Vector2 MinPoint;
public Vector2 MaxPoint;
public Boundary(Vector2 minPoint, Vector2 maxPoint)
{
MinPoint = minPoint;
MaxPoint = maxPoint;
}
}
写这个片段比写第一个片段痛苦得多。如果您真的不需要存储这4个坐标的其他方法,请查看Rect
here,因为它已经满足您的需求。