I have several values which adjust them self In Unity Inspector when I tweak one of them. So total sum of these values stays constant. (which is 100 as 100%)
Sometimes it is hard to get specific values on more when one slider. How can I lock value so it can't be affected by adjusting other values?
private const float TOTAL_STARS_SHARE = 100.0f; //total share of all stars
// #0
[Tooltip("Share of Blue Star Hard prefabs in percentages.")]
[Range(0f, 100f)]
[SerializeField]
private float shareOfBlueStarHard;
private float shareOfBlueStarHardCACHE; //cache for value with same name
// #1
[Tooltip("Share of Blue Star Medium prefabs in percentages.")]
[Range(0f, 100f)]
[SerializeField]
private float shareOfBlueStarMedium;
private float shareOfBlueStarMediumCACHE; //cache for value with same name
// #2
[Tooltip("Share of Blue Star Soft prefabs in percentages.")]
[Range(0f, 100f)]
[SerializeField]
private float shareOfBlueStarSoft;
private float shareOfBlueStarSoftCACHE; //cache for value with same name
// #3
[Tooltip("Share of Red Star Soft prefabs in percentages.")]
[Range(0f, 100f)]
[SerializeField]
private float shareOfRedStarSoft;
private float shareOfRedStarSoftCACHE; //cache for value with same name
// #4
[Tooltip("Share of White Star Hard prefabs in percentages.")]
[Range(0f, 100f)]
[SerializeField]
private float shareOfWhiteStarHard;
private float shareOfWhiteStarHardCACHE; //cache for value with same name
// #5
[Tooltip("Share of White Star Medium prefabs in percentages.")]
[Range(0f, 100f)]
[SerializeField]
private float shareOfWhiteStarMedium;
private float shareOfWhiteStarMediumCACHE; //cache for value with same name
// #6
[Tooltip("Share of White Star Soft prefabs in percentages.")]
[Range(0f, 100f)]
[SerializeField]
private float shareOfWhiteStarSoft;
private float shareOfWhiteStarSoftCACHE; //cache for value with same name
// #7
[Tooltip("Share of Yellow Star Soft prefabs in percentages.")]
[Range(0f, 100f)]
[SerializeField]
private float shareOfYellowStarSoft;
private float shareOfYellowStarSoftCACHE; //cache for value with same name
/* Controls sliders for stars shares in Unity Inspector. Doesn't work in actual game.*/
#if UNITY_EDITOR
private void OnValidate()
{
ValidateStarsShares();
}
private void ValidateStarsShares() // Find which value the user changed, and update the rest from it.
{
// Skip this if we haven't cached the values yet.
if (shareOfBlueStarHardCACHE >= 0)
{
// Find which value the user changed, and update the rest from it.
if (shareOfBlueStarHardCACHE != shareOfBlueStarHard) // #0 star share changed
{
DistributeProportionatelyForStars(ref shareOfBlueStarHard, ref shareOfBlueStarMedium, ref shareOfBlueStarSoft, ref shareOfRedStarSoft,
ref shareOfWhiteStarHard, ref shareOfWhiteStarMedium, ref shareOfWhiteStarSoft, ref shareOfYellowStarSoft);
}
else if (shareOfBlueStarMediumCACHE != shareOfBlueStarMedium) // #1 star share changed
{
DistributeProportionatelyForStars(ref shareOfBlueStarMedium, ref shareOfBlueStarHard, ref shareOfBlueStarSoft, ref shareOfRedStarSoft,
ref shareOfWhiteStarHard, ref shareOfWhiteStarMedium, ref shareOfWhiteStarSoft, ref shareOfYellowStarSoft);
}
else if (shareOfBlueStarSoftCACHE != shareOfBlueStarSoft) // #2 star share changed
{
DistributeProportionatelyForStars(ref shareOfBlueStarSoft, ref shareOfBlueStarHard, ref shareOfBlueStarMedium, ref shareOfRedStarSoft,
ref shareOfWhiteStarHard, ref shareOfWhiteStarMedium, ref shareOfWhiteStarSoft, ref shareOfYellowStarSoft);
}
else if (shareOfRedStarSoftCACHE != shareOfRedStarSoft) // #3 star share changed
{
DistributeProportionatelyForStars(ref shareOfRedStarSoft, ref shareOfBlueStarHard, ref shareOfBlueStarMedium, ref shareOfBlueStarSoft,
ref shareOfWhiteStarHard, ref shareOfWhiteStarMedium, ref shareOfWhiteStarSoft, ref shareOfYellowStarSoft);
}
else if (shareOfWhiteStarHardCACHE != shareOfWhiteStarHard) // #4 star share changed
{
DistributeProportionatelyForStars(ref shareOfWhiteStarHard, ref shareOfBlueStarHard, ref shareOfBlueStarMedium, ref shareOfBlueStarSoft,
ref shareOfRedStarSoft, ref shareOfWhiteStarMedium, ref shareOfWhiteStarSoft, ref shareOfYellowStarSoft);
}
else if (shareOfWhiteStarMediumCACHE != shareOfWhiteStarMedium) // #5 star share changed
{
DistributeProportionatelyForStars(ref shareOfWhiteStarMedium, ref shareOfBlueStarHard, ref shareOfBlueStarMedium, ref shareOfBlueStarSoft,
ref shareOfRedStarSoft, ref shareOfWhiteStarHard, ref shareOfWhiteStarSoft, ref shareOfYellowStarSoft);
}
else if (shareOfWhiteStarSoftCACHE != shareOfWhiteStarSoft) // #6 star share changed
{
DistributeProportionatelyForStars(ref shareOfWhiteStarSoft, ref shareOfBlueStarHard, ref shareOfBlueStarMedium, ref shareOfBlueStarSoft,
ref shareOfRedStarSoft, ref shareOfWhiteStarHard, ref shareOfWhiteStarMedium, ref shareOfYellowStarSoft);
}
else if (shareOfYellowStarSoftCACHE != shareOfYellowStarSoft) // #7 star share changed
{
DistributeProportionatelyForStars(ref shareOfYellowStarSoft, ref shareOfBlueStarHard, ref shareOfBlueStarMedium, ref shareOfBlueStarSoft,
ref shareOfRedStarSoft, ref shareOfWhiteStarHard, ref shareOfWhiteStarMedium, ref shareOfWhiteStarSoft);
}
}
// Cache the old values for the next edit.
shareOfBlueStarHardCACHE = shareOfBlueStarHard;
shareOfBlueStarMediumCACHE = shareOfBlueStarMedium;
shareOfBlueStarSoftCACHE = shareOfBlueStarSoft;
shareOfRedStarSoftCACHE = shareOfRedStarSoft;
shareOfWhiteStarHardCACHE = shareOfWhiteStarHard;
shareOfWhiteStarMediumCACHE = shareOfWhiteStarMedium;
shareOfWhiteStarSoftCACHE = shareOfWhiteStarSoft;
shareOfYellowStarSoftCACHE = shareOfYellowStarSoft;
}
void DistributeProportionatelyForStars(ref float changed, ref float one, ref float two, ref float three,
ref float four, ref float five, ref float six, ref float seven)
{
changed = Mathf.Clamp(changed, 0.0f, TOTAL_STARS_SHARE);
float total = TOTAL_STARS_SHARE - changed;
float oldTotal = one + two + three + four + five + six + seven;
if (oldTotal > 0)
{
float fraction = 1f / oldTotal;
one = Mathf.RoundToInt(total * one * fraction);
two = Mathf.RoundToInt(total * two * fraction);
three = Mathf.RoundToInt(total * three * fraction);
four = Mathf.RoundToInt(total * four * fraction);
five = Mathf.RoundToInt(total * five * fraction);
six = Mathf.RoundToInt(total * six * fraction);
seven = Mathf.RoundToInt(total * seven * fraction);
}
else
{
one = two = three = four = five = six = seven = total / 7;
}
// Assign any rounding error to the last one, arbitrarily.
// (Better rounding rules exist, so take this as an example only)
//c += total - a - b - c;
}
#endif

