11
$\begingroup$

Is there a possibility in Mathematica to allow for manual rotation of 3D graphics when (auto)playing either using Manipulate or ListAnimate? (When one plays a sequence of 3D graphics using ListAnimate it is not possible to rotate manually the graph as when it is static.)

$\endgroup$
  • $\begingroup$ I hope it is not possible to do what you ask. I think any attempt to allow what you ask for would produce nightmarish thread conflict between the thread updating the graphics under animation control and the thread updating the graphics under mouse control. I would expect the 2nd of these two threads to be blocked while animation is running. $\endgroup$ – m_goldberg Oct 23 '15 at 15:05
  • 1
    $\begingroup$ @m_goldberg Instead of blocking, it might be done with time division multiplex technics? $\endgroup$ – Silvia Oct 23 '15 at 16:13
  • $\begingroup$ @Silvia. Sound good but do you think Mathematica's front-end supports that? $\endgroup$ – m_goldberg Oct 23 '15 at 16:20
  • $\begingroup$ @m_goldberg I doubt so. But maybe we can simulate one with nested Dynamics? $\endgroup$ – Silvia Oct 23 '15 at 16:55
  • 1
    $\begingroup$ @m_goldberg I made one along that way and the performance is indeed bad -- but not unacceptable IMO. Will try a 3D graphics case before shape an answer. $\endgroup$ – Silvia Oct 23 '15 at 17:00
11
$\begingroup$

As there seem no easy way to hack ListAnimate or Manipulate, we'll try to construct a custom "animator", using the method I mentioned in an earlier post with some generalization.

First we generate all frames of the animation:

frameLst =
        Module[{range},
            range = Range[0, 2, .1];
            Plot3D[
                   Im[ArcSin[(.5 Abs[# - 1])^3 (x + I y)^4 Exp[2 # π I]]],
                   {x, -2, 2}, {y, -2, 2},
                   (* quality too high will crash the Dynamic system: *)
                   PlotPoints -> 10, MaxRecursion -> 1,
                   ExclusionsStyle -> {None, Red},
                   PlotRange -> {{-2, 2}, {-2, 2}, 4 {-1, 1}}, 
                   SphericalRegion -> True
            ] & /@ range
        ];

Then we make it move automatically using a Clock:

With[{n = Length@frameLst, opts = glst[[1, 2]]},
    DynamicModule[
        { k,
          frameDataLst = Cases[frameLst, _GraphicsComplex, ∞]
        },
        DynamicWrapper[
           Graphics3D[
              Dynamic[frameDataLst[[k]]],
              opts
           ],
           k = Clock[{1, n, 1}, 3]
        ]
    ]
]

rotatable auto-animation

The key point of the trick is keeping a persistent Graphics3D object across frames. So instead of writing Dynamic[Graphics3D[...]], we should use Graphics3D[{...,Dynamic[...],...}, options] to prevent the Graphics3DBox being destroyed at each frame, which will leave it no time to respond to the dragging operations from mouse.

$\endgroup$
  • $\begingroup$ Excellent work! $\endgroup$ – m_goldberg Oct 23 '15 at 21:56
  • $\begingroup$ @m_goldberg Thanks :) $\endgroup$ – Silvia Oct 24 '15 at 6:09

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.