示例#1
0
class Game:
    def __init__(self, data):
        self._data = data
        self._score = Score()

        self._category = None
        self._iter_category = None
        self._word = Word()

    def displayCategory(self):
        cat = self._data.getHeadCategorys()
        View.displayCategory(cat)

    def selectCategory(self, category_id=0):
        head = self._data.getHeadCategorys()
        category = self._data.getCategory(head[category_id])
        self._category = Category(category)
        self._iter_category = iter(self._category)

    def inputCategory(self):
        category_id = input(">> ")
        try:
            category_id = int(category_id)
        except ValueError:
            print('press key integer')
            self.inputCategory()

        head = self._data.getHeadCategorys()
        if not category_id in range(head.__len__()):
            print('press key in range')
            self.inputCategory()

        return category_id

    def genWord(self):
        try:
            self._word = next(self._iter_category)
            return True
        except StopIteration:
            return False

    def displayHint(self):
        View.displayHint(self._word.getHint(), self._category.getCurIndex())

    def displayAskWord(self, char='', wrong=False):
        askword = self._word.getAskWord()
        score = self._score.getScore()
        wrong_guess = self._score.getWrongGuess()
        View.displayAskWord(askword, score, wrong_guess, char, wrong)

    def checkAskWord(self, char=''):
        hint_word = self._word.checkAskWord(char)
        if hint_word:
            self._score.addScore()
            return True
        elif self._score.getScore() == 0:
            self._score.delWrongGuess()
        else:
            self._score.delWrongGuess()
            self._score.delScore()

        return False

    def displayBye(self):
        score = self._score.getScore()
        View.displayBye(score)

    def isEndGame(self):
        return self._score.getWrongGuess() == 0 or self._category.isStop()

    def isWordPass(self):
        return self._word.isPass()
示例#2
0
class Game:
    """ 游戏 """
    def __init__(self, screen):
        """ 初始化 """
        self._screen = screen  # 屏幕画面
        self._gameState = GameState.start  # 游戏状态 0:开始画面; 1:游戏中; 2:游戏结束
        self._frameCount = 0  # 每个游戏状态的帧数计数
        self._score = Score(self)  # 分数系统

        # 游戏元素
        self._startScene = StartScene()
        self._gameoverScene = GameoverScene(self)
        self._dinosaur = Dinosaur(self)
        self._cactusGroup = pygame.sprite.RenderPlain()
        self._birdGroup = pygame.sprite.RenderPlain()
        self._terrian = Terrian(self)
        self._cloudGroup = pygame.sprite.RenderPlain()
        self._moon = Moon(self)
        self._starGroup = pygame.sprite.RenderPlain()

        # 控制难度的变量
        self._lastEnemyFrameCount = 0  # 上一次出现敌人的帧数计数
        self._curEnemeyProbability = Settings.enemyInitProbability  # x,当前每帧敌人出现的概率为1/x
        self._curEnemyMinFrameInterval = Settings.enemyInitMinFrameInterval  # 当前敌人最小帧数间隔
        self._curTerrianSpeed = Settings.terrianInitSpeed  # 当前地形移动速度

        # 控制环境的变量
        self._lastCloudFrameCount = Settings.cloudFrameInterval  # 上一次出现云的帧数计数
        self._isDay = True  # 是否白天
        self._dayNightFrame = Settings.dayNightChangeFrame  # 自从白天/黑夜开始的帧数,初始值不为0,因为开始无需昼夜交替

    @property
    def curShowScore(self):
        """ 获取当前展示分数 """
        return self._score.curShowScore

    @property
    def curTerrianSpeed(self):
        """ 获取当前地形移动速度 """
        return self._curTerrianSpeed

    def showNightImage(self):
        """ 是否显示夜晚图像 """
        if self._isDay:
            return self._dayNightFrame < Settings.dayNightChangeFrame - Settings.dayToNightChangeColorFrame
        return self._dayNightFrame >= Settings.dayToNightChangeColorFrame

    def handleEvents(self):
        """ 处理事件 """
        self._frameCount += 1
        for event in pygame.event.get():
            if event.type == pygame.QUIT:
                sys.exit()
            if self._gameState == GameState.start:
                if event.type == pygame.KEYDOWN and event.key == pygame.K_SPACE:
                    self._gameState = GameState.running
                    self._frameCount = 0
            elif self._gameState == GameState.running:
                if event.type == pygame.KEYDOWN:
                    if event.key == pygame.K_SPACE:
                        self._dinosaur.startUp()
                    elif event.key == pygame.K_DOWN:
                        self._dinosaur.startDown()
                    elif event.key == pygame.K_UP:
                        self._dinosaur.startUp()
                elif event.type == pygame.KEYUP:
                    if event.key == pygame.K_DOWN:
                        self._dinosaur.endDown()
                    elif event.key in (pygame.K_SPACE, pygame.K_UP):
                        self._dinosaur.endUp()
            else:
                if event.type == pygame.KEYDOWN and event.key == pygame.K_SPACE:
                    if self._frameCount >= Settings.restartMinFrameCount:
                        self._restart()

    def updateAndDraw(self):
        """ 更新并绘制 """
        def update():
            """ 更新游戏元素和状态 """
            self._terrian.update()
            self._updateClouds()
            self._moon.update()
            self._updateStars()
            self._updateEnemies()
            self._dinosaur.update()
            self._score.addScore(self._curTerrianSpeed)
            self._updateDayNight()
            self._updateDifficulty()

        def showGameScene():
            """ 显示当前帧 """
            colorValue = round(
                255 *
                min(self._dayNightFrame / Settings.dayNightChangeFrame, 1))
            if not self._isDay:
                colorValue = 255 - colorValue
            self._screen.fill(rect=self._screen.get_rect(),
                              color=(colorValue, colorValue, colorValue))

            if not self._isDay and self._dayNightFrame > Settings.dayToNightMoonShowFrame:
                self._starGroup.draw(self._screen)
                self._moon.draw(self._screen)
            self._terrian.draw(self._screen)
            self._cloudGroup.draw(self._screen)
            self._cactusGroup.draw(self._screen)
            self._birdGroup.draw(self._screen)
            self._dinosaur.draw(self._screen)
            self._score.draw(self._screen)

        def handleCollision():
            """ 处理碰撞 """
            if self._detectCollision():
                self._dinosaur.die()
                self._gameState = GameState.gameover
                self._frameCount = 0

        if self._gameState == GameState.start:
            self._startScene.draw(self._screen)
        elif self._gameState == GameState.running:
            update()
            showGameScene()
            handleCollision()
        else:
            if self._frameCount <= 1:  # 只需显示一次
                showGameScene()
                self._gameoverScene.draw(self._screen)
        pygame.display.update()

    def _updateEnemies(self):
        """ 更新敌人 """
        self._cactusGroup.update()
        for cactus in self._cactusGroup.copy():
            if cactus.rect.right < 0:
                self._cactusGroup.remove(cactus)
        self._birdGroup.update()
        for bird in self._birdGroup.copy():
            if bird.rect.right < 0:
                self._birdGroup.remove(bird)

        self._lastEnemyFrameCount += 1
        if self._lastEnemyFrameCount > self._curEnemyMinFrameInterval and\
                (random.randint(0, round(self._curEnemeyProbability)) == 0 or
                 self._lastEnemyFrameCount >= self._curEnemeyProbability):
            if self.curShowScore < Settings.birdScore or random.randint(
                    0, 2) <= 1:
                self._cactusGroup.add(Cactus(self))
            else:
                self._birdGroup.add(Bird(self))
            self._lastEnemyFrameCount = 0

    def _updateClouds(self):
        """ 更新云群 """
        self._cloudGroup.update()
        for cloud in self._cloudGroup.copy():
            if cloud.rect.right < 0:
                self._cloudGroup.remove(cloud)

        self._lastCloudFrameCount += 1
        if self._lastCloudFrameCount > Settings.cloudFrameInterval and\
                random.randint(0, Settings.cloudProbability) == 0:
            self._cloudGroup.add(Cloud(self))
            self._lastCloudFrameCount = 0

    def _updateStars(self):
        """ 更新星群 """
        self._starGroup.update()
        for star in self._starGroup.copy():
            if star.rect.right < 0:
                self._starGroup.remove(star)

        if random.randint(0, Settings.starProbability) == 0:
            self._starGroup.add(Star(self))

    def _updateDayNight(self):
        """ 更新日夜状态 """
        curIsDay = (self.curShowScore < Settings.dayNightScore) or\
                   (self.curShowScore % Settings.dayNightScore > Settings.nightScore)
        if curIsDay == self._isDay:
            self._dayNightFrame += 1
        else:
            self._isDay = curIsDay
            self._dayNightFrame = max(
                Settings.dayNightChangeFrame - self._dayNightFrame, 0)
            if curIsDay:
                self._moon.nextPhase()

    def _updateDifficulty(self):
        """ 更新难度参数 """
        self._curEnemeyProbability = Settings.enemyInitProbability +\
            (Settings.enemyMaxProbability - Settings.enemyInitProbability) /\
            Settings.maxDifficultyScore * self.curShowScore
        self._curEnemeyProbability = max(self._curEnemeyProbability,
                                         Settings.enemyMaxProbability)

        self._curEnemyMinFrameInterval = Settings.enemyInitMinFrameInterval +\
            (Settings.enemyMinMinFrameInterval - Settings.enemyInitMinFrameInterval) /\
            Settings.maxDifficultyScore * self.curShowScore
        self._curEnemyMinFrameInterval = max(self._curEnemyMinFrameInterval,
                                             Settings.enemyMinMinFrameInterval)

        self._curTerrianSpeed = Settings.terrianInitSpeed +\
            (Settings.terrianMaxSpeed - Settings.terrianInitSpeed) / Settings.maxDifficultyScore * self.curShowScore
        self._curTerrianSpeed = min(self._curTerrianSpeed,
                                    Settings.terrianMaxSpeed)

    def _detectCollision(self) -> bool:
        """ 检测碰撞 """
        return pygame.sprite.spritecollide(self._dinosaur, self._cactusGroup, False, pygame.sprite.collide_mask) or\
            pygame.sprite.spritecollide(self._dinosaur, self._birdGroup, False, pygame.sprite.collide_mask)

    def _restart(self):
        """ 重开游戏 """
        self._gameState = GameState.running
        self._frameCount = 0
        self._score.setScore(0)
        self._dinosaur.restart()
        self._cactusGroup.empty()
        self._birdGroup.empty()
        self._lastEnemyFrameCount = 0
        self._curEnemeyProbability = Settings.enemyInitProbability
        self._curEnemyMinFrameInterval = Settings.enemyInitMinFrameInterval
        self._curTerrianSpeed = Settings.terrianInitSpeed