Разрешение изменения размера окна pyGame

Я пытаюсь разрешить изменение размера для этого приложения, я помещаю флаг RESIZABLE, но когда я пытаюсь изменить размер, это испортится! Попробуйте мой код.

Это сетчатая программа, когда изменяется размер окна, я хочу, чтобы сетка также изменялась и уменьшалась.

import pygame,math
from pygame.locals import *
# Define some colors
black    = (   0,   0,   0)
white    = ( 255, 255, 255)
green    = (   0, 255,   0)
red      = ( 255,   0,   0)

# This sets the width and height of each grid location
width=50
height=20
size=[500,500]
# This sets the margin between each cell
margin=1


# Initialize pygame
pygame.init()

# Set the height and width of the screen

screen=pygame.display.set_mode(size,RESIZABLE)

# Set title of screen
pygame.display.set_caption("My Game")

#Loop until the user clicks the close button.
done=False

# Used to manage how fast the screen updates
clock=pygame.time.Clock()

# -------- Main Program Loop -----------
while done==False:
    for event in pygame.event.get(): # User did something
        if event.type == pygame.QUIT: # If user clicked close
            done=True # Flag that we are done so we exit this loop
        if event.type == pygame.MOUSEBUTTONDOWN:
            height+=10

    # Set the screen background
    screen.fill(black)

    # Draw the grid
    for row in range(int(math.ceil(size[1]/height))+1):
        for column in range(int(math.ceil(size[0]/width))+1):
            color = white
            pygame.draw.rect(screen,color,[(margin+width)*column+margin,(margin+height)*row+margin,width,height])

    # Limit to 20 frames per second
    clock.tick(20)

    # Go ahead and update the screen with what we've drawn.
    pygame.display.flip()
# Be IDLE friendly. If you forget this line, the program will 'hang'
# on exit.
pygame.quit ()

Скажите, пожалуйста, что случилось, спасибо.

Ответ 1

Вы не обновляете свою ширину, высоту или размер при изменении окна.

Из документов: http://www.pygame.org/docs/ref/display.html

Если на дисплее установлен флаг pygame.RESIZABLE, pygame.VIDEORESIZE будут отправляться, когда пользователь настраивает размеры окна.

Вы можете получить новый size, w, h из события VIDEORESIZE http://www.pygame.org/docs/ref/event.html

Ответ 2

Описание из ninMonkey было правильным (fooobar.com/questions/481514/...).

Вы не обновляете свою ширину, высоту или размер, когда окно изменения.

Итак, ответ заключается просто в воссоздании окна Pygame, обновлении его размера
(это изменяет размер текущего окна и удаляет все предыдущее содержимое на его поверхности).

>>> import pygame
>>> 
>>> pygame.display.set_mode.__doc__
'set_mode(resolution=(0,0), flags=0, depth=0) -> Surface\nInitialize a window or screen for display'
>>> 

Это нужно делать при событиях pygame.VIDEORESIZE, которые отправляются, когда пользователь изменяет размеры окна с изменяемым размером. Кроме того, может понадобиться использовать метод ниже, чтобы сохранить содержимое текущего окна.

Пример кода примера:

import pygame, sys
# from pygame.locals import * # This would make Pygame constants (in capitals) not need the prefix "pygame."

pygame.init()

# Create the window, saving it to a variable.
surface = pygame.display.set_mode((350, 250), pygame.RESIZABLE)
pygame.display.set_caption("Example resizable window")

while True:
    surface.fill((255,255,255))

    # Draw a red rectangle that resizes with the window as a test.
    pygame.draw.rect(surface, (200,0,0), (surface.get_width()/3,
                                          surface.get_height()/3,
                                          surface.get_width()/3,
                                          surface.get_height()/3))

    pygame.display.update()
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            pygame.quit()
            sys.exit()
        if event.type == pygame.KEYDOWN:
            if event.key == pygame.K_ESCAPE:
                pygame.quit()
                sys.exit()
        if event.type == pygame.VIDEORESIZE:
            # The main code that resizes the window:
            # (recreate the window with the new size)
            surface = pygame.display.set_mode((event.w, event.h),
                                              pygame.RESIZABLE)

Метод, позволяющий избежать риска потери предыдущего контента:
Здесь несколько шагов, чтобы оставить части вашего графического интерфейса без изменений:

  • сделать вторую переменную, установить значение старой переменной поверхности окна.
  • создайте новое окно, сохранив его как старую переменную.
  • нарисуйте вторую поверхность на первую (старую переменную) - используйте blit.
  • используйте эту переменную и удалите новую переменную (необязательно, используйте del), если вы "Не хочу терять память".

Некоторые примеры кода для вышеупомянутого решения (идет в инструкции pygame.VIDEORESIZE event if в начале):

            old_surface_saved = surface
            surface = pygame.display.set_mode((event.w, event.h),
                                              pygame.RESIZABLE)
            # On the next line, if only part of the window needs to be copied, there some other options.
            surface.blit(old_surface_saved, (0,0))
            del old_surface_saved # This line may not be needed.

Ответ 3

Простое окно Hello World, изменяемое по размеру, плюс я играл с классами.
Разбито на два файла, один для определения цветовых констант.

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


# Data Definition
class helloWorld:
    '''Create a resizable hello world window'''
    def __init__(self):
        pygame.init()
        self.width = 300
        self.height = 300
        DISPLAYSURF = pygame.display.set_mode((self.width,self.height), RESIZABLE)
        DISPLAYSURF.fill(WHITE)

    def run(self):
        while True:
            for event in pygame.event.get():
                if event.type == QUIT:
                    pygame.quit()
                    sys.exit()
                elif event.type == VIDEORESIZE:
                    self.CreateWindow(event.w,event.h)
            pygame.display.update()

    def CreateWindow(self,width,height):
        '''Updates the window width and height '''
        pygame.display.set_caption("Press ESC to quit")
        DISPLAYSURF = pygame.display.set_mode((width,height),RESIZABLE)
        DISPLAYSURF.fill(WHITE)


if __name__ == '__main__':
    helloWorld().run()

colors.py:

BLACK  = (0, 0,0)
WHITE  = (255, 255, 255)
RED    = (255, 0, 0)
YELLOW = (255, 255, 0)
BLUE   = (0,0,255)

GREEN = (0,255,0)