Containment
Containment

Reputation: 249

How can I reflect a point about a line in Unity?

I am drawing a line using the line renderer in the following way:

  public class MyLineRenderer : MonoBehaviour {
    LineRenderer lineRenderer;

    public Vector3 p0, p1;

    // Use this for initialization
    void Start () {
      lineRenderer = gameObject.GetComponent<LineRenderer>();
      lineRenderer.positionCount = 2;

      lineRenderer.SetPosition(0, p0);
      lineRenderer.SetPosition(1, p1);

    }
 }

From the image below, the line P0P1 is known and so is point A. How can a point B, which is the reflection of A about the line P0P1 be found?

enter image description here

Upvotes: 0

Views: 1618

Answers (2)

rutter
rutter

Reputation: 11452

You can achieve this using Vector3.Reflect.

  • Take the vector from a to p0 and call that your inDirection
  • Take the vector from p0 to p1 and call that your inNormal
  • Plug these values in: Vector3.Reflect(p0 - a, p1 - p0)

The above call gives you a vector from p0 to b, so you can find b as follows:

Vector3 b = p0 + Vector3.Reflect(p0 - a, p1 - p0);

To explain what's happening here, we're imagining that inNormal is the normal vector of a plane, then reflecting a vector against that plane. If all you care about is reflecting across a line, you could actually set that plane anywhere along the line and get the same result.

Vector3 reflection diagram

If you're working in 2D, there is a similar Vector2.Reflect function. This works for any number of dimensions as long as you have an appropriate vector class.

Upvotes: 2

sadrag
sadrag

Reputation: 575

For XZ coordinates, try this code;

public class Symmetry: MonoBehaviour
{
    public Transform p0;
    public Transform p1;
    public Transform pointA;
    public Transform pointB;

    float m, x1, z1, x2, z2, x3, z3, u, v;

    float targetPosX, targetPosZ;

    void Start()
    {

    }

    void Update()
    {
      CalculateSymmetry();
    }

    private void CalculateSymmetry()
    {
      x1 = p0.position.x;
      z1 = p0.position.z;
      x2 = p1.position.x;
      z2 = p1.position.z;
      x3 = pointA.position.x;
      z3 = pointA.position.z;

      m = ((x3 - x1) * (x2 - x1) + (z3 - z1) * (z2 - z1)) / ((x2 - x1) * (x2 - x1) + (z2 - z1) * (z2 - z1));

      u = x1 + m * (x2 - x1);
      v = z1 + m * (z2 - z1);

      targetPosX = 2 * u - x3;
      targetPosZ = 2 * v - z3;

      pointB.gameObject.transform.position = new Vector3(targetPosX, pointB.position.y, targetPosZ);
    }
}

Explanation;
pointA: A point in your pic.
pointB: Symmetry of A point (B in your pic)
p0: Line Start
p1: Line End

ps. I am using game objects. You can change it for yourself.

Upvotes: 0

Related Questions