2015-04-17 34 views
0

我需要改變一個級別,但我無法得到它的工作。我正在嘗試像this那樣做。Pygame LEVEL變化

當我嘗試開始時,我根本沒有水平。我的代碼:

#! /usr/bin/python 

import pygame 
from pygame import * 
#import pyganim 

#=========Display======# 
WIN_WIDTH = 800 
WIN_HEIGHT = 640 
HALF_WIDTH = int(WIN_WIDTH/2) 
HALF_HEIGHT = int(WIN_HEIGHT/2) 

DISPLAY = (WIN_WIDTH, WIN_HEIGHT) 
DEPTH = 32 
FLAGS = 0 
CAMERA_SLACK = 30 


#=========Game main==# 
def main(): 
    global cameraX, cameraY 
    pygame.init() 
    screen = pygame.display.set_mode(DISPLAY, FLAGS, DEPTH) 
    timer = pygame.time.Clock() 
    currentLevel = 0 

    up = down = left = right = running = False 


    bg = Surface((32,32)) 
    #bg = pygame.image.load('BG\BGL1.png').convert() 
    bg.fill(Color("#000000")) 
    entities = pygame.sprite.Group() 
    player = Player(32, 55) 




    levels = [[ 
     "", 
     "", 
     "", 
     "", 
     "", 
     "SSSSSSSSSSSSSSSS", 
     "PPPPPPPPPSSSSSSS   ", 
     " ", 
     "              

     ], 
     [ 
     "", 
     "", 
     "", 
     "", 
     "PPPPPPPPPPPP", 
     "PPPPPPPPPPPP" 
     ]] 


     # Level Generating code 
    def load_level(level): 
     platforms = [] 
     x = y = 0 
     for row in levels: 
      for col in row: 
       if col == "P": 
        p = Platform(x, y) 
        platforms.append(p) 
        entities.add(p) 
       if col == "E": 
        e = ExitBlock(x, y) 
        platforms.append(e) 
        entities.add(e) 
       if col == "G": 
        g = Platform1(x, y) 
        platforms.append(g) 
        entities.add(g) 
       if col == "A": 
        a = Stone(x, y) 
        platforms.append(a) 
        entities.add(a) 
       if col == "S": 
        s = Stone0(x, y) 
        platforms.append(s) 
        entities.add(s) 
       if col == "H": 
        h = HalfPlaform0(x, y) 
        platforms.append(h) 
        entities.add(h) 
       if col == "B": 
        b = StoneBack(x, y) 
        entities.add(b) 
       if col == "T": 
        t = Bridge(x,y) 
       x += 32 
      y += 32 
      x = 0 
     return platforms, entities 

    platforms, entities = load_level(currentLevel) 
    load_level(currentLevel) 




    total_levels_width = len(levels[0])*32 
    total_levels_height = len(levels)*32 
    camera = Camera(complex_camera, total_levels_width, total_levels_height) 
    entities.add(player) 



    while 1: 

     load_level(currentLevel) 
     timer.tick(60) 


     for e in pygame.event.get(): 
      if e.type == QUIT: raise SystemExit("QUIT") 
      if e.type == KEYDOWN and e.key == K_ESCAPE: 
       raise SystemExit("ESCAPE") 
      if e.type == KEYDOWN and e.key == K_UP: 
       up = True 
      if e.type == KEYDOWN and e.key == K_DOWN: 
       down = True 
      if e.type == KEYDOWN and e.key == K_LEFT: 
       left = True 
      if e.type == KEYDOWN and e.key == K_RIGHT: 
       right = True 
      if e.type == KEYDOWN and e.key == K_SPACE: 
       running = True 
      if e.type == KEYUP and e.key == K_l: 
       currentLevel += 1 
       load_level(currentLevel) 
       print(level) 

      if e.type == KEYUP and e.key == K_UP: 
       up = False 
      if e.type == KEYUP and e.key == K_DOWN: 
       down = False 
      if e.type == KEYUP and e.key == K_RIGHT: 
       right = False 
      if e.type == KEYUP and e.key == K_LEFT: 
       left = False 







     for y in range(32): 
      for x in range(32): 
       screen.blit(bg, (x * 32, y * 32)) 


     ##Update player, draw everything else## 
     ###THE PROBLEM IS HERE I THINK### 

     for e in entities: 
      screen.blit(e.image, camera.apply(e)) 

     ''' 
     BegimoAnim.anchor(anchorPoint = 'east') 
     BegimoAnim.blit(screen, (player)) 
     ''' 


     camera.update(player) 
     pygame.display.update() 
     player.update(up, down, left, right, running, platforms) 





class Camera(object): 
    def __init__(self, camera_func, width, height): 
     self.camera_func = camera_func 
     self.state = Rect(0, 0, width, height) 

    def apply(self, target): 
     return target.rect.move(self.state.topleft) 

    def update(self, target): 
     self.state = self.camera_func(self.state, target.rect) 

def simple_camera(camera, target_rect): 
    l, t, _, _ = target_rect 
    _, _, w, h = camera 
    return Rect(-l+HALF_WIDTH, -t+HALF_HEIGHT, w, h) 

def complex_camera(camera, target_rect): 
    l, t, _, _ = target_rect 
    _, _, w, h = camera 
    l, t, _, _ = -l+HALF_WIDTH, -t+HALF_HEIGHT, w, h 

    l = min(0, l)       ## stop scrolling at the left edge## 
    #l = max(-(camera.width-WIN_WIDTH), l) ## stop scrolling at the right edge## 
    t = max(-(camera.height-WIN_HEIGHT), t) ## stop scrolling at the bottom## 
    t = min(0, t)       ## stop scrolling at the top## 
    return Rect(l, t, w, h) 


#============PLAYER===============# 
right_standing = pygame.image.load('PlayerModels\Sprites\PlayerStill2.gif') 
left_standing = pygame.transform.flip(right_standing, True, False) 
animTypes = 'right_walk'.split() 

''' 
BegimoAnim = pyganim.PygAnimation([ 
    ('PlayerModels\Sprites\Player_right_walk1.gif', 0.2,), 
    ('PlayerModels\Sprites\Player_right_walk2.gif', 0.2,), 
            ]) 
''' 

class Entity(pygame.sprite.Sprite): 
    def __init__(self): 
     pygame.sprite.Sprite.__init__(self) 

class Player(Entity): 
    def __init__(self, x, y): 
     Entity.__init__(self) 
     self.xvel = 0 
     self.yvel = 0 
     self.onGround = False 
     self.image = Surface = right_standing 
     self.rect = self.image.get_rect() 
    def update(self, up, down, left, right, running, platforms): 
     a = 0 
     #BegimoAnim.blit(screen, (player)) 
     if up: 
      # Pasokti tik ant zemes 
      if self.onGround: self.yvel -= 7 
     if down: 
      pass 
     if running: 
      self.xvel = 12 
     if left: 
      self.xvel = -5 
      self.image = left_standing 
     if right: 
      self.xvel = 5 
      self.image = right_standing 




      #BegimoAnim.play() 

     if not self.onGround: 
      # gravitacija + acceleracija 
      self.yvel += 0.3 
      # Max kritimo greitis 
      if self.yvel > 100: self.yvel = 100 
     if not(left or right): 
      self.xvel = 0 
     # Prieaugis X direkcijoje 
     self.rect.left += self.xvel 
     # daryti X axis collision 
     self.collide(self.xvel, 0, platforms) 
     # Prieaugis Y direkcijoje 
     self.rect.top += self.yvel 
     # Ar ore? 
     self.onGround = False; 
     # daryti Y axis collision 
     self.collide(0, self.yvel, platforms) 



    def collide(self, xvel, yvel, platforms): 
     level = 0 
     for p in platforms: 
      if pygame.sprite.collide_rect(self, p): 
       if isinstance(p, ExitBlock): 
        currentLevel += 1 
        walls, players, finishes = load_level(currentLevel) 
        print(level) 
       if xvel > 0: 
        self.rect.right = p.rect.left 

       if xvel < 0: 
        self.rect.left = p.rect.right 

       if yvel > 0: 
        self.rect.bottom = p.rect.top 
        self.onGround = True 
        self.yvel = 0 
       if yvel < 0: 
        self.rect.top = p.rect.bottom 

#=========Platforms, ground 
class Platform(Entity): 
    def __init__(self, x, y): 
     Entity.__init__(self) 
     self.image = Surface = pygame.image.load("GroundModels\Ground0.png").convert() 
     self.rect = Rect(x, y, 32, 32) 

    def update(self): 
     pass 

class Platform1(Entity): 
    def __init__(self, x, y): 
     Entity.__init__(self) 
     self.image = Surface = pygame.image.load("GroundModels\Ground.png").convert() 
     self.rect = Rect(x, y, 32, 32) 

    def update(self): 
     pass 
#================stone 
class Stone(Entity): 
    def __init__(self, x, y): 
     Entity.__init__(self) 
     self.image = Surface = pygame.image.load("GroundModels\Stone.png").convert() 
     self.rect = Rect(x, y, 32, 32) 

    def update(self): 
     pass 

class Stone0(Entity): 
    def __init__(self, x, y): 
     Entity.__init__(self) 
     self.image = Surface = pygame.image.load("GroundModels\Stone0.png").convert() 
     self.rect = Rect(x, y, 32, 32) 

    def update(self): 
     pass 

class StoneBack(Entity): 
    def __init__(self, x, y): 
     Entity.__init__(self) 
     self.image = Surface = pygame.image.load("GroundModels\Stone.png").convert() 
     self.rect = Rect(x, y, 32, 32) 


class Bridge(Entity): 
    def __init__(self, x, y): 
     Entity.__init__(self) 

    def update(self): 
     pass 
#=================pusblokis zeme 
class HalfPlaform0(Entity): 
    def __init__(self, x, y): 
     Entity.__init__(self) 
     self.image = Surface = pygame.image.load("GroundModels\HalfGround0.png").convert() 
     self.rect = Rect(x, y + 16, 32, 16) 


    def update(self): 
     pass 


class ExitBlock(Platform): 
    def __init__(self, x, y): 
     Platform.__init__(self, x, y) 
     self.image.fill(Color("#0033FF")) 

if __name__ == "__main__": 
    main() 
+1

請只發布信息相關的代碼。 – PascalVKooten

回答

0

load_level功能需要一個level參數,但它絕不會使用它的任何地方。

相反,它的作用:現在

def load_level(level): 
    # ... 
    for row in levels: 
     for col in row: 

levels是水平,這是行,這是列的字符串列表清單。

但是你在做for row in levels,這意味着你命名每個級別row,然後for col in row名每一行的水平內一列,一整排的永遠不會是== "E"或任何其他的你檢查的東西。所以你找回一個空的平臺列表和一個空實體列表。

什麼你可能想要的是:

def load_level(level): 
    # ... 
    for row in levels[level]: 

後你解決這個問題:我不認爲你想離開精靈組entities滿1級的精靈,然後添加2級的精靈,然後是3級,依此類推,而不會將其清除。

但是,這正是你在做什麼。在main中,您將entities分配給一個空組。然後,在load_level的內部,您只需從外部函數entities調用add。然後你返回相同的entities,其main分配給entities,它已經是。

我想你想在load_level裏創建一個新的entities sprite組,就像你創建一個新的platforms列表一樣。 (如果不是,你絕對不希望修改外部變量的誤導性代碼然後返回它的值,只是爲了將它重新分配給相同的變量...做一個或另一個,而不是兩個。)

+0

嗯謝謝我也發現,但我現在當我的負載水平兩個級別都加載,然後我得到一些滯後。任何修復? – Justasmig

+0

@Justasmig:你確定兩個級別都加載了嗎?你肯定會第一次加載3次,這是很大的浪費。另外,正如我所提到的,每次加載一個關卡時,都會將其精靈添加到現有的精靈上,而不是替換現有的精靈。我敢打賭,還有其他一些缺陷,但是有太多的代碼試圖找到它們,然後猜測你首先看到哪一個。如果您有新問題,請創建一個新問題,然後嘗試爲該問題編寫一個[最小,完整,可驗證的示例](http://stackoverflow.com/help/mcve),而不是傾倒所有內容。 – abarnert

+0

我應該如何修復第一級加載3次?我現在想發佈一個關於優化的問題,但我認爲這是因爲我的代碼這樣做......而且我認爲我應該儘量寫最小化和完整。 – Justasmig