Stats not progressing

I added 5 levels of Damage Stat to the Player in the progression. In game, the first level of damage is dealt regardless of the actual level of the player. I also later noticed that the max health of the player isn’t going up after level up either. I tested to see if I changed the first level of Damage in the progression what would happen, it does deal the new number, so it’s getting the number from the first level, but not changing to the other levels. Also tested it with Health, same behavior.

I would guess there’s something wrong with the Progression or BaseStats script, but I can’t see the problem if there is one.

namespace RPG.Stats
{
    [CreateAssetMenu(fileName = "Progression", menuName = "Stats/New Progression", order = 0)]
    public class Progression : ScriptableObject 
    {
        [SerializeField] ProgressionCharacterClass[] characterClasses = null;
        Dictionary<CharacterClass, Dictionary<Stat, float[]>> lookupTable = null;

        public float GetStat(Stat stat, CharacterClass characterClass, int level)
        {
            BuildLookup();
            float[] levels = lookupTable[characterClass][stat];
            if (levels.Length < level)
            {
                return 0;
            }
            return levels[level - 1];
        }

        public int GetLevels(Stat stat, CharacterClass characterClass)
        {
            BuildLookup();
            
            float[] levels = lookupTable[characterClass][stat];
            return levels.Length;
        }

        void BuildLookup()
        {
            if (lookupTable != null) return;

            lookupTable = new Dictionary<CharacterClass, Dictionary<Stat, float[]>>();

            foreach (ProgressionCharacterClass progressionClass in characterClasses)
            {
                var statLookupTable = new Dictionary<Stat, float[]>();

                foreach(ProgressionStat progressionStat in progressionClass.stats)
                {
                    statLookupTable[progressionStat.stat] = progressionStat.levels;
                }

                lookupTable[progressionClass.characterClass] = statLookupTable;
            }
        }

        [System.Serializable]
        class ProgressionCharacterClass
        {
            public CharacterClass characterClass;
            public ProgressionStat[] stats;
        }

        [System.Serializable]
        class ProgressionStat
        {
            public Stat stat;
            public float[] levels;
        }
    }
}
namespace RPG.Stats
{

    public class BaseStats : MonoBehaviour
    {
        [Range(1,99)]
        [SerializeField] int startingLevel = 1;
        [SerializeField] CharacterClass characterClass;
        [SerializeField] Progression progression = null;
        [SerializeField] GameObject levelUpParticleEffect = null;

        int currentLevel = 0;

        public event Action onLevelUp;

        void Start() 
        {
            currentLevel = CalculateLevel();
            Experience experience = GetComponent<Experience>();
            if (experience != null)
            {
                experience.onExperienceGained += UpdateLevel;
            }
        }

        void UpdateLevel() 
        {
            int newLevel = CalculateLevel();
            if(newLevel > currentLevel)
            {
                currentLevel = newLevel;
                LevelUpEffect();
                onLevelUp();
            }
        }

        void LevelUpEffect()
        {
            Instantiate(levelUpParticleEffect, transform);
        }

        public float GetStat(Stat stat)
        {
            return progression.GetStat(stat, characterClass, startingLevel);
        }

        public int GetLevel()
        {
            if (currentLevel < 1)
            {
                currentLevel = CalculateLevel();
            }
            return currentLevel;
        }

        public int CalculateLevel()
        {
            Experience experience = GetComponent<Experience>();

            if(experience == null) return startingLevel;

            float currentXP = experience.GetPoints();
            
            int penultimateLevel = progression.GetLevels(Stat.XPToLevelUp, characterClass);
            for (int level = 1; level <= penultimateLevel; level++)
            {
                float XPToLevelUp = progression.GetStat(Stat.XPToLevelUp, characterClass, level);
                if(XPToLevelUp > currentXP) return level;
            }
            return penultimateLevel + 1;
        }
    }


}

It could be because the currentLevel is calculated on a character with an experience component, meaning that no matter what startingLevel is, it’s reset based on the value of experience.

Of course, you want this, because the player’s level should be saved/restored between sessions…

Let’s create a hack to let you increase the level while playing the game for testing.

Put this in Experience.cs:

        #if UNITY_EDITOR
        private void Update() {
            if (Input.GetKey(KeyCode.E))
            {
                GainExperience(Time.deltaTime * 1000);
            }
        }
        #endif

This will let you gain experience just by pressing the letter E on the keyboard. Then you can test the values at different levels.

Didn’t change anything. I can kill enemies for experience too and it shows the experience gained and the level on display, but the Stat values remain the same.

Missed this on the first pass…
You’re always sending startingLevel to the GetStat, when you should be sending currentLevel.

1 Like

This topic was automatically closed 24 hours after the last reply. New replies are no longer allowed.