Home > OS >  trying to plot position vector within loop
trying to plot position vector within loop

Time:09-17

I've been trying to code projectile motion and everything has been working so far except the graphing portion, which i'm trying to iterate within the loop. I want to graph the x and y coordinate of the position vector, but i keep getting the error "module not callable"

import numpy as np
import math as m
import matplotlib as plt

g = np.array([0,-9.8,0])

r = np.array([0,1.2,0])

theta = 35 * m.pi / 180

v1 = 3.3

v = v1 * np.array([np.cos(theta),np.sin(theta),0])

a = g

t = 0

dt = .01

while r[1]  > 0:
    v = v   a * dt
    r = r   v * dt
    t = t   dt
    plt.plot(r)
    
print("r = ",r , "m")

print("t = ",t, "s")

print("v = ",v, "m/s")

CodePudding user response:

I found two issues in your code:

  1. the plt import is not correct. Instead use from matplotlib import pyplot as plt
  2. plt.plot(r) works but nothing is shown since you are trying to draw a single point of infinitesimal size for each canvas. Since is a scatterplot, you should assign a dimension to each point, e.g.
    plt.plot(r[0], r[1], marker="o", markersize=5, markeredgecolor="blue", markerfacecolor="blue")
    
    enter image description here

If your goal is to generate an animation (as suggested by @3dSpatialUser), you need multiple pictures. Thus add plt.show() (or plt.savefig()) in the while loop.

CodePudding user response:

Here it is a bit of code, that corrects your mistakes and uses ① a little different looping scheme, that I find more flexible, ② a simple animation trick, as suggested in other answers and comments, and ③ an alternative algorithm that gives very similar results when you use a small time step, but is more accurate if you use a longer time step.

I include no graphic output because it's an animation, test it yourself, please.

import numpy as np
import matplotlib.pyplot as plt

# CONSTANTS
a = np.array([0.0, -9.8, 0.0])
theta = np.radians(35.0)
v1 = 3.3

# Initial conditions
t, dt = 0.0, 0.01
r = np.array([0.0, 1.2, 0.0])
v = v1 * np.array([np.cos(theta),np.sin(theta),0])

# set the limits of the plots, to avoid annoying resizing, and grid
plt.axis((-0.05, 2.05, -0.05, 1.45))
plt.grid()

# imo, it's better a never ending loop with a break condition
# placed where it is needed - also, it's better to plot
# also the first and the last points
while 1:
    plt.scatter(r[0], r[1], color='red', s=3)
    plt.pause(.00001)
    if r[1]  < 0: break
    v = v   a * dt
    r = r   v * dt
    t = t   dt

# reset the initial conditions
t, dt = 0.0, 0.01
r = np.array([0.0, 1.2, 0.0])
v = v1 * np.array([np.cos(theta),np.sin(theta),0])

# here a little improvement, instead of using the FINAL value
# of the velocity to compute the final displacement, let's
# use the MEAN value of the velocity during the time step
while 1:
    plt.scatter(r[0], r[1], color='blue', s=3)
    plt.pause(.00001)
    if r[1]  < 0: break
    v0 = v
    v = v   a * dt
    r = r   (v0 v)/2 * dt
    t = t   dt
  • Related