Performance Improvement For Time Controlled Slider?

Right now, I have to things:

  1. A Slider from 0 to 10.

  2. An empty gameObject using the following script:

       public Slider Slider;
    float timeLeft = 10.0f;
    
    void FixedUpdate()
    {
        timeLeft -= Time.deltaTime;
        Debug.Log(timeLeft);
        Slider.value = 10.0f - timeLeft;
        if (timeLeft < 0)
        {
            Debug.Log("Time's over!");
            timeLeft = 10.0f;
        }
    }
    

    }

It works like a charm, the slider is moving accordingly and resets when reaching the end. However I’m quite sure that’s not that efficient performance-wise. I’ve read something about using IEnumerator (yep, newbie here), but I couldn’t bring it to work.

Also, is it possible to set the value to whole numbers? Although it’s possible to tick the “whole numbers” box at the slider’s component itself, that won’t change the “real” value that’ll still have decimals. Not sure whether that’ll add something to the performance as well, but if so: why not.

Thanks in advance! :slight_smile:

A.

Use the performance tools to check and see if your seeing any noticable decrease in frames, if your not really actually seeing the performance hit in a meaningful way, don’t worry too much about optimizing for it.

co routines are “efficient” only in that most modern processors are multi threaded and co routines generally run on another processor, freeing up the one used by the game loop. This only matters if your CPU is being overly taxed by your game loop though, otherwise it doesn’t matter, which is why I said point A. That your CPU utilization goes from 40% to 55% or whatever doesn’t matter unless your really concerned about electricity.

a simple script is (pulled nearly directly from waitforseconds documentation)

using UnityEngine;
using System.Collections;

public class WaitForSeconds : MonoBehaviour
{
    void Start()
    {
        StartCoroutine(Timer(5));
    }

    IEnumerator Timer(int Seconds)
    {
        yield return new WaitForSeconds(Seconds);
    }
}``

you can’t directly wait as it were.

something like

void Update()
{
 StartCoRoutine(Timer(5));
//do something after 5 seconds
}

DOES NOT WORK

firstly, starting a co routine in an update in this case at least would mean a new timer is started every frame, so 60 timers a second, which would lock up your pc.

secondly.
because co routines run basically seperatly, the do something after 5 seconds code would run right away because the co routine gets handed off to another processor.

that is what makes co-routines nice, you can do things in parallel and utilize multiple processors.

that’s also what can make them confusing because you don’t realize that anything inside a co routine has basically broken out of the brackets the code is contained in.

So if you want to you can indeed use a enumerator and it’s probably good practice, but basically all your doing is this.

Ienumerator Timer()
{
         timeLeft -= Time.deltaTime;
         Debug.Log(timeLeft);
         Slider.value = 10.0f - timeLeft;
         if (timeLeft < 0)
         {
             Debug.Log("Time's over!");
             timeLeft = 10.0f;
         }
}

which is literally extracting your fixed update code and placing it running in parallel on another processor.

probably not needed if your game is simple, but fine practice.

You can use InvokeRepeating. This will round values and also limit the update rate of the slider

Something in the lines :

    [SerializeField] Slider timeSlider;
    float time = 10f;

    void Start()
    {
        InvokeRepeating ("UpdateTimer", 1.0f, 1.0f);
    }

    void UpdateTimer ()
    {
        time -= 1f;
        timeSlider.value = time;
    }