How can I create and scale up 100 cubes over time one by one with using Vector3.Lerp function. I need to be dependent on the duration variable. I need an efficient way.
Asked
Active
Viewed 119 times
1 Answers
0
Though your question is pretty vague:
Use a Coroutine like e.g.
// Adjust these in the Inspector
[SerilaizeField] private Vector3 targetScale = Vector3.one;
[SerilaizeField] private Vector3 startScale = Vector3.zero;
[SerilaizeField] private float durationPerCube = 1f;
[SerilaizeField] private Transform[] cubes;
private IEnumerator ScaleUpRoutine()
{
if(cubes.Length == 0) yield break;
foreach(var cube in cubes)
{
var timePassed = 0f;
while(timePassed < durationPerCube)
{
var factor = timePassed / duration;
// optional easing-in and -out
//factor = Mathf.SmoothStep(0, 1, factor);
cube.localScale = Vector3.Lerp(startScale, targetScale, factor);
timePassed += Time.deltaTime;
yield return null;
}
// just to be sure set a hard value
cube.localScale = targetScale;
}
}
You start it whenever you want via StartCoroutine
e.g.
private void Start()
{
StartCoroutine(ScaleUpRoutine);
}
If you rather wanted it based on overall duration you could do
// Adjust this in the Inspector
[SerilaizeField] private float overallDuration = 2f;
private IEnumerator ScaleUpRoutine()
{
if(cubes.Length == 0) yield break;
var durationPerCube = overallDuration / cubes.Length;
...
Keep in mind though that yield return null;
currently waits for at least one frame per cube so if your overallDuration
is very small (< 100 frames) it might not be accurate. In this case you might want to add a StopWatch
in order to only yield return
a frame after a certain real-time threshold like
...
private IEnumerator ScaleUpRoutine()
{
if(cubes.Length == 0) yield break;
var stopWatch = new StopWatch();
stopWatch.Restart();
...
while(timePassed < durationPerCube)
{
var factor = timePassed / duration;
// optional easing-in and -out
//factor = Mathf.SmoothStep(0, 1, factor);
cube.localScale = Vector3.Lerp(startScale, targetScale, factor);
timePassed += Time.deltaTime;
if(stopWatch.ElapsedMilliseconds >= maxMillisecondPerFrame)
{
yield return null;
stopWatch.Restart();
}
}
...
For the creating part: You shouldn't.
Depending on your needs I would either
- Use a hidden object that already holds 100 cubes in the scene. Only display it when needed
- Extend the same idea a bit further and use pooling instead

derHugo
- 83,094
- 9
- 75
- 115
-
Thank you for your answer, but my main question is how can I create 100 cubes an efficient way in the scene? – Elif Jun 03 '20 at 13:15
-
@Elif well ... that is a completely different Question to be honest ^^ ... quick answer: You shouldn't. Use [pooling](https://learn.unity.com/tutorial/object-pooling) instead – derHugo Jun 03 '20 at 13:17