Pygame滚动地图

时间:2014-06-21 02:54:21

标签: python camera pygame

我正在做一个像流氓一样的人,当他在地图上移动时,我试图让玩家跟随玩家。

我能够使得绘图功能仅在贴片位于摄影机视口[灰色显示]内时才会发生,但我无法使相机停留在窗口的角落。

这是怎么回事: enter image description here

这是应该如何: enter image description here

有没有办法'裁剪'屏幕Surface,或者可能只复制相机视口内的什么内容并再次在屏幕上显示它。

可能我正在努力做到这一点。 我正在迭代整个地图,为每个图块创建一个矩形,并使用'.contains()'检查它是否在Camera Viewport Rect内。

编辑: 这就是我绘制地图的方式:

for x in xrange(mymap.width):
    for y in xrange(mymap.height):
        lit = field_of_view.lit(x, y)
        visited = field_of_view.visited(x, y)
        graphic = mymap.tileAt(x, y).graphic
        if lit:
            color = mymap.tileAt(x, y).color
        elif visited:
            color = GRAY
        else:
            color = BLACK
        renderedgraphic = myfont.render(graphic, 1, color)
        screen.blit(renderedgraphic, (x*TILESIZE, y*TILESIZE))

我为玩家,怪物,物品等做同样的事情,但其中的一切都是自己的类方法。

我的相机设置如下:

class Camera(Object):
    def __init__(self, x, y):
        graphic = ''
        Object.__init__(self, graphic, x, y)
        self.rect = pygame.Rect(x, y, CAMERA_WIDTH * 2 + 5, CAMERA_HEIGHT * 2 + 5)

    def update(self):
        self.x = PLAYER.x
        self.y = PLAYER.y

        startx = ((self.x * TILESIZE) - CAMERA_WIDTH) + 5
        starty = ((self.y * TILESIZE) - CAMERA_HEIGHT) + 5
        self.rect = pygame.Rect(startx, starty, CAMERA_WIDTH * 2 + 5, CAMERA_HEIGHT * 2 + 5)

所以我尝试了user3762084所说的内容。

简而言之:

for x in xrange(mymap.width):
    for y in xrange(mymap.height):
        ... # do fov stuff        
        tile = Tile.At(x, y)  # get tile instance
        if tile:
            tile.update() # update it's relative position
            screen.blit(renderedgraphic, (tile.relX * TILESIZE, tile.relX * TILESIZE)) # blit the postion to it's relative position

这就是:

enter image description here

窗户旁边都被挤压了。如果玩家移动它全部变黑。

2 个答案:

答案 0 :(得分:2)

在制作滚动环境之前我所做的是为每个对象提供世界上的坐标,然后给你的相机一个位置。在绘图时,您可以根据对象的实际坐标和相机的坐标计算屏幕上每个对象的位置。

class Tile:
    def __init__(self, x, y, other_variables):
        self.x = x
        self.y = y

        # relative vars for later
        self.relX = None
        self.relY = None

# then your camera should have a position as well as its width and height:
class Camera:
    def __init__(self, x, y, width, height):
        # assign those variables here

# your drawing function:
for tile in tiles:
    tile.relX = tile.x - camera.x
    tile.relY = tile.y - camera.y
    # blit your tiles to the screen at the relative coordinates

此外,您还可以实施检查以查看图块是否完全位于相机空间之外,而不是绘制这些图块。

答案 1 :(得分:1)

好的,我得到了我想要的东西,我做了一个小黑客。所以,如果有人有更好的方法来做到这一点。

我改变了地图的绘制方式

  • 我采用了Camera Rect位置[topleft and bottomright];
  • 将其转换为世界位置;
  • 使用枚举器迭代它;
  • 是否有任何点燃/访问过的FOG与X和Y的关系;
  • 使用点查员在屏幕上显示' i'和' j'。

以下是代码:

topleft = Map.toWorld(camera.rect.topleft)
bottomright = Map.toWorld(camera.rect.bottomright)
for i, x in enumerate(xrange(topleft[0], bottomright[0])):
    for j, y in enumerate(xrange(topleft[1], bottomright[1])):
        tile = mymap.tileAt(x, y)
        object = [obj for obj in Object.OBJECTS if obj.pos == (x,y)]
        if tile:
            lit = field_of_view.lit(x, y)
            visited = field_of_view.visited(x, y)
            graphic = tile.graphic
            if lit:
                color = tile.color
            elif visited:
                color = GRAY
            else:
                color = BLACK
            renderedgraphic = myfont.render(ch, 1, graphic)
            screen.blit(renderedgraphic, Map.toScreen((i + 1, j)))
        if object:
            Draw.drawObject(object[0], Map.toScreen((i + 1, j)))

现在唯一的问题是,当玩家位于地图的两侧时,它会显示黑色边框。