private GameObject AddEffectToPool(FC_CHARACTER_EFFECT effId)
    {
        if (_myRoot == null)
        {
            _myRoot = Utils.NewGameObjectWithParent("Character_Effect_Root");
        }

        CharacterEffectConfig effConfig = _characterEffectTable[effId] as CharacterEffectConfig;

        GameObject instance = GameObject.Instantiate(effConfig.originalEffectObject) as GameObject;
        Transform  t        = instance.transform;

        t.parent        = _myRoot;
        t.localPosition = Vector3.zero;
        t.localRotation = Quaternion.identity;
        instance.SetActive(false);
        return(instance);
    }
    //play effect
    //lifetime: character effect may have a lift time from outside, > 0 will take effect.
    //          < 0 means use effect's built-in life time.
    public EffectInstance PlayEffect(FC_CHARACTER_EFFECT effId, AvatarController avatar, float liftTime)
    {
        if (effId == FC_CHARACTER_EFFECT.INVALID)
        {
            return(null);
        }

        //get empty gameobject?
        List <EffectInstance> effList   = _allEffectArray[effId];
        EffectInstance        effResult = null;

        if (effList.Count > 0)
        {
            foreach (EffectInstance effInst in effList)
            {
                if (effInst == null ||
                    effInst.myObject == null)
                {
                    int zz = 0;
                    zz++;
                }
                if (!effInst.myObject.activeSelf)
                {
                    effResult = effInst;
                    break;
                }
            }
        }

        //no empty? create one
        if (effResult == null)
        {
            GameObject ego = AddEffectToPool(effId);
            effResult = ego.GetComponent <EffectInstance>();
            Assertion.Check(effResult != null);
            effResult.character_effect_id = effId;
            effResult.myTransform         = ego.transform;
            effResult.myObject            = ego;
            effList.Add(effResult);
        }

        //set enable and parent and pos
        Assertion.Check(effResult != null);
        effResult.myObject.SetActive(true);

        //find parent node
        CharacterEffectConfig effConfig = _characterEffectTable[effId] as CharacterEffectConfig;

        Assertion.Check(effConfig != null);

        Transform parent = Utils.FindTransformByNodeName(avatar.myTransform,
                                                         FCEquipmentsBase.GetNodeByEquipSlot(effConfig._parentSlot)
                                                         );

        if (parent == null)
        {
            parent = avatar.myTransform;
        }
        Assertion.Check(parent != null);
        effResult.myTransform.parent        = parent;
        effResult.myTransform.localPosition = Vector3.zero;
        effResult.myTransform.localRotation = Quaternion.identity;

        //add to living list
        LivingEffect liveEff = new LivingEffect();

        liveEff._effect = effResult;
        liveEff._avatar = avatar;
        liveEff._effID  = (int)effId;
        _livingEffects.Add(liveEff);

        //get effect instance and start effect
        EffectInstance eff = effResult;

        Assertion.Check(eff != null);
        if (liftTime > 0)
        {
            eff.LifeTick = liftTime;
        }
        else
        {
            eff.LifeTick = eff._lifeTime;
        }

        eff.DeadTick = eff._deadTime;

        eff.BeginEffect();

        return(effResult);
    }