我正在尝试在Python Pygame中产生有弹性的球碰撞效果

发布于 2025-02-11 20:42:21 字数 1560 浏览 1 评论 0原文

因此,这是完整的代码,但是问题在于我的功能移动的班级球。当它执行时会发生什么是像现实生活一样弹跳并开始越来越降低。但是,当它碰到它的限制时,球就会开始在极限之下。 我很抱歉花了你的时间。

from selectors import SelectorKey
from tkinter import Y
import pygame

pygame.init()
width, height = 1000, 600
Win = pygame.display.set_mode((width, height))
clock = pygame.time.Clock()
Acs = 0.5


class Ball():
    def __init__(self):
        self.y = 200
        self.velocity = 10
        self.bouncy = 1

    def draw(self):
        pygame.draw.circle(Win, (255, 0, 0), (500, self.y), 15)

    def move(self):
        self.velocity += Acs
        self.y += self.velocity
        print(self.velocity)
        if self.y > 400:
            self.velocity = -self.velocity + self.bouncy
        if self.y <= 400:
            self.velocity == 0
            self.bouncy == 0
            self.y == 400


def game():
    ball = Ball()
    while True:
        for event in pygame.event.get():
            if event.type == pygame.QUIT:
                return
        ball.move()

        Win.fill((255, 255, 255))
        pygame.draw.line(Win, (0, 0, 0), (0, 400), (1000, 400), 10)
        ball.draw()
        clock.tick(60)
        pygame.display.update()


game()
pygame.quit()


我有问题的地方在这里:

    def move(self):
        self.velocity += Acs
        self.y += self.velocity
        print(self.velocity)
        if self.y > 400:
            self.velocity = -self.velocity + self.bouncy
        if self.y <= 400:
            self.velocity == 0
            self.bouncy == 0
            self.y == 400

So here is the full code, but the problem is in the class Ball where my function move is. What happens when it executes is that the ball bounces and starts going lower and lower, just like real life. But when it hits the limit of how low it can go, the ball starts going under the limit.
I am very sorry for having taken your time.

from selectors import SelectorKey
from tkinter import Y
import pygame

pygame.init()
width, height = 1000, 600
Win = pygame.display.set_mode((width, height))
clock = pygame.time.Clock()
Acs = 0.5


class Ball():
    def __init__(self):
        self.y = 200
        self.velocity = 10
        self.bouncy = 1

    def draw(self):
        pygame.draw.circle(Win, (255, 0, 0), (500, self.y), 15)

    def move(self):
        self.velocity += Acs
        self.y += self.velocity
        print(self.velocity)
        if self.y > 400:
            self.velocity = -self.velocity + self.bouncy
        if self.y <= 400:
            self.velocity == 0
            self.bouncy == 0
            self.y == 400


def game():
    ball = Ball()
    while True:
        for event in pygame.event.get():
            if event.type == pygame.QUIT:
                return
        ball.move()

        Win.fill((255, 255, 255))
        pygame.draw.line(Win, (0, 0, 0), (0, 400), (1000, 400), 10)
        ball.draw()
        clock.tick(60)
        pygame.display.update()


game()
pygame.quit()


where I have a problem is here:

    def move(self):
        self.velocity += Acs
        self.y += self.velocity
        print(self.velocity)
        if self.y > 400:
            self.velocity = -self.velocity + self.bouncy
        if self.y <= 400:
            self.velocity == 0
            self.bouncy == 0
            self.y == 400

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

﹉夏雨初晴づ 2025-02-18 20:42:21

弹跳球(以及每个非线性物理模拟的问题)的问题是,您的模拟可能使您以下 一个时间步骤,因此您必须确保确保您执行限制。解决游戏的一种简单方法是在撞到地板时强制y位置。将您的移动方法对此进行起作用(请注意,如果self.y&lt; = 400:分支没有做任何事情,所以我将其删除)。

    def move(self):
        self.velocity += Acs
        self.y += self.velocity
        if self.y > 400:
            self.velocity = -self.velocity + self.bouncy
            self.y = 400  # Ensure the limits

要获得更现实的弹跳效果,您可以将self.boncy属性用作实际恢复原状系数,并稍微更改反弹的公式。每次反弹的损失中有5%给出了相当不错的结果。

class Ball():
    def __init__(self):
        self.y = 200
        self.velocity = 10
        self.bouncy = 0.05  # Now a coefficient of restitution

    def draw(self):
        pygame.draw.circle(Win, (255, 0, 0), (500, self.y), 15)

    def move(self):
        self.velocity += Acs
        self.y += self.velocity
        if self.y > 400:  # Note that the loss of velocity is a function of the previous velocity
            self.velocity = -self.velocity + self.bouncy*self.velocity
            self.y = 400  # Ensure the limits

The problem with bouncing balls (and every non-linear physics simulation where you have very drastic changes) is that your simulation might put you below the limit in a single time step, so you have to make sure that you enforce the limit. A simple way to fix that for a game is to force the y position when you hit the floor. Change your move method to this and it works (note that the if self.y <= 400: branch didn't do anything, so I removed it).

    def move(self):
        self.velocity += Acs
        self.y += self.velocity
        if self.y > 400:
            self.velocity = -self.velocity + self.bouncy
            self.y = 400  # Ensure the limits

For a slightly more realistic bouncing effect, you can use your self.bouncy attribute as an actual coefficient of restitution and change slightly the formula for the bounce. 5% of loss every bounce gave a reasonably good result.

class Ball():
    def __init__(self):
        self.y = 200
        self.velocity = 10
        self.bouncy = 0.05  # Now a coefficient of restitution

    def draw(self):
        pygame.draw.circle(Win, (255, 0, 0), (500, self.y), 15)

    def move(self):
        self.velocity += Acs
        self.y += self.velocity
        if self.y > 400:  # Note that the loss of velocity is a function of the previous velocity
            self.velocity = -self.velocity + self.bouncy*self.velocity
            self.y = 400  # Ensure the limits
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文