Это можно сделать несколькими способами. Прежде чем показать вам конкретный материал, вот базовая структура, общая для всех примеров кода, которую я буду использовать:
public class ColorChanger : MonoBehaviour {
//Avoid Find and GetComponent methods in performance-critical contexts like Update and FixedUpdate
//Store the value once in the beginning. This is called 'caching'
public SpriteRenderer _renderer;
//Don't hard-code stuff like this
public Color[] _colors;
public float _colorChangeInterval = 0.5f;
//Convenience property to access _renderer.color
public Color Color {
get => _renderer.color;
set => _renderer.color = value;
}
private void Start() {
//Attempts to find the SpriteRenderer in the object if it wasn't set in the inspector
if (!_renderer)
_renderer = GetComponent<SpriteRenderer>();
}
//This piece of code does a specific thing, so it's best to put it in a method
public void ChangeColor() {
if (_colors.Length < 1)
Debug.LogError($"You forgot to set {nameof(_colors)} in the Inspector. Shame! Shame!");
Color = _colors[Random.Range(0, _colors.Length - 1)];
}
}
Вот некоторые из основных, в порядке того, насколько интуитивно понятенони, по моему мнению:
Шаблон таймера:
Два варианта для этого.
1) Может быть аккумулятором за прошедшее время (как в кодениже), или наоборот, и уменьшите от интервала до нуля:
private float _elapsed;
private void Update() {
_elapsed += Time.deltaTime;
if (_elapsed < _colorChangeInterval)
return;
ChangeColor();
_elapsed %= _colorChangeInterval;
}
или 2) Может быть триггером проверки отметки времени с последней или до следующей (как показано ниже) отметки времени:
//Replaces _elapsed
private float _timestamp;
private void Start() {
//...
_timestamp = Time.time; //Initial timestamp
}
private void Update() {
if (Time.time < _timestamp + _colorChangeInterval)
return;
ChangeColor();
_timestamp = Time.time;
}
Coroutine & WaitForSeconds:
Это рекомендуемая процедура для случаев, когда вам нужно задержать или упорядочить код в единицу.
Обратите внимание, что существуют другие типы методов ожиданияобеспечивается единством, например WaitWhile
, WaitUntil
и т. д. *
//Since unlike code in Update, coroutines need to be started and stopped, we start it when the script is enabled
private void OnEnable() {
StartCoroutine(ChangeColorContinuously());
}
//This is automatically stopped by unity when the script is disabled
private IEnumerator ChangeColorContinuously() {
while (true) {
yield return new WaitForSeconds(_colorChangeInterval);
ChangeColor();
}
}
Не выполняйте Async Await!
Ну, это может сделано, но в нем много подводных камней и очень много НЕ рекомендуется для начинающих.
И яВ любом случае, он не предназначен для замены сопрограмм.
Не выполняйте InvokeRepeating!
Это метод, основанный на магических строках и отражении. Полезно для быстрой и простой установки, например, кода, но его следует избегать, если это вообще возможно (и это возможно, благодаря вышеописанным методам), как чума в рабочем коде.