与 tkinter-canvas 交互球
Posted
技术标签:
【中文标题】与 tkinter-canvas 交互球【英文标题】:Interacting balls with tkinter-canvas 【发布时间】:2020-08-17 17:01:39 【问题描述】:我能够使用 tkinter 对一些移动球进行编程。我用了两种不同的颜色。现在我希望白球在击中红球时将颜色变为红色。有人可以帮我吗?
(一个额外但不那么重要的一点是,如果一个球撞到另一个球会改变方向,那么哪个方向应该是随机的,但这不是那么重要)
总的来说,我有一个问题要弄清楚,球是如何相互作用的。这是我的代码:
from tkinter import *
import time
import random
WIDTH = 800
HEIGHT = 500
tk = Tk()
canvas = Canvas(tk, width=WIDTH, height=HEIGHT, bg="black")
tk.title("Drawing")
canvas.pack()
colors = ['red', 'green', 'blue', 'orange', 'yellow', 'cyan', 'magenta',
'dodgerblue', 'turquoise', 'grey', 'gold', 'pink']
class Ball:
def __init__(self, color):
self.size = random.randrange(5, 10)
#color = random.choice(colors)
self.xpos = random.randrange(0,WIDTH)
self.ypos =random.randrange(0,HEIGHT)
self.shape = canvas.create_oval(self.xpos-self.size, self.ypos -self.size,self.xpos +self.size,self.ypos+self.size, fill=color)
self.speedx = random.randrange(-5, 5)
self.speedy = random.randrange(-5, 5)
def update(self):
canvas.move(self.shape, self.speedx, self.speedy)
pos = canvas.coords(self.shape)
if pos[2] >= (WIDTH) or (pos[0] ) <= 0:
self.speedx *= -1
if pos[3] >= (HEIGHT) or (pos[1]) <= 0:
self.speedy *= -1
ball_list = []
Infiziert_list =[]
for i in range(100):
ball_list.append(Ball('white'))
for j in range(3):
ball_list.append(Ball('red'))
while True:
for ball in ball_list:
ball.update()
tk.update()
#time.sleep(0.001)
非常感谢
【问题讨论】:
这能回答你的问题吗? How to detect collisions of two canvas object Tkinter 首先:非常感谢,但不是真的,因为我不知道如何在我拥有的代码中得到它。所以我需要在更新的东西中以某种方式实现它,但是从 pos 我得到一个返回 3 点的向量。所以对于每个球individuell。所以我不知道如何将位置 ball1 连接到所有其他球 【参考方案1】:您需要执行以下代码。
如果您想编写自己的代码。这里有一个很好的参考资料,请查看Ball collisions 部分。
运行此代码以获得碰撞球的完整工作示例,这些球在碰撞时会改变颜色。
from tkinter import *
import random
class Balls:
color = ["red", "orange", "yellow", "green", "blue", "violet"]
v1x,v2x,v1y,v2y=0.1*random.randint(-10, 10),0.1*random.randint(-10, 10),0.1*random.randint(-10, 10),0.1*random.randint(-10, 10)
def __init__(self, canvas,R,x1,y1,x2,y2):
self.R=R
self.x1 = x1
self.y1=y1
self.x2=x2
self.y2 = y2
self.canvas = canvas
self.ball1 = canvas.create_oval(self.x1-self.R, self.y1-self.R,self.x1+self.R,self.y1+self.R, fill=random.choice(self.color))
self.ball2 = canvas.create_oval(self.x2-self.R, self.y2-self.R,self.x2+self.R,self.y2+self.R, fill=random.choice(self.color))
def callback(self):
color=["red", "orange", "yellow", "green", "blue", "violet"]
self.AA=canvas.create_oval(self.x-10, self.y-10,self.x+10,self.y+10, fill=random.choice(color))
self.vx,self.vy=0.5*random.randint(-10, 10),0.5*random.randint(-10, 10)
canvas.move(self.AA, self.vx,self.vy)
def move_balls(self):
self.canvas.move(self.ball1, self.v1x,self.v1y)
self.canvas.move(self.ball2, self.v2x,self.v2y)
self.canvas.after(5, self.move_balls)
def eventt(self):
A=[(canvas.coords(self.ball1)[0]-canvas.coords(self.ball2)[0]),
(canvas.coords(self.ball1)[1]-canvas.coords(self.ball2)[1])]
if ((A[0])**2+(A[1])**2)**0.5<=2*self.R:
self.v1x,self.v1y,self.v2x,self.v2y=self.v2x,self.v2y,self.v1x,self.v1y
canvas.itemconfig(self.ball1,fill=random.choice(self.color))
canvas.itemconfig(self.ball2,fill=random.choice(self.color))
if canvas.coords(self.ball1)[0]<=0 or canvas.coords(self.ball1)[2]>=400:
self.v1x=-self.v1x
if canvas.coords(self.ball1)[1]<=0 or canvas.coords(self.ball1)[3]>=400:
self.v1y=-self.v1y
if canvas.coords(self.ball2)[0]<=0 or canvas.coords(self.ball2)[2]>=400:
self.v2x=-self.v2x
if canvas.coords(self.ball2)[1]<=0 or canvas.coords(self.ball2)[3]>=400:
self.v2y=-self.v2y
self.canvas.after(10,self.eventt)
# initialize root Window and canvas
root = Tk()
root.title("Balls")
root.resizable(False,False)
canvas = Canvas(root, width = 400, height = 400)
canvas.bind("<Button-1>", Balls.callback)
canvas.pack()
# create two ball objects and animate them
ball = Balls(canvas ,20, 100, 200, 200, 300)
ball.move_balls()
ball.eventt()
root.mainloop()
【讨论】:
非常感谢,但我仍然不知道如何使用例如 50 个白球和 3 个红球来做到这一点。我现在尝试了很长时间,还有你给我的提示。但我无法找到有效的解决方案。也许我再说一遍重点:一开始我想有50个白球和3个红球。如果白球碰到红球,它们应该变成红色。如果任何球撞到另一个球,则应向随机方向移动。如果我不需要自己初始化每个球,那就太好了:/以上是关于与 tkinter-canvas 交互球的主要内容,如果未能解决你的问题,请参考以下文章