Unity-如何为每一个好动作显示几秒钟的文本



我是Unity和编程的新手,所以我需要一些帮助。在玩家做出好动作后,我试图显示文本3秒。它正在进行第一次移动,文本消失了,但它仍在闪烁。可能是因为它处于更新方法中,并且此项目仍处于锁定状态。。。但是,我如何在每次好动作后将其更改为显示此文本3秒?每个项目仅一次。谢谢

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class GameControl : MonoBehaviour
{
[SerializeField]
private GameObject someText
[SerializeField]
private GameObject goodMove;
// Use this for initialization
void Start()
{
someText.SetActive(false);
goodMove.SetActive(false);
}
void Update()
{
if (item1.locked && item2.locked && item3.locked)
{
someText.SetActive(true);
}
if (item1.locked || item2.locked || item3.locked)
{
StartCoroutine(waiter());
}
}
IEnumerator waiter()
{
goodMove.SetActive(true);
yield return new WaitForSeconds(3);
goodMove.SetActive(false);
}

}

编辑:项目被拖动到正确的位置时被锁定

...case TouchPhase.Ended:
if (Mathf.Abs(transform.position.x - somePlace.position.x) <= 2f &&
Mathf.Abs(transform.position.y - somePlace.position.y) <= 2f)
{
transform.position = new Vector2(somePlace.position.x, somePlace.position.y);
transform.localScale -= new Vector3(0.4F, 0.4F, 0.4F);
locked = true;
}
else
{
transform.position = new Vector2(initialPosition.x, initialPosition.y);
}
break;

它在闪烁,因为您每帧都在调用StartCoroutine(waiter());。您可以使用布尔变量使其只调用一次。如果我是你,我会删除Update函数,并使用协程来修复它,避免在触摸检测脚本中移动代码。

此外,下面的代码正在执行每一帧:

if (item1.locked && item2.locked && item3.locked)
{
someText.SetActive(true);
}

最好创建另一个锁定变量,以便在执行if语句之前可以使用它来检查锁定变量何时发生了更改。注意下面的ItemChanged()函数,它就是这么做的。

public class GameControl : MonoBehaviour
{
//Change YourItemType to whatver your item1, item2, item3 types are
YourItemType item1, item2, item3;
[SerializeField]
private GameObject someText;
[SerializeField]
private GameObject goodMove;
bool oldVal1;
bool oldVal2;
bool oldVal3;
// Use this for initialization
void Start()
{
someText.SetActive(false);
goodMove.SetActive(false);
StartCoroutine(LockChecker());
}
IEnumerator LockChecker()
{
oldVal1 = item1.locked;
oldVal2 = item2.locked;
oldVal3 = item3.locked;
//Run this code forever as the Update function
while (true)
{
//Check if item has changed
if (ItemChanged())
{
if (item1.locked && item2.locked && item3.locked)
{
someText.SetActive(true);
}
if (item1.locked || item2.locked || item3.locked)
{
//Call the waiter function then wait for it to return
yield return StartCoroutine(waiter());
}
}
yield return null;
}
}
bool ItemChanged()
{
//Check if the booelan variable changed
if (oldVal1 != item1.locked ||
oldVal2 != item2.locked ||
oldVal3 != item3.locked)
{
//Update old values
oldVal1 = item1.locked;
oldVal2 = item2.locked;
oldVal3 = item3.locked;
return true;
}
return false;
}
IEnumerator waiter()
{
goodMove.SetActive(true);
yield return new WaitForSeconds(3);
goodMove.SetActive(false);
}
}

更好的是,将锁定的变量声明为属性,然后使用getset评估器来检测锁定的变量何时更改并启动协同程序。这里有一个例子。

你是对的,它可能在闪烁,因为一旦一个项目被锁定,它将继续被锁定,Update方法将继续激发你的协同程序。相反,我会在项目被锁定的时候给你的协同程序打电话(当然也会从你的更新中删除复选框(:

if (Mathf.Abs(transform.position.x - somePlace.position.x) <= 2f &&
Mathf.Abs(transform.position.y - somePlace.position.y) <= 2f)
{
transform.position = new Vector2(somePlace.position.x, somePlace.position.y);
transform.localScale -= new Vector3(0.4F, 0.4F, 0.4F);
locked = true;
StartCoroutine(waiter());
}

最新更新