简体   繁体   中英

Pygame screen won't blit

I have an Agar.io like test game where the square player touches the "bit"s and grows. The problem is the bit generation. The bit generates every second and has its own surface. But, the program will not blit the bit (no pun intended) into the initial surface.

Here is the code:

import pygame
import random
pygame.init()
clock = pygame.time.Clock()
display = pygame.display
screen = display.set_mode([640,480])
rect_x = 295
rect_y = 215
display.set_caption("Agar")
d = False
bits = []
size = 50
steps = 0
class Bit:
    cscreen = display.set_mode([640,480])
    circ = pygame.draw.circle(cscreen, (65, 76, 150), (random.randrange(40, 600), random.randrange(40, 440)), 5)
while True:
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            d = True
    if d == True:
        break

    # Fill background
    screen.fill((5, 58, 0))

    # Create player object
    player = pygame.draw.rect(screen, (250, 197, 255), [rect_x, rect_y, size, size])

    # Moving
    if pygame.key.get_pressed()[pygame.K_UP]:
        rect_y -= 2
    if pygame.key.get_pressed()[pygame.K_DOWN]:
        rect_y += 2
    if pygame.key.get_pressed()[pygame.K_RIGHT]:
        rect_x += 2
    if pygame.key.get_pressed()[pygame.K_LEFT]:
        rect_x -= 2

    # Bit generation
    if steps == 60:
        new_bit = Bit()
        bits.append(new_bit.circ)
        screen.blit(new_bit.cscreen, (0,0))
        steps = 0
    steps += 1

    # Collision detection
    collision = player.collidelist(bits)
    if collision != -1:
        bits[collision].cscreen.fill((0,0,0,0))
        # Make player larger
        size += 10

    # FPS limit
    clock.tick(60)

    # Refresh
    display.flip()

PS There is no error message.

Thanks in advance.

To have each Bit object have different locations and instance variables, you need to have an __init__ method in your bit class. By adding an __init__ , and adding self. to the variables, the blitting works.

But a word of warning. When you make a separate cscreen for each object, and then blit that cscreen to your actual screen, you get rid of every other cscreen thats been blitted, making only 1 Bit viewable at a time. Even if you had cscreen outside of __init__ , you would have an issue erasing older ones now, so I advise you take a different approach.

My recommendation is to find a small picture of a dot, and write these lines in the Bit 's __init__ method.

self.image = pygame.image.load("reddot.png")
self.rect = self.image.get_rect()

Once you create your bit, add it to a pygame.sprite.Group() . These groups have very handy built in methods. One of them being .draw() . It will go through your Group of Bits and use each's self.image and self.rect to draw them in the correct place every time, without you having to worry about it. When a Bit is eaten, you can delete the Bit from the Group and it is now erased for you.

A random side note: I recommend you change your event loop to just break when it event.type == pygame.QUIT . That way, Python does not need to check the if d == True statement on every frame, while making the code slightly more readable. If it only breaks out of the for loop (for me it exited fine), you can use sys.exit() after importing sys

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