Как установить лимит времени для игры?

1

Я запрограммировал игру, которая берет имя песни и исполнителя из внешнего файла. Программа печатает имя исполнителя, но маскирует название песни, и пользователь должен правильно угадать заголовок, чтобы заработать очки. Это отлично работает, но я хочу добавить ограничение по времени, поэтому у них есть только 60 секунд, чтобы получить максимальный результат, который они могут сделать.

Вот часть кода, на который я ссылаюсь:

def pickSong_random():
  score=0
  lives=5
  songFile = open("F_Songs.txt","r")
  songList = songFile.readlines() #Reads from the bridged file
  songFile.close()
  while True:
    chosenSong = random.choice(songList)

    chosenSong = chosenSong.strip("\n")
    artistAndSong = chosenSong.split(":") #Defines song split

    toDisplay = ""
    toDisplay += artistAndSong[0] + ": "
    songTitleWords = artistAndSong[1].split(" ")

    for word in songTitleWords:
      #loop through
      toDisplay += word[0] + " "
    print(toDisplay)
    #print("2" +toDisplay)
    toDisplay = toDisplay.strip("None")
    guesses = 0
    while guesses <2:
        guesses += 1
        guess = input("[Guess]: ")

        #Guess checking
        if guess.lower() == artistAndSong[1].lower():
            print("Correct! The song was " + artistAndSong[1] + " by " + artistAndSong[0])
            print("It took you", guesses, "guess(es)!")
            if guesses == 1:
                print ("(+3 points)")
                print("\n")
                score += 3
                break
            elif guesses == 2:
                print ("(+1 point)")
                print("\n")
                score += 1
                break
        else:
            print("That incorrect, guess again.\n")
            lives = lives-1
        if lives == 0:
          print ("You have no more lives to continue! Your score was:",score)
          time.sleep(3)
          slow_print ("Would you like to play again?")
          playAgain = input("[Y/N]: ")
          if playAgain == ("n") or playAgain == ("N"):
            sys.exit()
          if playAgain == ("Y") or playAgain == ("y"):
            print ("Your last score was",score,", lets see if you can beat it this time...")
            time.sleep(1)
            print ("\n")
            pickSong_random()

Я пробовал играть с этой концепцией, но пока не повезло:

import time
countdown=True
time=60
while countdown == True:
    time = time-1
    time.sleep(1.0)
    print (time)
    countdown=True
    if time == 0:
        print ("You've ran out of time!")

UPDATE 1 Мой код проектов теперь сильно изменился

#Casey_Neale
import sys
import random
import time
import math
import csv
import time, sys
newaccounts=True
loggedIn=False
yn=True

def tutorial(): #Games introduction
  slow_print("Your aim is to get as many points as possible...")
  print("\n")
  time.sleep(1.5)
  slow_print("You need to guess the name of each song to gain points...")
  print("\n")
  time.sleep(1.5)
  slow_print("You have two guesses for each song...")
  print("\n")
  time.sleep(1.5)
  slow_print ("The artist name is provided for you...")
  time.sleep(0.5)
  print("\n")

def slow_print(s):
  for c in s:
    sys.stdout.write( '%s' % c )
    sys.stdout.flush()
    time.sleep(0.03)

def leaderboard():
  print ("\n")
  print (" Check out the leaderboard ") #LEADERBOARD SECTION
  f = open('H_Highscore.txt', 'r')
  leaderboard = [line.replace('\n','') for line in f.readlines()]
  for i in leaderboard:
      print(i)
  f.close()
  time.sleep(10)
  sys.exit()

def loginsys():
  doublecheck=True
  while doublecheck == True:
    verifyRegister = input ("Welcome | Are you a registered user?\n[Y/N]: ")
    print (" ")
    if verifyRegister == "n" or verifyRegister == "N":  #If the user is not already registered
      if newaccounts == True:
        loop=True
        while loop == True:
            username = input ("Please enter a username\n[User]: ")#Prompts the user to provide a desired username
            print (" ")#Prompts for username
            checkusername = input ("Please retype your username\n[Verify]: ")#Verifys username
            print (" ")#Prompts to verify username
            if checkusername != username:
              print ("Invalid, please try again")
              loop=True
            else:
              loop=False       
              time.sleep(0.5)
              passloop=True
              while passloop == True:
                      password = input ("Please enter a password\n[Password]: ") #Prompts the user to provide a desired password
                      print (" ")#Prompts for password
                      checkpassword = input ("Please retype your password\n[Verify]: ") #Verifys password
                      print (" ")#Prompts to verify password
                      if checkpassword != password:
                        print ("Invalid, please try again")
                        print (" ")
                        passloop=True
                      else:
                        passloop=False
                        file = open("C_AccountData.txt","a") #Opens the file C_AccountData.txt in write mode/opens connection
                        file.write("USRN:") #Prefix Username to make the file easier to read
                        file.write(username) #Writes the username 
                        file.write("|") #Partition for visual ease to make the file easier to read
                        file.write("PSWD:") #Prefix Password to make the file easier to read
                        file.write(password)#Writes the password
                        file.write("\n") #New line to make the file easier to read
                        file.close() #Closes file/ends connection
                        print ("✓Your account has been created") #Verifies that the account has been made to the user
                        time.sleep(2)
                        print ("\n")
                        doublecheck=True #Loop

    if verifyRegister == "Y" or verifyRegister == "y":
      loop=True
      if loop == True:
          user = input("[User]: ")
          passw = input("[Password]: ")
          f = open("C_AccountData.txt", "r")
          for line in f.readlines():
            uspwd = line.split("|")
            us = uspwd[0]
            pw = uspwd[1]
            if (user in us) and (passw in pw):
              loop=False
              print("Login successful, welcome",user)
              doublecheck=False
          else:
            if loop == True:
                  print ("\n")
                  print ("Sorry, your account details were not recognised. ")

    else:
      if verifyRegister != "Y" or verifyRegister != "y" or verifyRegister != "N" or verifyRegister != "n" or verifyRegister !="backup":
        print("\n")
        doublecheck=True

def pickSong_random():
  score=0
  lives=5
  songFile = open("F_Songs.txt","r")
  songList = songFile.readlines() #Reads from the bridged file
  songFile.close()
  while True:
    chosenSong = random.choice(songList)

    chosenSong = chosenSong.strip("\n")
    artistAndSong = chosenSong.split(":") #Defines song split

    toDisplay = ""
    toDisplay += artistAndSong[0] + ": "
    songTitleWords = artistAndSong[1].split(" ")

    for word in songTitleWords:
      #loop through
      toDisplay += word[0] + " "
    print(toDisplay)
    #print("2" +toDisplay)
    toDisplay = toDisplay.strip("None")
    guesses = 0
    while guesses <2:
        guesses += 1
        guess = input("[Enter your guess]: ")

        #Guess checking
        if guess.lower() == artistAndSong[1].lower():
            print("✓Correct! The song was " + artistAndSong[1] + " by " + artistAndSong[0])
            print("It took you", guesses, "guess(es)!")
            if guesses == 1:
                print ("\n")
                print ("(+3 points)")
                print("\n")
                score += 3
                break
            elif guesses == 2:
                print ("\n")
                print ("(+1 point)")
                print("\n")
                score += 1
                break
        else:
            print("The song name isn't",guess,"\n")
            lives = lives-1
            if guesses == 2:
              print ("Sorry, you couldn't guess the song.")
              print ("\n")
        if lives == 0:
          print ("You have no more lives to continue! Your score was:",score)
          time.sleep(3)
          print("\n")
          slow_print ("Would you like to play again?")
          playAgain = input("\n[Y/N]: ")
          if playAgain == ("n") or playAgain == ("N"):
            print ("\n")
            user = str(input("Enter a name to save your highscore: ")) #user variable is not saved from the login system as it is defined as a function separately
            file = open ("H_Highscore.txt","a")
            file.write(user)
            file.write(",")      
            file.write(str(score)) #(int(x)) can not be written
            file.write("pts")
            file.write("\n")
            file.close()
            time.sleep(0.5)
            leaderboard()
            sys.exit()
          if playAgain == ("Y") or playAgain == ("y"):
            print ("Your last score was",score,", lets see if you can beat it this time...")
            time.sleep(1)
            print ("\n")
            pickSong_random()
loginsys() #LOGIN PROTOCOL
time.sleep(3)
print("\n")
tutorial() #TUTORIAL PROTOCOL
slow_print ("Prepare yourself! The game will begin in...\n")
time.sleep(0.5)
print("\n")
slow_print("5...")
time.sleep(0.5)
print("\n")
slow_print("4...")
time.sleep(0.5)
print("\n")
slow_print ("3...")
time.sleep(0.5)
print("\n")
slow_print ("2...")
time.sleep(0.5)
print("\n")
slow_print ("1...")
time.sleep(0.5)
print("\n")

pickSong_random() #GAME PROTOCOL
sys.exit() #EXIT PROTOCOL
  • 1
    Вызов sleep() просто останавливает весь ваш скрипт. Вместо этого я бы предложил использовать класс threading.Timer который будет работать одновременно в фоновом режиме и позволять вашему сценарию продолжать выполнение. Объект Timer будет вызывать функцию по вашему выбору, чтобы сообщить игровой части вашего скрипта, когда закончится время.
Теги:
timer

4 ответа

0
Лучший ответ

Вот как это сделать с помощью класса threading.Timer() я предложил в комментарии. Они могут быть настроены так, чтобы задерживать определенное количество времени и вызов как функцию по вашему выбору.

В приведенном ниже коде я определил функцию обратного вызова с именем timeout() и глобальную переменную с именем time_ran_out, для которой устанавливается значение True по истечении таймера. Там есть комментарии в добавленном коде, описывающие, что делается. Все, что делает функция обратного вызова, это устанавливает значение переменной. Другой код в функции pickSong_random() проверяет значение этой переменной, чтобы определить, была ли вызвана функция обратного вызова или нет.

Хорошая вещь об экземплярах Timer (и функциях, которые они вызывают) заключается в том, что их выполнение происходит в фоновом режиме, параллельно основному потоку, в котором выполняется сама игра, поэтому их использование не сильно влияет на выполнение игры или код.

Заметьте, я также переформатировал ваш код, чтобы он соответствовал руководству по стилю PEP 8 - Руководствам по коду Python, чтобы, на мой взгляд, он был намного более читабельным (и с ним легче работать).

import random
import sys
import time
from threading import Timer

TIMELIMIT = 10.0  # Seconds (set low for testing).


def slow_print(s):
    for c in s:
        sys.stdout.write('%s' % c)
        sys.stdout.flush()
        time.sleep(0.03)


def pickSong_random():
    # Local Timer callback function.
    def timeout():
        nonlocal time_ran_out  # Reference variable defined in enclosing scope
                               # (so a local one isn't created automatically).
        time_ran_out = True

    score = 0
    lives = 5
    songFile = open("F_Songs.txt", "r")
    songList = songFile.readlines() # Reads from the bridged file
    songFile.close()

    while True:
        chosenSong = random.choice(songList)
        chosenSong = chosenSong.strip("\n")
        artistAndSong = chosenSong.split(":") # Defines song split

        toDisplay = ""
        toDisplay += artistAndSong[0] + ": "
        songTitleWords = artistAndSong[1].split(" ")

        for word in songTitleWords:
            # loop through
            toDisplay += word[0] + " "
        print(toDisplay)
        # print("2" +toDisplay)
        toDisplay = toDisplay.strip("None")

        guesses = 0
        timer = Timer(TIMELIMIT, timeout)  # Create a timer thread object.
        time_ran_out = False  # Define local variable the callback function modifies.

        timer.start()  # Start the background timer.
        while guesses < 2:
            if time_ran_out:
                print('Times up!')
                break

            guesses += 1
            guess = input("[Enter your guess]: ")

            # Guess checking
            if guess.lower() == artistAndSong[1].lower():
                print("✓Correct! The song was " + artistAndSong[1]
                        + " by " + artistAndSong[0])
                print("It took you", guesses, "guess(es)!")
                if guesses == 1:
                    print("\n")
                    print("↑(+3 points)↑")
                    print("\n")
                    score += 3
                    break
                elif guesses == 2:
                    print("\n")
                    print("↑(+1 point)↑")
                    print("\n")
                    score += 1
                    break
            else:
                print("╳The song name isn't", guess, "\n")
                lives = lives-1
                if guesses == 2:
                    print("Sorry, you couldn't guess the song.")
                    print("\n")
            if lives == 0:
                print("You have no more lives to continue! Your score was:", score)
                time.sleep(3)
                print("\n")
                slow_print("Would you like to play again?")
                playAgain = input("\n[Y/N]: ")
                if playAgain == ("n") or playAgain == ("N"):
                    print("\n")
                    # user variable is not saved from the login system as it is
                    # defined as a function separately
                    user = str(input("Enter a name to save your highscore: "))
                    file = open ("H_Highscore.txt", "a")
                    file.write(user)
                    file.write(",")
                    file.write(str(score)) # (int(x)) can not be written
                    file.write("pts")
                    file.write("\n")
                    file.close()
                    time.sleep(0.5)
                    leaderboard()
                    sys.exit()
                if playAgain == ("Y") or playAgain == ("y"):
                    print("Your last score was", score,", lets see if you can beat it this time...")
                    time.sleep(1)
                    print("\n")
                    pickSong_random()

if __name__ == '__main__':
    pickSong_random()
  • 0
    Я попытался запустить код, но, к сожалению, он не работает.
  • 0
    Пожалуйста, попробуйте обновленную версию - проблема, возможно, была из-за моей первоначальной попытки использовать вложенную функцию и глобальную переменную - похоже, работает для меня.
Показать ещё 1 комментарий
0

Просто запишите время начала и перерыв от вашей циклы, если время наступает. Спящий, вы делаете свою спящую программу, и пользователь ничего не может сделать. Таким образом, "быстрота" не имеет никакого значения, потому что вы не можете ничего делать, пока программа спит:

import random 
import datetime
correct = 0
start = datetime.datetime.now()
while True:
    print("Math test. Add , dont screw up, you got {}s left".
          format(20-(datetime.datetime.now()-start).seconds)) 
    a,b = random.choices(range(1,20),k=2)
    c = input("  {:>2} + {:>2} = ".format(a,b))

    if (datetime.datetime.now()-start).seconds > 20:
        print("Times up. Score: {}".format(correct))
        break
    try: 
        if a+b == int(c): 
            correct += 1
            print("Correct")
        else:
            print("Wrong")
    except:
        print("Wrong")

Выход:

Math test. Add , dont screw up, you got 20s left
  17 +  8 = 23
Wrong
Math test. Add , dont screw up, you got 18s left
  10 +  2 = 12
Correct
Math test. Add , dont screw up, you got 14s left
   1 +  7 = 8
Correct
Math test. Add , dont screw up, you got 12s left
   5 + 19 = 24
Correct
Math test. Add , dont screw up, you got 8s left
   4 +  3 = 7
Correct
Math test. Add , dont screw up, you got 5s left
   3 + 18 = 21
Correct
Math test. Add , dont screw up, you got 3s left
  15 + 12 = 27
Correct
Math test. Add , dont screw up, you got 1s left
   7 +  8 = 15
Times up. Score: 6 
0

Оказывается, вы фактически переназначили модуль "время" на целое число 60, перезаписывая библиотеку, поэтому у него не было атрибута ".sleep()". Также обратный отсчет не имеет значения и немного избыточен. В любом случае, этот отредактированный бит кода работал для меня:

import time
sec=60
while sec != 0:            
    print(sec)
    sec = sec-1
    time.sleep(1)
print ("You've ran out of time!")

Надеюсь это поможет!

0

Хотя у Om Agarwal может быть возможное решение, вы также можете рассмотреть возможность использования неблокирующего подхода в своей игре с использованием встроенного времени pygame.

start_ticks = pygame.time.get_ticks()
while guesses < 2:
    # OTHER GAME CODE HERE
    seconds = (pygame.time.get_ticks() - start_ticks) / 1000
    if seconds > 60:
        print ("You've ran out of time!")
        break

Ура!

Редактировать 1: Добавлена модификация примера.

import pygame
import time
import random
import sys


def pickSong_random():
    score = 0
    lives = 5
    songFile = open("F_Songs.txt", "r")
    songList = songFile.readlines()  # Reads from the bridged file
    songFile.close()
    while True:
        chosenSong = random.choice(songList)

        chosenSong = chosenSong.strip("\n")
        artistAndSong = chosenSong.split(":")  # Defines song split

        toDisplay = ""
        toDisplay += artistAndSong[0] + ": "
        songTitleWords = artistAndSong[1].split(" ")

        for word in songTitleWords:
            # loop through
            toDisplay += word[0] + " "
        print(toDisplay)
        # print("2" +toDisplay)
        toDisplay = toDisplay.strip("None")
        guesses = 0
        start_ticks = pygame.time.get_ticks()
        while guesses < 2:
            guesses += 1
            guess = input("[Guess]: ")

            seconds = (pygame.time.get_ticks() - start_ticks) / 1000

            if seconds > 60:
                print("You've ran out of time!")
                break

            # Guess checking
            if guess.lower() == artistAndSong[1].lower():
                print("Correct! The song was " + artistAndSong[1] + " by " + artistAndSong[0])
                print("It took you", guesses, "guess(es)!")
                if guesses == 1:
                    print("(+3 points)")
                    print("\n")
                    score += 3
                    break
                elif guesses == 2:
                    print("(+1 point)")
                    print("\n")
                    score += 1
                    break
            else:
                print("That incorrect, guess again.\n")
                lives = lives - 1
            if lives == 0:
                print("You have no more lives to continue! Your score was:", score)
                time.sleep(3)
                slow_print("Would you like to play again?")
                playAgain = input("[Y/N]: ")
                if playAgain == "n" or playAgain == "N":
                    sys.exit()
                if playAgain == "Y" or playAgain == "y":
                    print("Your last score was", score, ", lets see if you can beat it this time...")
                    time.sleep(1)
                    print("\n")
                    pickSong_random()
  • 0
    Я предполагаю, что # ДРУГОЙ КОД ИГРЫ ЗДЕСЬ - это весь мой игровой сценарий? Игровая система определяется как функция.
  • 0
    @ Соло Я отредактировал свой пост, чтобы включить то, что я думал, с точки зрения редактирования вашего существующего метода.

Ещё вопросы

Сообщество Overcoder
Наверх
Меню