- Home /
Can't get this bool variable to switch on inside my OnCollisionEnter function
Hey guys,
I have the following C# script that detects collisions on a specific collider. In it, I have a bool variable called hitDetected01, which when true, signals another script to add the damage amount calculated in this script to the damage total in the other script. My problem is that the hitDetected bool is not showing as true when it is supposed to, and I am having considerable difficulty figuring out why.
Can anyone take a look and tell me what I'm doing incorrectly?
using UnityEngine;
using System.Collections;
public class cs_damageSec01 : MonoBehaviour
{
// hitDetected bool
public bool hitDetected01;
public float damSecAmount01;
void Start ()
{
// a collision is not detected by default
hitDetected01 = false;
}
// *** DETECT COLLISIONS WITH OTHER OBJECTS - CALCULATES COLLISION DAMAGE ***
void OnCollisionEnter(Collision collisionInfo)
{
// the following code ensures that only one collision detection occurs per call
if (hitDetected01)
return;
hitDetected01 = true;
// detects the collision
float rvX = collisionInfo.relativeVelocity.x;
float rvY = collisionInfo.relativeVelocity.y;
float rvZ = collisionInfo.relativeVelocity.z;
// calculates impact velocity
float velocityMod = Mathf.Abs(rvX) + Mathf.Abs(rvY) + Mathf.Abs(rvZ);
// calculates damage amount
damSecAmount01 = (Random.value * 5) * velocityMod;
Debug.Log("collision object 01 hit");
}
void Update ()
{
// hitDetected bool returns to its default state
hitDetected01 = false;
}
The other script it communicates with:
public class cs_playerShipDamage : MonoBehaviour {
// if a hit is detected
// record damage amount
// deduct from affected health bar
// calculate what systems are affected
// assign damage to those systems
public float damSecHealth_01 = 100f;
public float damSecHealth_02 = 100f;
public float damSecHealth_03 = 100f;
public GameObject damSecGO_01; // collider object 01
public GameObject damSecGO_02; // collider object 02
public GameObject damSecGO_03; // collider object 03
private cs_damageSec01 ref_cs_damageSec01; // collider script : collider script reference
private cs_damageSec02 ref_cs_damageSec02; // collider script : collider script reference
private cs_damageSec03 ref_cs_damageSec03; // collider script : collider script reference
public bool hitPositive_01 = false; // variable that determines if a collider is detecting a hit
public bool hitPositive_02 = false; // variable that determines if a collider is detecting a hit
public bool hitPositive_03 = false; // variable that determines if a collider is detecting a hit
void Start () {
ref_cs_damageSec01 = damSecGO_01.GetComponent<cs_damageSec01>();
ref_cs_damageSec02 = damSecGO_02.GetComponent<cs_damageSec02>();
ref_cs_damageSec03 = damSecGO_03.GetComponent<cs_damageSec03>();
hitPositive_01 = false;
hitPositive_02 = false;
hitPositive_03 = false;
}
// *** TALLIES UP DAMAGE AND HEALTH VALUES - DESTROYS SHIP IF OUT OF HEALTH ***
void Update () {
//
if (ref_cs_damageSec01.hitDetected01 == true)
{
hitPositive_01 = true;
Debug.Log("Section 01 Taking Damage.");
damSecHealth_01 += -ref_cs_damageSec01.damSecAmount01;
}
hitPositive_02 = false;
if (ref_cs_damageSec02.hitDetected02 == true)
{
hitPositive_02 = true;
Debug.Log("Section 02 Taking Damage.");
damSecHealth_02 += -ref_cs_damageSec02.damSecAmount02;
}
hitPositive_02 = false;
if (ref_cs_damageSec03.hitDetected03 == true)
{
hitPositive_03 = true;
Debug.Log("Section 03 Taking Damage.");
damSecHealth_03 += -ref_cs_damageSec03.damSecAmount03;
}
hitPositive_03 = false;
}
}
Answer by fafase · Jun 30, 2016 at 05:28 AM
You set it to false in Update so even though a collision is detected in Physics update, you set it back to false in that same frame.
You may have some scripts that actually see it as true if Unity ordered them so they would happen first.
My solution would be to reset it in LateUpdate so all scripts using the variable in Update have run.
Best solution is to actually propagate the info via event and listener.
Thanks. That worked perfectly. However, I didn't understand what you meant in the last sentence:"Best solution is to actually propagate the info via event and listener."
Ins$$anonymous$$d of setting a variable and having other classes checking in update if it is true, you would use an event/listener system where all the classes that need to know about that class state would register to an event and when the collision is called, that event is triggered and tells all listener about it.
Too long and irrelevant to explain in details here, so you should look into an event/listener tutorial, quite a few on the internet.
Thanks. I'm definitely going to look into that.
Your answer
![](https://koobas.hobune.stream/wayback/20220612083945im_/https://answers.unity.com/themes/thub/images/avi.jpg)
Follow this Question
Related Questions
Raycast passes Collider 0 Answers
detecting collision of collided object 2d 1 Answer
Weird Collision Detection with a Cube and OnCollisionEnter 2 Answers
How to make a cube (go to a certain position) after colliding with a plane? 1 Answer
[2D] Getting particles to collide with a game object(Explosion debris effect) 0 Answers