好的,所以我正在用pygame做一个小游戏,并通过生成多维数组的图块来构建地图。为了做到这一点,我使用两个for循环。
def create(this, t):
if t == "grasslands":
for j in range(0, this.numRows):
for i in range(0, this.numColumns):
this.column.append(this.Tile("grass", j * this.tileWidth, i * this.tileHeight))
this.row.append(this.column)
j * this.tileWidth 的值正在正确传递到Tile初始化。虽然列[无论] .x 值仍为0. y 值设置得很好,如果我使用 i 或任何其他价值而不是 j 事情就好了。这是我做错了什么还是用Python来解决的问题?
mapgen.py
import pygame
from sprite import *
from assets import *
class mapG:
def __init__(this, resw, resh):
this.numRows = 3
this.numcolumns = 3
this.tileWidth = 128
this.tileHeight = 128
this.row = []
this.column = []
this.width = this.numRows * this.tileWidth
this.height = this.numcolumns * this.tileHeight
def create(this, t):
if t == "grasslands":
for j in range(0, this.numRows):
for i in range(0, this.numcolumns):
this.column.append(this.Tile("grass", j * this.tileWidth, i * this.tileHeight))
this.row.append(this.column)
def tileAt(this, x, y):
pass
def moveRight(this):
for j in range(0,this.numRows):
for i in range(0, this.numcolumns):
this.row[j][i].incX(1)
def Update(this, src):
for j in range(0,this.numRows):
for i in range(0, this.numcolumns):
this.row[j][i].Update(src)
print(this.row[j][i].y, this.row[j][i].x)
class Tile:
def __init__(this, name, xpos, ypos):
this.y = ypos
this.x = xpos
this.image = assets.tile[name + ".png"]
this.sprite = sprite(this.image, this.x, this.y, 100, 100)
def incX(this, amount):
this.sprite.IncX(amount)
def decX(this, amount):
this.sprite.DecX(amount)
def incY(this, amount):
this.sprite.IncY(amount)
def decY(this, amount):
this.sprite.DecY(amount)
def Update(this, src = None):
if src != None:
this.sprite.Update(src)
sprite.py
import pygame
import assets
class sprite:
def __init__(this, image, xpos, ypos, width = None, height = None):
this.image = image
this.x = xpos
this.y = ypos
this.width = width
this.height = height
if this.width != None and this.height != None:
this.image = pygame.transform.scale(image, (this.width,this.height))
def GetPos(this):
return (this.x, this.y)
def IncX(this, amount):
this.x += amount
def IncY(this, amount):
this.y += amount
def DecX(this, amount):
this.x -= amount
def DecY(this, amount):
this.y -= amount
def Update(this, src = None):
if src != None:
src.blit(this.image, this.GetPos())
答案 0 :(得分:5)
我相信您遇到的问题来自于您使用this.column
方法中的create
变量。
您只需创建一个列列表(在__init__
中),然后将其重新用于地图的所有列。这不起作用。
您的this.row
列表最终会对同一列列表进行多次引用,最终会包含您创建的所有Tile
个对象。您之后只能看到其中的一些,因为您的迭代代码使用预定义的维度,而不是实际迭代整个列表。
要理解这一点,请尝试设想2x2网格的迭代进度(忽略切片尺寸)。我将每个i
和j
值放在它自己的行上以显示它的进展情况,并在每个步骤后给出row
和columns
的值:
j=0:
i=0:
column.append(Tile(i, j))
# column is [Tile(0, 0)]
# row is []
i=1:
column.append(Tile(i, j))
# column is [Tile(0, 0), Tile(0, 1)]
# row is []
row.append(column)
# column is [Tile(0, 0), Tile(0, 1)]
# row is [[Tile(0, 0), Tile(0, 1)]]
j=1: # column is not reset!
i=0:
column.append(Tile(i, j))
# column is [Tile(0, 0), Tile(0, 1), Tile(1, 0)]
# row is [[Tile(0, 0), Tile(0, 1), Tile(1, 0)]]
i=1:
column.append(Tile(i, j))
# column is [Tile(0, 0), Tile(0, 1), Tile(1, 0), Tile(1, 1)]
# row is [[Tile(0, 0), Tile(0, 1), Tile(1, 0), Tile(1, 1)]]
row.append(column)
# column is [Tile(0, 0), Tile(0, 1), Tile(1, 0), Tile(1, 1)]
# row is [[Tile(0, 0), Tile(0, 1), Tile(1, 0), Tile(1, 1)],
# [Tile(0, 0), Tile(0, 1), Tile(1, 0), Tile(1, 1)]]
row
列表包含两个对四个图块的column
列表的引用。您的代码曾打算将前两个Tile(0, 0)
和Tile(0,1)
添加到第一列,然后将最后两个切片Tile(1, 0)
和Tile(1, 1)
添加到第二列。但是因为两次使用相同的列表,所以你最终得到了所有的值,然后重复了一堆。迭代时,您只能看到上图左侧的重复值。
以下是修复方法:
def create(this, t):
if t == "grasslands":
for j in range(0, this.numRows):
column = [] # Create a new list! This is the key!
for i in range(0, this.numColumns):
column.append(this.Tile("grass",
j * this.tileWidth,
i * this.tileHeight))
this.row.append(column)
您可以删除构造函数中初始化self.column
的行。它只是暂时需要的,所以不需要使用实例变量。
答案 1 :(得分:0)
您最终不会创建宽度为3的行(numColumns
)。最终会得到宽度为9(行* cols)的行,因为每次循环都不会创建新行。
你的循环应如下所示:
for j in range(0, this.numRows):
row=[]
for i in range(0, this.numColumns):
row.append(this.Tile("grass", j * this.tileWidth, i * this.tileHeight))
this.rows.append(row)
然后你可能在调试它时最终查看了错误的数据,没有意识到行的长度超出了你的预期。 (名字也有点令人困惑,所以我稍微改了一下。)