2016-06-13 23 views
0

Mayavi mlabを使って地球をアニメーション化しようとしています。私は過去に、地球のBuiltinSurface表現の周りをカメラを回転させるだけで成功しましたが、フレーム内に他の多くのオブジェクト(宇宙船、星など)をプロットする必要があるとき、これは不便になります。以下のコードは「ほとんど」機能しているようです。私のWindows 10マシンでは、8回繰り返してアニメーションがフリーズします。このコードを修正するにはどうすればよいですか、またはBuiltinSurfaceを一般的にアニメーション化するより良い方法がありますか?Mayavi mlabでBuiltinSurfaceをアニメーション化する方法は?

import numpy as np 
from mayavi import mlab 
from mayavi.sources.builtin_surface import BuiltinSurface 
from mayavi.modules.surface import Surface 
from mayavi.filters.transform_data import TransformData 


def rotMat3D(axis, angle, tol=1e-12): 
    """Return the rotation matrix for 3D rotation by angle `angle` degrees about an 
    arbitrary axis `axis`. 
    """ 
    t = np.radians(angle) 
    x, y, z = axis 
    R = (np.cos(t))*np.eye(3) +\ 
    (1-np.cos(t))*np.matrix(((x**2,x*y,x*z),(x*y,y**2,y*z),(z*x,z*y,z**2))) + \ 
    np.sin(t)*np.matrix(((0,-z,y),(z,0,-x),(-y,x,0))) 
    R[np.abs(R)<tol]=0.0 
    return R 



@mlab.show  
@mlab.animate(delay=200) 
def anim(): 

    fig = mlab.figure() 

    engine = mlab.get_engine() 

    # Add a cylinder builtin source 
    cylinder_src = BuiltinSurface() 
    engine.add_source(cylinder_src) 
    cylinder_src.source = 'earth' 
    # Add transformation filter to rotate cylinder about an axis 
    transform_data_filter = TransformData() 
    engine.add_filter(transform_data_filter, cylinder_src) 
    Rt = np.eye(4) 
    Rt[0:3,0:3] = rotMat3D((0,0,1), 0) # in homogeneous coordinates 
    Rtl = list(Rt.flatten()) # transform the rotation matrix into a list 

    transform_data_filter.transform.matrix.__setstate__({'elements': Rtl}) 
    transform_data_filter.widget.set_transform(transform_data_filter.transform) 
    transform_data_filter.filter.update() 
    transform_data_filter.widget.enabled = False # disable the rotation control further. 

    # Add surface module to the cylinder source 
    cyl_surface = Surface() 
    engine.add_filter(cyl_surface, transform_data_filter) 
    #add color property 
    #cyl_surface.actor.property.color = (1.0, 0.0, 0.0) 

    ind=1 
    while ind<90: 
     print ind 
     Rt[0:3,0:3] = rotMat3D((0,0,1), ind) # in homogeneous coordinates 
     Rtl = list(Rt.flatten()) # transform the rotation matrix into a list 

     transform_data_filter.transform.matrix.__setstate__({'elements': Rtl}) 
     transform_data_filter.widget.set_transform(transform_data_filter.transform) 
     transform_data_filter.filter.update() 
     transform_data_filter.widget.enabled = False # disable the rotation control further. 

     # Add surface module to the cylinder source 
     cyl_surface = Surface() 
     engine.add_filter(cyl_surface, transform_data_filter) 
     # add color property 
     #cyl_surface.actor.property.color = (1.0, 0.0, 0.0) 

     yield 
     ind+=1 


anim() 

答えて

0

私はこれを実現するためにMayaviを使用する方法を理解できませんでした。しかし、Vpythonはこの作業を行うのにはるかに適しているようです。私はいくつかの他の機能と一緒に、回転地球を作るためのコードの例セクションを掲載しました。

from visual import * 

def destroy(): 
    for obj in scene.objects: 
     obj.visible = False 
     del obj 

R = 6378. # radius of sphere 
angle=0. 
scene.range = 10000. 
SunDirection=vector(.77,.77,0) 
# scene.fov = 0.5 
scene.center = (0,0,0) 
scene.forward = (-1,0,-1) 
scene.up = (0,0,1) 
scene.lights=[distant_light(direction=SunDirection, color=color.gray(0.8)), 
       distant_light(direction=-SunDirection, color=color.gray(0.3))] 
x=0 
y=0 

while True: 
    rate(10) 

    angle=angle+1.*pi/180. 

    destroy() 
    s = sphere(pos=(x,y,0), radius=R, material=materials.BlueMarble) 
    s.rotate(angle=90.*pi/180.,axis=(1,0,0)) # Always include this to rotate Earth into correct ECI x y z frame 
    s.rotate(angle=90.*pi/180.,axis=(0,0,1)) # Always include this to rotate Earth into correct ECI x y z frame 
    s.rotate(angle=angle, axis=(0,0,1)) # This rotation causes Earth to spin on its axis 

    xaxis = arrow(pos=(0,0,0), axis=vector(1,0,0)*7000, shaftwidth=100, color=color.red) 
    yaxis = arrow(pos=(0,0,0), axis=vector(0,1,0)*7000, shaftwidth=100, color=color.green) 
    zaxis = arrow(pos=(0,0,0), axis=vector(0,0,1)*7000, shaftwidth=100, color=color.blue) 

    ST = cone(pos=(0,8000,0),axis=(0,700,0),radius=700*tan(10*pi/180),color=color.blue,opacity=1) 
関連する問題