英文:
Unity Can't get bullet to fire the right direction
问题
我试图让我的坦克朝着鼠标方向开火。目前坦克可以旋转以面向鼠标,但我不知道如何使子弹朝正确的方向前进!
目前位于顶部的炮塔可以正确旋转,我不确定该对象的旋转是否可以用于确定方向?
这是在Unity 3D中,但实际上是2.5D倾斜的俯视视角。
public class tankScript : MonoBehaviour
{
public float rotateSpeed = 90;
public float speed = 5.0f;
public float fireInterval = 0.5f;
public float bulletSpeed = 20;
public Transform spawnPoint;
public GameObject bulletObject;
float nextFire;
Camera cam;
Collider planecollider;
RaycastHit hit;
Ray ray;
Vector3 mouseDirection;
void Start()
{
nextFire = Time.time + fireInterval;
cam = GameObject.Find("Main Camera").GetComponent<Camera>();
planecollider = GameObject.Find("Plane").GetComponent<Collider>();
}
void Update()
{
var transAmount = speed * Time.deltaTime;
var rotateAmount = rotateSpeed * Time.deltaTime;
if (Input.GetKey("w"))
{
transform.Translate(0, 0, transAmount);
}
if (Input.GetKey("s"))
{
transform.Translate(0, 0, -transAmount);
}
if (Input.GetKey("a"))
{
transform.Rotate(0, -rotateAmount, 0);
}
if (Input.GetKey("d"))
{
transform.Rotate(0, rotateAmount, 0);
}
if (Input.GetButtonDown("Fire1") && Time.time > nextFire)
{
nextFire = Time.time + fireInterval;
fire();
}
}
void fire()
{
ray = cam.ScreenPointToRay(Input.mousePosition);
if (Physics.Raycast(ray, out hit))
{
if (hit.collider == planecollider)
{
mouseDirection = new Vector3(hit.point.x, 0.25f, hit.point.z);
float step = bulletSpeed * Time.deltaTime;
var bullet = Instantiate(bulletObject, spawnPoint.position, spawnPoint.rotation);
bullet.GetComponent<Rigidbody>().transform.localPosition = Vector3.MoveTowards(transform.localPosition, mouseDirection, step);
}
}
}
}
英文:
I'm trying to get my tank to shoot in the direction the mouse is facing. Currently the tank can rotate to look at the mouse, but I have no idea how to make the bullet go the right direction!
Currently the turret on the top does rotate correctly, I'm not sure if the rotation on that object can be used for the direction?
It is iin unity 3d but it is really 2.5d angled topdown.
public class tankScript : MonoBehaviour
{
public float rotateSpeed = 90;
public float speed = 5.0f;
public float fireInterval = 0.5f;
public float bulletSpeed = 20;
public Transform spawnPoint;
public GameObject bulletObject;
float nextFire;
Camera cam;
Collider planecollider;
RaycastHit hit;
Ray ray;
Vector3 mouseDirection;
void Start()
{
nextFire = Time.time + fireInterval;
cam = GameObject.Find("Main Camera").GetComponent<Camera>();
planecollider = GameObject.Find("Plane").GetComponent<Collider>();
}
void Update()
{
var transAmount = speed * Time.deltaTime;
var rotateAmount = rotateSpeed * Time.deltaTime;
if (Input.GetKey("w"))
{
transform.Translate(0, 0, transAmount);
}
if (Input.GetKey("s"))
{
transform.Translate(0, 0, -transAmount);
}
if (Input.GetKey("a"))
{
transform.Rotate(0, -rotateAmount, 0);
}
if (Input.GetKey("d"))
{
transform.Rotate(0, rotateAmount, 0);
}
if (Input.GetButtonDown("Fire1") && Time.time > nextFire)
{
nextFire = Time.time + fireInterval;
fire();
}
}
void fire()
{
ray = cam.ScreenPointToRay(Input.mousePosition);
if (Physics.Raycast(ray, out hit))
{
if (hit.collider == planecollider)
{
mouseDirection = new Vector3(hit.point.x, 0.25f, hit.point.z);
float step = bulletSpeed * Time.deltaTime;
var bullet = Instantiate(bulletObject, spawnPoint.position, spawnPoint.rotation);
bullet.GetComponent<Rigidbody>().transform.localPosition = Vector3.MoveTowards(transform.localPosition, mouseDirection, step);
}
}
}
答案1
得分: 1
以下是翻译好的部分:
"The key issue here is that you likely want to set the velocity of the rigidbody rather than moving it by setting the localPosition
. Otherwise you lose all the benefits of the physics system, and won't be able to detect collisions correctly.
What value should you set it to, though? Well, velocity consists of two components:
- Direction: This should be the difference between the mouse hit point and the spawn point.
- Speed (magnitude): This should be
bulletSpeed
.
Let's change your script to see what using velocity instead of manually moving the bullet would look like:
void fire()
{
ray = cam.ScreenPointToRay(Input.mousePosition);
if (Physics.Raycast(ray, out hit))
{
if (hit.collider == planecollider)
{
mouseDirection = new Vector3(hit.point.x, 0.25f, hit.point.z);
// This vector is the direction vector we want to fire along
Vector3 firingDirection = mouseDirection - spawnPoint.position;
var bullet = Instantiate(bulletObject, spawnPoint.position, spawnPoint.rotation);
// Now, we set the velocity to firingDirection, but scaled to bulletSpeed
bullet.GetComponent<Rigidbody>().velocity = firingDirection.normalized * bulletSpeed;
}
}
}
英文:
The key issue here is that you likely want to set the velocity of the rigidbody rather than moving it by setting the localPosition
. Otherwise you lose all the benefits of the physics system, and won't be able to detect collisions correctly.
What value should you set it to, though? Well, velocity consists of two components:
- Direction: This should be the difference between the mouse hit point and the spawn point.
- Speed (magnitude): This should be
bulletSpeed
.
Let's change your script to see what using velocity instead of manually moving the bullet would look like:
<!-- language: lang-cs -->
void fire()
{
ray = cam.ScreenPointToRay(Input.mousePosition);
if (Physics.Raycast(ray, out hit))
{
if (hit.collider == planecollider)
{
mouseDirection = new Vector3(hit.point.x, 0.25f, hit.point.z);
// This vector is the direction vector we want to fire along
Vector3 firingDirection = mouseDirection - spawnPoint.position;
var bullet = Instantiate(bulletObject, spawnPoint.position, spawnPoint.rotation);
// Now, we set the velocity to firingDirection, but scaled to bulletSpeed
bullet.GetComponent<Rigidbody>().velocity = firingDirection.normalized * bulletSpeed;
}
}
}
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论