在输入左键单击(Fire1)时,弹丸从projectileSpawn位置生成。右键单击(Fire2),我要使射弹“反向”射击,并从projectileSpawnTwo位置开始,再返回到初始的projectileSpawn位置。目前它向前方射击,但我希望射弹重生回精确的位置。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class PlayerWeapon : MonoBehaviour
{
public GameObject projectilePrefab;
public GameObject projectileTwoPrefab;
public Transform projectileSpawn;
public Transform projectileSpawnTwo;
public float projectileSpeed = 30;
void Update ()
{
if (Input.GetButtonDown("Fire1"))
{
Fire();
}
if (Input.GetButtonDown("Fire2"))
{
Fire2();
}
}
private void Fire()
{
GameObject projectile = Instantiate(projectilePrefab);
Physics.IgnoreCollision(projectile.GetComponent<Collider>(),
projectileSpawn.parent.GetComponent<Collider>());
projectile.transform.position = projectileSpawn.position;
var rot = projectile.transform.rotation.eulerAngles;
projectile.transform.rotation = Quaternion.Euler(rot.x, transform.eulerAngles.y, rot.z);
projectile.GetComponent<Rigidbody>().AddForce(projectileSpawn.forward * projectileSpeed, ForceMode.Impulse);
}
private void Fire2()
{
GameObject projectile = Instantiate(projectileTwoPrefab);
Physics.IgnoreCollision(projectile.GetComponent<Collider>(),
projectileSpawnTwo.parent.GetComponent<Collider>());
projectile.transform.position = projectileSpawnTwo.position;
var rot = projectile.transform.rotation.eulerAngles;
projectile.transform.rotation = Quaternion.Euler(rot.x, transform.eulerAngles.y, rot.z);
projectile.GetComponent<Rigidbody>().AddForce(projectileSpawnTwo.forward * projectileSpeed, ForceMode.Impulse);
}
}
答案 0 :(得分:2)
由于这两种方法都非常相似,因此可以概括一下您的方法
private Collider projectileSpawnParentCollider;
privtae enum FireType
{
One,
Two
}
private void Awake()
{
// this hould probably done only once to be more efficient
projectileSpawnParentCollider = projectileSpawn.parent.GetComponent<Collider>();
}
private void Update()
{
if (Input.GetButtonDown("Fire1"))
{
Fire(FireType.One);
}
if (Input.GetButtonDown("Fire2"))
{
Fire(FireType.Two);
}
}
private void Fire(FireType fireType)
{
var position = fireType == FireType.One ? projectileSpawn.position : projectileSpawnTwo.position;
var rot = projectile.transform.rotation.eulerAngles;
var rotation = Quaternion.Euler(rot.x, transform.eulerAngles.y, rot.z);
// pass the position and rotation alraedy
GameObject projectile = Instantiate(projectilePrefab, position, rotation);
Physics.IgnoreCollision(projectile.GetComponent<Collider>(), projectileSpawnParentCollider);
var forceDirection = fireType == FireType.One ? projectileSpawn.forward : (projectileSpawn.position - projectileSpawnTwo.position).normalized;
projectile.GetComponent<Rigidbody>().AddForce(forceDirection * projectileSpeed, ForceMode.Impulse);
}
The
projectileSpawn.position - projectileSpawnTwo.position
返回从projectileSpawnTwo.position
指向projectileSpawn.position
的向量。使用normalized
返回具有相同方向但使用magnitude = 1
的向量。
但是,请注意,这仅在玩家第二次射击后没有移动时才起作用。如果玩家可以移动,则您可能应该实现另一个组件,以使子弹对象实际上跟随玩家的位置。
您可以使用Quaternion.LookRotation
和Rigidbody.MoveRotation
编写单独的组件,例如
public class FollowPlayer : MonoBehaviour
{
public Transform PlayerTransform;
public RigidBody rigiBody;
public speed;
private void Awake()
{
rigidBody = GetComponent<RigidBody>();
}
private void LateUpdate()
{
if(!PlayerTrasnform) return;
var rotation = Quaternion.LookRotation(PlayerTransform.position - transform.position, Vector3.up);
rigidBody.MoveRotation(rotation);
rigidBody.velocity = (PlayerTransform.position - transform.position).normalized * speed;
}
}
并在脚本中添加组件,以防出现两个类似的情况
private void Fire(FireType fireType)
{
var position = fireType == FireType.One ? projectileSpawn.position : projectileSpawnTwo.position;
var rot = projectile.transform.rotation.eulerAngles;
var rotation = Quaternion.Euler(rot.x, transform.eulerAngles.y, rot.z);
// pass the position and rotation alraedy
GameObject projectile = Instantiate(projectilePrefab, position, rotation);
Physics.IgnoreCollision(projectile.GetComponent<Collider>(), projectileSpawnParentCollider);
if(fireType == FireType.One)
{
projectile.GetComponent<Rigidbody>().AddForce(projectileSpawn.forward * projectileSpeed, ForceMode.Impulse);
}
else
{
var follow = projectile.AddComponent<FollowPlayer>();
follow.speed = projectileSpeed;
follow.PlayerTransform = YourPlayerTransform; // or probably projectileSpawn
}
}
注意:请在智能手机上输入内容,因此无需任何担保,但我希望这个主意会变得清晰起来。