從0開始用python寫一個命令列小遊戲(二)

leosz發表於2019-02-16

我回來了!今天,我們真正會亮相的植物要出來了哦!還有,我們敵人的基礎類(我叫它BaseZombie)也會閃亮登(lai)場(xi)。很期待?那就開始吧!

注:我使用的是Python 3.7(但只要是3,變化應該都不大)。還有,這是第二篇。沒看過上篇的話,這是連結。閒話少說,進入正題!

兩種植物:SunflowerPeashooter

向日葵是Sunflower,豌豆射手是Peashooter。好,上程式碼!

向日葵

board = [0] * 10
sunlight = 50

class GameObject:
    indicating_char = ``       # 子類已經出現,所以把基礎類的顯示字元刪除
    pass                       # 剩餘部分同前

class Plant(GameObject):
    pass                       # 同前,但將顯示字元刪除

class Sunflower(Plant):
    """ 向日葵 """
    indicating_char = `s`
    
    def __init__(self, pos):
        """ 初始化,陽光50 """
        super().__init__(pos, 50)
    
    def step(self):
        """ 生產陽光 """
        global sunlight
        sunlight += 25

嗯,向日葵編好了。IPython(注:增強版Python shell),你怎麼看?

In [1]: import game as g

In [2]: g.sunlight
Out[2]: 50

In [3]: g.Sunflower(0)
Out[3]: s

In [4]: g.board[0].step()

In [5]: g.sunlight
Out[5]: 25                    # 種植向日葵損失50,它又產生25

成功!現在,該編豌豆射手了。

豌豆射手

class Peashooter(Plant):
    indicating_char = `p`
    
    def __init__(self, pos):
        super().__init__(pos, 100)           # 豌豆射手需要100陽光
    
    def step(self):
        for obj in board[self.pos:]:
            if isinstance(obj, BaseZombie):  # 就當BaseZombie存在
                pass                         # 哎呀!

好好程式設計,“哎呀”什麼?因為我突然發現,目前還沒有定義角色的生命值(你們盡情吐槽吧)!於是,在GameObject__init__方法前面追加:

class GameObject:
    blood = 10             # 初始生命值
    pass                   # 剩餘同前

然後又突然想到,角色死沒死不也是用這個定義的嗎?於是加了幾個方法和屬性:

class GameObject:
    indicating_char = ``
    blood = 10
    alive = True
    
    def __init__(self, pos):
        pass                   # 同前
    
    def step(self):
        pass
    
    def die(self):
        pass
    
    def check(self):
        if self.blood < 1:
            self.alive = False
    
    def full_step(self):
        self.check()
        if not self.alive:
            board[self.pos] = 0
            self.die()
        else:
            self.step()

好,現在把豌豆射手裡的那個pass改成:

for obj in board[self.pos:]:
    if isinstance(obj, BaseZombie):
        obj.blood -= 1.5            # 這裡原來是pass

但是因為沒有BaseZombie,我們也不能使用Peashooter。好,現在,3,2,1,放殭屍!

殭屍基礎類

我們即將親手創造遊戲中的大壞蛋:殭屍!來吧,面對這個基礎類······

class BaseZombie(GameObject):
    indicating_char = `b`
    
    def __init__(self, pos, speed, harm, die_to_exit=False):
        super().__init__(pos)
        self.speed = speed
        self.harm = harm
        self.die_to_exit = die_to_exit
    
    def step(self):
        if board[self.pos - self.speed] == 0:
            orig_pos = self.pos
            self.pos -= self.speed
            board[orig_pos] = 0
            board[self.pos] = self
        elif isinstance(board[self.pos - 1], Plant):
            board[self.pos - 1].blood -= 1
        else:
            self.pos -= 1
            board[self.pos + 1] = 0
            board[self.pos] = self
    
    def die(self):
        if self.die_to_exit:
            import sys
            sys.exit()

好,讓我們的新類們去IPython裡大展身手吧!

In [1]: import game as g

In [2]: def step():
   ...:     for obj in g.board:
   ...:         if isinstance(obj, g.GameObject):
   ...:             obj.step()
   ...: 

In [3]: g.Sunflower(0)

In [4]: step()

In [5]: step()

In [6]: step()

In [7]: step()

In [8]: g.sunlight
Out[8]: 100

In [9]: g.Peashooter(1)

In [10]: g.BaseZombie(9, 1, 1)

In [11]: step()

In [12]: step()

......
In [18]: step()

In [19]: g.board
Out[19]: [s, p, 0, 0, 0, 0, 0, 0, 0, 0]

看來,豌豆射手打敗殭屍了!

下集預告

下次,趕快把BaseZombie的子類編出來後,我們就要開始開發使用者介面了!歡迎來看!

相關文章