[英]Proper way to create a static virtual factory method in C#
我正在Unity3D中實現效果類(具有在FixedUpdate循環中應用行為的持續時間)。
我有一個基本抽象效果類,它具有跟蹤持續時間的行為,在持續時間結束時刪除自身,並在持續時間結束時調用受保護的抽象_doEffect函數。 在我的派生類中,我重寫_doEffect來創建具有不同行為的效果。
public abstract class Effect : MonoBehaviour
{
public virtual float kDuration { get { return 1.0f; }}
public static bool IsStackable { get { return false; }}
private float _elapsed = 0.0f;
protected virtual void Start()
{
_elapsed = kDuration;
}
protected virtual void FixedUpdate()
{
_elapsed -= Time.fixedDeltaTime;
if(_elapsed <= 0) {
Destroy(this);
}
_doEffect();
}
protected abstract void _doEffect();
}
現在,因為你不能在Unity3D中使用構造函數,所以當我將一個新的Effect類型應用於游戲對象時,我需要一種方法為每個派生的Effect類執行以下操作:
1)如果這種類型的效果不可疊加,則從游戲對象中刪除此monobehaviour的所有其他實例。 2)為游戲對象創建效果類型的新組件。 3)做一些特定於該效果類型的初始化。
對於這些要求,我想象做的事情
public class DerivedEffect : Effect
{
public override float kDuration { get {return 1.0f; }}
public static bool IsStackable { get { return true; }}
private int _derivedData;
public static void Create(GameObject obj, int data)
{
DerivedEffect effect = DerivedEffect.CreateEffect(obj);
effect._data = data;
}
protected override void _doEffect()
{
//Do some stuff
}
}
然后在基類推桿
public static virtual Effect CreateEffect(GameObject obj)
{
//T is somehow magically the type of the class you called this function on
if(!T.IsStackable()) {
//delete all components of type T on obj
}
T effect = obj.AddComponent<T>();
return effect;
}
顯然這是不可能的,除非我做一些奇怪的東西與泛型和反射似乎有點極端,可能不是正確的做事方式。
關鍵在於我想要一個執行1),2),3)的靜態函數,並且我希望共享執行1)和2)的代碼,並且1)取決於每個派生類不同的bool。
這些需求的適當設計是什么?
這些需求的適當設計是什么?
Unity是基於組件的,當您希望以普通C#應用程序中的方式使用它時會使事情變得復雜。
最簡單的方法是使用Composition。 使Effect
類成為自己的非抽象類。 只是一個繼承自MonoBehaviour
的普通類。 您可以輕松地創建它的新實例AddComponent
,把事情GetComponent
。 在計時器完成計數后,此腳本也可以直接銷毀自己,沒有任何問題。
在DerivedEffect
類中創建一個全局變量來保存創建的Effect
腳本的實例,這可以反復使用,直到它變為null,這意味着腳本被銷毀。 請注意,此處不涉及繼承, DerivedEffect
腳本僅用作管理Effect
腳本的腳本示例。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.