- Home /
Raycast should ignore all childs of its parent objects of
Heyhey, i got this raycast script:
using UnityEngine;
using System.Collections;
using RootMotion.Dynamics;
namespace RootMotion.Demos {
public class RaycastShooter : MonoBehaviour {
public LayerMask layers;
public float unpin = 10f;
public float force = 10f;
public ParticleSystem blood;
public Vector3 offset;
[SerializeField] private bool m_ShowDebugRay; // Optionally show the debug ray.
[SerializeField] private float m_DebugRayLength = 5f; // Debug ray length.
[SerializeField] private float m_DebugRayDuration = 1f; // How long the Debug ray will remain visible.
[SerializeField] private float m_RayLength = 500f; // How far into the scene the ray is cast.
// Update is called once per frame
void Update () {
if (m_ShowDebugRay)
{
Debug.DrawRay(transform.position + offset, transform.forward * m_DebugRayLength, Color.blue, m_DebugRayDuration);
Ray ray = new Ray (transform.position + offset , transform.forward);
// Raycast to find a ragdoll collider
RaycastHit hit = new RaycastHit();
if (Physics.Raycast(ray, out hit, 100f, layers)) {
Debug.DrawRay(transform.position, transform.forward * m_DebugRayLength, Color.red, m_DebugRayDuration);
}
}
if (Input.GetMouseButtonDown(0)) {
//Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
Ray ray = new Ray (transform.position, transform.forward);
// Raycast to find a ragdoll collider
RaycastHit hit = new RaycastHit();
if (Physics.Raycast(ray, out hit, 100f, layers)) {
var broadcaster = hit.collider.attachedRigidbody.GetComponent<MuscleCollisionBroadcaster>();
if (broadcaster != null) {
broadcaster.Hit(unpin, ray.direction * force, hit.point);
blood.transform.position = hit.point;
blood.transform.rotation = Quaternion.LookRotation(-ray.direction);
blood.Emit(5);
}
}
}
}
}
}
how can i ignore all children of the parent where the raycast script is in? the important parts of the script are after "if (Input.GetMouseButtonDown(0)) {"
so my character layer is layer 9 and the weapon where the ray got shot is inside this character object.
iam using a complicated ragdoll physics character controller. so that leads sometimes to the case, that the character shoot itself. so both, enemy and my character are on the layer 9. so how can i do it that the ray still hits everything on layer 9, but not the one where it is inside?
btw, the objects/weapon which shoots the ray can be droped. so it can be picked up by every character in the scene again after its dropped. so a fixed gameobject that should be ignored doesent work here.
Answer by nonathaj · Sep 30, 2016 at 10:18 PM
There is no built in function that sorts like this. However it is easy enough to manually sort through the output of a raycast.
RaycastHit closestValidHit = new RaycastHit();
RaycastHit[] hits = Physics.RaycastAll(ray, 100f, layers);
foreach(RaycastHit hit in hits)
{
if(hit.transform.IsChildOf(tranform) && (closestValidHit.collider == null || closestValidHit.distance > hit.distance))
{
closestValidHit = hit;
}
}
This is no less efficient than a standard Raycast, as Unity has to check all of those objects anyway. The function you are using simply ignores all other output.
This is over 5 years old and yet it's still relevant so thanks a LOT!
I had some major issues with the raycasts generated from screen-touch on a tile-like map selection system. One problem is related to how the physic engine skips the layers exclusion for childs of a parent within a targeted layer. Another was that the order taken from a raycast hit is not based on which one is hit first, but which one is computed first and the result seems random at best.
For the first problem, as each "tile" in the map has a specific script, I can just check if whatever is hit by the raycast has that specific script with a GetComponent(). For the lack of "order", your solution gave me the hint.
In my case, I'm building a Tower Defense mobile game and I needed to be able to select the "tiles" based on the volume of their content (each tiles has a box collision trigger box set specifically with a size based on its content such as buildings). For example, a map set in a city would requires that the play can select a building which might be between 1 and 4 floors high by selecting the building. As buildings are overlaying themselves a bit (from the camera perspective), I had to check which one is the "closest" to the camera. By checking if each hits has a certain script attached to it, I can cull out the childs from the hit list as only the tiles parent got a certain script (which includes some stats and info about the tile's content.)
Your answer
Follow this Question
Related Questions
Help Playing "Sound Clip" on RayCastHit? (RayCast help?) 2 Answers
RaycastHit.distance 1 Answer
How to register if my Raycast hits nothing(Solved) 2 Answers
Hit distance Change light range 1 Answer
How to hit two object with one raycast? 2 Answers