Tkinter移动球程序创建4个球而不是2个

时间:2017-06-12 12:44:02

标签: python canvas tkinter tkinter-canvas

我创建了一个程序,让球在画布周围移动并弹出画布的边缘。这非常有效,所以我尝试添加另一个球,但不是创造2个球,而是创造4个,2个球移动而另外两个保持静止。 这是代码:

#imports
from tkinter import *
import random
from random import randint



#Creating random x and y for the balls to move along
x = random.randint(1,10)
y = random.randint(1,10)
print(x, " Ball 1y")
print(y, " Ball 1x")

x0 = random.randint(1,10)
y0 = random.randint(1,10)
print(y0," Ball2y")
print(x0, " Ball2x")


class Ball:

    #creates balls
    def __init__(self, canvas, x1,y1,x2,y2):
        self.x1 = x1
        self.y1 = y1
        self.x2 = x2
        self.y2 = y2
        self.canvas = canvas
        self.ball = canvas.create_oval(self.x1, self.y1, self.x2, self.y2,         fill="red")
        self.ball2 = canvas.create_oval(self.x1, self.y1, self.x2, self.y2,     fill="red")


    def move_ball(self, x, y):
        #function to move ball

        coords = canvas.coords(self.ball)
        #Because coord is stored in a list I need to call which coord is bigger than the edge of the canvas
        if coords[0] >= 280:
            #multiplying by a negative number makes the ball "bounce"
            x *= -1
        if coords[0] <= 0:
            x *= -1
        if coords[3] <= 20:
            y *= -1
        if coords[3] >= 300:
            y *= -1
        print(coords, " Ball1")
        #makes ball move
        self.canvas.move(self.ball, x, y)
        self.canvas.after(50, self.move_ball, x, y)


    def move_ball2(self, x0, y0):

        #same as previous different variables
        coords2 = canvas.coords(self.ball2)

        if coords2[0] >= 280:
            x0 *= -1
        if coords2[0] <= 0:
            x0 *= -1
        if coords2[3] <= 20:
            y0 *= -1
        if coords2[3] >= 300:
            y0 *= -1
        print(coords2, " Ball2")
        self.canvas.move(self.ball2, x0, y0)
        self.canvas.after(50, self.move_ball2, x0, y0)



#changes window titles etc.
root = Tk()
root.title("Balls")
root.resizable(False, False)
canvas = Canvas(root, width = 300, height = 300)
canvas.pack()

#creates ball with dimensions of the ball
ball1 = Ball(canvas, 10, 10, 30, 30)
ball2 = Ball(canvas, 60, 60, 80, 80)
#calls move ball function
ball1.move_ball(x, y)
ball2.move_ball2(x0,y0)

root.mainloop()

2 个答案:

答案 0 :(得分:2)

问题是除了添加第二个球之外,你还改变了Ball类。面向对象编程的想法(即在python中简单的单词类)是创建一个类,这里​​是Ball,它定义了一个通用球如何工作。你可以从这个类创建任意数量的对象(这里是ball1,ball2等)。

在您的代码中,您只需要

  1. 删除该行

    self.ball2 = canvas.create_oval(self.x1,self.y1,self.x2,self.y2,fill =“red”)

  2. 删除完整的move_ball2函数

  3. 更改

  4. ball2.move_ball2(X0,Y0)

    ball2.move_ball(x0,y0)
    

    它将按预期工作。

答案 1 :(得分:2)

您正在使用__init()__方法初始化两个球。

self.ball = canvas.create_oval(self.x1, self.y1, self.x2, self.y2, fill="red")
self.ball2 = canvas.create_oval(self.x1, self.y1, self.x2, self.y2,fill="red")

为两个球而不是一个球创建对象时。因此,更改类中的init方法应该可以解决它。您需要为两个不同的球创建两个不同的对象,而不是类本身中的两个不同的变量。

class Ball:

    #creates balls
    def __init__(self, canvas, x1,y1,x2,y2):
        self.x1 = x1
        self.y1 = y1
        self.x2 = x2
        self.y2 = y2
        self.canvas = canvas
        self.ball = canvas.create_oval(self.x1, self.y1, self.x2, self.y2, fill="red")

此外,你有两种不同的移动球1和2的方法。一种方法应该适用于两个球。

ball1 = Ball(canvas, 10, 10, 30, 30)
ball2 = Ball(canvas, 60, 60, 80, 80)

当执行两个语句时,它们将类Ball的对象返回到变量ball1和ball2。这些对象彼此独立,move_ball方法将单独调用它们而不会相互影响。为两个不同的变量创建两个函数会破坏创建类的目的。

您可能想要了解herehere中的类和对象的更多内容。类和对象上有video tutorials以及它们如何在tkinter上实现。