KittyL
KittyL

Reputation: 101

Using Vpython to simulate sun-earth-moon orbit

I am trying to use Newton's 2nd law to simulate sun-earth-moon system. I can get the moon and earth parallely rotating around the sun. But the moon does not rotate around the earth.

I know there should be attraction between the moon and sun, and also between the moon and the earth. So I added the acceleration together. But in the 3D visualization, it seems there's no effect of the earth to the moon.

Could anyone check my code on the motion part:

def movePlanets(self):
    rate(200)

    G = (6.673e-11) 
    dt =  12*3600 # half day

    for p in self.planets:

        p.moveTo((p.getXPos() + dt * p.getXVel()),
                 (p.getYPos() + dt * p.getYVel()),
                 (p.getZPos() + dt * p.getZVel()))


        rx = self.thesun.getXPos() - p.getXPos()

        ry = self.thesun.getYPos() - p.getYPos()
        rz = self.thesun.getZPos() - p.getZPos()

        r = math.sqrt(rx**2 + ry**2 + rz**2)

        accx = G * self.thesun.getMass()*rx/r**3
        accy = G * self.thesun.getMass()*ry/r**3
        accz = G * self.thesun.getMass()*rz/r**3


        for pTwo in self.planets:
            if(pTwo != p):
                rx = pTwo.getXPos() - p.getXPos()
                ry = pTwo.getYPos() - p.getYPos()
                rz = pTwo.getZPos() - p.getZPos()
                r = math.sqrt(rx**2 + ry**2 + rz**2)

                accx = accx + (G * pTwo.getMass()*rx/r**3)
                accy = accy + (G * pTwo.getMass()*ry/r**3)
                accz = accz + (G * pTwo.getMass()*rz/r**3)

        p.setXVel(p.getXVel() + dt * accx)
        p.setYVel(p.getYVel() + dt * accy)
        p.setZVel(p.getZVel() + dt * accz)

Thank you so much!

Upvotes: 0

Views: 3989

Answers (2)

vossmalte
vossmalte

Reputation: 184

I think a third 'star' can easily be added easily:

from visual import *

G = 6.7e-11

giant = sphere(pos=(-1e11,0,0), radius=2e10, color=color.red,
               make_trail=True, interval=10)
giant.mass = 2e30
giant.p = vector(0, 0, -1e4) * giant.mass

dwarf = sphere(pos=(1.5e11,0,0), radius=1e10, color=color.yellow,
               make_trail=True, interval=10)
dwarf.mass = 1e30
dwarf.p = -giant.p

dt = 1e5

while True:
  rate(200)

  dist = dwarf.pos - giant.pos
  force = G * giant.mass * dwarf.mass * dist / mag(dist)**3
  giant.p = giant.p + force*dt
  dwarf.p = dwarf.p - force*dt

  for star in [giant, dwarf]:
    star.pos = star.pos + star.p/star.mass * dt

I hope this one helps!

Upvotes: 1

Huy Pham
Huy Pham

Reputation: 11

I have done this simulation, and I don't think you use "enough" Physics, which makes the code a lot easier to understand. Honestly, I cannot understand your code. Here is the approach (as my Physics professor taught me):

  • Create 3 sphere objects as Earth, Sun, and Moon
  • Each object has following attributes: mass, position, velocity, and net force
  • in the main loop:

    while True:
        for each "planet":
            calculate net force (use the gravity formula)
            update momentum: P = P + net_force*dt
            update velocity: v = P/mass
            update position: pos = pos + v*dt
    

Notes: the following variables (attributes) should be vector type for easy calculation using vector operators (addition, subtraction, and scalar multiplication): position, velocity, and net_force

Upvotes: 1

Related Questions