2016-04-23 83 views
1

我正在嘗試編寫一個函數來生成在圓內移動的點。我已經有了一個用matpltolib動畫繪製動畫點的功能(感謝Tony Babarino),但是我很難編寫強制點的部分留在圓圈中如何繪製在圓內移動的動畫點?

這就是運動起作用的部分

import numpy as np 
from matplotlib import pyplot as plt 
from matplotlib import animation 

# Initializing number of dots 
N = 25 


# Creating dot class 
class dot(object): 
    def __init__(self): 
     self.x = 10 * np.random.random_sample() 
     self.y = 10 * np.random.random_sample() 
     self.velx = self.generate_new_vel() 
     self.vely = self.generate_new_vel() 

    def generate_new_vel(self): 
     return (np.random.random_sample() - 0.5)/5 

    def move(self) : 
      if np.random.random_sample() < 0.95: 
       self.x = self.x + self.velx 
       self.y = self.y + self.vely 
      else: 
       self.velx = self.generate_new_vel() 
       self.vely = self.generate_new_vel() 
       self.x = self.x + self.velx 
       self.y = self.y + self.vely 

# Initializing dots 
dots = [dot() for i in range(N)] 

# First set up the figure, the axis, and the plot element we want to animate 
fig = plt.figure() 
ax = plt.axes(xlim=(0, 10), ylim=(0, 10)) 
d, = ax.plot([dot.x for dot in dots], 
      [dot.y for dot in dots], 'ro', markersize=3) 
circle = plt.Circle((5, 5), 1, color='b', fill=False) 
ax.add_artist(circle) 


# animation function. This is called sequentially 
def animate(i): 
    for dot in dots: 
     dot.move() 
    d.set_data([dot.x for dot in dots], 
       [dot.y for dot in dots]) 
    return d, 

# call the animator. 
anim = animation.FuncAnimation(fig, animate, frames=200, interval=20) 

plt.show() 

我想補充說,強制點在圈內 我想圓的邊界要像圍牆,該點不能跨越到SATY的一部分,以完善的功能舉動

我知道如何檢測一個點c拋出線路,但我不知道該怎麼做。

非常感謝您的幫助

+0

你需要弄清楚你想要當一個點打圓的邊界發生什麼PLT :它反彈?留在這?重新出現在另一邊?無論如何,中心思想是你需要強制執行圓的約束:'x ** 2 + y ** 2 Cyb3rFly3r

+0

點應該反彈 – Jkev

+0

然後你可以簡單地顛倒速度(兩個分量)。由於你的圓的原點沒有中心,在這種情況下,方程略有不同:當(x - xc)** 2 +(y - yc)** 2 Cyb3rFly3r

回答

0

我改變了代碼,這樣你就不必vibarting和逃避圓的問題。進入圓圈的每個點都不會逃脫(點的起點可能在圓外),也不會在圓的邊緣振動。 進口numpy的是NP 從matplotlib進口pyplot從matplotlib進口動畫

# Initializing number of dots 
N = 25 
XC = 5 
YC = 5 
R = 1 
R_SQR = R **2 

# Creating dot class 
class dot(object): 
    def __init__(self, ind): 
     self.x = 10 * np.random.random_sample() 
     self.y = 10 * np.random.random_sample() 
     self.velx = self.generate_new_vel() 
     self.vely = self.generate_new_vel() 
     self.in_circle = not self.calc_out_of_circle() 

    def generate_new_vel(self): 
     return (np.random.random_sample() - 0.5)/5 

    def move(self) : 
     if np.random.random_sample() < 0.95: 
      self.check_out_of_circle() 
      self.x += self.velx 
      self.y += self.vely 
     else: 
      self.velx = self.generate_new_vel() 
      self.vely = self.generate_new_vel() 
      self.check_out_of_circle() 
      self.x += self.velx 
      self.y += self.vely 
     self.check_inside_circle() 

    def calc_out_of_circle_with_params(self, x, y): 
     return (x - XC) ** 2 + (y - YC) ** 2 >= R_SQR ** 2 

    def calc_out_of_circle(self): 
     return self.calc_out_of_circle_with_params(self.x, self.y) 

    def check_out_of_circle(self): 
     if self.in_circle and self.calc_out_of_circle_with_params(self.x + self.velx, self.y + self.vely): 
      self.velx = -self.velx 
      self.vely = -self.vely 

    def check_inside_circle(self): 
     if not self.calc_out_of_circle(): 
      self.in_circle = True 


# Initializing dots 
dots = [dot(i) for i in range(N)] 

# First set up the figure, the axis, and the plot element we want to animate 
fig = plt.figure() 
ax = plt.axes(xlim=(0, 10), ylim=(0, 10)) 
d, = ax.plot([dot.x for dot in dots], 
      [dot.y for dot in dots], 'ro', markersize=3) 
circle = plt.Circle((XC, YC), R, color='b', fill=False) 
ax.add_artist(circle) 


# animation function. This is called sequentially 
def animate(i): 
    for dot in dots: 
     dot.move() 
    d.set_data([dot.x for dot in dots], 
       [dot.y for dot in dots]) 
    return d, 

# call the animator. 
anim = animation.FuncAnimation(fig, animate, frames=200, interval=20) 
# plt.axis('equal') 
plt.show()