【问题标题】:pygame: Stopping movement behind linepygame:停止线后面的运动
【发布时间】:2015-04-29 19:25:09
【问题描述】:

我正在尝试创建一个游戏,让方块移动“跳跃”并降落在其上方的平台上。然后,再次跳到下一个平台。

不幸的是,我的代码目前只是在块触及平台底部并且不再移动时停止。我不确定为什么,因为我认为它应该只在块的底部触及线时才停止

具体是看这段代码,但完整的代码如下:

    #the floor landing code
def hasJumperLanded(rect1, rect2):
    for a, b in [(rect1, rect2), (rect2, rect1)]:
        if isFloorTouching(a.bottom, b):
            return True

def isFloorTouching(y, rect):
    if (y > rect.top) and (y < rect.bottom):
        return True
    else:
        return False

剪辑

    #stop when land on floor
for n in range(len(floors)):
    if (hasJumperLanded(j['rect'], floors[n]['line'])):
        j['jump'] = STILL

完整的代码上下文:

import pygame, sys, time
from pygame.locals import *

    #the deadzone collision code
def doRectsOverlap(rect1, rect2):
    for a, b in [(rect1, rect2), (rect2, rect1)]:
        if ((isPointInsideRect(a.left, a.top, b)) or
            (isPointInsideRect(a.left, a.bottom, b)) or
            (isPointInsideRect(a.right, a.top, b)) or
            (isPointInsideRect(a.right, a.bottom, b))):
            return True

    return False

def isPointInsideRect(x, y, rect):
    if (x > rect.left) and (x < rect.right) and (y > rect.top) and (y < rect.bottom):
        return True
    else:
        return False


    #the floor landing code
def hasJumperLanded(rect1, rect2):
    for a, b in [(rect1, rect2), (rect2, rect1)]:
        if isFloorTouching(a.bottom, b):
            return True

def isFloorTouching(y, rect):
    if (y > rect.top) and (y < rect.bottom):
        return True
    else:
        return False


# set up pygame
pygame.init()
mainClock = pygame.time.Clock()

# set up the window
WINDOWWIDTH = 480
WINDOWHEIGHT = 800
windowSurface = pygame.display.set_mode((WINDOWWIDTH, WINDOWHEIGHT), 0, 32)
pygame.display.set_caption('Jumper')

#Directions
LEFT = 4
RIGHT = 6
UP = 8
DOWN = 2
STILL = 5

#blocks location for jumping
#BLOCKLOCY = 700

#Binary for stopping movement
#STOPPER = 0

MOVESPEED = 1

# set up the colors
BLACK = (0, 0, 0)
RED = (255, 0, 0)
GREEN = (0, 255, 0)
BLUE = (0, 0, 255)


j = {'rect':pygame.Rect(240, 700, 20, 20), 'color':GREEN, 'dir':LEFT, 'jump':STILL}


f1 = {'line':pygame.Rect(0,720,480,2), 'color':GREEN, 'dir':STILL}
f2 = {'line':pygame.Rect(0,650,480,2), 'color':GREEN, 'dir':STILL}
floors = [f1,f2]

# run the game loop
while True:
    # check for the QUIT event
    for event in pygame.event.get():
        if event.type == QUIT:
            pygame.quit()
            sys.exit()



    # draw the black background onto the surface
    windowSurface.fill(BLACK)


        # This way or that way. Speed Code
    if j['dir'] == LEFT:
        j['rect'].left -= MOVESPEED
    if j['dir'] == RIGHT:
        j['rect'].left += MOVESPEED

        #JUST JUMP ALREADY!
    if j['jump'] == UP:
        j['rect'].bottom -= MOVESPEED
        #BLOCKLOCY -= MOVESPEED

        #Bouce when side hitting
    if j['rect'].left < 0:
        j['dir'] = RIGHT
    if j['rect'].left > WINDOWWIDTH-j['rect'].width:
        j['dir'] = LEFT

        #Press to Jump
     if event.type == KEYDOWN:
        if event.key == K_SPACE:
             j['jump'] = UP

        #stop when land on floor
    for n in range(len(floors)):
         if (hasJumperLanded(j['rect'], floors[n]['line'])):
            j['jump'] = STILL


    #Floor controll code for moving level - not working currently
    for f in floors:
        #if f['dir'] == DOWN:
          #  f['line'].y += MOVESPEED

      #  if event.type == KEYDOWN:
          #  if event.key == K_SPACE:
              # f['dir'] = DOWN

     #   if f['line'].top == BLOCKLOCY:
      #      f['dir'] = STILL
       #     STOPPER = 1

        #if f['line'].bottom == BLOCKLOCY:
         #   f['dir'] = STILL
          #  STOPPER = 1




        # draw the block onto the surface
        pygame.draw.rect(windowSurface, j['color'], j['rect'])

        pygame.draw.rect(windowSurface, f['color'], f['line'])


    # draw the window onto the screen
    pygame.display.update()
    mainClock.tick(1000)

【问题讨论】:

    标签: python pygame


    【解决方案1】:
    #the floor landing code
    def hasJumperLanded(rect1, rect2):
        for a, b in [(rect1, rect2), (rect2, rect1)]:  ## **
            if isFloorTouching(a.bottom, b):
                return True
    

    看看我在这个 sn-p 中标记的行。

    在这里,您正在检查矩形以双向碰撞。

    所以你失去了哪个是地板,哪个是移动的含义。

    如果你只检查 (rect1, rect2) 你会看到区别。

    --

    编辑:

    看看这个

    def hasJumperLanded(rect1, rect2):
        for a, b in [(rect1, rect2), (rect2, rect1)]:
            if isFloorTouching(rect1, rect2):
                return True
    
    def isFloorTouching(y, rect):
        if (y.bottom > rect.top) and (y.bottom < rect.bottom):
            return True
        else:
            return False
    

    在isFloorTouching()函数内部处理地板的含义更符合逻辑。

    【讨论】:

    • 啊哈,太棒了。并且一旦到达线的顶部就停止了该块。但是,它无法跳第二次......知道为什么会被欣赏
    • 等等。我通过在跳转命令之前放置 Keydown 事件来让它工作
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-02-22
    • 1970-01-01
    • 2013-12-19
    • 2022-12-18
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多