1
#Dashman_Classes
import pygame
            

class Platform(pygame.sprite.Sprite):
    def __init__(self,xbound,ybound,center):
        super().__init__()
        self.xbound=xbound
        self.ybound=ybound
        self.center=center
        self.surf = pygame.Surface((self.xbound, self.ybound))
        self.colour=((255,0,0))
        self.rect = self.surf.get_rect(center = self.center)
    def change_size(self):
        self.surf = pygame.Surface((self.xbound, self.ybound))
        self.surf.fill(self.colour)
        self.rect = self.surf.get_rect(center = self.center)


class Screen():
    def __init__(self,platform_list,screenpos,respawn_point):
        self.platform_list=list(platform_list)
        self.screenpos=screenpos
        self.respawn_point=respawn_point
        self.level_platforms_list=pygame.sprite.Group()

        
class Level():
    def __init__(self,screen_array,level_num,level_name):
        self.screen_array=screen_array
        self.level_num=level_num
        self.level_name=level_name

#Level Editor
import pygame
from Dashman_Classes import *
pygame.init()
xbound=1000
ybound=1000
window = pygame.display.set_mode([xbound, ybound])
pygame.display.set_caption("Level Editor")
running = True
FPS = pygame.time.Clock()
screen_1=Screen([],[0,0],[500,500])
current_screen=screen_1
viewed_screen_pos=[0,0]
platform=Platform(0,0,(0,0))
platform_toggle=False
height_mode=False #False is width True is height
spawn_place_mode=False #True is placing a spawn False is not
spawn_point_indicator=pygame.Rect(0,0,0,0)
level=Level([screen_1],0,"Name")
screen_found=False#Used for screen traversal
repeated_screen=False#Checks if screen that is on during screen traversal is new


while running:

    
    #Mouse positioning and detecting inputs
    mouse_position=pygame.mouse.get_pos()
    left,middle,right=pygame.mouse.get_pressed()


    #Event Handling
    keys=pygame.key.get_pressed()
    for event in pygame.event.get():
        if event.type==pygame.QUIT:
            running = False
        if event.type==pygame.KEYDOWN:


            #Platform Placing
            if event.key==pygame.K_j:
                if platform_toggle==False:
                    platform=Platform(100,100,mouse_position)
                    platform_toggle=True
                    height_mode=False
                else:
                    platform=Platform(0,0,mouse_position)
                    platform_toggle=False


            #Platform resize mode
            if event.key==pygame.K_k:
                height_mode=not height_mode

            #Screen spawn placement
            if event.key==pygame.K_l:
                if not spawn_place_mode:
                    spawn_point_indicator.width=45
                    spawn_point_indicator.height=45
                else:
                    spawn_point_indicator.width=0
                    spawn_point_indicator.height=0
                spawn_place_mode = not spawn_place_mode
                

            #Platform resizing horizontally
            if not height_mode:
                if event.key==pygame.K_EQUALS:
                    if keys[pygame.K_LSHIFT]:
                        if platform.xbound<1000:
                            platform.xbound+=100
                    else:
                        if platform.xbound>10:
                            platform.xbound+=10  
                    platform.xbound+=10
                elif event.key==pygame.K_MINUS:
                    if keys[pygame.K_LSHIFT]:
                        if platform.xbound>100:
                            platform.xbound-=100
                    else:
                        if platform.xbound>10:
                            platform.xbound-=10


            #Platform resizing vertically
            else:
                if event.key==pygame.K_EQUALS:
                    if keys[pygame.K_LSHIFT]:
                        if platform.ybound<1000:
                            platform.ybound+=100
                    else:
                        if platform.ybound>10:
                            platform.ybound+=10  
                    platform.xboundy=10
                elif event.key==pygame.K_MINUS:
                    if keys[pygame.K_LSHIFT]:
                        if platform.ybound>100:
                            platform.ybound-=100
                    else:
                        if platform.ybound>10:
                            platform.ybound-=10


            #Screen Traversal
            if event.key==pygame.K_UP:
                pass


            if event.key==pygame.K_RIGHT:
                viewed_screen_pos[0]+=1
                for screen in level.screen_array:
                    print(viewed_screen_pos,screen.screenpos,current_screen.screenpos)
                    if viewed_screen_pos == screen.screenpos:
                        current_screen=screen
                        screen_found=True
                        print("Screen found true")
                        break
                if not screen_found:
                    print("second code is running")
                    current_screen=Screen([],viewed_screen_pos,[500,500])
                    level.screen_array.append(current_screen)
                print(viewed_screen_pos,screen.screenpos,current_screen.screenpos,"\n")
                screen_found=False


            if event.key==pygame.K_DOWN:
                pass


            if event.key==pygame.K_LEFT:
                viewed_screen_pos[0]-=1
                for screen in level.screen_array:
                    print(viewed_screen_pos,screen.screenpos,current_screen.screenpos)
                    if viewed_screen_pos == screen.screenpos:
                        current_screen=screen
                        screen_found=True
                        print("Screen found true")
                        break
                if not screen_found:
                    print("second code is running")
                    current_screen=Screen([],viewed_screen_pos,[500,500])
                    level.screen_array.append(current_screen)
                print(viewed_screen_pos,screen.screenpos,current_screen.screenpos,"\n")
                screen_found=False
                

    platform.change_size()
    

    #Places down platform and saves it to the current screens array
    if left and platform_toggle:
        current_screen.platform_list.append(platform)
        current_screen.level_platforms_list.add(platform)
        platform=Platform(0,0,mouse_position)
        platform_toggle=False
    if right:
        for screen in level.screen_array:
            print(level.screen_array)


    #Setting spawn for screen to indicator and placing indicator   
    if spawn_place_mode:
        spawn_point_indicator.center=mouse_position
        if left:
            current_screen.respawn_point=spawn_point_indicator
            spawn_place_mode=False
            
    #print(current_screen.screenpos)
    #Platform following mouse
    platform.center=mouse_position

    #window and drawing initial platform
    window.fill((0, 0, 0))
    pygame.draw.rect(window,(255,0,0),platform.rect)
    pygame.draw.rect(window,(0,150,0),spawn_point_indicator)
    for entity in current_screen.level_platforms_list:
        window.blit(entity.surf, entity.rect)
    pygame.display.update()
    FPS.tick(144)
pygame.quit()

I am trying to make a level editor for my game in pygame, each level is a series of screens, and the level editor is supposed to make it so that when i move screens and a screen hasn't been created in that position yet to create a new blank screen however instead it will create 1 new screen and then it will change that new screens position (screenpos) instead of making a new one,

Code snippet for traversing screens (i've only done left and right so far)

#Screen Traversal
            if event.key==pygame.K_UP:
                pass


            if event.key==pygame.K_RIGHT:
                viewed_screen_pos[0]+=1
                for screen in level.screen_array:
                    print(viewed_screen_pos,screen.screenpos,current_screen.screenpos)
                    if viewed_screen_pos == screen.screenpos:
                        current_screen=screen
                        screen_found=True
                        print("Screen found true")
                        break
                if not screen_found:
                    print("second code is running")
                    current_screen=Screen([],viewed_screen_pos,[500,500])
                    level.screen_array.append(current_screen)
                print(viewed_screen_pos,screen.screenpos,current_screen.screenpos,"\n")
                screen_found=False


            if event.key==pygame.K_DOWN:
                pass


            if event.key==pygame.K_LEFT:
                viewed_screen_pos[0]-=1
                for screen in level.screen_array:
                    print(viewed_screen_pos,screen.screenpos,current_screen.screenpos)
                    if viewed_screen_pos == screen.screenpos:
                        current_screen=screen
                        screen_found=True
                        print("Screen found true")
                        break
                if not screen_found:
                    print("second code is running")
                    current_screen=Screen([],viewed_screen_pos,[500,500])
                    level.screen_array.append(current_screen)
                print(viewed_screen_pos,screen.screenpos,current_screen.screenpos,"\n")
                screen_found=False
  • Try replacing every instance of `current_screen=Screen([],viewed_screen_pos,[500,500])` to `current_screen=Screen([],viewed_screen_pos.copy(),[500,500])` – Red Dec 02 '21 at 18:07
  • Dude your a life saver thank you so much but could you explain how it works? – Kaptain_kek Dec 03 '21 at 00:37
  • I've added an answer that explains in detail. – Red Dec 03 '21 at 13:15

1 Answers1

1

You'll need to replace every instance of

current_screen=Screen([],viewed_screen_pos,[500,500])

to

current_screen=Screen([],viewed_screen_pos.copy(),[500,500])

The reason for this is because when you pass the original viewed_screen_pos variable to the Screen object, when the initialization meets self.screenpos=screenpos, they are actually pointing at the same piece of data.

You see, variables only point to a piece of memory, so altering that piece of memory at any variable will affect the rest of the variables that point to that piece of memory.

For more information, see: List changes unexpectedly after assignment. Why is this and how can I prevent it?

Red
  • 26,798
  • 7
  • 36
  • 58