【问题标题】:Positioning objects parallel with a mesh将对象与网格平行定位
【发布时间】:2021-08-27 21:53:36
【问题描述】:

我正在尝试根据网格中三角形的方向沿人体圆周对齐多个线对象。我想把线平行于网格。我正确地分配了沿圆周的线条的位置,但我还需要添加线条的旋转,使其与身体平行。 身体是由多个三角形组成的网格,每条线都与一个三角形“链接”。

我只有:

  • 每条线距离网格最近的三角形 3 个点

  • 三角形的法线

  • 实例化线的位置(2 点,起点和终点)

我需要计算直线的每个 X、Y、Z 轴的角度,以使三角形的法线与线网格垂直。我不知道如何获得所需的角度。如果有人愿意帮助我,我真的很感激。

输入:

FVector TrianglePoints[3];

FVector Triangle_Normal; //计算为(B-A)^(C-A),其中A,B,C是三角形的点

FVector linePosition; //如果有帮助,我也有起始线和结束线位置

输出

//FRotator rotation(x,y,z),使得三角形法线与直线对象垂直。

圆周线构造概述。现在使用每条线的开始位置和结束位置计算旋转。当我们穿过网格的一些不规则部分时,我们想要正确地旋转线条。现在旋转是固定的,仅取决于行的开始和结束位置。

【问题讨论】:

    标签: math 3d geometry unreal-engine4 normals


    【解决方案1】:

    如果我正确理解了你的目标,这里有一些相关的矢量几何:

    A,B,C are the vertices of the triangle:
    A = [xA, yA, zA],
    B = [xB, yB, zB]
    C = [xC, yC, zC]
    
    K,L are the endpoints of the line-segment:
    K = [xK, yK, zK]
    L = [xL, yL, zL]
    
    vectors are interpreted as row-vectors
    by . I denote matrix multiplication
    by x I denote cross product of 3D vectors
    by t() I denote the transpose of a matrix
    by | | I denote the norm (magnitude) of a vector
    
    Goal: find the rotation matrix and rotation transformation of segment KL 
          around its midpoint, so that after rotation KL is parallel to the plane ABC
          also, the rotation is the "minimal" angle rotation by witch we need to 
          rotate KL in order to make it parallel to ABC
    
    AB = B - A
    AC = C - A
    KL = L - K
    
    n = AB x AC
    n = n / |n|
    
    u = KL x n
    u = u / |u|
    
    v = n x u
    
    cos = ( KL . t(v) ) / |KL|
    sin = ( KL . t(n) ) / |KL|   
    
    U = [[ u[0],  u[1],  u[2] ],
         [ v[0],  v[1],  v[2] ],
         [ n[0],  n[1],  n[2] ],
    
    R = [[1,    0,    0],
         [0,  cos,  sin],
         [0, -sin,  cos]]
    
    ROT = t(U).R.U
    
    then, one can rotate the segment KL around its midpoint 
    M = (K + L)/2
    
    Y = M + ROT (X - M)
    

    这是一个python脚本版本

    A = np.array([0,0,0])
    B = np.array([3,0,0])
    C = np.array([2,3,0])
    
    K = np.array([ -1,0,1])
    L = np.array([  2,2,2])
    KL = L-K
    
    U = np.empty((3,3), dtype=float)
    
    U[2,:] = np.cross(B-A, C-A)
    U[2,:] = U[2,:] / np.linalg.norm(U[2,:])
    
    U[0,:] = np.cross(KL, U[2,:])
    U[0,:] = U[0,:] / np.linalg.norm(U[0,:])
    
    U[1,:] = np.cross(U[2,:], U[0,:])
    
    norm_KL = np.linalg.norm(KL)
    cos_ = KL.dot(U[1,:]) / norm_KL 
    sin_ = KL.dot(U[2,:]) / norm_KL 
    
    R = np.array([[1,    0,    0],
                  [0, cos_, sin_],
                  [0,-sin_, cos_]])
    
    ROT = (U.T).dot(R.dot(U))
    
    M = (K+L) / 2
    
    K_rot = M + ROT.dot( K - M )
    L_rot = M + ROT.dot( L - M )
    
    print(L_rot)
    print(K_rot)
    print(L_rot-K_rot)
    print((L_rot-K_rot).dot(U[2,:]))
    

    【讨论】:

    • 感谢您的回答。现在我改变了实例化线条的过程。现在我使用程序网格并使用三角形来创建网格。该实现使我免于计算每条线的旋转角度的补充工作。我看了你的回答,我认为它可能适合我的需要。再次感谢您的支持!
    • @BogdanGalatanu 很高兴您解决了您的问题。有时解决方案需要不同的方法。祝你好运和欢呼!
    【解决方案2】:

    一个更有启发性的解决方案是使用在运行时生成的程序网格,它具有我需要的所有要求:

    • 沿多个顶点连续
    • 易于应用 UV 贴图进行纹理平铺
    • 可以在运行时更新
    • 计算/使用它并不难

    【讨论】:

    • 这没有提供问题的答案。要批评或要求作者澄清,请在他们的帖子下方留下评论。 - From Review
    猜你喜欢
    • 1970-01-01
    • 2022-06-12
    • 1970-01-01
    • 1970-01-01
    • 2021-02-11
    • 1970-01-01
    • 2019-10-08
    • 2021-05-03
    • 1970-01-01
    相关资源
    最近更新 更多