- Home /
Clock script not working
Hello Everyone, I am trying to make a simple clock but the script is not working. But each time the game is played, all three hands turn to 180*. Any help?
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Clock : MonoBehaviour {
public float Hours, Minutes, Seconds;
public GameObject hourHand, minuteHand, secondHand;
void increment()
{
Seconds++;
}
private void Start()
{
InvokeRepeating("increment", 0f, 1.0f);
}
void Update()
{
if (Seconds == 60)
{
Seconds = 0;
Minutes++;
}
if (Minutes == 60)
{
Minutes = 0;
Hours++;
}
if (Hours == 13) Hours = 0;
hourHand.transform.localRotation = new Quaternion(0f, 0f, (float)Hours * 6.0f, 0f);
minuteHand.transform.localRotation = new Quaternion(0f, 0f, (float)Minutes * 6, 0f);
secondHand.transform.localRotation = new Quaternion(0f, 0f, (float)Seconds * 6, 0f);
}
}
Answer by Xarbrough · May 10, 2018 at 11:45 AM
Try this:
using UnityEngine;
public class Clock : MonoBehaviour
{
public GameObject hourHand, minuteHand, secondHand;
public int hours, minutes, seconds;
float timer;
void Update()
{
if (timer >= 1f)
{
updateClock();
updateVisuals();
timer = 0f;
}
timer += Time.deltaTime;
}
void updateClock()
{
seconds++;
if (seconds >= 60)
{
seconds = 0;
minutes++;
}
if (minutes >= 60)
{
minutes = 0;
hours++;
}
if (hours >= 13)
{
hours = 0;
}
}
void updateVisuals()
{
hourHand.transform.localRotation = Quaternion.Euler(0f, 0f, -hours * (360f / 12f));
minuteHand.transform.localRotation = Quaternion.Euler(0f, 0f, -minutes * (360f / 60f));
secondHand.transform.localRotation = Quaternion.Euler(0f, 0f, -seconds * (360f / 60f));
}
}
I wouldn't use InvokeRepeating because of the string reference to a method, instead just track time with Time.deltaTime. Next, it is not the best idea to compare float values to discrete integers. In this case it was probably working because the values are set discretely in code, but in a lot of other cases you may run into floating point precision issues, where a comparison would fail.
Now the important aspect of updating the visuals: You were setting the values of a Quaternion directly, which is something you wouldn't normally do (maybe in very special cases and if you understand Quaternions well). In short, the z-value of the Quaternion does not correspond to the z-value, which you see in the Rotation field of the inspector. Unity shows Euler angles to the user, but expects a quaternion when setting the localRotation property. In this case, we simply want to do our math in euler degrees (360 degrees around the clock) and let Unity convert the value to a Quaternion via the Quaternion.Euler function.
Finally, the math for converting to "hour hand degrees" was not correct. We divide 360 degrees of a circle by 12 hour clock pieces and 60 minute/second pieces.
Here's a unity project showing the setup of the visual clock hands.
I hope this helps! Have fun!