VS5 - Functions for Euclidean Geometry

Elvan Ceyhan

2023-12-18

First we load the pcds and plot2D packages:

library(pcds)
library(plot3D)

1 Auxiliary Functions for Two and Three Dimensional Euclidean Geometry

We provide the equations for the \(d-1\) dimensional hyper-planes and related geometric structures in \(d\)-dimensional Euclidean space for \(d=2,3\). That is, we provide the equations of the lines, planes, and intersection points, etc. in \(\mathbb R^2\) and \(\mathbb R^3\). Some of these functions are used in the construction of proximity regions and the related PCDs hence are auxiliary functions in the construction of PCDs (see Ceyhan (2005) and Ceyhan (2010) for more details).

1.1 Geometric Structures in 2D Euclidean Space

The equation of the line and other related quantities like slope and intercept and the plot of the line are provided by the function Line. This function is different from the line function in the standard stats package in R in the sense that Line(a,b,x) fits the line passing through points a and b and returns various quantities related to this line (see below) and x is the vector of \(x\)-coordinates of the points on the line Line(a,b,x) (i.e., want the compute the \(y\) coordinates of the points on the line Line(a,b,x) whose \(x\)-coordinates are given in the vector x while line(a,b) fits a straight line robustly whose \(x\)-coordinates are in vector a and \(y\)-coordinates are in vector b.

1.1.1 Equation of the Line Crossing two Distinct 2D Points

The function Line is an object of class Lines and has arguments a,b,x where

  • a,b, 2D points that determine the straight line (i.e., through which the straight line passes) and
  • x, a scalar or a vector of scalars representing the \(x\)-coordinates of the line.

Its call (with lnAB in the below script) just returns Coefficients of the line (for the form: y = slope * x + intercept). Its summary returns the defining points, selected \(x\) points (first row) and estimated \(y\) points (second row) that fall on the line (first 6 or fewer), the equation of the line, and the coefficients of the line (i.e., the slope and intercept). The plot function (or plot.Lines) returns the plot of the line together with the defining points.

A<-c(-1.22,-2.33); B<-c(2.55,3.75)

xr<-range(A,B);
xf<-(xr[2]-xr[1])*.1 #how far to go at the lower and upper ends in the x-coordinate
x<-seq(xr[1]-xf,xr[2]+xf,l=5)  #try also l=10, 20, or 100

lnAB<-Line(A,B,x)
lnAB
#> Call:
#> Line(a = A, b = B, x = x) 
#> 
#> Coefficients of the line (in the form: y = slope * x + intercept) 
#>  1.6127321 -0.3624668
summary(lnAB)
#> Call:
#> Line(a = A, b = B, x = x) 
#> 
#> Defining Points
#>    [,1]  [,2]
#> A -1.22 -2.33
#> B  2.55  3.75
#> 
#> Selected x points (first row) and estimated y points (second row)
#>   that fall on the Line (first 6 or fewer are printed at each row) 
#> -2.938 -1.114  0.710  2.534  4.358 
#> -5.1006737 -2.1590504  0.7825729  3.7241963  6.6658196 
#> 
#> Equation of the Line Passing through two Distinct Points A and B 
#> y=1.61273209549072x-0.362466843501326 
#> 
#> Coefficients (slope and intercept) of the line  
#>      slope  intercept 
#>  1.6127321 -0.3624668
plot(lnAB)
The line joining the points $A$ and $B$ in 2D space.

Figure 1.1: The line joining the points \(A\) and \(B\) in 2D space.

The difference of the function Line from the line function in the standard stats package in R is illustrated below.

line(A,B)  #this takes vector A as the x points and vector B as the y points and fits the line
#> 
#> Call:
#> line(A, B)
#> 
#> Coefficients:
#> [1]   1.231  -1.081

line(x,lnAB$y) #gives the same line as Line(A,B,x) above
#> 
#> Call:
#> line(x, lnAB$y)
#> 
#> Coefficients:
#> [1]  -0.3625   1.6127
c(lnAB$intercept,lnAB$slope)
#>  intercept      slope 
#> -0.3624668  1.6127321

The slope of the line joining two distinct 2D points a and b can be found by the slope function with arguments a,b which are as in the function Line.

slope(A,B)
#> [1] 1.612732

1.1.2 Equation of the Line Crossing a Point and Parallel to the Line Crossing two Distinct 2D Points

The equation of the line crossing a point p parallel to the line segment joining two distinct 2D points a and b is provided by the function paraline. Other related quantities like slope and intercept and the plot of the line are also provided. The function paraline is an object of class Lines which takes arguments p,a,b,x where

  • a,b,x are as in the function Line and
  • p is a 2D point at which the parallel line to line segment joining a and b crosses.

Its call, summary, and plot are also as in Line.

A<-c(1.1,1.2); B<-c(2.3,3.4); P<-c(.51,2.5)

pts<-rbind(A,B,P)
xr<-range(pts[,1])
xf<-(xr[2]-xr[1])*.25 #how far to go at the lower and upper ends in the x-coordinate
x<-seq(xr[1]-xf,xr[2]+xf,l=5)  #try also l=10, 20, or 100

plnAB<-paraline(P,A,B,x)
plnAB
#> Call:
#> paraline(p = P, a = A, b = B, x = x)
#> 
#> Coefficients of the line (in the form: y = slope * x + intercept) 
#>     slope intercept 
#>  1.833333  1.565000
summary(plnAB)
#> Call:
#> paraline(p = P, a = A, b = B, x = x)
#> 
#> Defining Points
#>   [,1] [,2]
#> A 1.10  1.2
#> B 2.30  3.4
#> P 0.51  2.5
#> 
#>  Selected x points (first row) and estimated y points (second row) that fall on the Line
#>       (first 6 or fewer are printed at each row) 
#> [1] 0.06250 0.73375 1.40500 2.07625 2.74750
#> [1] 1.679583 2.910208 4.140833 5.371458 6.602083
#> 
#> Equation of the Line Crossing Point P and Parallel to Line Segment [AB] 
#> [1] "y=1.83333333333333x+1.565"
#> 
#> Coefficients of the line (when the line is in the form: y = slope * x + intercept) 
#> intercept     slope 
#>  1.565000  1.833333
plot(plnAB)

1.1.3 Equation of the Line Crossing a Point and Perpendicular to the Line Crossing two Distinct 2D Points

The equation of the line crossing a point p perpendicular to the line segment joining two distinct 2D points a and b is provided by the function perpline. Other related quantities like slope and intercept and the plot of the line are also provided. The function perpline is an object of class Lines and has the same arguments as paraline. Its call, summary, and plot are as in Line. In the plot of the object, we use asp=1 so that the lines are depicted correctly, i.e., as perpendicular to each other.

A<-c(1.1,1.2); B<-c(2.3,3.4); P<-c(.51,2.5)

pts<-rbind(A,B,P)
xr<-range(pts[,1])
xf<-(xr[2]-xr[1])*.25 #how far to go at the lower and upper ends in the x-coordinate
x<-seq(xr[1]-xf,xr[2]+xf,l=5)  #try also l=10, 20, or 100

plnAB<-perpline(P,A,B,x)
plnAB
#> Call:
#> perpline(p = P, a = A, b = B, x = x)
#> 
#> Coefficients of the line (in the form: y = slope * x + intercept) 
#>      slope  intercept 
#> -0.5454545  2.7781818
summary(plnAB)
#> Call:
#> perpline(p = P, a = A, b = B, x = x)
#> 
#> Defining Points
#>   [,1] [,2]
#> A 1.10  1.2
#> B 2.30  3.4
#> P 0.51  2.5
#> 
#>  Selected x points (first row) and estimated y points (second row) that fall on the Line
#>       (first 6 or fewer are printed at each row) 
#> [1] 0.06250 0.73375 1.40500 2.07625 2.74750
#> [1] 2.744091 2.377955 2.011818 1.645682 1.279545
#> 
#> Equation of the Line Crossing Point P Perpendicular to Line Segment [AB] 
#> [1] "y=-0.545454545454545x+2.77818181818182"
#> 
#> Coefficients of the line (when the line is in the form: y = slope * x + intercept) 
#>  intercept      slope 
#>  2.7781818 -0.5454545
plot(plnAB,asp=1)

The point of intersection of two lines, where each line is defined by a pair of points, is provided by the function intersect2lines. The arguments of the functions are the four points p1,q1,p2,q2, where the first line is defined with the points p1,q1, and the second line is defined with the points p2,q2.

A<-c(-1.22,-2.33); B<-c(2.55,3.75); C<-c(0,6); D<-c(3,-2)
ip<-intersect2lines(A,B,C,D)
ip
#> [1] 1.486767 2.035289

The angles to draw arcs between two line segments can be computed with the function angle.str2end which takes arguments a,b,c,radian where

  • a,b,c three 2D points which represent the intersecting line segments \([ba]\) and \([bc]\).
  • radian, a logical argument (default=TRUE). If TRUE, the smaller angle or counter-clockwise angle between the line segments \([ba]\) and \([bc]\) is provided in radians, else it is provided in degrees.

This function returns the output

  • small.arc.angles, angles of \([ba]\) and \([bc]\) with the \(x\)-axis so that difference between them is the smaller angle between \([ba]\) and \([bc]\), and
  • ccw.arc.angles, angles of \([ba]\) and \([bc]\) with the \(x\)-axis so that difference between them is the counter-clockwise angle between \([ba]\) and \([bc]\)

The two pairs of angles in radians or degrees in the output of this function is used to draw arcs between two vectors or line segments for the plotrix::draw.arc function in the plotrix package. More specifically, these angles are used to draw AS proximity regions (for the circular parts, i.e., arc-slices inside the triangle), The angles are provided with respect to the \(x\)-axis in the coordinate system. The line segments are \([ba]\) and \([bc]\) for the arguments a,b,c of the function.

Below are the angles between line segments \(BA\) and \(BC\) first in radians and then in degrees.

A<-c(.3,.2); B<-c(.6,.3); C<-c(1,1)

angle.str2end(A,B,C)
#> $small.arc.angles
#> [1] 1.051650 3.463343
#> 
#> $ccw.arc.angles
#> [1] -2.819842  1.051650
angle.str2end(A,B,C,radian=FALSE)
#> $small.arc.angles
#> [1]  60.25512 198.43495
#> 
#> $ccw.arc.angles
#> [1] -161.56505   60.25512

We plot the line segments \(BA\) and \(BC\) and annotate the angles between them and also the angles between the line segments and the \(x\)-axis using the below code, type also ? angle.str2end for the code to generate this figure.

pts<-rbind(A,B,C)

Xp<-c(B[1]+max(abs(C[1]-B[1]),abs(A[1]-B[1])),0)

#plot of the line segments
ang.rad<-angle.str2end(A,B,C,radian=TRUE); ang.rad
ang.deg<-angle.str2end(A,B,C,radian=FALSE); ang.deg
ang.deg1<-ang.deg$s; ang.deg1
ang.deg2<-ang.deg$c; ang.deg2

rad<-min(Dist(A,B),Dist(B,C))

Xlim<-range(pts[,1],Xp[1],B+Xp,B[1]+c(+rad,-rad))
Ylim<-range(pts[,2],B[2]+c(+rad,-rad))
xd<-Xlim[2]-Xlim[1]
yd<-Ylim[2]-Ylim[1]

#plot for the counter-clockwise arc
plot(pts,pch=1,asp=1,xlab="x",ylab="y",xlim=Xlim+xd*c(-.05,.05),ylim=Ylim+yd*c(-.05,.05))
L<-rbind(B,B,B); R<-rbind(A,C,B+Xp)
segments(L[,1], L[,2], R[,1], R[,2], lty=2)
plotrix::draw.arc(B[1],B[2],radius=.3*rad,angle1=ang.rad$c[1],angle2=ang.rad$c[2])
plotrix::draw.arc(B[1],B[2],radius=.6*rad,angle1=0, angle2=ang.rad$s[1],lty=2,col=2)
plotrix::draw.arc(B[1],B[2],radius=.9*rad,angle1=0,angle2=ang.rad$s[2],col=3)
txt<-pts
text(txt+cbind(rep(xd*.02,nrow(txt)),rep(-xd*.02,nrow(txt))),c("A","B","C"))

text(rbind(B)+.5*rad*c(cos(mean(ang.rad$c)),sin(mean(ang.rad$c))),
     paste(abs(round(ang.deg2[2]-ang.deg2[1],2))," degrees",sep=""))
text(rbind(B)+.6*rad*c(cos(ang.rad$s[1]/2),sin(ang.rad$s[1]/2)),paste(round(ang.deg1[1],2)),col=2)
text(rbind(B)+.9*rad*c(cos(ang.rad$s[2]/2),sin(ang.rad$s[2]/2)),paste(round(ang.deg1[2],2)),col=3)

The area of a polygon h in \(\mathbb R^2\) is provided by the function area.polygon with the sole argument h which is a vector of \(n\) 2D points, stacked row-wise, each row representing a vertex of the polygon, where \(n\) is the number of vertices of the polygon.. Here the vertices of the polygon h must be provided in clockwise or counter-clockwise order, otherwise the function does not yield the area. Also, the polygon could be convex or non-convex. See (Weisstein (2019)).

A<-c(0,0); B<-c(1,0); C<-c(0.5,.8);
Tr<-rbind(A,B,C);
area.polygon(Tr)
#> [1] 0.4

A<-c(0,0); B<-c(1,0); C<-c(.7,.6); D<-c(0.3,.8);
h1<-rbind(A,B,C,D);  #try also h1<-rbind(A,B,D,C) or h1<-rbind(A,C,B,D) or h1<-rbind(A,D,C,B);
area.polygon(h1)
#> [1] 0.49

1.3 Geometric Structures in 3D Euclidean Space

There are more possibilities for the geometric structures in \(\mathbb R^3\) compared to \(\mathbb R^2\). In \(\mathbb R^2\) only lines and their relationships exist, but in \(\mathbb R^3\), in addition to the lines and their relationships, there are also planes, and relationships between lines and planes, and planes and planes.

1.3.1 Equation of the Line Crossing a Point Parallel to (i.e., in the Direction of) a Vector

The equation of the line crossing a point in the direction of a vector in the 3D space are provided by the function Line3D. If the option dir.vec=TRUE (which is the default) in Line(p,v,t,dir.vec=T), the line crosses the point p in the direction of the vector v (i.e., parallel to the line joining the origin and v), otherwise, in Line(p,v,t,dir.vec=FALSE),the line crosses p and is in the direction of the vector joining p and v (i.e., in direction of \(v-r_0\)).

The function Line3D is an object of class Lines3D and takes arguments p,v,t,dir.vec where

  • p, a 3D point through which the straight line passes.
  • v, a 3D vector which determines the direction of the straight line (i.e., the straight line would be parallel to this vector) if the TRUE, otherwise it is 3D point and \(v-r_0\) determines the direction of the the straight line.
  • t, a scalar or a vector of scalars representing the parameter of the coordinates of the line (for the form: \(x=x_0 + A t\), \(y=y_0 + B t\), and \(z=z_0 + C t\) where \(r_0=(x_0,y_0,z_0)\) and \(v=(A,B,C)\) if TRUE, else \(v-r_0=(A,B,C)\)).
  • dir.vec, a logical argument about v, if TRUE v is treated as a vector, else v is treated as a point and so the direction vector is taken to be \(v-r_0\).

Its call (with lnPQ3D in the below script with the default option dir.vec=TRUE) just returns Coefficients of the parameterized line passing through initial point P =(x0,y0,z0) in the direction of OQ =(A,B,C) (for the form: x=x0 + A*t, y=y0 + B*t, and z=z0 + C*t). Its summary returns the defining vectors, namely, initial point as viewed as a vector joining the origin and the point and direction vector, estimated \(x\) points (first row), \(y\) points (second row), and \(z\) points (third row) (first 6 or fewer are printed at each row) , the equation of the line passing through point p in the direction of \(OQ\) with \(O\) representing the origin \((0,0,0)\) (i.e., parallel to \(OQ\) ), and the coefficients of the parameterized line passing through initial point \(P =(x_0,y_0,z_0)\) in the direction of \(OQ =(A,B,C)\) (for the form: \(x=x_0 + A\,t\), \(y=y_0 + B\,t\), and \(z=z_0 + C\,t\)). The plot function (or plot.Lines3D) returns the plot of the line together with the defining points and vectors.

P<-c(1,10,3); Q<-c(1,1,3);

vecs<-rbind(P,Q)

Line3D(P,Q,.1)
#> Call:
#> Line3D(p = P, v = Q, t = 0.1)
#> 
#> Coefficients of the parameterized line passing through initial point P = (x0,y0,z0) in the direction of OQ = (A,B,C) (for the form: x=x0 + A*t, y=y0 + B*t, and z=z0 + C*t) 
#>                  [,1] [,2] [,3]
#> initial point       1   10    3
#> direction vector    1    1    3
Line3D(P,Q,.1,dir.vec=FALSE)
#> Call:
#> Line3D(p = P, v = Q, t = 0.1, dir.vec = FALSE)
#> 
#> Coefficients of the parameterized line passing through initial point P = (x0,y0,z0) in the direction of PQ = (A,B,C) (for the form: x=x0 + A*t, y=y0 + B*t, and z=z0 + C*t) 
#>                  [,1] [,2] [,3]
#> initial point       1   10    3
#> direction vector    0   -9    0

tr<-range(vecs);
tf<-(tr[2]-tr[1])*.1 #how far to go at the lower and upper ends in the x-coordinate
tsq<-seq(-tf*10-tf,tf*10+tf,l=5)  #try also l=10, 20, or 100

lnPQ3D<-Line3D(P,Q,tsq)
lnPQ3D
#> Call:
#> Line3D(p = P, v = Q, t = tsq)
#> 
#> Coefficients of the parameterized line passing through initial point P = (x0,y0,z0) in the direction of OQ = (A,B,C) (for the form: x=x0 + A*t, y=y0 + B*t, and z=z0 + C*t) 
#>                  [,1] [,2] [,3]
#> initial point       1   10    3
#> direction vector    1    1    3
summary(lnPQ3D)
#> Call:
#> Line3D(p = P, v = Q, t = tsq)
#> 
#> Defining Vectors
#>                  [,1] [,2] [,3]
#> initial point       1   10    3
#> direction vector    1    1    3
#> 
#>  Estimated x points (first row), y points (second row), and z points (third row)
#>    that fall on the Line
#>       (first 6 or fewer are printed at each row) 
#> [1] -8.90 -3.95  1.00  5.95 10.90
#> [1]  0.10  5.05 10.00 14.95 19.90
#> [1] -26.70 -11.85   3.00  17.85  32.70
#> 
#> Equation of the line passing through point P in the direction of OQ  with O representing the origin (0,0,0)
#>                    (i.e., parallel to OQ ) 
#>      [,1]        
#> [1,] "x = 1 + t" 
#> [2,] "y = 10 + t"
#> [3,] "z = 3 + 3t"
#> 
#> Coefficients of the parameterized line passing through initial point P = (x0,y0,z0) in the direction of OQ = (A,B,C) (in the form: x = x0 + A*t, y = y0 + B*t, and z = z0 + C*t) 
#>    [,1] [,2] [,3]
#> P     1   10    3
#> OQ    1    1    3

plot(lnPQ3D)

1.3.2 Equation of the Line Crossing a Point and Parallel to the Line Crossing two Distinct 3D Points

The equation of the line in 3D space crossing a point p and parallel to line joining 3D points a and b is returned by the function paraline3D. Other related quantities and the plot of the line are also provided. The function paraline3D is an object of class Lines3D and takes arguments p,a,b,t where

  • p, a 3D point through which the straight line passes.
  • a,b, 3D points which determine the straight line to which the line passing through point p would be parallel (i.e., \(b-a\) determines the direction of the straight line passing through p).
  • t, a scalar or a vector of scalars representing the parameter of the coordinates of the line (for the form: \(x=x_0 + A t\), \(y=y_0 + B t\), and \(z=z_0 + C t\) where \(p=(x_0,y_0,z_0)\) and \(b-a=(A,B,C)\)).

Its call, summary, and plot are as in Line3D.

P<-c(1,10,4); Q<-c(1,1,3); R<-c(3,9,12)

vecs<-rbind(P,R-Q)
pts<-rbind(P,Q,R)
tr<-range(pts,vecs);
tf<-(tr[2]-tr[1])*.1 #how far to go at the lower and upper ends in the x-coordinate
tsq<-seq(-tf*10-tf,tf*10+tf,l=5)  #try also l=10, 20, or 100

pln3D<-paraline3D(P,Q,R,tsq)
pln3D
#> Call:
#> paraline3D(p = P, a = Q, b = R, t = tsq)
#> 
#> Coefficients of the parameterized line passing through initial point P = (x0,y0,z0) in the direction of R - Q = (A,B,C) (for the form: x=x0 + A*t, y=y0 + B*t, and z=z0 + C*t) 
#>                  [,1] [,2] [,3]
#> initial point       1   10    4
#> direction vector    2    8    9
summary(pln3D)
#> Call:
#> paraline3D(p = P, a = Q, b = R, t = tsq)
#> 
#> Defining Vectors
#>                  [,1] [,2] [,3]
#> initial point       1   10    4
#> direction vector    2    8    9
#> 
#>  Estimated x points (first row), y points (second row), and z points (third row)
#>    that fall on the Line
#>       (first 6 or fewer are printed at each row) 
#> [1] -23.2 -11.1   1.0  13.1  25.2
#> [1] -86.8 -38.4  10.0  58.4 106.8
#> [1] -104.90  -50.45    4.00   58.45  112.90
#> 
#> Equation of the line passing through point P parallel to the line joining points Q and R 
#>      [,1]         
#> [1,] "x = 1 + 2t" 
#> [2,] "y = 10 + 8t"
#> [3,] "z = 4 + 9t" 
#> 
#> Coefficients of the parameterized line passing through initial point P = (x0,y0,z0) in the direction of R - Q = (A,B,C) (in the form: x = x0 + A*t, y = y0 + B*t, and z = z0 + C*t) 
#>       [,1] [,2] [,3]
#> P        1   10    4
#> R - Q    2    8    9

plot(pln3D)

1.3.3 Equation of the Plane Crossing three Distinct 3D Points

The equation of the plane crossing three distinct points in \(\mathbb R^3\) is provided by the function Plane. Other related quantities and the plot of the plane are also provided. The function Plane is an object of class Planes and takes arguments a,b,c,x,y where

  • a,b,c are 3D points that determine the plane (i.e., through which the plane is passing) and
  • x,y are scalars or vectors of scalars representing the \(x\)- and \(y\)-coordinates of the plane.

Its call (with plP123 in the below script) just returns Coefficients of the Plane (in the form: z = A*x + B*y + C). Its summary returns the defining points, selected \(x\) and \(y\) points and estimated \(z\) points — presented row-wise, respectively — that fall on the plane (first 6 or fewer are printed on each row), the equation of the plane passing through points a, b, and c, and the coefficients of the plane (in the form \(z = A\,x + B\,y + C\)). The plot function (or plot.Planes) returns the plot of the plane together with the defining points.

P1<-c(1,10,3); P2<-c(1,1,3); P3<-c(3,9,12) #also try P2=c(2,2,3)

pts<-rbind(P1,P2,P3)
Plane(P1,P2,P3,.1,.2)
#> Call:
#> Plane(a = P1, b = P2, c = P3, x = 0.1, y = 0.2)
#> 
#> Coefficients of the Plane (in the form: z = A*x + B*y + C):
#>    A    B    C 
#>  4.5  0.0 -1.5

xr<-range(pts[,1]); yr<-range(pts[,2])
xf<-(xr[2]-xr[1])*.1 #how far to go at the lower and upper ends in the x-coordinate
yf<-(yr[2]-yr[1])*.1 #how far to go at the lower and upper ends in the y-coordinate
x<-seq(xr[1]-xf,xr[2]+xf,l=3)  #try also l=10, 20, or 100
y<-seq(yr[1]-yf,yr[2]+yf,l=3)  #try also l=10, 20, or 100

plP123<-Plane(P1,P2,P3,x,y)
plP123
#> Call:
#> Plane(a = P1, b = P2, c = P3, x = x, y = y)
#> 
#> Coefficients of the Plane (in the form: z = A*x + B*y + C):
#>    A    B    C 
#>  4.5  0.0 -1.5
summary(plP123)
#> Call:
#> Plane(a = P1, b = P2, c = P3, x = x, y = y)
#> 
#> Defining Points
#>    [,1] [,2] [,3]
#> P1    1   10    3
#> P2    1    1    3
#> P3    3    9   12
#> 
#>  Selected x and y points and estimated z points --- presented row-wise, respectively --- that fall on the Plane
#>       (first 6 or fewer are printed on each row) 
#> [1] 0.8 2.0 3.2
#> [1]  0.1  5.5 10.9
#> [1]  2.1  7.5 12.9
#> 
#> Equation of the Plane Passing through Points P1, P2, and P3 
#> [1] "z = 4.5x -1.5"
#> 
#> Coefficients of the Plane (in the form z = A*x + B*y + C):
#>    A    B    C 
#>  4.5  0.0 -1.5
plot(plP123,theta = 225, phi = 30, expand = 0.7, facets = FALSE, scale = TRUE)

1.3.4 Equation of the Plane Crossing a Point and Parallel to the Plane Crossing three Distinct 3D Points

The plane at a point p and parallel to the plane spanned by three distinct 3D points a, b, and c is provided by the function paraplane. Other related quantities and the plot of the plane are also provided. The function paraplane is an object of class Planes and takes arguments p,a,b,c,x,y where

  • p, a 3D point which the plane parallel to the plane spanned by three distinct 3D points a, b, and c crosses.
  • a,b,c, 3D points that determine the plane to which the plane crossing point p is parallel to.
  • x,y, Scalars or vectors of scalars representing the \(x\)- and \(y\)-coordinates of the plane parallel to the plane spanned by points a, b, and c and passing through point p.

Its call, summary, and plot are as in Plane.

Q<-c(1,10,3); R<-c(2,2,3); S<-c(3,9,12); P<-c(1,2,4)

pts<-rbind(Q,R,S,P)
xr<-range(pts[,1]); yr<-range(pts[,2])
xf<-(xr[2]-xr[1])*.25 #how far to go at the lower and upper ends in the x-coordinate
yf<-(yr[2]-yr[1])*.25 #how far to go at the lower and upper ends in the y-coordinate
x<-seq(xr[1]-xf,xr[2]+xf,l=5)  #try also l=10, 20, or 100
y<-seq(yr[1]-yf,yr[2]+yf,l=5)  #try also l=10, 20, or 100

plP2QRS<-paraplane(P,Q,R,S,x,y)
plP2QRS
#> Call:
#> paraplane(p = P, a = Q, b = R, c = S, x = x, y = y)
#> 
#> Coefficients of the Plane (in the form: z = A*x + B*y + C):
#>    A    B    C 
#>  4.8  0.6 -2.0
summary(plP2QRS)
#> Call:
#> paraplane(p = P, a = Q, b = R, c = S, x = x, y = y)
#> 
#> Defining Points
#>   [,1] [,2] [,3]
#> Q    1   10    3
#> R    2    2    3
#> S    3    9   12
#> P    1    2    4
#> 
#>  Selected x and y points and estimated z points --- presented row-wise, respectively --- that fall on the Plane
#>       (first 6 or fewer are printed on each row) 
#> [1] 0.50 1.25 2.00 2.75 3.50
#> [1]  0  3  6  9 12
#> [1]  0.4  4.0  7.6 11.2 14.8
#> 
#> Equation of the Plane Passing through Point P Parallel to the Plane 
#>  Passing through Points Q, R and S 
#> [1] "z = 4.8x + 0.6y -2"
#> 
#> Coefficients of the Plane (in the form z = A*x + B*y + C):
#>    A    B    C 
#>  4.8  0.6 -2.0

plot(plP2QRS,theta = 225, phi = 30, expand = 0.7, facets = FALSE, scale = TRUE)

1.3.5 Equation of the Line Crossing a Point and Perpendicular to the Plane Crossing three Distinct 3D Points

The line crossing the 3D point p and perpendicular to the plane spanned by the three points a, b, and c in \(\mathbb R^3\) is returned by the function perpline2plane. Other related quantities and the plot of the plane are also provided.

The function perpline2plane is an object of class Lines3D and takes arguments p,a,b,c,t where p,a,b,c are as in paraplane and t is as in paraline3D. Its call (with pln2pl in the below script) just returns Coefficients of the parameterized line passing through initial point P =(x0,y0,z0) in the direction of normal vector =(A,B,C) (for the form: x=x0 + A*t, y=y0 + B*t, and z=z0 + C*t). Its summary returns the defining vectors (i.e., the initial point viewed as a vector from the origin, and the normal vector), estimated \(x\) points (first row), \(y\) points (second row), and \(z\) points (third row) that fall on the Line (first 6 or fewer are printed at each row), the equation of the line crossing point \(p\) perpendicular to the plane spanned by points a, b, and c, and the coefficients of the parameterized line passing through initial point \(p =(x_0,y_0,z_0)\) in the direction of normal vector \((A,B,C)\) (in the form: \(x=x_0 + A\,t\), \(y=y_0 + B\,t\), and \(z=z_0 + C\,t\)). The plot function (or plot.Lines3D) returns the plot of the line together with the plane its perpendicular to.

P<-c(1,1,1); Q<-c(1,10,4); R<-c(1,1,3); S<-c(3,9,12)

cf<-as.numeric(Plane(Q,R,S,1,1)$coeff)
a<-cf[1]; b<-cf[2]; c<- -1;

vecs<-rbind(Q,c(a,b,c))
pts<-rbind(P,Q,R,S)
tr<-range(pts,vecs);
tf<-(tr[2]-tr[1])*.1 #how far to go at the lower and upper ends in the x-coordinate
tsq<-seq(-tf*10-tf,tf*10+tf,l=5)  #try also l=10, 20, or 100

pln2pl<-perpline2plane(P,Q,R,S,tsq)
pln2pl
#> Call:
#> perpline2plane(p = P, a = Q, b = R, c = S, t = tsq)
#> 
#> Coefficients of the parameterized line passing through initial point P = (x0,y0,z0) in the direction of normal vector = (A,B,C) (for the form: x=x0 + A*t, y=y0 + B*t, and z=z0 + C*t) 
#>                   [,1]      [,2] [,3]
#> initial point 1.000000 1.0000000    1
#> normal vector 4.055556 0.1111111   -1
summary(pln2pl)
#> Call:
#> perpline2plane(p = P, a = Q, b = R, c = S, t = tsq)
#> 
#> Defining Vectors
#>                   [,1]      [,2] [,3]
#> initial point 1.000000 1.0000000    1
#> normal vector 4.055556 0.1111111   -1
#> 
#>  Estimated x points (first row), y points (second row), and z points (third row)
#>    that fall on the Line
#>       (first 6 or fewer are printed at each row) 
#> [1] -56.99444 -27.99722   1.00000  29.99722  58.99444
#> [1] -0.5888889  0.2055556  1.0000000  1.7944444  2.5888889
#> [1]  15.30   8.15   1.00  -6.15 -13.30
#> 
#> Equation of the line crossing point P perpendicular to the plane spanned by points Q, Rand S 
#>      [,1]                        
#> [1,] "x = 1 + 4.05555555555555t" 
#> [2,] "y = 1 + 0.111111111111111t"
#> [3,] "z = 1-t"                   
#> 
#> Coefficients of the parameterized line passing through initial point P = (x0,y0,z0) in the direction of normal vector = (A,B,C) (in the form: x = x0 + A*t, y = y0 + B*t, and z = z0 + C*t) 
#>                   [,1]      [,2] [,3]
#> P             1.000000 1.0000000    1
#> normal vector 4.055556 0.1111111   -1

plot(pln2pl,theta = 225, phi = 30, expand = 0.7, facets = FALSE, scale = TRUE)

The point of intersection of a line and a plane is returned by the function intersect.line.plane with arguments p1,p2,p3,p4,p5, where line is defined by the points p1 and p2, while the plane is defined by the points p3, p4, and p5.

L1<-c(2,4,6); L2<-c(1,3,5);
A<-c(1,10,3); B<-c(1,1,3); C<-c(3,9,12)

Pint<-intersect.line.plane(L1,L2,A,B,C)
Pint
#> [1] 1.571429 3.571429 5.571429

The distance from a point p to a plane spanned by three points a, b, and c in \(\mathbb R^3\) is returned by the function dist.point2plane with arguments p,a,b,c which are same as in the function paraplane. The function also returns the point of orthogonal projection from point p to the plane.

P<-c(5,2,40)
P1<-c(1,2,3); P2<-c(3,9,12); P3<-c(1,1,3);

dis<-dist.point2plane(P,P1,P2,P3);
dis
#> $distance
#> [1] 4.121679
#> 
#> $prj.pt2plane
#> [1]  9.023529  2.000000 39.105882

References

Ceyhan, E. 2005. “An Investigation of Proximity Catch Digraphs in Delaunay Tessellations, Also Available as Technical Monograph Titled Proximity Catch Digraphs: Auxiliary Tools, Properties, and Applications.” PhD thesis, The Johns Hopkins University, Baltimore, MD, 21218.
———. 2010. “Extension of One-Dimensional Proximity Regions to Higher Dimensions.” Computational Geometry: Theory and Applications 43(9): 721–48.
Weisstein, E. W. 2019. “Polygon Area.” http://mathworld.wolfram.com/PolygonArea.html.