import scene3d
ORBIT_SPEED = 40.0
scene = scene3d.Scene()
scene.set_sky(scene3d.Sky.DEEP_SPACE)
planet = scene3d.Shapes.Sphere(diameter=2, segments=24)
planet.set_material(scene3d.Material.Planets.Earth)
scene.add(planet)
moon_group = scene3d.Group()
moon = scene3d.Shapes.Sphere(diameter=0.6, segments=14)
moon.set_material(scene3d.Material.Planets.Moon)
moon.set_position(4, 0, 0)
moon_group.add(moon)
scene.add(moon_group)
ctx = scene.get_context('2d')
angle = 0.0
orbit_speed = ORBIT_SPEED
def speed_up():
global orbit_speed
orbit_speed = min(orbit_speed + 20, 180)
planet.on_click(speed_up)
@scene.on_frame
def animate(dt):
global angle
angle += orbit_speed * dt
moon_group.set_rotation(y=angle)
pos = moon.get_position()
ctx.clear()
ctx.fill_style = '#ffffff'
ctx.font = '18px sans-serif'
ctx.fill_text(
f'Speed: {orbit_speed:.0f} deg/s | Click the planet to speed up!',
10, 28
)
scene.run()Now Experiment!
You’ve covered a lot in Lesson 3. Here’s what you now know how to do:
- Read object state with
get_position(),get_rotation(), andget_scale() - Combine shapes into one unit using
scene3d.Group(), so a single transform moves everything - Respond to user actions by connecting functions to mesh clicks with
on_click() - Animate every frame using the
@scene.on_framedecorator anddtfor smooth, frame-rate-independent motion
The cell below is your sandbox. It starts with a scene that uses all four ideas: a planet with an orbiting moon (group), a click handler that speeds up the orbit, an animation loop, and a HUD that reads the moon’s position with a getter. The rest is up to you.
Ideas to try: - Add a second moon at a different orbit radius and speed - Add a click handler to the moon that slows the orbit back down - Make the planet slowly spin on its own axis using planet.set_rotation(y=angle) - Add a while loop to build a ring of asteroids, each in its own group offset from center - Show the moon’s current x and z from get_position() on the HUD, updating each frame