Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

VisPy animation point by point from NumPy array

I'm wondering if something is possible using VisPy, or if I should start looking for other alternatives.

Here's what's going on - I'm writing an undergraduate thesis on some of the paradox-like situations of Special Relativity. What I am doing is this essentially this, I'll have some script in python producing arrays of ordered triplets (points in 3D space) that change with a time like variable (the "time like" variable is actually velocity, but it will count on just like time). I need to animate these points, which in the simpler cases will form rods, 2D squares, and 3D cubes, and of course produce .gif or similar.

Coding is definitely not my strong suit, but I have been using Python for a while. I have looked into VisPy and like that it uses OpenGL capability, and generally like how nice the various examples are (which I can get to work).

My question is: Is VisPy the best thing for what I need to do? I am having a hard time figuring out how to make VisPy make individual points into 3D objects and such - I have played around with the various Geometry things like create_cube, but it doesn't look like I can shift just the vertices around.

If anyone has any suggestions on where to start, or if Mayavi or another thing would be easier please let me know.

Update: I did figure out how to make a really nice (and simple) 3D cube outline, which is exactly what I'm wanting. I am still not sure how to get it to animate, as examples using VisPy for animation are quite different.

Does anyone have any direction? In the code, what needs to happen is that initial array of points needs to update each frame (the points can be imported or calculated in the script, either way)

import numpy as np
import vispy
import vispy.scene
from vispy.scene import visuals
from vispy import app

canvas = vispy.scene.SceneCanvas(keys='interactive', show=True)
view = canvas.central_widget.add_view()

# generate data
pos = np.array([[0, 0, 0], [0.5, 0.5, 0.5], [0, 0.5, 0.5], [0.5, 0, 0.5],
                [0.5, 0.5, 0], [0, 0, 0.5], [0, 0.5, 0], [0.5, 0, 0]])
# These are the data that need to be updated each frame --^

scatter = visuals.Markers()
scatter.set_data(pos, edge_color=None, face_color=(1, 1, 1, .5), size=10)
view.add(scatter)

view.camera = 'turntable'

# just makes the axes
axis = visuals.XYZAxis(parent=view.scene)

if __name__ == '__main__':
    import sys
    if sys.flags.interactive != 1:
        vispy.app.run()
like image 873
AstroJason Avatar asked Dec 25 '17 16:12

AstroJason


1 Answers

I have the same problem and it though to seek a solution. I checked the Vispy API and changed the codes, it works well. Hope this is helpful for you and the others.

import numpy as np
import vispy
import vispy.scene
from vispy.scene import visuals
from vispy import app

canvas = vispy.scene.SceneCanvas(keys='interactive', show=True)
view = canvas.central_widget.add_view()
view.camera = 'turntable'
# generate data
def solver(t):
    pos = np.array([[0.5 + t/10000, 0.5, 0], [0, 0, 0.5], [0, 0.5, 0], [0.5, 0, 0]])
    return pos
# These are the data that need to be updated each frame --^

scatter = visuals.Markers()
view.add(scatter)


#view.camera = scene.TurntableCamera(up='z')

# just makes the axes
axis = visuals.XYZAxis(parent=view.scene)


t = 0.0
def update(ev):
    global scatter
    global t
    t += 1.0
    scatter.set_data(solver(t), edge_color=None, face_color=(1, 1, 1, .5), size=10)

timer = app.Timer()
timer.connect(update)
timer.start(0)
if __name__ == '__main__':
    canvas.show()
    if sys.flags.interactive == 0:
        app.run()
like image 103
zihaowang Avatar answered Sep 20 '22 06:09

zihaowang