Table of Contents
Projecting a Point onto a Plane
This is done in a series of small steps;
- Defining an Arbitrary point on the plane
- Creating a Vector from the point to be Projected to the Arbitrary point
- Define the Dot product of the two vectors
- Translate the point to be Projected along the Planes Vector
A plane passing through the Point (P) = 1 ; 3 ; 2 and has Normal Vector (N) = 6 ; 7 ; 5, then the equation of the plane is;
Point (P) = 1 \space; \space 3 \space ; \space 2 \\ \overrightarrow{N} = 6 \space ; \space 7 \space ; \space 5 \\ Plane \space Equation = 6(x−1 \normalsize)+7(y−3 \normalsize)+5(z−2 \normalsize)=0 \\ = 6x - 6 + 7y-21+5z-10 = 0 \\ = 6x + 7y + 5z -6 -21 -10 = 0 \\ = 6x + 7y + 5z -37 = 0 \\
Defining the Arbitrary Point on the Plane
So now we have the plane equation that we want to work with. Lets start of with an easy one, a Point(B) 12 ; 23 ; 34 projected onto the plane, our first step is to create an arbitrary point on the plane, to do this well use Point(A) 5 ; 5 ; Z
Point (A) = 5 \space; \space 5 \space ; \space Z \\ Plane Equation = 6x + 7y + 5z - 37 = 0 \\ = ( 6 * 5 ) + ( 7 * 5 ) + ( 5 * Z ) - 37 = 0 \\ = 30 + 35 + 5Z - 37 = 0 \\ = 5Z = - 30 - 35 + 37 \\ = 5Z = -28 \\ = Z = -28/5\\ = Z = -5.6
We have now fully resolved Point(A) 5 ; 5 ; -5.6, if we cant resolve for Z, then we should retry resolving for Y or X to define the arbitrary point on the surface.
Defining the Arbitrary Unit Vector
The next step is to create an additional vector from the arbitrary Point(A) 5 ; 5 ; -5.6 to the projection Point(B) 12 ; 23 ; 34
\overrightarrow{BA} \\ = Ax - Bx ; Ay - By ; Az - Bz \\ = 5 - 12 ; 5 - 23 ; -5.6 - 34 \\ \overrightarrow{BA}= -7 ; -18 ; -39.6 \\ I = -7 ; J = -18 ; K = -39.6
Dot Product of the Projection
First Step the magnitude of the planes vector.
||{N}|| = \sqrt{I^2 + J^2 + K^2} \\ = \sqrt{6^2 + 7^2 + 5^2} \\ = \sqrt{36 + 49 + 25} \\ = \sqrt{110} \\ = 10.488 \\
Next we can convert the planes vector into a unit vector.
\widehat{N} = \overrightarrow{N} / ||{N}|| \\ = (6/10.488) ; (7/10.488) ; (5/10.488)\\ = 0.572 ; 0.667 ; 0.476 \\
Ok so far so good. Now for the Dot Product of the Projection.
||BP|| = \overrightarrow{BA} \cdotp \widehat{N} \\ = (BA\tiny{X}\cdotp \normalsize N\tiny{X} \normalsize)+(BA\tiny{Y}\cdotp \normalsize N\tiny{Y} \normalsize)+(BA\tiny{Z}\cdotp \normalsize N\tiny{Z} \normalsize)\\ = ( -7 * 0.5721 ) + ( -18 * 0.6674 ) + ( -39.6 * 0.4767 ) \\ = -4.0047 + (-12.0132) + (-18.5913) \\ = -34.897
Translating the vector
Last steps
\overrightarrow{BP} = ||BP||\cdotp(\widehat{N}/||N||)\\ = (-34.897 * 0.5721) ; (-34.897 * 0.667) ; (-34.897 * 0.476) \\ = -19.964 ; -23.291 ; -16.636
Finally well add the projection point to the vector(BP)
Point(C) = \overrightarrow{BP} + Point(B)\\ = (12 + (-19.964)) ; (23 +(-23.291)) ; (34+(-16.636))\\ =-7.9636 ; -0.2909 ; 17.364
C# Code
Using the following C# Code this can be demonstrated.
We can see in the Point Class the Projection Code.
Wireframe Class
namespace BasicGeometry { public interface IWireframe { } public class Wireframe:IWireframe { } }
Point Class
namespace BasicGeometry { public interface IPoint { double X { get; set; } double Y { get; set; } double Z { get; set; } } public class Point : Wireframe,IPoint { public double X { get; set; } = 0; public double Y { get; set; } = 0; public double Z { get; set; } = 0; public Point() { } public Point(double x, double y, double z) { X = x; Y = y; Z = z; } public Point(IPoint point, IPlane plane) { //5,5,Z is Arbitary but we Must Calculate Z double i = plane.UnitVector.I * -5; double j = plane.UnitVector.J * -5; double Z = (i + j + plane.D)/plane.UnitVector.K; Point pointOnPlane = new Point(5,5,Z); //Define a New Vector Back to the Poitn Being Projected Vector vector = new Vector(point, pointOnPlane); //Dot Projection of the Vector, get the distance from the point to the plane double dist = ((Math.Abs((plane.A * vector.I) + (plane.B * vector.J) + (plane.C * vector.K)))/plane.Vector.Length); //Move Original Point by Length and Distance IPoint projectionPoint = TranslatePointAlongVector(point, plane.UnitVector, dist*-1); this.X= projectionPoint.X; this.Y= projectionPoint.Y; this.Z= projectionPoint.Z; } private IPoint TranslatePointAlongVector(IPoint point, IUnitVector vector, double offset) { IPoint returnPoint = new Point(); returnPoint.X = (vector.I * offset) + point.X; returnPoint.Y = (vector.J * offset) + point.Y; returnPoint.Z = (vector.K * offset) + point.Z; return returnPoint; } } }
Line Class
namespace BasicGeometry { public interface ILine { Point SPt { get; set; } Point EPt { get; set; } double Length { get; } } public class Line : Wireframe, ILine { public Point SPt { get; set; } = new Point(0,0,0); public Point EPt { get; set; } = new Point(0,0,1); public double Length { get{ return Math.Sqrt( Math.Pow((EPt.X - SPt.X),2) + Math.Pow((EPt.Y - SPt.Y),2) + Math.Pow((EPt.Z - SPt.Z),2) ); } } } }
Vector Class
namespace BasicGeometry { public interface IVector { double I { get; set; } double J { get; set; } double K { get; set; } double Length { get;} UnitVector UnitVector { get;} } public class Vector : Wireframe, IVector { public double I { get; set; } = 0; public double J { get; set; } = 0; public double K { get; set; } = 1; public double Length { get { return Math.Sqrt( Math.Pow(I, 2) + Math.Pow(J, 2) + Math.Pow(K, 2) ); } } public UnitVector UnitVector { get { return new UnitVector(this); } } public Vector() { } public Vector(double i, double j, double k) { I = i; J = j; K = k; } public Vector(IPoint SPt, IPoint EPt) { I = EPt.X-SPt.X; J = EPt.Y-SPt.Y; K = EPt.Z-SPt.Z; } } }
Unit Vector Class
namespace BasicGeometry { public interface IUnitVector { double I { get; } double J { get; } double K { get;} double Length { get; } } public class UnitVector : Wireframe, IUnitVector { public double I { get; } = 0; public double J { get; } = 0; public double K { get; } = 1; public double Length { get { return Math.Sqrt( Math.Pow(I, 2) + Math.Pow(J, 2) + Math.Pow(K, 2) ); } } public UnitVector() { } public UnitVector(IVector vector) { I = vector.I/vector.Length; J = vector.J/vector.Length; K = vector.K/vector.Length; } } }
Plane Class
namespace BasicGeometry { public interface IPlane { double A { get; set; } double B { get; set; } double C { get; set; } double D { get; set; } UnitVector UnitVector { get; } Vector Vector { get;} } public class Plane : Wireframe, IPlane { public double A { get; set; } = 0; public double B { get; set; } = 0; public double C { get; set; } = 1; public double D { get; set; } = 0; public UnitVector UnitVector { get { return new UnitVector(new Vector(A, B, C)); } } public Vector Vector { get { return new Vector(A, B, C); } } public Plane() {} public Plane(double a, double b, double c, double d) { A = a; B = b; C = c; D = d; } public Plane(Vector vector,Point point) { A = vector.I; B = vector.J; C = vector.K; D = ((point.X * UnitVector.I) + (point.Y * UnitVector.J) + (point.Z * UnitVector.K)); } public Plane(Vector vector1,Vector vector2,Point point) { Vector vector3 = VectorCrossProduct(vector1, vector2); A = vector3.I; B = vector3.J; C = vector3.K; D = ((point.X * UnitVector.I) + (point.Y * UnitVector.J) + (point.Z * UnitVector.K)); } public Plane(Point point1, Point point2, Point point3) { Vector vector1 = new Vector(point1, point2); Vector vector2 = new Vector(point1, point3); Vector vector3 = VectorCrossProduct(vector1, vector2); A = vector3.I; B = vector3.J; C = vector3.K; D = ((point1.X* UnitVector.I) + (point1.Y * UnitVector.J) + (point1.Z * UnitVector.K)); } private Vector VectorCrossProduct(Vector vector1, Vector vector2) { double i = (vector1.J * vector2.K) - (vector2.J * vector1.K); double j = -((vector1.I * vector2.K) - (vector2.I * vector1.K)); double k = (vector1.I * vector2.J) - (vector2.I * vector1.J); return new Vector(i, j, k); } private double distance(Point point) { return Math.Sqrt( Math.Pow((point.X), 2) + Math.Pow((point.Y), 2) + Math.Pow((point.Z), 2) ); } } }