欧拉角万向节锁问题
這兩天一直糾結(jié)在歐拉角的萬向節(jié)鎖問題上,查了很多資料,可是依舊沒有完全弄懂這個(gè)問題,引用《3D數(shù)學(xué)基礎(chǔ):圖形與游戲開發(fā)》一書中的一句話,”如果您從來沒有遇到過萬向鎖情況,你可能會(huì)對(duì)此感到困惑,而且不幸的是,很難在本書中講清楚這個(gè)問題,你需要親身經(jīng)歷才能明白?!?#xff0c;認(rèn)為這個(gè)確實(shí)需要在以后的實(shí)踐過程中遇到這個(gè)問題時(shí),才會(huì)理解地更加透徹.
雖然沒有完全弄明白,但還是有一點(diǎn)總結(jié):
(1)萬向節(jié)鎖問題,和具體的旋轉(zhuǎn)順序相關(guān),例如最常用的ZXY順序,在X軸旋轉(zhuǎn)為+-90°時(shí),無論Z軸和Y軸的旋轉(zhuǎn)角度如何變化,物體將在某個(gè)維度上被鎖住這篇文章中第二部分手機(jī)旋轉(zhuǎn)的例子比較生動(dòng)形象;如果此時(shí)X軸不是+-90°,那么在X軸不變的前提下,依舊可以通過選取適當(dāng)?shù)腪軸和Y軸旋轉(zhuǎn)值使物體指向三維空間中的任意方向.
(2)(1)中的鎖住并不是很多文章中所說的物體無法通過旋轉(zhuǎn)改變方向了,而是若要改變成某個(gè)方向,那么yaw-pitch-roll的角度會(huì)發(fā)生”突變”,如何理解這種突變呢?借助一個(gè)例子來,該例子來源于這篇文章,對(duì)于一個(gè)炮塔模型,假設(shè)地面上的一個(gè)炮塔有兩個(gè)旋轉(zhuǎn)軸:Y(對(duì)應(yīng)于yaw)垂直于地面,使炮塔可以平行地面360°旋轉(zhuǎn)(12點(diǎn)方向?yàn)?°);X(對(duì)應(yīng)于pitch)平行于地面,使得炮口可以繞著它上下90°旋轉(zhuǎn)(平行地面設(shè)為0°),這里我們省略roll旋轉(zhuǎn)角,因?yàn)閞oll是對(duì)炮口本身進(jìn)行旋轉(zhuǎn)(炮口本身的旋轉(zhuǎn)對(duì)于這里的例子沒有太大意義,為了簡單,故省略),這里的X和Y已經(jīng)足夠表示天空中的任意一點(diǎn)!
這時(shí),一架敵機(jī)從3點(diǎn)鐘方向飛來,其在炮臺(tái)坐標(biāo)系的坐標(biāo)是XY-(10,-90),Y=-90°的原因是炮口初始對(duì)準(zhǔn)的是12點(diǎn)方向,需要順時(shí)針旋轉(zhuǎn)90°(以逆時(shí)針為正)指向三點(diǎn)方向.飛機(jī)保持9點(diǎn)鐘的方向飛行,隨著飛機(jī)逐步向炮臺(tái)正上方飛來,X不斷增大,當(dāng)飛機(jī)恰好飛到炮塔頂端時(shí),即X=90°時(shí)(XY-(90,-90)),飛機(jī)突然向6點(diǎn)鐘方向飛行,且假設(shè)其飛至XY-(89, -180),我們發(fā)現(xiàn),簡單地轉(zhuǎn)動(dòng)X軸或者Y軸都無法使得炮口由正上方(89,-90)轉(zhuǎn)到飛機(jī)所在的方向,只有先將Y軸順時(shí)針轉(zhuǎn)動(dòng)90°,再將X軸逆時(shí)針轉(zhuǎn)動(dòng)1°,才能重新指向飛機(jī)的位置,我們發(fā)現(xiàn),炮口相比于之前(10,-90)->(90,-90)的方向連續(xù)變化,現(xiàn)在卻發(fā)生了“突變”.那么這種突變的影響是,在飛機(jī)由(90,-90)->(89,-180)時(shí),飛機(jī)是直線飛行,若炮口繼續(xù)保持勻速轉(zhuǎn)動(dòng),炮口方向在由(90,-90)->(89,-180)時(shí),其過程可能是這樣的(90,-90)->(89.8,-108)->(89.6,-126)->(89.4, -144)->(89.2, -162)->(89, -180),如果在坐標(biāo)系中畫出這些點(diǎn)并連接起來,就會(huì)發(fā)現(xiàn)其近似一根弧線,這樣,飛機(jī)是直線飛行,但炮口在這段時(shí)間內(nèi)是曲線運(yùn)動(dòng),結(jié)果就是這段時(shí)候內(nèi)炮口會(huì)丟失目標(biāo)!上述這個(gè)過程在做插值動(dòng)畫時(shí)尤為明顯(插值過程就是上述的坐標(biāo)變化過程),而萬向節(jié)鎖的真正問題也在于此!并不是上述鏈接中說的,炮口方向無法變化.
(3)雖然可以通過修改旋轉(zhuǎn)順序來改善萬向節(jié)鎖問題(例如Unity里采用的ZXY順序,就可以確保Y在0~360角度旋轉(zhuǎn)時(shí)都不會(huì)發(fā)生這個(gè)問題),但治標(biāo)不治本,修改旋轉(zhuǎn)順序只能在某個(gè)旋轉(zhuǎn)角上避免出現(xiàn)萬向節(jié)鎖,可是其它角度依舊會(huì)有問題;實(shí)際上,”任何使用三個(gè)數(shù)來表達(dá)3D方位的系統(tǒng),若能保證空間的唯一性,就都會(huì)遇到這個(gè)問題”.解決的辦法是,采用四元數(shù),具體課搜索其它博客了解,在這多說一句,四元數(shù)理解起來相對(duì)歐拉角比較困難,但可以有效解決萬向節(jié)鎖的問題;
(4)歐拉角出現(xiàn)萬向節(jié)鎖的另一個(gè)原因是,別名!例如(2)中的炮臺(tái),(90,-90)和(90,-180)實(shí)際上都是炮口豎直朝上,因此也導(dǎo)致了旋轉(zhuǎn)路徑發(fā)生偏移!
(5)萬向節(jié)死鎖會(huì)導(dǎo)致位置上連續(xù)變化 在數(shù)值表示上確是非連續(xù)的,給定的兩個(gè)關(guān)鍵幀之間無法平滑過渡.
實(shí)際上,自己對(duì)于萬向節(jié)鎖以及相關(guān)的問題還存在很多困惑,
(1)這篇文章中的數(shù)學(xué)證明過程無法理解,感覺作者的證明過程有點(diǎn)以結(jié)果來證明結(jié)果,特別是”Rb = Rr~*Ry*Rr 要得到繞 坐標(biāo)系E在繞z軸旋轉(zhuǎn)r后的新系E’下的y軸旋轉(zhuǎn)β的旋轉(zhuǎn)矩陣為Rb,可以先應(yīng)用Rr~這時(shí)可以視作在E下,然后使用E下的旋轉(zhuǎn)Ry繞舊的y軸旋轉(zhuǎn),在應(yīng)用Rr轉(zhuǎn)回到E’”這一段,完全不知所云!
(2)這篇文章里提及的靜態(tài)歐拉角和動(dòng)態(tài)歐拉角;
(3)我在草稿上演示旋轉(zhuǎn)過程時(shí),發(fā)現(xiàn)對(duì)于給定的角度(x1, y1,z1),分別繞X,Y,Z軸以一定的順序?qū)χ付ǖ狞c(diǎn)或者線段進(jìn)行旋轉(zhuǎn)時(shí),最終的結(jié)果都是(2)中靜態(tài)歐拉角的結(jié)果,但看到的書籍和博客關(guān)于這個(gè)都是指動(dòng)態(tài)歐拉角的結(jié)果,疑惑不解!
(4)物體坐標(biāo)系和世界坐標(biāo)系的軸發(fā)生重合,為何會(huì)導(dǎo)致萬向節(jié)鎖問題?
這些問題困擾了很久,這兩天一直在查資料,畫圖驗(yàn)證,演算,依舊沒有完全弄明白,而且弄得心神疲憊,在此做記錄,希望以后實(shí)踐經(jīng)歷豐富后,再逐步解決這些問題!
解決該問題過程中一些不錯(cuò)的博客:
1.Unity 中的旋轉(zhuǎn)
2.【Unity技巧】四元數(shù)(Quaternion)和旋轉(zhuǎn)
3.游戲動(dòng)畫中歐拉角與萬向鎖的理解
4.歐拉角與萬向節(jié)死鎖
5.萬向節(jié)死鎖問題
總結(jié)
- 上一篇: 【视频处理】嵌入式硬件编码(6818)进
- 下一篇: ALPS TCP新建配置——网络测试仪实