1
\$\begingroup\$

noob here

So I am using two push buttons (connected to an Arduino Uno) as an input to my game. The player has to push down both buttons at the same time for the character to move in the game. I want the player to hold down the buttons for a different amount of time in each level. I have a working Arduino and a working Unity timer and player script, but am not able to get the code to do what I want. What I basically want is that only when the player presses the buttons down, does the timer start counting down. Right now, the timer starts as soon as the scene begins. I know that I somehow have to reference the timer script to the button object, I have tried this but it still doesn't work. Note that the timer UI does have a Timer tag on it. I have also referenced the Player Controller script in the Timer script. Right now, the timer just doesn't count down at all. Please help Please assist in any manner

The Timer script:

   using UnityEngine;
using System.Collections;
using UnityEngine.UI;
using UnityEngine.SceneManagement;

public class Timer : MonoBehaviour
{
    //int startTime = 0;
    public bool buttonPressed = false;
    public int timeLeft;
    public Text countdownText;
    GameObject Character;
    void Awake()
    {
        Character = GameObject.FindWithTag("Player");
    }

    // Use this for initialization
    public void Start()
    {
        //StartCoroutine("LoseTime");
        BeginTimer();

    }

    // Update is called once per frame
    void Update()
    {
        countdownText.text = ("Time Left = " + timeLeft);

        if (timeLeft <= 0)
        {
            //StopCoroutine("LoseTime");
            //countdownText.text = "Times Up!";
            Invoke("ChangeLevel", 0.1f);
        }
       }
    public void BeginTimer()
    {

        Character.GetComponent<PlayerController>().Update();
        if (buttonPressed == true )
        {
            StartCoroutine("LoseTime");
        }
    }

IEnumerator LoseTime()
    {
        while (true)
        {
            yield return new WaitForSeconds(1);
            timeLeft--;
        }

    }
    void ChangeLevel()
    {

        SceneManager.LoadScene(SceneManager.GetActiveScene().buildIndex + 1);
    }
}

The Player controller script:

    using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using System.IO.Ports;

public class PlayerController : MonoBehaviour
{
    SerialPort sp = new SerialPort("\\\\.\\COM4", 9600);
    //player == GameObject.FindWithTag("Player").GetComponent<>();

    public float Speed;
    public Vector2 height;
    public float xMin, xMax, yMin, yMax;
    public bool buttonPressed = false;
    GameObject Character;

    void Awake()
    {
        Character = GameObject.FindWithTag("Player");
    }
    void Start()
    {
        if (!sp.IsOpen)
        { // If the erial port is not open 
            sp.Open(); // Open 
        }
        sp.ReadTimeout = 1; // Timeout for reading
    }

    public void Update()
    {

        if (sp.IsOpen)
        { // Check to see if the serial port is open 
            try
            {

                string value = sp.ReadLine();//To("Button"); //Read the information
                int button = int.Parse(value);
                //float amount = float.Parse(value);
                //transform.Translate(Speed * Time.deltaTime, 0f, 0f);  //walk


                if (button == 0) //*Input.GetKeyDown(KeyCode.Space*/)  //jump
                {
                    buttonPressed = true;

                    Character.GetComponent<Rigidbody2D>().AddForce(height, ForceMode2D.Impulse);

                    Character.GetComponent<Rigidbody2D>().position = new Vector3
                    (
                        Mathf.Clamp(GetComponent<Rigidbody2D>().position.x, xMin, xMax),
                        Mathf.Clamp(GetComponent<Rigidbody2D>().position.y, yMin, yMax)
                    );
                    Timer tmr = GameObject.Find("Timer").GetComponent<Timer>();
                        tmr.BeginTimer();


                }
            }
            catch (System.Exception)
            {


            }
        }
        void ApplicationQuit()
        {
            if (sp != null)
            {

                {
                    sp.Close();
                }
            }
        }
    }
}

Any tips and assistance will be appreciated

\$\endgroup\$
  • \$\begingroup\$ You said that you have a working timer script and working arduino, so what specifically is the issue you are encountering? What is desired behavior vs current behavior? Are you getting any error messages? \$\endgroup\$ – disc_code22 Nov 6 at 14:05
  • \$\begingroup\$ @disc_code22 So right now as soon as the scene starts, the timer begins counting down. So even if the player doesn't press the push buttons, the timer will start and once it reaches 0 will change to the next scene. So what I want is that only when the player presses the buttons, will the timer start and let's say the time for that level is 50 seconds, then the player has to hold the buttons down for 50 seconds for the character to move. So that's the issue that I am currently having \$\endgroup\$ – user19964 Nov 6 at 14:40
  • \$\begingroup\$ @disc_22 And then if the player releases the button before the time is over, the timer will reset and the player will have to start again with the original time \$\endgroup\$ – user19964 Nov 6 at 14:43
  • \$\begingroup\$ Right now the timer doesn't know anything about the ports or inputs and is just decrementing unconditionally. If you want the timer behavior controlled by the port inputs you need to implement that somewhere, either in the timer class, or in the player class, then communicate that to the timer. Eg: the "LoseTime" coroutine could check a boolean flag to see if the button is being held and only decrement the time if true. By toggling the flag based on the port inputs you can have the timer run only if certain inputs are held. Using a similar approach you can reset the timer value on input change \$\endgroup\$ – disc_code22 Nov 6 at 15:51
  • \$\begingroup\$ @disc_22 Thank you. I thought as much...that I would to reference the port input to the timer somehow. This is what I am struggling with: I don't really know how to do that. Think you could help me with that? \$\endgroup\$ – user19964 Nov 6 at 18:41

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.