我目前正在Unity中开发游戏,但有一个小问题。我正在尝试创建一种效果,其中当计分计数器递增时,游戏中计分计数器的颜色会临时更改颜色,然后切换回其原始颜色。但是,当我尝试执行此操作时,我的游戏将继续崩溃。我正在使用while循环来执行此任务,但是一旦我尝试在游戏中触发该事件,我的游戏以及Unity崩溃便会立即执行。有谁知道为什么会这样,也许有解决的办法来解决这个问题?
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class StarCollision : MonoBehaviour
{
private void OnTriggerEnter2D(Collider2D other)
{
if (other.gameObject.tag == "White Ball" )
{
gameObject.SetActive(false);
ScoreScript.scoreValue += 1;
while (Time.deltaTime < 0.2f)
{
ScoreScript.score.color = Color.yellow;
}
ScoreScript.score.color = Color.white;
}
}
}
答案 0 :(得分:3)
使用协同程序及其WaitForSeconds方法
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class StarCollision : MonoBehaviour
{
private void OnTriggerEnter2D(Collider2D other)
{
if (other.gameObject.CompareTag("White Ball"))
{
ScoreScript.scoreValue += 1;
StartCoroutine(ChangeColor());
}
}
private IEnumerator ChangeColor ()
{
ScoreScript.score.color = Color.yellow;
yield return new WaitForSeconds(0.2f);
ScoreScript.score.color = Color.white;
gameObject.SetActive(false);
}
}
答案 1 :(得分:2)
您的public enum ValueType {
LITERAL() {
@Override
String getRepresentation(String... args) {
return MvelStringUtil.representAsLiteral(args[0]);
}
},
NUMBER() {
@Override
String getRepresentation(String... args) {
return args[0];
}
},
//converts a string representation of a date to a java.util.Date representation, because this is what is required
DATE() {
@Override
// should have two params, 1- date in string, 2- format of the passed string
String getRepresentation(String... args) {
// DateUtil.parse accepts dateInString and dateFormat.
return DateUtil.parse(args[0], args[1]).toString();
}
};
abstract String getRepresentation(String... args);
}
循环正在阻塞Main / UI线程=>它被执行,并且下一帧仅在完成后才呈现!
另外Time.deltaTime
是渲染最后一帧以来经过的时间...因此它可能永远不会达到while
,因为假设您以0.2
运行值将约为60 fps
=> Unity冻结!
您应该改用Coroutine:
0.017
在协程结束之前,我会离开您的public class StarCollision : MonoBehaviour
{
private void OnTriggerEnter2D(Collider2D other)
{
if (other.gameObject.tag == "White Ball" )
{
ScoreScript.scoreValue += 1;
// start the routine
StartCoroutine(ChangeColor());
gameObject.SetActive(false);
}
}
private IEnumerator ChangeColor()
{
ScoreScript.score.color = Color.yellow;
// yield says: return to main thread, renderer the frame
// and continue from here in the next frame
// WaitForseconds .. does exactly this
yield return new WaitForseconds(0.2f);
ScoreScript.score.color = Color.white;
}
}
,但在您开始后之后,因为您要立即这样做
注意:禁用
gameObject.SetActive(false);
时不会停止Coroutines,而只有在肯定将其销毁时才停止。您可以使用MonoBehaviour
和MonoBehaviour.StopCoroutine
停止协程。当MonoBehaviour.StopAllCoroutines
被销毁时,协程也将停止。
答案 2 :(得分:-1)
为此,您必须使用Coroutine
。检出https://docs.unity3d.com/Manual/Coroutines.html
基本上,您只需要在循环的每次迭代中产生一帧,即所需的时间,或者产生特定的时间。
希望有帮助