简体   繁体   中英

How do I make a collision in pygame with 2 images?

So I am trying to make a collision with 2 images, I even used get_rect but still doesnt work for me. In function draw i tried to make the collision with player_rect and rect_img which is an image of GRASS_IMAGE, any help is appreciated.

If you want to test the code, create 2 python file one main.py and second mapdata.py, in the main include the first code i wrote and in the mapdata include the second one. And change the.png (images).

Sorry if the code is hard to read or is written bad.

import pygame as pg
import sys
import os
from pygame import image
from pygame import rect
from mapdata import game_map_data

#CONSTANT VARIABLES
#WIDTH;HEIGHT
WINDOW_WIDTH = 800
WINDOW_HEIGHT = 598
PLAYER_WIDTH = 20
PLAYER_HEIGHT = 20
#COLORS
COLOR_DARKBLUE = 'darkblue'
COLOR_RED = 'red'
#WINDOW
WINDOW = pg.display.set_mode((WINDOW_WIDTH,WINDOW_HEIGHT))
sky = pg.image.load('sky.png')
sky = pg.transform.scale(sky,(800,599))

class Player(object):
    def __init__(self,x,y,width,height):
        self.x = x
        self.y = y
        self.width = width
        self.height = height

    def Draw(self):
        self.player = pg.image.load('player.png')
        self.player = pg.transform.scale(self.player,(PLAYER_WIDTH,PLAYER_HEIGHT))
        self.player_rect = self.player.get_rect()
        WINDOW.blit(self.player,dest=(self.x,self.y))
        self.player_rect.x = self.x
        self.player_rect.y = self.y

        if self.rect_img.colliderect(self.player_rect): #COLLISIONS DONT WORK
            print("collided")

    def handle_keys(self,speed):
        keys = pg.key.get_pressed()
        self.speed = speed
        if keys[pg.K_RIGHT]:
            self.x += speed
        if keys[pg.K_LEFT]:
            self.x -= speed
        if keys[pg.K_DOWN]:
            self.y+= speed
        if keys[pg.K_UP]:
            self.y -= speed

    ###########
    ##TILEMAP##
    ###########

    def tile(self,data,tile_size,img_size):
        self.tile_list = []

        #TEXTURES
        GRASS_IMAGE = pg.image.load('platform.jpg')
        #stone_img = pg.image.load('')

        row_count = 0
        self.tile_size = tile_size
        self.img_size = img_size

        for row in data:
            col_count = 0
            for tile in row:
                if tile == 1:
                    img = pg.transform.scale(GRASS_IMAGE,(img_size,img_size))
                    self.rect_img = img.get_rect()
                    self.rect_img.x = col_count * tile_size
                    self.rect_img.y = row_count * tile_size
                    tile = (img,self.rect_img)
                    self.tile_list.append(tile)
                col_count += 1
            row_count += 1


    def draw_tile(self):
        for tile in self.tile_list:
            WINDOW.blit(tile[0], tile[1])


#FPS
clock = pg.time.Clock()




game_map_data = game_map_data


#PLAYER
player = Player(x=30,y=30,width=PLAYER_WIDTH,height=PLAYER_HEIGHT)
gamemap = player.tile(game_map_data,17,20)
while True:
    FPS = 60
    pg.display.update()
    clock.tick(FPS)

    
    for event in pg.event.get():
        if event.type == pg.QUIT:
            sys.exit()

    SKY_POSITION = (0,0)

    WINDOW.blit(sky,SKY_POSITION)
    player.draw_tile()
    #player.col()
    player.Draw()
    player.handle_keys(speed=3)
    pg.display.update()
    pg.display.flip()

tilemap (mapdata.py): ACTUAL MAP

game_map_data = [
[1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,0,0,0,0,0,0,0,0,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
[1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1],
]

self.rect_img is the rect of the last grass tile that you set by going through the for loops in tile function. So,

self.rect_img.colliderect(self.player_rect):

is actually only testing the last grass tile.

You need to test against all the tiles, not just the last one. Luckily, you are storing those tiles in a list, so you can go through that list can check against player and all the tiles.

 for t in self.tile_list:
      if t[1].colliderect(self.player_rect): #COLLISIONS DONT WORK
            print("collided")

Also, you code could be faster if you load and transform your images once instead of every frame.

To make two objects collide you can use colliderect: Rect = rectangle

if Rect1.colliderect(Rect2):

Then by using this you can determine what you want Rect1 to do when it collides with Rect2. In this case we want the player to stop or be blocked.

 if Rect1.colliderect(Rect2):
   Rect1.bottom = Rect2.top #changing y pos
   Rect1.left = Rect2.right #changing x pos
   Rect1.right = Rect.left #changing x pos
   Rect1.top = Rect.bottom #changing y pos

This will stop Rect1 from moving when it hits Rect2. I don't know if that helps but i hope it can give you an idea of the possibilities for this collision.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM