Exemple #1
0
    public void SetDir(TileDir tileDir, bool reorientate)
    {
        if (tileDir == this.tileDir)
        {
            if (reorientate && shown)
            {
                actor.transform.rotation *= Quaternion.AngleAxis(tileDir.ToAngle(), Vector3.up);
            }
            return;
        }
        if (removed)
        {
            this.tileDir = tileDir;
            return;
        }
        var orig = this.tileDir;

        this.tileDir = tileDir;
        if (reorientate && shown)
        {
            actor.transform.rotation = Quaternion.Euler(actor.transform.eulerAngles.x, tileDir.ToAngle(), actor.transform.eulerAngles.z);
        }
        using (var scope = new Hooks.Scope()) {
            this.hooks.ForEach <IOnChangeDirection_Unit>(scope, v => v.OnChangeDirection(orig, tileDir));
            tile.hooks.ForEach <IOnChangeDirection_Tile>(scope, v => v.OnChangeDirection(this, orig, tileDir));
            Game.hooks.ForEach <IOnChangeDirection_Game>(scope, v => v.OnChangeDirection(this, orig, tileDir));
        }
    }
Exemple #2
0
    /// <summary> Called when the ability is actually cast. </summary>
    public virtual void OnCast()
    {
        isCasting = true;
        if (uses.enabled)
        {
            uses.current.value--;
        }
        if (charges.current == charges.max)
        {
            cooldown.Max();
        }
        if (cooldown.current <= 0 && cooldown.max <= 0)
        {
            charges.Max();
        }
        else
        {
            charges.current.value--;
        }
        unit.energy.current.value -= energyCost.current;
        unit.RefreshEnergy();

        using (var scope = new Hooks.Scope()) {
            unit.hooks.ForEach <IOnAbilityCastStart_Unit>(scope, v => v.OnAbilityCastStart(this));
            unit.tile.hooks.ForEach <IOnAbilityCastStart_Tile>(scope, v => v.OnAbilityCastStart(this));
            Game.hooks.ForEach <IOnAbilityCastStart_Game>(scope, v => v.OnAbilityCastStart(this));
        }
    }
Exemple #3
0
        /// <summary> Creates a Modifier based on the given source and attaches it to the master. </summary>
        public static T Create <T>(TSelf master, T source, Action <T> initializer = null) where T : RootModifier
        {
            if (source == null)
            {
                throw new ArgumentNullException(nameof(source));
            }
            if (!source.isSource)
            {
                throw new ArgumentException($"{nameof(source)} must be a source", nameof(source));
            }

            var modifier = Instantiate(source);

            modifier.master = master;
            modifier.source = source;

            master.AttachModifier(modifier);
            Game.dataObjects.Add(modifier);
            Game.hooks.Hook(modifier);

            initializer?.Invoke(modifier);

            modifier.OnConfigureNonpersistent(true);
            modifier.OnCreate();
            modifier.Show();

            using (var scope = new Hooks.Scope()) Game.hooks.ForEach <IOnModifierCreate>(scope, v => v.OnModifierCreate(modifier));

            return(modifier);
        }
Exemple #4
0
    /// <summary> Is this Edge considered to be passable from Tile "from" to Tile "to". </summary>
    public bool CanPass(Tile from, Tile to)
    {
        if (from is null)
        {
            throw new ArgumentNullException(nameof(from));
        }
        if (to is null)
        {
            throw new ArgumentNullException(nameof(to));
        }
        if (to != hex1 && to != hex2)
        {
            throw new ArgumentException("To must be one of the Tiles connected to the Edge.", nameof(to));
        }
        if (from != hex1 && from != hex2)
        {
            throw new ArgumentException("From must be one of the Tiles connected to the Edge.", nameof(from));
        }
        var value = to.passable.current.value;

        using (var scope = new Hooks.Scope()) {
            this.hooks.ForEach <IOnGetCanPass_Edge>(scope, v => v.OnGetCanPass(from, to, ref value));
            Game.hooks.ForEach <IOnGetCanPass_Game>(scope, v => v.OnGetCanPass(from, this, to, ref value));
        }
        return(value);
    }
Exemple #5
0
 protected override void OnCreate()
 {
     base.OnCreate();
     using (var scope = new Hooks.Scope()) {
         tile.hooks.ForEach <IOnTileModifierCreate_Tile>(scope, v => v.OnTileModifierCreate(this));
         Game.hooks.ForEach <IOnTileModifierCreate_Game>(scope, v => v.OnTileModifierCreate(this));
     }
 }
Exemple #6
0
 protected override void OnRemove()
 {
     using (var scope = new Hooks.Scope()) {
         edge.hooks.ForEach <IOnEdgeModifierRemove_Edge>(scope, v => v.OnEdgeModifierRemove(this));
         Game.hooks.ForEach <IOnEdgeModifierRemove_Game>(scope, v => v.OnEdgeModifierRemove(this));
     }
     base.OnRemove();
 }
Exemple #7
0
 public void Dispell()
 {
     using (var scope = new Hooks.Scope()) {
         this.hooks.ForEach <IOnDispell_Unit>(scope, v => v.OnDispell());
         tile.hooks.ForEach <IOnDispell_Tile>(scope, v => v.OnDispell(this));
         Game.hooks.ForEach <IOnDispell_Game>(scope, v => v.OnDispell(this));
     }
 }
Exemple #8
0
 public void ExecuteMoveOff(Unit unit, Tile tile)
 {
     using (var scope = new Hooks.Scope()) {
         tile.hooks.ForEach <IOnMoveOff_Tile>(scope, v => v.OnMoveOff(this, unit));
         unit.hooks.ForEach <IOnMoveOff_Unit>(scope, v => v.OnMoveOff(this, tile));
         Game.hooks.ForEach <IOnMoveOff_Game>(scope, v => v.OnMoveOff(this, unit, tile));
     }
 }
Exemple #9
0
 public void ExecuteMoveOver(Unit unit, Tile from, Edge edge, Tile to)
 {
     edge = from.EdgeBetween(to);
     using (var scope = new Hooks.Scope()) {
         edge.hooks.ForEach <IOnMoveOver_Edge>(scope, v => v.OnMoveOver(this, unit, from, to));
         unit.hooks.ForEach <IOnMoveOver_Unit>(scope, v => v.OnMoveOver(this, from, edge, to));
         Game.hooks.ForEach <IOnMoveOver_Game>(scope, v => v.OnMoveOver(this, unit, from, edge, to));
     }
 }
Exemple #10
0
 protected override void OnRemove()
 {
     using (var scope = new Hooks.Scope()) {
         unit.hooks.ForEach <IOnUnitModifierRemove_Unit>(scope, v => v.OnUnitModifierRemove(this));
         unit.tile.hooks.ForEach <IOnUnitModifierRemove_Tile>(scope, v => v.OnUnitModifierRemove(this));
         Game.hooks.ForEach <IOnUnitModifierRemove_Game>(scope, v => v.OnUnitModifierRemove(this));
     }
     base.OnRemove();
 }
Exemple #11
0
 public void Heal(float heal)
 {
     using (var scope = new Hooks.Scope()) {
         this.hooks.ForEach <IOnHeal_Unit>(scope, v => v.OnHeal(ref heal));
         tile.hooks.ForEach <IOnHeal_Tile>(scope, v => v.OnHeal(this, ref heal));
         Game.hooks.ForEach <IOnHeal_Game>(scope, v => v.OnHeal(this, ref heal));
     }
     health.current.value += Mathf.Max(0, heal);
     health.Clamp();
 }
Exemple #12
0
 protected override void OnCreate()
 {
     base.OnCreate();
     using (var scope = new Hooks.Scope()) Game.hooks.ForEach <IOnCombatLog>(scope, v => v.OnCombatLog($"Unit spawn: {Lang.GetStr($"{identifier}_DisplayName")} ({team})"));
     using (var scope = new Hooks.Scope()) {
         this.hooks.ForEach <IOnSpawn_Unit>(scope, v => v.OnSpawn());
         tile.hooks.ForEach <IOnSpawn_Tile>(scope, v => v.OnSpawn(this));
         Game.hooks.ForEach <IOnSpawn_Game>(scope, v => v.OnSpawn(this));
     }
 }
Exemple #13
0
    /// <summary> Gets the estimated speed of this unit after a number of rounds have passed. </summary>
    public int GetEstimatedSpeed(int roundsAhead)
    {
        var speed = this.speed.current.raw;

        using (var scope = new Hooks.Scope()) {
            this.hooks.ForEach <IOnGetEstimatedSpeed_Unit>(scope, v => v.OnGetEstimatedSpeed(roundsAhead, ref speed));
            tile.hooks.ForEach <IOnGetEstimatedSpeed_Tile>(scope, v => v.OnGetEstimatedSpeed(this, roundsAhead, ref speed));
            Game.hooks.ForEach <IOnGetEstimatedSpeed_Game>(scope, v => v.OnGetEstimatedSpeed(this, roundsAhead, ref speed));
        }
        return(speed);
    }
Exemple #14
0
    /// <summary> Calculates damage for later use. Amplifications and modifiers are applied to the ref values. </summary>
    public void CalculateDamage(ref float damage, ref DamageType damageType)
    {
        var abilityType = this.abilityType;

        using (var scope = new Hooks.Scope()) {
            var(_damage, _damageType) = (damage, damageType);
            unit.hooks.ForEach <IOnCalculateDamage_Unit>(scope, v => v.OnCalculateDamage(this, ref _damage, ref _damageType));
            unit.tile.hooks.ForEach <IOnCalculateDamage_Tile>(scope, v => v.OnCalculateDamage(this, ref _damage, ref _damageType));
            Game.hooks.ForEach <IOnCalculateDamage_Game>(scope, v => v.OnCalculateDamage(this, ref _damage, ref _damageType));
            (damage, damageType) = (_damage, _damageType);
        }
    }
Exemple #15
0
 public virtual void OnAnimationEventEnd()
 {
     if (isCasting)
     {
         isCasting = false;
         //!!! Is work? No onFinishEvent before
         Hooks.onFinishEvent += () => {
             using (var scope = new Hooks.Scope()) {
                 unit.hooks.ForEach <IOnAbilityCastEnd_Unit>(scope, v => v.OnAbilityCastEnd(this));
                 unit.tile.hooks.ForEach <IOnAbilityCastEnd_Tile>(scope, v => v.OnAbilityCastEnd(this));
                 Game.hooks.ForEach <IOnAbilityCastEnd_Game>(scope, v => v.OnAbilityCastEnd(this));
             }
         };
     }
 }
Exemple #16
0
        public override EventHandler GetHandler()
        {
            Debug.Log($"{this.GetType().Name}: Called");
            var caster  = ResolveCaster();
            var ability = ResolveAbility(caster);
            var str     = ability.CombatLog(this);

            if (str != null)
            {
                using (var scope = new Hooks.Scope()) Game.hooks.ForEach <IOnCombatLog>(scope, v => v.OnCombatLog(str));
            }
            EventHandler <Ability> abilityHandler = ability.CreateHandler(this);

            ability.OnCast();
            return(abilityHandler);
        }
Exemple #17
0
    /// <summary> The move cost over this Edge. </summary>
    public float MoveCost(Tile from, Tile to)
    {
        if (to != hex1 && to != hex2)
        {
            throw new ArgumentException("To must be one of the Tiles connected to the Edge.", nameof(to));
        }
        if (from != hex1 && from != hex2)
        {
            throw new ArgumentException("From must be one of the Tiles connected to the Edge.", nameof(from));
        }
        var value = to.moveCost.current.value;

        using (var scope = new Hooks.Scope()) {
            this.hooks.ForEach <IOnGetMoveCost_Edge>(scope, v => v.OnGetMoveCost(from, to, ref value));
            Game.hooks.ForEach <IOnGetMoveCost_Game>(scope, v => v.OnGetMoveCost(from, this, to, ref value));
        }
        return(Mathf.Max(0, value));
    }
Exemple #18
0
        /// <summary> Removes this Modifier from the Master and the game. </summary>
        public void Remove()
        {
            if (removed)
            {
                return;
            }
            removed = true;
            Hide();

            master.DetachModifier(this);
            Game.dataObjects.Remove(this);
            Game.hooks.Unhook(this);

            using (var scope = new Hooks.Scope()) Game.hooks.ForEach <IOnModifierRemove>(scope, v => v.OnModifierRemove(this));

            OnConfigureNonpersistent(false);
            OnRemove();
        }
Exemple #19
0
        public override EventHandler GetHandler()
        {
            Debug.Log($"{this.GetType().Name}: Called");

            if (Game.game.started)
            {
                Debug.LogWarning("Readied after Game already started.");
                return(null);
            }

            foreach (var spawn in spawns)
            {
                var tile     = Game.grid.tiles[spawn.position];
                var unitData = App.library.GetById <Unit>(spawn.unit);
                var unit     = Unit.Create(unitData, Game.grid.tiles[spawn.position], 0, team);
                unit.actor.gameObject.SetActive(team == Game.game.team);
            }

            if (!Game.game.readied.Contains(team))
            {
                Game.game.readied.Add(team);
            }

            if (Game.game.readied.Count == Game.game.mode.teams.Count)
            {
                foreach (var spawnCtrl in FindObjectsOfType <SpawnControl>())
                {
                    Destroy(spawnCtrl.gameObject);
                }
                foreach (var unit in Game.dataObjects.Get <Unit>())
                {
                    unit.actor.gameObject.SetActive(true);
                }

                Game.game.StartGame();
            }

            using (var scope = new Hooks.Scope()) Game.hooks.ForEach <IOnTeamReady>(scope, v => v.OnTeamReady(team));

            return(null);
        }
Exemple #20
0
    public void SetTile(Tile tile, bool reposition)
    {
        if (tile == null)
        {
            throw new ArgumentNullException(nameof(tile));
        }
        if (tile == this.tile)
        {
            if (reposition && actor)
            {
                actor.transform.position = this.tile.center;
            }
            return;
        }
        if (removed)
        {
            this.tile = tile;
            return;
        }
        var orig = this.tile;

        if (orig != null)
        {
            orig.units.Remove(this);
        }
        tile.units.Add(this);
        this.tile = tile;
        if (reposition && shown)
        {
            actor.transform.position = this.tile.center;
        }
        using (var scope = new Hooks.Scope()) {
            this.hooks.ForEach <IOnChangePosition_Unit>(scope, v => v.OnChangePosition(orig, tile));
            tile.hooks.ForEach <IOnChangePosition_Tile>(scope, v => v.OnChangePosition(this, orig, tile));
            Game.hooks.ForEach <IOnChangePosition_Game>(scope, v => v.OnChangePosition(this, orig, tile));
        }
    }
Exemple #21
0
    /// <summary> Applies any statuses caused by energy deficit or excess </summary>
    public void RefreshEnergy()
    {
        var deficit = 0 - energy.current;

        if (deficit > 0)
        {
            using (var scope = new Hooks.Scope()) {
                this.hooks.ForEach <IOnEnergyDeficit_Unit>(scope, v => v.OnEnergyDeficit(deficit));
                tile.hooks.ForEach <IOnEnergyDeficit_Tile>(scope, v => v.OnEnergyDeficit(this, deficit));
                Game.hooks.ForEach <IOnEnergyDeficit_Game>(scope, v => v.OnEnergyDeficit(this, deficit));
            }
        }
        var excess = energy.current - energy.max;

        if (excess > 0)
        {
            using (var scope = new Hooks.Scope()) {
                this.hooks.ForEach <IOnEnergyExcess_Unit>(scope, v => v.OnEnergyExcess(excess));
                tile.hooks.ForEach <IOnEnergyExcess_Tile>(scope, v => v.OnEnergyExcess(this, excess));
                Game.hooks.ForEach <IOnEnergyExcess_Game>(scope, v => v.OnEnergyExcess(this, excess));
            }
        }
        energy.Clamp();
    }
Exemple #22
0
    /// <summary> Deals damage that is calculated prior to calling this method by e.g. Ability.CalculateDamage(). </summary>
    public void DealCalculatedDamage(Modifier source, float damage, DamageType type)
    {
        using (var scope = new Hooks.Scope()) {
            switch (source)
            {
            case UnitModifier um:
                um.unit.hooks.ForEach <IOnDealDamage_Unit>(scope, v => v.OnDealDamage(um, this, damage, type));
                Game.hooks.ForEach <IOnDealDamage_Game>(scope, v => v.OnDealDamage(um, this, damage, type));
                break;

            case TileModifier tm:
                tm.tile.hooks.ForEach <IOnDealDamage_Tile>(scope, v => v.OnDealDamage(tm, this, damage, type));
                Game.hooks.ForEach <IOnDealDamage_Game>(scope, v => v.OnDealDamage(tm, this, damage, type));
                break;

            case EdgeModifier em:
                em.edge.hooks.ForEach <IOnDealDamage_Edge>(scope, v => v.OnDealDamage(em, this, damage, type));
                Game.hooks.ForEach <IOnDealDamage_Game>(scope, v => v.OnDealDamage(source, this, damage, type));
                break;
            }
        }
        using (var scope = new Hooks.Scope()) {
            this.hooks.ForEach <IOnTakeDamage_Unit>(scope, v => v.OnTakeDamage(source, ref damage, ref type));
            tile.hooks.ForEach <IOnTakeDamage_Tile>(scope, v => v.OnTakeDamage(this, source, ref damage, ref type));
            Game.hooks.ForEach <IOnTakeDamage_Game>(scope, v => v.OnTakeDamage(this, source, ref damage, ref type));
        }
        switch (type)
        {
        case DamageType.Physical:
            health.current.value -= (1 - defense.current / 100f) * damage;
            health.Clamp();
            break;

        case DamageType.Magical:
            health.current.value -= (1 - resistance.current / 100f) * damage;
            health.Clamp();
            break;

        case DamageType.Pure:
            health.current.value -= damage;
            health.Clamp();
            break;

        default:
            health.current.value -= damage;
            health.Clamp();
            Debug.LogWarning($"Damage type was either unknown or None. Damage was applied as {DamageType.Pure}");
            break;
        }

        if (health.current <= 0)
        {
            using (var scope = new Hooks.Scope()) Game.hooks.ForEach <IOnCombatLog>(scope, v => v.OnCombatLog($"Unit death: {Lang.GetStr($"{identifier}_DisplayName")} ({team})"));
            using (var scope = new Hooks.Scope()) {
                this.hooks.ForEach <IOnDeath_Unit>(scope, v => v.OnDeath());
                tile.hooks.ForEach <IOnDeath_Tile>(scope, v => v.OnDeath(this));
                Game.hooks.ForEach <IOnDeath_Game>(scope, v => v.OnDeath(this));
            }
            Remove();
        }
    }