• 用VMD做太極拳動畫

    用VMD做太極拳動畫

    文/Sobereva    2009-May-25


    做出來的動畫:



    VMD不僅僅可以用來做研究,還可以用來娛樂,在娛樂過程中也可以學到很多使用技巧。

    這里我用VMD做了一個小人打太極拳的軌跡動畫,以此為基礎對方法進行說明,希望起到拋磚引玉的作用,由于時間所限,只作了5個動作。所用VMD為windows版1.8.6。





    動畫下載地址:
    /usr/uploads/file/20150605/20150605011055_88604.rar
    下載后,把解壓后的文件放到vmd默認目錄下(vmd控制臺輸入pwd后顯示的路徑)。啟動一個新的vmd,在控制臺輸入source start.tcl,即開始播放,如上圖。視角會自動調好,上方文字顯示動作名稱。



    制作方法:
    制作前先考慮做什么內容,不適合通過VMD來實現的題材盡量避開,這需要對VMD比較熟悉才能判斷。用原子構成小人,做太極拳動作在VMD里是比較容易實現的。

    首先繪制小人,雖然很多軟件都可以干這個活,但是GaussView在我看來是最方便的。首先通過旋轉調整好坐標軸,使YZ平面與屏幕平行。然后選擇成添加原子的模式,在屏幕上點出來小人的關節原子,之后用設置化學鍵的方法將關節間連上。建議將頭部、胳膊、腿、身子分別用不同元素原子,這可以使不同部位有不同顏色。此例中身體使用5個氮原子,名字為N1、N2、N3、N4、N5。最終繪制好后小人的整體平面應當恰在YZ平面上,腳踩在XY平面上。如果小人相對于坐標軸偏斜了,可以用這兩個操作來調整:按住ALT后左鍵/右鍵拖動小人可以讓小人旋轉,但不旋轉坐標軸。按住ALT和SHIFT后左鍵拖動小人可以讓小人平移,但不平移坐標軸。



    之后保存為man.mol2。mol2格式的一個好處是包含了原子間的拓撲關系,避免讀入VMD后胡亂判斷成鍵。接下來制作動畫過程中的工作目錄假定為d:\study\VMD186\manmovie(VMD啟動后默認目錄為d:\study\VMD186)。將man.mol2拷到工作目錄下。



    做動畫之前應當先把做動畫的工具準備好,工欲善其事必先利其器,否則很難做。顯然不可能做動畫中每一幀時都挪動一次小人的原子然后保存,太費事。可以使用類似做flash的方法,先通過移動原子創建兩個關鍵幀,然后生成過渡幀。我編了一個小軟件vmdmovie,下載地址/usr/uploads/file/20150605/20150605011319_86069.rar。將壓縮包內的vmdmovie.exe拷到工作目錄下。

    使用方法:vmdmovie f.pdb l.pdb 10 3,其中f.pdb為起始關鍵幀,l.pdb為結束關鍵幀,10代表生成的過渡幀數,3代表過渡幀名字的前綴。vmdmovie輸入和輸出的都是.pdb格式。此例會輸出003-00001.pdb 003-00002.pdb ..... 003-00011.pdb。實際共生成了11幀,其中最后一幀003-00011.pdb與結束關鍵幀l.pdb是一樣的。

    接下來要在vmd里構建好制作動畫的環境。通過移動原子設定人物動作需要有準確的坐標,需要有東西作為參考,否則可能小人越做越歪。VMD的坐標軸在左下角,不好用來作為參考,所以需要在坐標原點處自行繪制一個新的坐標軸,并且顯示出地面(XY平面)。另外每次移動小人原子后通過VMD菜單保存坐標太麻煩,若每次按一個鍵就能保存一個新坐標文件,且文件名連續就會方便很多。這需要下面的腳本。

    在d:\study\VMD186下面創建一個reset.tcl文件,內容如下:
    set nowframe 0  #關鍵幀起始編號
    cd D:\\study\\VMD186\\manmovie  #進入工作目錄

    mol delete top
    mol default style CPK  #設默認顯示方式為CPK,新載入的結構就會以CPK顯示
    mol new D:\\study\\VMD186\\manmovie\\man.mol2

    draw delete all  #刪除其它自行繪制的物件,繪制新的坐標軸
    draw color red
    draw cylinder { 0 0 0 } { 20 0 0 } radius 0.2
    draw cone { 20 0 0 } { 22 0 0 } radius 1 resolution 20
    draw color green
    draw cylinder { 0 0 0 } { 0 20 0 } radius 0.2
    draw cone { 0 20 0 } { 0 22 0 } radius 1 resolution 20
    draw color blue
    draw cylinder { 0 0 0 } { 0 0 20 } radius 0.1
    draw cone { 0 0 20 } { 0 0 22 } radius 1 resolution 20
    draw color white  #繪制兩個白色的三角組成矩形,來表示地面
    draw triangle {15 -35 0} {-15 -35 0} {-15 35 0}
    draw triangle {15 -35 0} {15 35 0} {-15 35 0}

    rotate y by -90  #旋轉、調整好視角
    rotate z by 270
    scale to 0.12  #設定縮放尺寸,越小則人物越小
    mol addrep top  #新增一個representation(以下簡稱rep)
    mol modselect 1 top {name N1 N2 N3 N4 N5}  #新rep所選內容設為小人的身體原子

    set sel [atomselect top all]

    user add key o {  #新加入一個快捷鍵,在VMD的3D窗口中按o,小人的坐標就會被保存一次
    global nowframe
    incr nowframe  #每次保存坐標時更新文件名,最終得到1.pdb 2.pdb ......
    $sel writepdb $nowframe.pdb}

    啟動vmd,控制臺運行source reset.tcl,此時會看到場景被布置好了。



    現在按o,得到第一個關鍵幀。會看到工作目錄出現了1.pdb。然后按數字鍵5,即選成移動原子的模式,拖動每個關節原子,將它們擺成下一個關鍵幀的位置,再按o,工作目錄就有了2.pdb,依此類推,得到所有關鍵幀的結構文件。挪動原子時主要靠三視圖來定位原子,以避免偏離,也就是依次在三個坐標軸垂直于屏幕時挪動原子。建議不要使用透視模式,而使用正交模式(Display-Orthographic),這樣可以比較容易看出當前視角是否擺正了。

    涉及到小人身體移動的時候將組成身體的5個原子一個一個地移動比較麻煩,而且可能導致身體變形。VMD里面有個很好的功能,就是可以移動整個rep包含的原子,由于rep的內容可以十分靈活地選擇,所以可以整體移動任意范圍的原子。前面的腳本已經將小人的身體設定了一個rep,但是由于身體的rep與整個小人rep相重疊,鼠標點這個rep不到,所以在Representations里先將身體的rep原子半徑設大(Sphere Scale設大),這樣就可以點到了。之后在3D窗口里點數字9進入Rep移動模式,就可以鼠標拖動身體平移了,按住shift拖動是旋轉身體。



    之后我們把所有關鍵幀之間生成過渡幀,控制臺運行:
    for {set i 0} {$i<100} {incr i 1} {vmdmovie $i.pdb [expr $i+1].pdb 10 $i}
    這里假設關鍵幀數小于100,每個關鍵幀之間插10幀。

    現在我們來看看結果,刪除當前分子的所有幀,然后運行:
    foreach i [glob 0*.pdb] {mol addfile $i}
    這里假設關鍵幀數小于100,所以生成的幀名字開頭為0,這條命令就把所有生成的幀讀進去了。注意讀入的不僅僅是過渡幀,也包括關鍵幀,因為vmdmovie每次生成的幀的最后一幀就是關鍵幀。

    現在就可以播放了。如果發現某幀不合適,就把那幀讀入,改完坐標后保存,再用vmdmovie生成過渡幀,vmdmovie的速度是比較快的。

    如果沒問題,就file-save coordinates,選擇原子范圍設all,文件類型設.trr,保存為all.trr放到工作目錄下。



    最后我們希望在動畫播放時加一些花樣,比如顯示字幕、用VMD繪圖函數繪制場景等等,可以使用一個.tcl腳本來完成。太極拳動畫壓縮包里的start.tcl就是做這個用的,這里解釋一下:

    trace variable vmd_frame(1) w sdf  #每當ID=1的分子幀數變化時(比如播放時),即vmd_frame(1)變量變化時,就調用sdf命令,這里ID=1就是小人的動畫
    mol new  #新生成一個層,即ID=0的層,用來繪制地面、顯示文字

    proc sdf {args} {  #下面定義sdf命令的行為,用來顯示當前小人動作的名稱
    global vmd_frame  #vmd_frame是VMD自帶的數組變量,第n個元素就是ID=n的幀的當前幀號,在自定義指令里調用這個全局數組變量需要先用這條命令使它在內部可用。
    graphics 0 delete all  #刪除之前的字
    graphics 0 color white  #設字為白色

    if {$vmd_frame(1)<150} {graphics 0 text {0 -23 18} "Qi Shi" size 4
    } elseif {$vmd_frame(1)<580} {graphics 0 text {0 -23 18} "ZuoYouYeMaFenZong" size 3  #當幀數在150~580之間的時候就在屏幕上方顯示ZuoYouYeMaFenZong,文字的坐標需要自行調整嘗試才能合適。VMD不支持中文,所以只能將“左右野馬分鬃”用拼音來寫。
    } elseif {$vmd_frame(1)<640} {graphics 0 text {0 -23 18} "BaiHeLiangChi" size 3
    } elseif {$vmd_frame(1)<850} {graphics 0 text {0 -23 18} "ZuoLouXiAoBu" size 3
    } elseif {$vmd_frame(1)<964} {graphics 0 text {0 -23 18} "Shou Shi" size 4}

    if {$vmd_frame(1)==640} {after 800}  #在白鶴亮翅這個動作做完時停頓一下,停止800ms
    if {$vmd_frame(1)==545} {after 500}
    }

    mol default style CPK
    mol new man.mol2  #讀入小人.mol2文件作為初始幀并確定拓撲關系,隨后讀入動畫軌跡all.trr
    mol addfile all.trr
    draw color white  #繪制地面
    draw triangle {15 -35 0} {-15 -35 0} {-15 35 0}
    draw triangle {15 -35 0} {15 35 0} {-15 35 0}
    rotate y by -90
    rotate z by 270
    scale to 0.1
    animate speed 0.96  #播放速度,1為全速
    translate by 1 0 0  #平移場景至位置合適
    animate forward  #播放動畫


    本文的目的是希望大家能夠解放思想,運用VMD可以制作出有趣的動畫,寓教于樂。VMD還可以用來制作簡單游戲,我會在以后談到。
    久久精品国产99久久香蕉