(2D) Collectible Objects using Raycasts
Hello fellow Unity users. :)
I've completed the excellent series of tutorials here (https://www.youtube.com/playlist?list=PLFt_AvWsXl0f0hqURlhyIoAabKPgRsqjz) and I'd like to add 'collectible' items to my prototype game.
This tutorial series develops a 2D platformer, whereby all collisions are worked out using raycasting (as opposed to rigid bodies / colliders). It works fine, but I'm not sure how to proceed so as when my player (a simple quad, currently) collides with another quad (tagged as 'Pickup') the other object is destroyed.
I tried this via the usual method of adding rigid bodies / box colliders and checking onTriggerEnter2D (after setting the relevant setting of 'Is Trigger?' to yes. But the event doesn't ever appear to fire.
(Code Below: Controller2D)
using UnityEngine;
using System.Collections;
[RequireComponent (typeof (BoxCollider2D))]
public class Controller2D : MonoBehaviour {
public LayerMask collisionMask;
const float skinwidth = .015f;
public int horizontalRayCount = 4;
public int verticalRayCount = 4;
float horizontalRaySpacing;
float verticalRaySpacing;
BoxCollider2D coll;
RaycastOrigins raycastOrigins;
void Start () {
coll = GetComponent<BoxCollider2D>();
calculateRaySpacing();
}
public void Move(Vector3 velocity){
UpdateRaycastOrigins();
if (velocity.x != 0){
HorizontalCollisions(ref velocity);
}
if (velocity.y !=0){
VerticalCollisions(ref velocity);
}
transform.Translate(velocity);
}
void HorizontalCollisions(ref Vector3 velocity){
float directionX = Mathf.Sign (velocity.x);
float rayLength = Mathf.Abs(velocity.x) + skinwidth;
for (int i = 0; i < horizontalRayCount; i++) {
Vector2 rayOrigin = (directionX == -1)?raycastOrigins.bottomLeft:raycastOrigins.bottomRight;
rayOrigin += Vector2.up * (horizontalRaySpacing * i);
RaycastHit2D hit = Physics2D.Raycast(rayOrigin,Vector2.right * directionX,rayLength,collisionMask);
Debug.DrawRay(rayOrigin, Vector2.right * directionX * rayLength,Color.red);
if (hit) {
velocity.x = (hit.distance - skinwidth) * directionX;
rayLength = hit.distance;
}
}
}
void VerticalCollisions(ref Vector3 velocity){
float directionY = Mathf.Sign (velocity.y);
float rayLength = Mathf.Abs(velocity.y) + skinwidth;
for (int i = 0; i < verticalRayCount; i++) {
Vector2 rayOrigin = (directionY == -1)?raycastOrigins.bottomLeft:raycastOrigins.topLeft;
rayOrigin += Vector2.right * (verticalRaySpacing * i + velocity.x);
RaycastHit2D hit = Physics2D.Raycast(rayOrigin,Vector2.up * directionY,rayLength,collisionMask);
Debug.DrawRay(rayOrigin, Vector2.up * directionY * rayLength,Color.red);
if (hit) {
velocity.y = (hit.distance - skinwidth) * directionY;
rayLength = hit.distance;
}
}
}
void UpdateRaycastOrigins(){
Bounds bounds = coll.bounds;
bounds.Expand(skinwidth * -2);
raycastOrigins.bottomLeft = new Vector2(bounds.min.x,bounds.min.y);
raycastOrigins.bottomRight = new Vector2(bounds.max.x,bounds.min.y);
raycastOrigins.topLeft = new Vector2(bounds.min.x,bounds.max.y);
raycastOrigins.topRight = new Vector2(bounds.max.x,bounds.max.y);
}
void calculateRaySpacing(){
Bounds bounds = coll.bounds;
bounds.Expand(skinwidth * -2);
horizontalRayCount = Mathf.Clamp(horizontalRayCount,2,int.MaxValue);
verticalRayCount = Mathf.Clamp(verticalRayCount,2,int.MaxValue);
horizontalRaySpacing = bounds.size.y / (horizontalRayCount - 1);
verticalRaySpacing = bounds.size.x / (verticalRayCount - 1);
}
struct RaycastOrigins {
public Vector2 topLeft,topRight;
public Vector2 bottomLeft,bottomRight;
}
}
(Code Below: Player)
using UnityEngine;
using System.Collections;
[RequireComponent (typeof (Controller2D))]
public class Player : MonoBehaviour {
float moveSpeed = 6;
float gravity = -20;
Vector3 velocity;
Controller2D controller;
void Start(){
controller = GetComponent<Controller2D>();
}
void Update(){
Vector2 input = new Vector2(Input.GetAxisRaw("Horizontal"),Input.GetAxisRaw("Vertical"));
velocity.x = input.x * moveSpeed;
velocity.y += gravity * Time.deltaTime;
controller.Move(velocity * Time.deltaTime);
}
}
Could anyone kindly point me in the right direction and advise as to what I would need to consider when trying to make my player collect an item?
My first request on here, so hopefully I've done everything within the guidelines. :)
Answer by MattusFinchus · Nov 19, 2015 at 10:00 AM
Sorry, just to clarify, the code posted above is taken straight from the tutorial and does not include my failed attempts at making the pickups work via OnTriggerEntry2D etc. :)
Your answer
Follow this Question
Related Questions
RayCast not working , why ??? 0 Answers
RayCast not working with MeshCollider - Unity's roller ball collision works 1 Answer
Raycast ignores objects with colliders 1 Answer
Raycasting Stopped Working all of a sudden 0 Answers
Raycast so i can pick up an object and add it to my inventory in javascript? 0 Answers