Ray2D Behavior

I’ve been messing around drawing lines in circles and checking if they collide with things and ran into a problem, i feel like i’m missing something, I can draw lines just fine with line renderer, but when make a ray, the further from the global origin i set the ray origin the more it appears to be rotating around the origin. the red lines are rays and the white lines are rendered lines:

using System.Collections.Generic;
using UnityEngine;

public class raycheck : MonoBehaviour
{


    private Vector2 _origin;
    private Vector2 _circumfrance;
    public float radius = 8;
    public int lines = 360;
    private int linenumber;
    private float _degrees;

    public Material spriteMaterial;

    private List<GameObject> listOfLines;

    public Color outerColor;
    public Color innerColor;

    // Use this for initialization
    void Start()
    {
        _origin = transform.position;
        _degrees = 360 / (float)lines;
        linenumber = 1;
        listOfLines = new List<GameObject>();
        CreateCircle();
    }

    // Update is called once per frame
    void Update()
    {
        if (!Vector2.Equals(_origin, transform.position))
        {
            DestroyCircle();
            //transform.position = (Vector2)Camera.main.ScreenToWorldPoint(Input.mousePosition);
            _origin = transform.position;
            CreateCircle();
        }

    }
    void CreateCircle()
    {
        for (int i = 0; i < lines; i++)
        {
            DrawLine(transform.position, radius, innerColor, outerColor);
        }
    }
    void DestroyCircle()
    {
        foreach(GameObject line in listOfLines)
        {
            Destroy(line);
        }
        listOfLines.Clear();
        linenumber = 1;
    }

    void DrawLine(Vector2 startingPoint, float vertexRadius, Color startColor, Color endColor)
    {
        GameObject obj = new GameObject();
        obj.name = "Line " + linenumber;
        listOfLines.Add(obj);
        LineRenderer line = obj.AddComponent<LineRenderer>();
        line.material = spriteMaterial;
        line.enabled = true;
        line.sortingLayerName = "UI";
        line.sortingOrder = 0;
        line.positionCount = 2;
        line.SetPosition(0, startingPoint);
        //float sidelength = 2 * vertexRadius * Mathf.Sin((180 / (float)lines) * Mathf.Deg2Rad);
        //float apothem = sidelength / (2 * Mathf.Tan((180 / (float)lines) * Mathf.Deg2Rad));//interchangable
        //float apothem = vertexRadius * Mathf.Cos((180 / (float)lines) * Mathf.Deg2Rad); // interchangable
        float t_x = startingPoint.x + vertexRadius * Mathf.Sin((_degrees * (linenumber - 1) * Mathf.Deg2Rad));
        float t_y = startingPoint.y + vertexRadius * Mathf.Cos((_degrees * (linenumber - 1) * Mathf.Deg2Rad));
        Vector2 midpoint = new Vector2(t_x, t_y);
        RaycastHit2D hit = Physics2D.Raycast(startingPoint, midpoint);
        Debug.DrawRay(startingPoint, midpoint,Color.red);
        if (hit)
        {
            midpoint = hit.point;
        }
        //else
        //{
        //    Ray2D ray = new Ray2D((Vector3)startingPoint, (Vector3)midpoint);
        //    midpoint = ray.GetPoint(radius);
        //}
        line.SetPosition(1, midpoint);
        line.startWidth = .05f;
        line.endWidth = .05f;
        line.useWorldSpace = true;
        line.startColor = startColor;
        line.endColor = endColor;
        linenumber++;
    }
}

edit
Switched to line casting and it works as expected, odd, hopefully i’ll find out whay that is eventually.

Did you look at the documentation for Physics2D.Raycast ? I only ask because you seem to be passing a point in space as the second argument whereas the docs show that it’s a relative direction. This would explain why Physics2D.Linecast works as it takes a start and end point.

1 Like

Ah, that makes sense, I was thinking the direction was a point in the world space. So in order to make raycast work I’d need to just make a circle around 0,0. Thanks for clarifying.

Behind there scenes, there’s only a Linecast (line segment) implemented anyway. The Raycast is just a convenience allowing you to specify a direction/distance. Even if you leave the distance at infinity, it cannot do an infinite cast so does so using a relatively large distance.

Sort of but still, the second argument is supposed to be a unit normal and not a position in space. It works because we normalize the direction you send and presumably you’re using an infinite distance. This also means it’ll be slower because projecting to infinite (large distance) means that the potential set it produces can be quite large even if the actual results you get back are few. You are always better off using a Linecast if you know the start/end points or at least using the Distance arg in Raycast to limit the number of potentials it’ll encounter.

Hope that helps.

1 Like