C# Can';t使游戏对象从另一个脚本移动

C# Can';t使游戏对象从另一个脚本移动,c#,unity3d,C#,Unity3d,我正在开发一款2D STG游戏,就像《投后》系列一样,因为我对Unity还很陌生。我在控制敌人的子弹方面遇到了麻烦,尤其是在我想移动的地方。 这是我的两个脚本,我认为它们有一些问题。 首先是EnemyAttackBehavior。我试图设计敌人可以直接射击子弹并狙击玩家。我发现我可以在这个脚本中生成bullet,但是我不能更改bullet的位置 public class EnemyAttackBehaviors : MonoBehaviour{ public float bulletSpeed;

我正在开发一款2D STG游戏,就像《投后》系列一样,因为我对Unity还很陌生。我在控制敌人的子弹方面遇到了麻烦,尤其是在我想移动的地方。 这是我的两个脚本,我认为它们有一些问题。 首先是EnemyAttackBehavior。我试图设计敌人可以直接射击子弹并狙击玩家。我发现我可以在这个脚本中生成bullet,但是我不能更改bullet的位置

public class EnemyAttackBehaviors : MonoBehaviour{
public float bulletSpeed;
public float attackCD;
public float eachWaveCD;
public int oneWaveAmount;

public enum AttackFunctionName
{
    StraightAttack, SnipeAttack,
}

public AttackFunctionName attackFunction;

private int checkNumber;
private float nextShotTime;

private void Start()
{
    checkNumber = (int)attackFunction;
    nextShotTime = Time.time;
}
private void Update()
{
    CheckWhatTypeAttack();
}

private void CheckWhatTypeAttack()
{

    if (checkNumber == 0)
        StraightAttack();            
    else if (checkNumber == 1)
        SnipeAttack();
}

private void StraightAttack()
{
    for (int i = 0; i < oneWaveAmount; i++)
    {
        if (Time.time > nextShotTime)
        {
            GameObject t = ObjectPool.TakeFromPool("EnemyBullet");
            t.transform.SetPositionAndRotation(this.transform.position, this.transform.rotation);
            //t.GetComponent<Rigidbody2D>().velocity = new Vector2(0, -bulletSpeed);
            //t.transform.Translate(Vector3.up * -bulletSpeed * Time.deltaTime);
            t.transform.position -= new Vector3(0, bulletSpeed, 0);
            nextShotTime = Time.time + attackCD;
        }
    }
}

private void SnipeAttack()
{

}
公共类EnemyAttackBehaviors:MonoBehavior{
公共交通速度;
公众浮标攻击;
公共交通工具;
公营机构数目;
公共枚举攻击函数名
{
直击,狙击,
}
public attackFunction name attackFunction;
私人整数校验号;
私人浮动下一个拍摄时间;
私有void Start()
{
checkNumber=(int)attackFunction;
nextShotTime=Time.Time;
}
私有void更新()
{
检查WhatTypeAttack();
}
私有void CheckWhatTypeAttack()
{
if(checkNumber==0)
直击();
else if(checkNumber==1)
SnipeAttack();
}
私人攻击()
{
对于(int i=0;inextShotTime)
{
GameObject t=ObjectPool.TakeFromPool(“EnemyBullet”);
t、 transform.SetPositionAndRotation(this.transform.position,this.transform.rotation);
//t、 GetComponent().velocity=新矢量2(0,-速度);
//t、 transform.Translate(Vector3.up*-bulletSpeed*Time.deltaTime);
t、 transform.position-=新矢量3(0,bulletSpeed,0);
nextShotTime=Time.Time+attackCD;
}
}
}
私人空间SnipeAttack()
{
}
} 在代码攻击中。我尝试了三种方法来改变子弹的位置。唯一能改变子弹位置的是rigibody2D.velocity。但我不喜欢这种方式,因为使用这种方式我无法轻松测量我想要的速度值。不幸的是,其他方法无法更改项目符号的位置。我不知道当我直接修改值时(例如t.transform.position-=new Vector3(0,bulletSpeed,0)),为什么项目符号的位置不更改。然后我想可能是另一个脚本中的错误-Stage1Path

public class Stage1Path : MonoBehaviour{
public float firstWave = 4f;

private float timer;
private bool w1Check = true;
private void Start()
{
    timer = 0f;
}

private void Update()
{
    timer += Time.realtimeSinceStartup;
    CheckWhatWave();
}

private void CheckWhatWave()
{
    if (Time.time > firstWave && w1Check == true)
        FirstWave();
}

private void FirstWave()
{
    GameObject e1 = ObjectPool.TakeFromPool("Enemy");
    e1.transform.position = new Vector3(-2f, 3f, 0f);
    EnemyBehaviors e1Script = e1.GetComponent<EnemyBehaviors>();
    e1Script.moveSpeed = 0.01f;
    e1Script.moveFunction = EnemyBehaviors.MoveFunctionName.VerticalMove;
    e1Script.lifeTime = 3f;
    
    EnemyAttackBehaviors e1AttackScript = e1.GetComponent<EnemyAttackBehaviors>();
    e1AttackScript.attackCD = 0.1f;
    e1AttackScript.attackFunction = EnemyAttackBehaviors.AttackFunctionName.StraightAttack;
    e1AttackScript.bulletSpeed = 4f;
    e1AttackScript.eachWaveCD = 3f;
    e1AttackScript.oneWaveAmount = 5;

    w1Check = false;
}
公共类Stage1Path:monobhavior{
公共浮式第一波=4f;
专用浮点定时器;
私有布尔w1Check=true;
私有void Start()
{
定时器=0f;
}
私有void更新()
{
计时器+=Time.realtimesincestart;
检查WhatWave();
}
私有void CheckWhatWave()
{
if(Time.Time>firstWave&&w1Check==true)
第一波();
}
第一波
{
gameobjecte1=ObjectPool.TakeFromPool(“敌人”);
e1.transform.position=新矢量3(-2f,3f,0f);
enemyscript=e1.GetComponent();
e1Script.moveSpeed=0.01f;
e1Script.moveFunction=EnemyBehaviors.MoveFunctionName.VerticalMove;
e1Script.life=3f;
EnemyAttackBehaviors e1AttackScript=e1.GetComponent();
e1AttackScript.attackCD=0.1f;
e1AttackScript.attackFunction=EnemyAttackBehaviors.AttackFunctionName.StraightAttack;
e1AttackScript.bulletSpeed=4f;
e1AttackScript.eachWaveCD=3f;
e1AttackScript.oneWaveAmount=5;
w1Check=false;
}
}
在Stage1Path中,我尝试在FirstWave()中生成名为e1的第一个敌人。它发生在比赛开始4秒后。在FirstWave()中,我通过脚本EnemyBehavior设置e1的移动。它工作得很好!但当我在e1的拍摄类型中使用相同的方式时。子弹“是产卵的,但它们没有移动。”。我不知道错误发生在EnemyAttackBehavior或Stage1Path中。我花了好几个小时在互联网上搜索,试图修复这个错误。我还尝试在EnemyAttackBehavior中使用协同程序,我认为它可能会解决这个问题。但我还是失败了。非常感谢您的帮助。对不起,我的英语不好。

你需要在每一帧应用翻译。这行不错,但是

t.transform.Translate(Vector3.up * -bulletSpeed * Time.deltaTime);
在你的情况下,你只应用一次,因为这一点。所以你基本上在一帧中移动它一次,然后等待其他时间再移动它一次

    if (Time.time > nextShotTime)
    {
      // movement logic
      nextShotTime = Time.time + attackCD;
    }

由于基于速度的运动是由物理引擎计算的,因此它与修改速度一起工作。如果是transform.Translate,您需要自己应用每一帧的移动。

谢谢。但我想知道Update()中包含CheckWhatTypeAttack(),而StraightAttack()中包含CheckWhatTypeAttack(),为什么我只应用一次?它应该在我的逻辑中更新perframe,因为它在更新中?你是对的,谢谢你,但是现在我不明白CheckWhatTypeAttack()和Update()之间的关系。是的,基本上它在
Update()中
Update()
->
检查WhattTypeAttack()
->
StraightAttack()
检查
nextShotTime
有一个问题,该检查会阻止每一帧的移动。