给定x和z的3D平面的y坐标

时间:2019-10-16 00:20:49

标签: python arrays numpy scipy interpolation

我生成了一个3D圆形平面,该平面已沿x轴旋转了45度:

enter image description here

在给定x和z坐标的情况下,我想确定平面的y坐标,但是我不知道该怎么做。如何对平面进行插值,以便在将x坐标和z坐标馈入平面时获得y坐标?

这是我的代码:

def coord_rotation(theta):
    # Convert to radians
    theta_1_rad = theta[0] * np.pi/180.0
    theta_2_rad = theta[1] * np.pi/180.0
    theta_3_rad = theta[2] * np.pi/180.0
    # The bicone and dust angles correspond to Euler angles which are 
    # (e1,e2,e3) -> (rotation about z, rotation about x, rotation about z again)
    theta_1,theta_2,theta_3 = theta_1_rad,theta_2_rad,theta_3_rad
    R_x = np.array([[1,         0,                  0                   ],
                    [0,         np.cos(theta_1),   np.sin(theta_1)   ],
                    [0,         -np.sin(theta_1),  np.cos(theta_1)    ]
                    ])
    R_y = np.array([[np.cos(theta_2),    0,        -np.sin(theta_2)    ],
                    [0,                   1,        0                    ],
                    [np.sin(theta_2),    0,         np.cos(theta_2)    ]
                    ])
    R_z = np.array([[np.cos(theta_3),       np.sin(theta_3),        0],
                    [-np.sin(theta_3),      np.cos(theta_3),       0],
                    [0,                      0,                      1]
                    ])             
    R = np.dot(R_z, np.dot( R_y, R_x ))
    return R

theta_D1_deg  = -45.0)
theta_D3_deg  = 0.0  
D = 2
sampling = 25
########################################################################################
phi       = 2*np.pi # rotation 
phi    = np.linspace(0,phi,sampling)
r      = np.linspace(-D,D,sampling)

ri,pi = np.ix_(r,phi) # get open grids            
X = ri*np.cos(pi)
Y = ri*np.sin(pi)
Z = np.zeros(np.shape(X))
# Rotate the dust plane in 3d
t = np.transpose(np.array([X,Y,Z]), (1,2,0))
R = coord_rotation((theta_D1_deg,0,theta_D3_deg))
xd,yd,zd = np.transpose(np.dot(t, R), (2,0,1))

# Make uniform grid
points = (xd.ravel(),yd.ravel())
values = zd.ravel()
xdgrid,ydgrid = np.meshgrid(np.linspace(-2,2,1000),np.linspace(-2,2,1000))
zdgrid = griddata(points, values, (xdgrid, ydgrid), method='linear')

# Plot
fig = plt.figure(figsize=(6,6))
ax1 = fig.add_subplot(1,1,1, projection='3d')
ax1.view_init(elev=15, azim=35)
ax1.plot_wireframe(xdgrid,ydgrid,zdgrid,alpha=0.25,color='xkcd:orange',zorder=3)

fontsize = 12
# x-axis
ax1.set_xlim(-2,2)
ax1.set_xlabel(r'$x$',fontsize=fontsize)
xAxisLine = ((np.min(xd), np.max(xd)), (0, 0), (0,0))
ax1.plot(xAxisLine[0], xAxisLine[1], xAxisLine[2], color='black',zorder=1,alpha=0.5)
# y-axis
ax1.set_ylim(-2,2)
ax1.set_ylabel(r'$y$',fontsize=fontsize)
yAxisLine = ((0, 0), (np.min(yd), np.max(yd)), (0,0))
ax1.plot(yAxisLine[0], yAxisLine[1], yAxisLine[2], color='black',zorder=1,alpha=0.5)
# z-axis
ax1.set_zlim(-2,2)
ax1.set_zlabel(r'$z$',fontsize=fontsize)
zAxisLine = ((0, 0), (0,0), (np.min(xd), np.max(xd)))
ax1.plot(zAxisLine[0], zAxisLine[1], zAxisLine[2], color='black',zorder=1,alpha=0.5)
plt.tight_layout()

2 个答案:

答案 0 :(得分:1)

这是简单明了的3D解析几何。首先,请注意没有“圆平面”之类的东西;您已经描述了一个圆及其内部,根据定义,它们被嵌入到特定平面中。

该平面的方程为y + z = 0x是不受约束的变量,但用于定义圆的边界的除外。

因此,您的问题可以简化为

y = -z

答案 1 :(得分:0)

首先,生成旋转磁盘投影到x-z平面上的椭圆:

https://math.stackexchange.com/questions/2388747/formula-for-ellipse-formed-from-projecting-a-tilted-circle-onto-the-xy-plane

在这种情况下,这有点容易,因为磁盘倾斜了45度。椭圆的长轴仅是原始圆盘的直径,而短轴与直径的关系是diameter**2 = 2 * (minor**2)

一旦有了椭圆的长轴和短轴,就可以使用以下公式确定测试点的x,z分量是否位于该椭圆内并不难:

https://math.stackexchange.com/questions/76457/check-if-a-point-is-within-an-ellipse

如果测试点位于磁盘内,则磁盘上的y分量如以上答案所述(仅对于45度倾斜,但这只是一个直角三角形):y = -z 现在,您已经找到了x-y-z空间中位于旋转磁盘上的点,因此只需从测试点的y值中减去y值即可确定沿y轴到磁盘的距离。