projecting points onto a plane given by a normal and a point

hadi k

I am using the following function to try to project bunch of vertices onto a plane. Basically mapping a polyhedron to polygon. My plane is defined by a normal vector and a point (called centroid here).

import numpy as np
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
from numpy import linalg as la
#######################################################################################################
#this part is for drawing the vector arrow
#copy pasted
#http://stackoverflow.com/questions/22867620/putting-arrowheads-on-vectors-in-matplotlibs-3d-plot
#######################################################################################################
from matplotlib.patches import FancyArrowPatch
from mpl_toolkits.mplot3d import proj3d
from mpl_toolkits.mplot3d.art3d import Poly3DCollection
import matplotlib.cm as cm#for color selection
import itertools
class Arrow3D(FancyArrowPatch):
    def __init__(self, xs, ys, zs, *args, **kwargs):
        FancyArrowPatch.__init__(self, (0,0), (0,0), *args, **kwargs)
        self._verts3d = xs, ys, zs

    def draw(self, renderer):
        xs3d, ys3d, zs3d = self._verts3d
        xs, ys, zs = proj3d.proj_transform(xs3d, ys3d, zs3d, renderer.M)
        self.set_positions((xs[0],ys[0]),(xs[1],ys[1]))
        FancyArrowPatch.draw(self, renderer)
#######################################################################################################
#function to project onto the plane
#takes normal vector of the plane, the centroid of the plane and vertices to be projected as argument
#returns the position vector of the projected point on the plane
#######################################################################################################
def planeprojection(normalvector,centroid,vertices):
    shape = vertices.shape#shape of vertex array, can be one vertex or multiple vertices to project
    if len(shape)==1:#meaning there is only one vertex
        vertex = vertices
        #dot product of position vector to the vertex from plane and normal vector
        dotscalar = np.dot(np.subtract(vertex,centroid),normalvector)
        #now returning the position vector of the projection onto the plane
        return np.subtract(vertex,dotscalar*normalvector)
    else:
        #array to store projectedvectors
        projectedvectors = np.zeros((shape[0],shape[1]))
        #now projecting onto plane, one by one
        for counter in range(shape[0]):
            vertex = vertices[counter,:]
            print vertex
            dotscalar = np.dot(np.subtract(centroid,vertex),normalvector)
            print dotscalar
            #now returning the position vector of the projection onto the plane
            projectedvectors[counter,:] = np.subtract(vertex,dotscalar*normalvector)
        #now returning the vectors projected
        return projectedvectors
#######################################################################################################
###normalising function
#######################################################################################################
def normalise(v):
    norm=np.linalg.norm(v)
    if norm==0: 
       return v
    return v/norm
##############################################################################################################
##########points to project####################
##############################################################################################################
xcod = np.array([1,2,1,3,-1,1])
ycod = np.array([2,1,4.5,5.,6,2])
zcod = np.array([1,-2,0,2,3,1])
num = len(xcod)-1
#centroid of the cell
centroid = np.array([np.mean(xcod[0:num]),np.mean(ycod[0:num]),np.mean(zcod[0:num])])
#getting tuples of x,y,z
verts = [zip(xcod,ycod,zcod)]
#numpy array of vertices
vertices =np.array(verts[0])
#normal to the plane
averagenormal = np.array([ 0.91008281, -0.24978471,  0.3306915 ])
#Projecting the vertices now
projectedvertices = planeprojection(averagenormal,centroid,vertices)
#changing the format to tuple for plotting polyhedron surface
projectedverts = [map(tuple,projectedvertices)]
################################################################################
######plotting #################################################################
################################################################################
#also defining the plot in 3d for start plotting
fig = plt.figure()
ax = fig.add_subplot(111,projection = '3d')
#plotting all the points
ax.plot(xcod,ycod,zcod,'x-')
#plotting polyhedron surface
ax.add_collection3d(Poly3DCollection(projectedverts,alpha=0.5,color="k"))
#adding labels for vertice
for i in range(num):
    ax.text(xcod[i],ycod[i],zcod[i],'%d(%.2f,%.2f,%.2f)'%(i,xcod[i],ycod[i],zcod[i]))
#drawing vector arrow for averal normal vector
drawvec=Arrow3D([centroid[0],averagenormal[0]+centroid[0]],[centroid[1],averagenormal[1]+centroid[1]],[centroid[2],averagenormal[2]+centroid[2]],mutation_scale=8,lw=1,color='k')
ax.add_artist(drawvec)
#draw average vector from origin as originally found out
drawvec = Arrow3D([0,averagenormal[0]],[0,averagenormal[1]],[0,averagenormal[2]],mutation_scale=8,lw=1,color='g')
ax.add_artist(drawvec)
#plotting averagenormal vector point
ax.scatter(averagenormal[0],averagenormal[1],averagenormal[2],marker = 'o',color="g")
#plotting centroid 
ax.scatter(centroid[0],centroid[1],centroid[2],marker = 'o',color="g")
#plotting averagenormal vector point from centroid
ax.scatter(averagenormal[0]+centroid[0],averagenormal[1]+centroid[1],averagenormal[2]+centroid[2],marker = 'o',color="g")#plot show
ax.set_xlim([-1,5])
ax.set_ylim([-1,6])
ax.set_zlim([-5,6])
plt.show()

Here, in the figure below, black shaded part is supposed to be the plane. Something is not working right shouldnt this be the right way to go?
I am basically using following formula for projection, where Proj(P) is the projection onto plane, Centriod is the point on the plane and n is the normal vector.

Proj(P) = P-((P-Centroid).n)n  

enter image description here black shaded

EDIT

Changing the mistake suggested by Nico below, dotscalar = np.dot(np.subtract(vertex,centroid),normalvector) it works !

enter image description here

Nico Schertler

Your formula

Proj(P) = P-((P-Centroid).n)n  

is correct.

But your implementation

dotscalar = np.dot(np.subtract(centroid,vertex),normalvector)

is not. You swapped centroid and vertex. Thus, instead of moving the point onto the plane, your algorithm doubles its distance from the plane.

Collected from the Internet

Please contact [email protected] to delete if infringement.

edited at
0

Comments

0 comments
Login to comment

Related

From Dev

Projecting 3D Model onto 2d plane

From Dev

Projecting 3D points to 2D plane

From Dev

Projecting a point onto the intersection of n-dimensional spaces in Python

From Dev

Convert a plane from Point/Normal/D to plane equation

From Dev

Separation of plane by line given two points

From Dev

Perspective transform given point (x,y) in quadrilateral plane to Rectangle plane's point (x', y')?

From Dev

Perspective transform given point (x,y) in quadrilateral plane to Rectangle plane's point (x', y')?

From Dev

orientate a 3d plane from 3 given points

From Dev

Find K nearest Points to Point P in 2-dimensional plane

From Dev

Find K nearest Points to Point P in 2-dimensional plane

From Dev

Automapper query for projecting an anonymous type onto a viewmodel

From Dev

Projecting a line segment onto a polygon mesh

From Dev

How to order a list of points by distance to a given point?

From Dev

Ordering a list of points nearest to a given point

From Dev

Given n points on a 2D plane, find the maximum number of points that lie on the same straight line

From Dev

Given n points on a 2D plane, find the maximum number of points that lie on the same straight line

From Dev

Summing While Projecting a Dictionary Onto a Sub-Tuple Key

From Dev

Given a set of points in the plane, find a (not necessarily convex) polygon of minimal area containing them

From Dev

How to generate a set of random points within a given (x,y) coordinates in an x-y plane?

From Dev

Finding the point in 2d plane such that maximum distance from a set of points is minimum

From Dev

Prove that the farthest point among a set of points(in 2-d plane) should lie on the convex hull

From Dev

Getting closest point on a plane

From Dev

Getting closest point on a plane

From Dev

Maximize point in plane value

From Dev

Given 2 points, return a 3rd point between them that is closer to the first point given

From Dev

How to draw the normal to the plane in PCL

From Dev

Find which points are within a given distance of each point

From Dev

Drawing a circular, minor arc given the centre point and two other points

From Dev

Get N random equidistant points from a given point

Related Related

  1. 1

    Projecting 3D Model onto 2d plane

  2. 2

    Projecting 3D points to 2D plane

  3. 3

    Projecting a point onto the intersection of n-dimensional spaces in Python

  4. 4

    Convert a plane from Point/Normal/D to plane equation

  5. 5

    Separation of plane by line given two points

  6. 6

    Perspective transform given point (x,y) in quadrilateral plane to Rectangle plane's point (x', y')?

  7. 7

    Perspective transform given point (x,y) in quadrilateral plane to Rectangle plane's point (x', y')?

  8. 8

    orientate a 3d plane from 3 given points

  9. 9

    Find K nearest Points to Point P in 2-dimensional plane

  10. 10

    Find K nearest Points to Point P in 2-dimensional plane

  11. 11

    Automapper query for projecting an anonymous type onto a viewmodel

  12. 12

    Projecting a line segment onto a polygon mesh

  13. 13

    How to order a list of points by distance to a given point?

  14. 14

    Ordering a list of points nearest to a given point

  15. 15

    Given n points on a 2D plane, find the maximum number of points that lie on the same straight line

  16. 16

    Given n points on a 2D plane, find the maximum number of points that lie on the same straight line

  17. 17

    Summing While Projecting a Dictionary Onto a Sub-Tuple Key

  18. 18

    Given a set of points in the plane, find a (not necessarily convex) polygon of minimal area containing them

  19. 19

    How to generate a set of random points within a given (x,y) coordinates in an x-y plane?

  20. 20

    Finding the point in 2d plane such that maximum distance from a set of points is minimum

  21. 21

    Prove that the farthest point among a set of points(in 2-d plane) should lie on the convex hull

  22. 22

    Getting closest point on a plane

  23. 23

    Getting closest point on a plane

  24. 24

    Maximize point in plane value

  25. 25

    Given 2 points, return a 3rd point between them that is closer to the first point given

  26. 26

    How to draw the normal to the plane in PCL

  27. 27

    Find which points are within a given distance of each point

  28. 28

    Drawing a circular, minor arc given the centre point and two other points

  29. 29

    Get N random equidistant points from a given point

HotTag

Archive