Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/287.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 在c中从不同脚本访问实例#_C#_Unity3d_Oop - Fatal编程技术网

C# 在c中从不同脚本访问实例#

C# 在c中从不同脚本访问实例#,c#,unity3d,oop,C#,Unity3d,Oop,这是一个我陷入困境的OOP问题。。 假设我有这种情况 Player.cs: public class Player { int hp,armor; string nickName; public Player() { hp=3; armor=3; nickName="Unknown"; } public void minusHP() { hp--;

这是一个我陷入困境的OOP问题。。 假设我有这种情况 Player.cs:

public class Player
{
    int hp,armor;
    string nickName;
    public Player()
    {
        hp=3;
        armor=3;
        nickName="Unknown";
    }
    public void minusHP()
    {
        hp--;
    }
}
PlayerManager.cs

public class PlayerManager
{
    Player p = new Player();
}
public class TakeDMG
{
    //if event happens then : 
    p.minusHP();
}
TakeDMG.cs

public class PlayerManager
{
    Player p = new Player();
}
public class TakeDMG
{
    //if event happens then : 
    p.minusHP();
}

如何从不同的脚本访问播放器实例并使用它,以及如何在另一个脚本中声明其他方法?

如果您的所有脚本都已连接到同一个播放器对象,则可以在任何脚本中使用
gameObject
访问播放器对象

从那里,您可以调用
GetComponent
来获取另一个脚本的实例

例如:

public class TakeDMG
{
    //if event happens then : 
    public void SomeEvent()
    {
        var p = gameObject.GetComponent<Player>();
        p.minusHP();
    }
}
公共类TakeDMG
{
//如果事件发生,则:
公共事件()
{
var p=gameObject.GetComponent();
p、 minusHP();
}
}
请注意,还有优化的余地。在启动时,每个脚本只能使用字段对GetComponent进行一次“搜索”

public class TakeDMG
{
    Player player;   // private field to store the reference to Player script;

    public Start()
    {
        player = gameObject.GetComponent<Player>();
    }

    //if event happens then : 
    public void SomeEvent()
    {
        player.minusHP();
    }
}
公共类TakeDMG
{
Player;//用于存储对Player脚本的引用的私有字段;
公共启动()
{
player=gameObject.GetComponent();
}
//如果事件发生,则:
公共事件()
{
player.minusHP();
}
}
当然,这只能做的球员脚本是从一开始就附加到球员的对象,我想这可能是这样的情况

如果必须在许多脚本上重复相同的代码(获取播放器实例),则可以使用继承来“排除”相同的代码

public class PlayerScript
{
    protected Player player;   // field to store the reference to Player script;

    public virtual Start()
    {
        player = gameObject.GetComponent<Player>();
    }
}

// This scripts inherit from PlayerScript
public class TakeDMG : PlayerScript
{
    //if event happens then : 
    public void SomeEvent()
    {
        player.minusHP();
    }
}


// This one as well
public class AnotherScript : PlayerScript
{
    //if event happens then : 
    public void SomeOtherEvent()
    {
        player.minusHP();
    }
}

公共类PlayerScript
{
受保护的播放器;//用于存储对播放器脚本的引用的字段;
公共虚拟开始()
{
player=gameObject.GetComponent();
}
}
//此脚本继承自PlayerScript
公共类TakeDMG:PlayerScript
{
//如果事件发生,则:
公共事件()
{
player.minusHP();
}
}
//这个也是
公共类另一个脚本:PlayerScript
{
//如果事件发生,则:
public void SomeOtherEvent()
{
player.minusHP();
}
}

最好的方法是在其他脚本上获取播放器参考:

public class TakeDMG : MonoBehaviour
{
    //This is the player reference to set on editor mode
    public Player player;
}
或者,如果它不是
monobhavior

如果不可能,您可以使用该模式

以下是我使用的示例(灵感来源):


如果脚本附加到播放器,那么您可以简单地使用
gameObject
字段作为对播放器对象的引用。然后,使用GetComponent获取另一个脚本的实例。@Pac0每次访问该实例时,我都必须为脚本获取组件,但我不记得在哪里看到一些YouTube以另一种更简单的方式访问它,但我不记得我是如何写出正确答案的,如果不清楚,请随时发表评论。我必须强烈建议您观看一些Unity教程。注意:在这种情况下,我不确定是否应该使用
Awake
而不是
Start
。如果您在
Start
中遇到问题,请尝试改用
Awake
。将您的评论复制到别处:“Pac0是否有其他方法可以访问类实例,而不必为我生成的每个脚本获取组件,因为假设我不在unity上,而只是生成一个CMD程序,只需输入一些简单的输入即可执行p.minshp()“您的答案是非常感谢,谢谢!”@YESSINE:我看到的最简单的方法是设置这些字段,以便您可以在编辑器上“拖放”脚本(即:使用
公共播放器;
!)。您还可以使用“单例模式”(参见[D.B的answe[())。您还可以使用继承,参见我的(已编辑的)最后一部分)回答。谢谢你的回答。我想这就是我一直在寻找的答案。我会花时间去理解这个模式,因为我认为我可能会非常感激地使用它!注意不要滥用它。不要陷入spagetti代码漩涡。试着使用“hard”通过公共字段或构造函数进行引用,当您没有其他选项时,可以使用Singleton。
public class OtherClass : MonoBehaviour
{
    public void SomeMethod()
    {
        PlayerManager.Instance.Player.minusHP();
    }
}