widgetti / ipyvolume

3d plotting for Python in the Jupyter notebook based on IPython widgets using WebGL
MIT License
1.94k stars 234 forks source link

deal with multiples figures #357

Open Damzo opened 3 years ago

Damzo commented 3 years ago

Hi fellows, I'm trying to create a web app using ipywidgets. I have 2 ipyvolume figures, created at the beginning of my code:

main_scene = ipv.figure()
zoom_scene = ipv.figure()

I know that when making a plot, ipyvolume uses the last created figure, but I would like to specify to ipyvolume which figure to use. The reason is that I need to make plot in any of the 2 figures at any moment in my code.

I don't find anywhere in the documentation how to do that...

Thanks !!!

maartenbreddels commented 3 years ago

Hi,

ipv.figure(main_scene) should change it

cheers,

Maarten

Damzo commented 3 years ago

Hi,

ipv.figure(main_scene) should change it

cheers,

Maarten

Ooooh GREAT !!! That works... Thank you Maarten. Your module saves me a lot of time, you can't imagine. Here is the result, the app is not finished. It's a solar concentrator simulator. image

maartenbreddels commented 3 years ago

Thanks for sharing this, look very nice!

Damzo commented 3 years ago

You're welcome !!! I will try to contribute to exemples in ipyvolume.readthedocs.io when everything will work (the app will be open source for physics research purposes).

Please one last question ! Actually I would like to clear the different plots in the main_scene figure (parabola and rays), but want to keep the main-scene for next use... ipv.clear() does not make it...

Here is a simplified version of the code that plot things in the main scene:

def plot_parabola(*arg):
    ipv.figure(main_scene)
   # ...
   # code that compute values...
   # ...
    surf = ipv.plot_isosurface(values, level=0, extent=[[-rx, rx], [-ry, ry], [0, h]])
    ipv.style.axes_off()
    ipv.xlim(-rx, rx)
    ipv.ylim(-ry, ry)

plot_surfBut.on_click(plot_parabola)

def plot_rays(*arg):
   ipv.figure(main_scene)
   for loop:
         # ...
         # code that compute x,y,z...
         # ...
         ipv.plot(x,y,z)
    ipv.xlim(-rx, rx)
    ipv.ylim(-ry, ry)

plot_raysBut.on_click(plot_rays)

Please any idea ?

maartenbreddels commented 3 years ago

You can also directly manipulate figure.scatters figures.meshes etc. That gives you more control.

Damzo commented 3 years ago

ok great, I check on that direction !!! Thanks

Damzo commented 3 years ago

So here is the solution that works for me (it can help someone else...) instead of ipv.clear() one should clear the type of plot directly with figure.scatters.clear() or figure.meshes.clear() as advised by Maarteen.

In my case, I use ipv.plot_isosurface plot(), which returns a mesh and ipv.plot() which returns a scatters. So I use: main_scene.scatters.clear()or main_scene.meshes.clear() depending on the plot I want to clear.