I'm trying to record what I'm looking at based o camera movement, it's working fine if I play this on UnityEditor, but when I run the app on Oculus quest 2 I can't see the debug printing out the name of the object that it's hitting.
It works on Unity but not on Oculus.
private BaseEvent RecordRayCastHits()
{
Ray ray = cameraToRecord.ViewportPointToRay(centerOfScreen);
RaycastHit hit;
if (Physics.Raycast(ray, out hit, 50F, 1, QueryTriggerInteraction.Ignore))
{
Debug.Log(hit.transform.gameObject.name);
return new BaseEvent(eventName, hit.point);
}
return null;
}
Related
so, basically, I have created a pretty simple turret script that basically just smoothly aims at the player, so long as the player is within a certain amount of range. The problem I am having, is that the Raycast I wrote that actually checks if the 'bullet' (which is nothing - it's just a raycast), would hit the target. This means that even if the player hides behind a wall, the turret can still shoot him.
My current raycast script allows the raycast to go straight through the wall, and since I am new to Unity, I have no idea how to make it check if the first object it hits is the player, so that it cannot go through walls.
Here is my current raycast script:
void Shoot()
{
//I think the problem is here - I want the raycast to return false if it hits a wall - which has the layer "ground", and true if it hits the player. Problem is, I need to make the turret return to resting position when the player is behind a wall.
//To do this, I can just set inRange = true; But I need to be able to determine when the player is behind a wall.
LayerMask layerMask = LayerMask.GetMask("Player");
if (Physics.Raycast(transform.position, transform.TransformDirection(Vector3.forward), out RaycastHit hit, Mathf.Infinity, layerMask))
{
//This determines how much damage will the player take.
int damage = Random.Range(1, 5);
hit.collider.gameObject.GetComponent<playerMovement>().Shot(damage);
//I personally THINK this means that it only triggers collisions with the player, which is why it is not working.
// The player has layer "Player", and tag "Player", so if anyone who wants to help can figure out how to make it stop when it hits anything - and then only return true if it hit the player (meaning the player is not behind walls).
}
}
If you want to check if there is anything between the player and the Raycast, then simply remove the Layermask
Change this:
LayerMask layerMask = LayerMask.GetMask("Player");
if (Physics.Raycast(transform.position, transform.TransformDirection(Vector3.forward), out RaycastHit hit, Mathf.Infinity, layerMask))
To this:
Ray ray = new Ray(transform.position, transform.TransformDirection(Vector3.forward));
if (Physics.Raycast(ray, out RaycastHit hit) {..}
You want to
remove the check for the layer in order to hit everything with the raycast
then you can use TryGetComponent to check whether the hit object has such component attached or not
and in general instead of
transform.TransformDirection(Vector3.forward)
simply use transform.forward ;)
So something like
void Shoot()
{
if (Physics.Raycast(transform.position, transform.forward, out var hit))
{
// Without the need for any tag or layer check
// Simply check if the object you hit has a playerMovement component
// GetComponent was improved a lot lately and now uses hashes
// it's not that performance intense anymore and almost as fast as CompareTag
if(hit.gameObject.TryGetComponent<playerMovement>(out var movement)
{
int damage = Random.Range(1, 5);
movement.Shot(damage);
}
}
}
All you'd need to do is cast from the turret to the player and detect what the raycast has hit. Your current code is setting a mask to only be on the player, so it will never hit a wall. You can change your code to something like this:
private LayerMask layerMask = (1 << LayerMask.NameToLayer("Player") | (1 << LayerMask.NameToLayer("ground")));
void Update () {
if (Physics.Raycast(transform.position, transform.TransformDirection(Vector3.forward), out RaycastHit hit, Mathf.Infinity, layerMask))
{
if(hit.collider.gameObject.layer == LayerMask.NameToLayer("Player"))
{
// you can shoot as you see the player
}
else
{
// you hit the ground - player is behind a wall
}
}
}
I'm making a multiplayer FPS with Unity 2018 and I'm trying to detect if grounded using a raycast to see whether the player can jump or not.
I've written a function which should work based on multiple guides, but it returns seemingly random values whether the player is actually grounded or not.
My function:
bool IsGrounded()
{
RaycastHit hit;
if (Physics.Raycast(transform.position, -transform.up, out hit, 1f))
{
Debug.Log("Hit");
return true;
}
else
{
Debug.Log("Miss");
return false;
}
}
#SgtOddball I had a similar issue. I believe 1f is hitting your Player.
Add a layermask to exclude your player, make 1f Mathf.Infinity for now since I believe it is too small, and use
Debug.DrawRay(transform.position, -transform.up * 1f, Color.RED)
to see just how long 1f really is. I don't believe it is.
There are many questions like this, but I didn't find a valid solution to my problem.
I would like to click an object behind a collider, this is my code:
void Update () {
RaycastHit hit;
Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
if (Physics.Raycast(ray, out hit))
{
Debug.Log(hit.transform.name);
}
}
I put this code inside the script attached to the first object but the debug log will never be called.
Any ideas?
If I understand your question right, you want to click on the yellow sphere (see image) and want the name of the white cube?
There are two possible ways to do that:
1. Ignore Raycast Layer
You could give the yellow sphere the unity standard layer "Ignore Raycast":
Then your code should work (I added the on left mouse click)
void Update()
{
if (Input.GetMouseButtonDown(0)) // Click on left mouse button
{
RaycastHit hit;
Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
if (Physics.Raycast(ray, out hit))
{
Debug.Log(hit.transform.name);
}
}
}
2. Use Layer Mask
See: Using Layers and Bitmask with Raycast in Unity
If that's not what you're looking for please give further information and a screen shot of your problem.
I have a Physics Raycaster attached to the Camera. The Pointer Click Event Trigger is working correctly. However I need to do it from the source code. These are my attempts:
private void SetOnPushButtonFireManager(){
cardboard.OnTrigger += () => {
Debug.Log("Button triggered!");
RaycastHit hit;
// if(Physics.Raycast(headGameObject.GetComponent<GvrHead>().Gaze, out hit, Mathf.Infinity)){
if(Physics.Raycast(cameraGameObject.transform.position, cameraGameObject.transform.forward, out hit, Mathf.Infinity)){
Debug.Log("Collision detected!");
}
};
}
"Button triggered!" is shown in the Console. Unfortunately "Collision detected!" is not. However the Pointer Click Event Trigger is working correctly (the component attached in the inspector). How can I know what is going on? Why isn't it working?
UPDATE: I have answered this answer here: http://answers.unity3d.com/answers/1200449/view.html
(stackoverflow does not allow me to delete this question)
Here's some code I've been using to fire a ray from the camera. I don't have Google Cardboard, this was setup for a camera and a mouse pointer.
// Fire ray from camera
float rayLength = 2f
Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
RaycastHit hit;
// If ray hits object within length
if (Physics.Raycast(ray, out hit, rayLength))
{
Debug.Log("Collision detected!:);
}
It didn't work for me either, in the end, I forgot to put the "GvrPointerPhysicsRaycaster" class in the camera. Inspector Image
Once added, it worked perfectly.
void Update()
{
RaycastHit hit;
if (Physics.Raycast(Camera.main.transform.position, Camera.main.transform.forward, out hit, Mathf.Infinity))
{
if (activeSelected == null)
{
if (hit.collider.tag == "Plane")
activeSelected = Instantiate(mainApp.mainModel.preafabSelect, hit.point, Quaternion.LookRotation(hit.normal));
} else
{
activeSelected.transform.position = hit.point;
activeSelected.transform.rotation = Quaternion.LookRotation(hit.normal);
}
}
}
probably is too easy but.....
This Script is working well, got it from Boris Media it shows a text when the character enter in the box collider, I do not use characters I am using a 3D model so the user has to touch the model, not walk through the game.
Thanks in advance.
#pragma strict
var note : GameObject;
function Start () {
note.SetActive (false);
}
function OnTriggerEnter () {
note.SetActive (true);
}
function OnTriggerExit () {
note.SetActive (false);
}
Here is an example in C# but it shouldn't be too hard to convert to JavaScript if you need to:
Vector2 touchPos = Input.GetTouch(0).position;
Ray ray = Camera.main.ScreenPointToRay(new Vector3(touchPos.x, touchPos.y, 0));
RaycastHit hit;
if (Physics.Raycast (ray, out hit)) {
// The user's touch has collided with something now we have to check what it collided with
// You can also use hit.point if you want to get the position of the touch in the world
if (hit.collider.tag == "GameObjectTag") {
Debug.Log("Hit " + hit.collider.name);
hit.collider.gameObject.setActive(true);
}
}