簡體   English   中英

如何使用碰撞在另一種形狀的槳式游戲中反彈球?

[英]How to bounce ball in paddle game on another shape using collisions?

試圖讓球在平台上彈跳,但無法檢測到碰撞? 我們如何檢測碰撞或使其從平台反彈? 我們制造了球和它的重力。 球也可以從畫布的兩側反彈,並使平台從鍵盤箭頭鍵移動。

from tkinter import*
import random
import time
import math
import tkinter

WIDTH = 800
HEIGHT = 1000

tk=Tk()
canvas = Canvas(tk, width=1200, height=900)

tk.title("Brick Breaker")

platform = canvas.create_rectangle(5, 40, 250, 30, fill ="black")
def leftKey(event):
    canvas.move(platform, -40, 0)
    pass
def rightKey(event):
    canvas.move(platform, 40, 0)
    pass
tk.bind('<Left>', leftKey)
tk.bind('<Right>', rightKey)
canvas.pack()
tk.update()
#alligns the platform
left = 0
for x in range(0,18):
        canvas.move(1, 40, 40)
        tk.update()

ball = canvas.create_oval(5, 5, 30, 30, fill ="black")
xspeed = 0.1   #gravity
yspeed = 0.4
while True:
        canvas.move(ball, xspeed, yspeed)
        pos = canvas.coords(ball)
        if pos[3] >= 900 or pos[1] <= 0: # y range
            yspeed = -yspeed
        if pos[2] >=  1200 or pos[0] <= 0: # x range
            xspeed = -xspeed
        tk.update()
        time.sleep(0.00000001) #speed

tk.mainloop()

您可以使用canvas.find_overlapping(*ball_pos)來檢查球是否與其他對象重疊。 它返回矩形ball_pos的所有對象的ID - 事件球 - 因此它永遠不會為空。

它並不理想,因為它不會檢查球是否碰撞下方/上方/左側/右側,因此您不知道如何改變方向。

import tkinter as tk

# --- constants ---

WIDTH = 800
HEIGHT = 1000

# --- functions ---

# for smooth move of platform

def left_press(event):
    global platform_left
    platform_left = True

def left_release(event):
    global platform_left
    platform_left = False

def right_press(event):
    global platform_right
    platform_right = True

def right_release(event):
    global platform_right
    platform_right = False


def eventloop():
    global xspeed
    global yspeed

    # move ball
    canvas.move(ball, xspeed, yspeed)
    ball_pos = canvas.coords(ball)

    # move platform
    if platform_left:
        # move
        canvas.move(platform, -20, 0)
        platform_pos = canvas.coords(platform)
        # check if not leave canvas
        if platform_pos[0] < 0:
            # move back
            canvas.move(platform, 0-platform_pos[0], 0)
    if platform_right:
        # move
        canvas.move(platform, 20, 0)
        # check if not leave canvas
        platform_pos = canvas.coords(platform)
        if platform_pos[2] > 1200:
            # move back
            canvas.move(platform, -(platform_pos[2]-1200), 0)

    # - collisions -

    # check collision with border

    if ball_pos[3] >= 900 or ball_pos[1] <= 0: # y range
        yspeed = -yspeed
    if ball_pos[2] >= 1200 or ball_pos[0] <= 0: # x range
        xspeed = -xspeed

    # check collisions with objects 

    collide = canvas.find_overlapping(*ball_pos)

    if platform in collide:
        yspeed = -yspeed

    remove = []

    # check collision with bricks
    for brick in bricks:
        if brick in collide:
            remove.append(brick)
            yspeed = -yspeed

    # remove bricks
    for brick in remove:
        bricks.remove(brick)
        canvas.delete(brick)

    root.after(10, eventloop)

# --- main ---

# - init -

root = tk.Tk()
root.title("Brick Breaker")

canvas = tk.Canvas(root, width=1200, height=900)
canvas.pack()

# - objects -

ball = canvas.create_oval(5, 5, 30, 30, fill="black")
xspeed = 1 # gravity
yspeed = 4

platform = canvas.create_rectangle(5, 40, 250, 30, fill="black")
platform_left = False
platform_right = False
root.bind('<Left>', left_press)
root.bind('<KeyRelease-Left>', left_release)
root.bind('<Right>', right_press)
root.bind('<KeyRelease-Right>', right_release)

bricks = []

for i in range(10):
    x = i*100
    y = 700
    brick = canvas.create_rectangle(x, y, x+50, y+30, fill="red")
    bricks.append(brick)

# - mainloop -

root.after(100, eventloop)
root.mainloop()

BTW:控制速度更好地改變xspeedyspeed而不是after()

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM