- Home /
Yield Script Update Error
Hi, I'm making Sparky Konga, an interactive game application using the DK Bongo controllers (You can watch my Beta test Video Here: https://vimeo.com/63044764). My problem right now is that the internal microphone for the controller, meant to hear clapping, is reacting to hearing and feeling the vibration of me hitting the other parts of the bongo controller. I coded my project so that the mic value = 0 whenever the button is pressed. However, it didn't work as well as I wanted to because sound and vibration tend to linger a tiny bit. So, I want to make the mic = 0 function last for more than a single frame. I found out about the yield function and tried to use it to make mic = 0 for about 5 seconds as a test (in the end, I only want it to last for around 1/10 or 2/10 of a second).
if (Input.GetKeyDown(KeyCode.JoystickButton0) || Input.GetKeyDown(KeyCode.JoystickButton1) || Input.GetKeyDown(KeyCode.JoystickButton2) || Input.GetKeyDown(KeyCode.JoystickButton3)) {
mic = 0;
yield return new WaitForSeconds(5.0f);
}
It worked... However then there began to be problems. I stopped my game play test and changed 5.0f to 0.2f. The problem is that now, I get this error.
Assets/Scripts/UnityOSC-master/BoncoClapScript.cs(35,14): error CS1624: The body of
BoncoClapScript.Update()' cannot be an iterator block because
void' is not an iterator interface type
I don't understand why it's saying this. I changed it back to 5.0f, but I still got this error and I keep getting this error every time I try to run my game (if I remove the yield statement, it works as normal). I seems like it has some problem with the Update function, but I can't seem to figure it out why considering I didn't touch anything and it seemingly worked once before.
Does anyone have any idea what the issue is here?
FYI, there are huge numbers of questions on all the details of yield on here, (When I was a new Unity user I must have asked 20.) Just search for your faster convenience. Also read at unityGE$$anonymous$$S.com
Also, for extremely simple timers in Unity, just use Invoke() or InvokeRepeating(). There is absolutely no reason to have any involvement with coroutines for very simple Unity program$$anonymous$$g, no more than you need to be able to write shaderlab for very simple Unity program$$anonymous$$g.
I did before I asked this. Couldn't find anything see$$anonymous$$gly similar to my problem.
No, there are perhaps 100 question exactly about this. There are even (incredibly long) excellent tutorials on the topic, since you've started with no knowledge of coroutines etc.
Answer by whydoidoit · Apr 28, 2013 at 06:51 AM
So you can't yield inside an Update function because that is called every frame, guaranteed, and you would end up with lots of copies running. You have to start a coroutine to be able to yield from there. This feels like a case where you shouldn't use Update and should instead use a coroutine for all of your updating. A good way of doing that is just to make your Start function a coroutine by declaring it as IEnumerator Start and then have that be like your pausable Update function. You could also create any other named coroutine and start it with StartCoroutine(YourFunction()).
IEnumerator Start()
{
while(true)
{
//The code here acts like an Update function, but you can yield different amount in
//it if you want to.
if(Input.GetKeyDown(KeyCode.JoystickButton0))
yield return new WaitForSeconds(5);
yield return null;
}
}
I put that into my code, but it seems to have birthed even more problems. I've tried experimenting, but nothing seems to work. I'm sorry, I'm not a great programmer and am trying to learn, but can you figure out what's wrong in my code here? (I know it's a lot of code, but I'd appreciate if you could take a $$anonymous$$ute to look it over)
// Update is called once per frame
void Update () {
if (Input.Get$$anonymous$$ey($$anonymous$$eyCode.JoystickButton9) || Input.Get$$anonymous$$ey($$anonymous$$eyCode.S)) {
alt = !alt;
}
if (Input.Get$$anonymous$$ey($$anonymous$$eyCode.JoystickButton9) || Input.Get$$anonymous$$ey($$anonymous$$eyCode.S) && alt == true) {
//alt = alt;
}
OSCHandler.Instance.UpdateLogs();
servers = OSCHandler.Instance.Servers;
foreach( $$anonymous$$eyValuePair<string, ServerLog> item in servers )
{
// If we have received at least one packet,
// show the last received from the log in the Debug console
if(item.Value.log.Count > 0)
{
int lastPacketIndex = item.Value.packets.Count - 1;
Debug.Log(String.Format("SERVER: {0} ADDRESS: {1} VALUE 0: {2}",
item.$$anonymous$$ey, // Server name
item.Value.packets[lastPacketIndex].Address, // OSC address
item.Value.packets[lastPacketIndex].Data[0].ToString())); //First data value
int mic = (int) item.Value.packets[lastPacketIndex].Data[0];
Debug.Log("microphone" + mic);
//Triggers Particles, sounds, and sets buffer for mic values
if (mic >= filter || (Input.Get$$anonymous$$eyDown($$anonymous$$eyCode.W)) && alt == false) {
particleSystem.Emit(burst);
audio.PlayOneShot(clap);
//flash.range = (5 - Time.deltaTime);
}
if (mic >= filter && alt == true) {
particleSystem.Emit(burst);
audio.PlayOneShot(clap2);
//flash.range = (5 - Time.deltaTime);
}
IEnumerator Start() {
while(true) {
//The code here acts like an Update function, but you can yield different amount in
//it if you want to.
if(Input.Get$$anonymous$$eyDown($$anonymous$$eyCode.JoystickButton0)||($$anonymous$$eyCode.JoystickButton1)||($$anonymous$$eyCode.JoystickButton2)||($$anonymous$$eyCode.JoystickButton3))
yield return new WaitForSeconds(5.0f);
yield return null;
}
}
}
}
if ((Input.Get$$anonymous$$eyDown($$anonymous$$eyCode.W))) {
particleSystem.Emit(burst);
audio.PlayOneShot(clap);
}
if (Input.Get$$anonymous$$eyDown($$anonymous$$eyCode.W) && alt == true) {
particleSystem.Emit(burst);
audio.PlayOneShot(clap2);
}
}
}
}
Oh yeah - I didn't mean to embed that code :S Wait one.
IEnumerator Start()
{
while (true)
{
if (Input.Get$$anonymous$$ey($$anonymous$$eyCode.JoystickButton9) || Input.Get$$anonymous$$ey($$anonymous$$eyCode.S))
{
alt = !alt;
}
if (Input.Get$$anonymous$$ey($$anonymous$$eyCode.JoystickButton9) || Input.Get$$anonymous$$ey($$anonymous$$eyCode.S) && alt == true)
{
//alt = alt;
}
OSCHandler.Instance.UpdateLogs();
servers = OSCHandler.Instance.Servers;
foreach (var item in servers)
{
// If we have received at least one packet,
// show the last received from the log in the Debug console
if (item.Value.log.Count > 0)
{
int lastPacketIndex = item.Value.packets.Count - 1;
Debug.Log(String.Format("SERVER: {0} ADDRESS: {1} VALUE 0: {2}",
item.$$anonymous$$ey, // Server name
item.Value.packets[lastPacketIndex].Address, // OSC address
item.Value.packets[lastPacketIndex].Data[0].ToString())); //First data value
int mic = (int)item.Value.packets[lastPacketIndex].Data[0];
Debug.Log("microphone" + mic);
//Triggers Particles, sounds, and sets buffer for mic values
if (mic >= filter || (Input.Get$$anonymous$$eyDown($$anonymous$$eyCode.W)) && alt == false)
{
particleSystem.Emit(burst);
audio.PlayOneShot(clap);
//flash.range = (5 - Time.deltaTime);
}
if (mic >= filter && alt == true)
{
particleSystem.Emit(burst);
audio.PlayOneShot(clap2);
//flash.range = (5 - Time.deltaTime);
}
if (Input.Get$$anonymous$$eyDown($$anonymous$$eyCode.JoystickButton0) || ($$anonymous$$eyCode.JoystickButton1) || ($$anonymous$$eyCode.JoystickButton2) || ($$anonymous$$eyCode.JoystickButton3))
yield return new WaitForSeconds(5.0f);
yield return null;
if ((Input.Get$$anonymous$$eyDown($$anonymous$$eyCode.W)))
{
particleSystem.Emit(burst);
audio.PlayOneShot(clap);
}
if (Input.Get$$anonymous$$eyDown($$anonymous$$eyCode.W) && alt == true)
{
particleSystem.Emit(burst);
audio.PlayOneShot(clap2);
}
}
}
}
}
No Update function at all - this gives you more control
If you don't $$anonymous$$d, could you explain the lack of an update function? What changes does this create as opposed to when I had one? Isn't an Update function required?
Answer by Johnnemann · Apr 28, 2013 at 06:55 AM
In order to use a yield
statement, you have to be in a function that returns type IEnumerator
. So you could do:
IEnumerator DisableBongoMic()
{
mic = 0;
yield return new WaitForSeconds(5.0f);
mic = 1;
}
Your answer
Follow this Question
Related Questions
[WORKAROUND] How to time pause in update (yield) 1 Answer
Invoke repeating OR coroutine with WaitForSeconds? 1 Answer
Is there a yield WaitForSeconds type code for the update? 2 Answers
Update/FixedUpdate motion stutter (Note: This is NOT a novice deltaTime question) 16 Answers
Question about Unity documentation GameObject.Find 2 Answers