這應該很容易,但我一直試圖找到一個簡單的解釋,我可以把握。我有一個對象,我想在OpenGL中表示爲一個圓錐體。該物體具有x,y,z座標和速度矢量vx,vy和vz。錐應指向速度矢量的方向。OpenGL從速度矢量旋轉
所以,我覺得我的PyOpenGL代碼應該是這個樣子:
glPushMatrix()
glTranslate(x, y, z)
glPushMatrix()
# do some sort of rotation here #
glutSolidCone(base, height, slices, stacks)
glPopMatrix()
glPopMatrix()
那麼,是正確的(迄今爲止)?我用什麼來代替「#在這裏做某種旋轉#」?
在我的世界裏,Z軸指向(0,0,1),沒有任何旋轉,我的錐體也是如此。
好吧,雷託Koradi的答案似乎是,我應該採取的辦法,但我不知道的一些實施細則和我的代碼是行不通的。
如果我理解正確,旋轉矩陣應該是4x4。 Reto向我展示瞭如何獲得3x3,所以我假定3x3應該是4x4單位矩陣的左上角。這裏是我的代碼:
import numpy as np
def normalize(v):
norm = np.linalg.norm(v)
if norm > 1.0e-8: # arbitrarily small
return v/norm
else:
return v
def transform(v):
bz = normalize(v)
if (abs(v[2]) < abs(v[0])) and (abs(v[2]) < abs(v[1])):
by = normalize(np.array([v[1], -v[0], 0]))
else:
by = normalize(np.array([v[2], 0, -v[0]]))
#~ by = normalize(np.array([0, v[2], -v[1]]))
bx = np.cross(by, bz)
R = np.array([[bx[0], by[0], bz[0], 0],
[bx[1], by[1], bz[1], 0],
[bx[2], by[2], bz[2], 0],
[0, 0, 0, 1]], dtype=np.float32)
return R
,這裏是它被插入渲染代碼的方式:
glPushMatrix()
glTranslate(x, y, z)
glPushMatrix()
v = np.array([vx, vy, vz])
glMultMatrixf(transform(v))
glutSolidCone(base, height, slices, stacks)
glPopMatrix()
glPopMatrix()
不幸的是,這是行不通的。我的測試案例錐體只是沒有正確指出,我無法識別失敗模式。如果沒有「glutMultMatrixf(變換(V)」行,錐沿z軸對齊,符合市場預期。
它的工作。雷託Koradi正確地確定了需要旋轉矩陣,以便匹配移調。的OpenGL列順序的代碼應該是這樣的(優化前):
def transform(v):
bz = normalize(v)
if (abs(v[2]) < abs(v[0])) and (abs(v[2]) < abs(v[1])):
by = normalize(np.array([v[1], -v[0], 0]))
else:
by = normalize(np.array([v[2], 0, -v[0]]))
#~ by = normalize(np.array([0, v[2], -v[1]]))
bx = np.cross(by, bz)
R = np.array([[bx[0], by[0], bz[0], 0],
[bx[1], by[1], bz[1], 0],
[bx[2], by[2], bz[2], 0],
[0, 0, 0, 1]], dtype=np.float32)
return R.T
不旋轉矩陣需要一個4x4矩陣(我假設我應該使用glMultMatrixf呼叫)?速度矢量爲[0,0,0]時的情況如何?我需要特殊情況下的那種情況嗎? – user2483736
是的,如果您使用的是固定管道,則必須將其擴展到4x4。如果您使用着色器(在Core Profile中需要),則可以將3x3矩陣傳遞到着色器中。 –
您在上面添加的代碼看起來很合理。根據OpenGL綁定處理矩陣的方式,您可能需要按轉置順序編寫元素。至少在本地接口中,OpenGL期望矩陣按列主要順序傳入。爲了調試,我將從非常簡單的案例開始,並查看結果矩陣中的值。例如。用一個指向'z'方向的矢量,你應該能夠通過查看矩陣來判斷它是否正確。 –