jupyter-widgets / pythreejs

A Jupyter - Three.js bridge
https://pythreejs.readthedocs.io
Other
934 stars 185 forks source link

bug in multiple object animation #405

Open nikhilmishra000 opened 11 months ago

nikhilmishra000 commented 11 months ago

I have a scene where two leaf bodies have the same name (and they have different parents).

scene/
      -- sphere/
                -- child
      -- box/
             -- child

I cannot animate both child bodies at the same time. It seems that only the one that was added to the scene first can be animated.

In the following example, I specify the track name to be scene/box/child.position, but it seems to animate sphere/child instead!

import pythreejs 
import ipywidgets
import numpy as np

camera = pythreejs.PerspectiveCamera(fov=90, aspect=1.0, position=[1, 0, 0], up=[0, 0, 1])
orbit_controls = pythreejs.OrbitControls(controlling=camera)
scene = pythreejs.Scene(
    children=[camera, orbit_controls, pythreejs.AmbientLight(color="#FFFFFF")], background="black",
)
renderer = pythreejs.Renderer(scene=scene, camera=camera, controls=[orbit_controls], width=256, height=256)
renderer.camera.add(pythreejs.HemisphereLight())

box = pythreejs.Mesh(
    name="box",
    position=[0, 0.5, 0],
    geometry=pythreejs.BoxGeometry(0.1, 0.1, 0.1),
    material=pythreejs.MeshPhysicalMaterial(color='orange')
)
box.add(
    pythreejs.Mesh(
        name="child",
        position=[0, 0.25, 0],
        geometry=pythreejs.BoxGeometry(0.1, 0.1, 0.1),
        material=pythreejs.MeshPhysicalMaterial(color='cyan')
    ),
)

sphere = pythreejs.Mesh(
    name="sphere",
    position=[0.5, 0, 0],
    geometry=pythreejs.SphereGeometry(radius=0.1, widthSegments=32, heightSegments=32),
    material=pythreejs.MeshPhysicalMaterial(color='red')
)
sphere.add(
    pythreejs.Mesh(
        name="child",
        position=[0.25, 0, 0],
        geometry=pythreejs.SphereGeometry(radius=0.1, widthSegments=32, heightSegments=32),
        material=pythreejs.MeshPhysicalMaterial(color='lime')
    ),
)

scene.add(sphere)
scene.add(box)

t = np.linspace(0, 2 * np.pi, 16)
track = pythreejs.VectorKeyframeTrack(
    name='scene/box/child.position',
    times=t,
    values=np.stack([0.25 * np.cos(t), 0.25 * np.sin(t), np.zeros_like(t)], axis=-1)
)

clip = pythreejs.AnimationClip(tracks=[track])
mixer = pythreejs.AnimationMixer(scene)
action = pythreejs.AnimationAction(mixer, clip, scene)

display(ipywidgets.VBox([renderer, action]))