import random
import os
import sys
import time  # Import time for the timer functionality

# Print ASCII Art Banner
ascii_art = """
██╗    ██╗ ██████╗ ██████╗ ██████╗      ██████╗  █████╗ ███╗   ███╗███████╗
██║    ██║██╔═══██╗██╔══██╗██╔══██╗    ██╔════╝ ██╔══██╗████╗ ████║██╔════╝
██║ █╗ ██║██║   ██║██████╔╝██║  ██║    ██║  ███╗███████║██╔████╔██║█████╗  
██║███╗██║██║   ██║██╔══██╗██║  ██║    ██║   ██║██╔══██║██║╚██╔╝██║██╔══╝  
╚███╔███╔╝╚██████╔╝██║  ██║██████╔╝    ╚██████╔╝██║  ██║██║ ╚═╝ ██║███████╗
 ╚══╝╚══╝  ╚═════╝ ╚═╝  ╚═╝╚═════╝      ╚═════╝ ╚═╝  ╚═╝╚═╝     ╚═╝╚══════╝
"""
print(ascii_art)

# Constants
HIGH_SCORES_FILE = 'data/high_scores.txt'
USER_DATA_FILE = 'data/user_data.txt'

# Word lists for different difficulty levels
DIFFICULTY_WORDS = {
    'easy': ['cat', 'fish', 'dog', 'bird', 'frog', 'apple', 'table', 'chair', 'book', 'lamp'],
    'medium': ['giraffe', 'monkey', 'penguin', 'squirrel', 'elephant', 'dolphin', 'computer', 'pencil', 'candle', 'window'],
    'hard': ['chimpanzee', 'extraordinary', 'microorganism', 'unbelievable', 'determination', 'superintendent', 'phenomenon', 'incomprehensible', 'electromagnetic', 'characteristic']
}

# Set number of tries based on difficulty
TRIES = {
    'easy': 5,
    'medium': 7,
    'hard': 10
}

def ensure_data_directory():
    """Ensure the data directory exists."""
    if not os.path.exists('data'):
        os.makedirs('data')

def load_user_data():
    """Load user data from a file."""
    if not os.path.exists(USER_DATA_FILE):
        return {}

    user_data = {}
    with open(USER_DATA_FILE, 'r') as file:
        for line in file:
            username = line.strip()
            user_data[username] = True  # Using a dictionary to track registered users
    return user_data

def register_user(username):
    """Register a new user."""
    ensure_data_directory()
    with open(USER_DATA_FILE, 'a') as file:
        file.write(username + '\n')

def load_high_scores():
    """Load high scores from a file."""
    if not os.path.exists(HIGH_SCORES_FILE):
        return {}

    high_scores = {}
    with open(HIGH_SCORES_FILE, 'r') as file:
        for line in file:
            parts = line.strip().split(',')
            if len(parts) == 3:
                difficulty, name, score_str = parts
                try:
                    score = int(score_str)
                    # Only keep the highest score per difficulty
                    if difficulty not in high_scores or score > high_scores[difficulty][1]:
                        high_scores[difficulty] = (name, score)
                except ValueError:
                    continue
    return high_scores

def save_high_score(name, score, difficulty):
    """Save player's name and score to a file."""
    ensure_data_directory()  # Ensure data directory exists
    with open(HIGH_SCORES_FILE, 'a') as file:
        file.write(f"{difficulty},{name},{score}\n")

def get_word(difficulty):
    """Select a random word from a given difficulty level."""
    return random.choice(DIFFICULTY_WORDS[difficulty])

def display_progress(selected_word, guessed_letters):
    """Display the current state of the guessed word."""
    display_word = ''
    for letter in selected_word:
        if letter in guessed_letters:
            display_word += letter + ' '
        else:
            display_word += '_ '
    print("\nCurrent word:", display_word.strip())

def user_login():
    """Handle user login, registration, or viewing high scores."""
    user_data = load_user_data()
    high_scores = load_high_scores()  # Load high scores here to show on demand

    while True:
        try:
            print("\nWelcome! Please choose an option:")
            print("Login (l)")
            print("Register (r)")
            print("View High Scores (h)")
            print("Quit (q)")
            print("Enter your choice: ", end='', flush=True)
            choice = sys.stdin.readline().strip().lower()

            if choice == 'l':
                print("Enter your username: ", end='', flush=True)
                username = sys.stdin.readline().strip()
                if username in user_data:
                    print(f"Welcome back, {username}!")
                    return username
                else:
                    print("Username does not exist. Please register first.")
            
            elif choice == 'r':
                print("Enter your desired username: ", end='', flush=True)
                username = sys.stdin.readline().strip()
                if username not in user_data:
                    register_user(username)
                    print(f"User {username} registered successfully!")
                    return username
                else:
                    print("Username already exists. Please choose a different one.")

            elif choice == 'h':
                print("\n--- High Scores ---")
                modes = ['easy', 'medium', 'hard', 'timed']
                for mode in modes:
                    if mode in high_scores:
                        name, score = high_scores[mode]
                        mode_name = "Timed" if mode == 'timed' else mode.capitalize()
                        print(f"{mode_name} mode: {name} with {score} points")
                    else:
                        mode_name = "Timed" if mode == 'timed' else mode.capitalize()
                        print(f"{mode_name} mode: No scores yet")
                print("-------------------")

            elif choice == 'q':
                print("Exiting. Goodbye!")
                sys.exit(0)

            else:
                print("Invalid choice. Please enter 'l', 'r', 'h', or 'q'.")

        except EOFError:
            print("\nInput error: Please ensure you're running this in an interactive console.")
            break
        except KeyboardInterrupt:
            print("\nInput interrupted. Exiting user login.")
            break
        except Exception as e:
            print(f"An error occurred: {e}")
            break

def guess_the_word(username):
    """Guess the word game."""
    while True:  # outer loop controls replay or main menu or quit
        print("\nWelcome to 'Guess the Word'!")
        difficulty = input("Choose difficulty (easy, medium, hard): ").lower()

        if difficulty not in DIFFICULTY_WORDS:
            print("Invalid difficulty. Please try again.")
            continue

        selected_word = get_word(difficulty)
        guessed_letters = []
        score = 100
        remaining_tries = TRIES[difficulty]

        while remaining_tries > 0:
            display_progress(selected_word, guessed_letters)
            print(f"Remaining tries: {remaining_tries}")
            guess = input("Guess a letter: ").lower()

            if guess in guessed_letters:
                print("You've already guessed that letter!")
                continue

            guessed_letters.append(guess)

            if guess in selected_word:
                print("Good guess!")
            else:
                remaining_tries -= 1
                score -= 10
                print("Wrong guess! -10 points")

            if all(letter in guessed_letters for letter in selected_word):
                print(f"You guessed the word '{selected_word}'! Congratulations!")
                break

            if remaining_tries <= 0:
                print(f"Game over! The correct word was '{selected_word}'.")
                score = 0

        save_high_score(username, score, difficulty)

        while True:
            play_again = input("Do you wish to play again? (yes/no/m for main menu): ").lower()
            if play_again == 'yes':
                break
            elif play_again == 'm':
                return  # back to main menu
            elif play_again == 'no':
                print("Thank you for playing! Exiting game.")
                sys.exit(0)
            else:
                print("Invalid input. Please enter 'yes', 'no', or 'm'.")

def display_shark(shark):
    """Display the shark's position."""
    print("Shark's position:", shark)

def beat_the_shark(username):
    """A simple race game where player guesses letters and compares to a shark opponent."""
    while True:
        print("\nWelcome to 'Beat the Shark'!")
        difficulty = input("Choose difficulty (easy, medium, hard): ").lower()

        if difficulty not in DIFFICULTY_WORDS:
            print("Invalid difficulty. Please try again.")
            continue

        selected_word = get_word(difficulty)
        guessed_letters = []
        score = 100
        remaining_tries = TRIES[difficulty]

        if difficulty == 'easy':
            shark = "﹏﹏﹏𓂁"
        elif difficulty == 'medium':
            shark = "﹏﹏﹏﹏﹏𓂁"
        else:
            shark = "﹏﹏﹏﹏﹏﹏﹏﹏𓂁"

        display_shark(shark)

        while remaining_tries > 0:
            display_progress(selected_word, guessed_letters)
            print(f"Remaining tries: {remaining_tries}")
            guess = input("Guess a letter: ").lower()

            if guess in guessed_letters:
                print("You've already guessed that letter!")
                continue

            guessed_letters.append(guess)

            if guess in selected_word:
                print("Good guess! The shark is still behind!")
            else:
                remaining_tries -= 1
                score -= 10
                print("Wrong guess! -10 points. The shark moves forward!")

                if len(shark) > 1:
                    shark = shark[:-1]
                if len(shark) <= 1:
                    shark = '𓂁'

            display_shark(shark)

            if all(letter in guessed_letters for letter in selected_word):
                print(f"You guessed the word '{selected_word}'! The shark couldn't catch you!")
                break

        if remaining_tries <= 0:
            print(f"The shark caught you! Game over! The correct word was '{selected_word}'.")
            score = 0

        save_high_score(username, score, difficulty)

        while True:
            play_again = input("Do you wish to play again? (yes/no/m for main menu): ").lower()
            if play_again == 'yes':
                break
            elif play_again == 'm':
                return  # back to main menu
            elif play_again == 'no':
                print("Thank you for playing! Exiting game.")
                sys.exit(0)
            else:
                print("Invalid input. Please enter 'yes', 'no', or 'm'.")

def timed_guess_the_word(username):
    """Timed Guess the Word game."""
    while True:
        print("\nWelcome to 'Timed Guess the Word'!")
        print("You have infinite guesses but must guess the word within the time limit.")

        while True:
            print("Choose a time limit:")
            print("1. 30 seconds")
            print("2. 1 minute (60 seconds)")
            print("3. 1 minute and 30 seconds (90 seconds)")
            time_choice = input("Select a time limit (1, 2, 3): ").strip()

            if time_choice == '1':
                timer_duration = 30
                break
            elif time_choice == '2':
                timer_duration = 60
                break
            elif time_choice == '3':
                timer_duration = 90
                break
            else:
                print("Invalid choice. Please select 1, 2, or 3.")

        difficulty = input("Choose difficulty (easy, medium, hard): ").lower()

        if difficulty not in DIFFICULTY_WORDS:
            print("Invalid difficulty. Please try again.")
            continue

        selected_word = get_word(difficulty)
        guessed_letters = []
        score = 100
        remaining_tries = TRIES[difficulty]

        start_time = time.time()

        while remaining_tries > 0:
            display_progress(selected_word, guessed_letters)
            print(f"Remaining tries: {remaining_tries}")
            elapsed_time = time.time() - start_time
            remaining_time = max(0, timer_duration - elapsed_time)

            print(f"Time remaining: {int(remaining_time)} seconds")

            if remaining_time <= 0:
                print(f"Time's up! The correct word was '{selected_word}'.")
                score = 0
                break

            guess = input("Guess a letter: ").lower()

            if guess in guessed_letters:
                print("You've already guessed that letter!")
                continue

            guessed_letters.append(guess)

            if guess in selected_word:
                print("Good guess!")
            else:
                remaining_tries -= 1
                score -= 10
                print("Wrong guess! -10 points")

            if all(letter in guessed_letters for letter in selected_word):
                print(f"You guessed the word '{selected_word}'! Congratulations!")
                break

        save_high_score(username, score, 'timed')

        while True:
            play_again = input("Do you wish to play again? (yes/no/m for main menu): ").lower()
            if play_again == 'yes':
                break
            elif play_again == 'm':
                return  # back to main menu
            elif play_again == 'no':
                print("Thank you for playing! Exiting game.")
                sys.exit(0)
            else:
                print("Invalid input. Please enter 'yes', 'no', or 'm'.")

def display_high_scores(high_scores):
    """Display the high scores."""
    print("\nHigh Scores:")
    modes = ['easy', 'medium', 'hard', 'timed']
    for mode in modes:
        mode_name = "Timed" if mode == 'timed' else mode.capitalize()
        if mode in high_scores:
            name, score = high_scores[mode]
            print(f"{mode_name} mode: {name} with {score} points")
        else:
            print(f"{mode_name} mode: No scores yet")

def start_menu():
    """Display the start menu and handle user choices."""
    while True:
        print("\nPick a game mode!")
        print("1. Guess the Word: Earn points by guessing the correct letters.")
        print("2. Beat the Shark: Race against a shark by guessing the word correctly.")
        print("3. Timed Guess the Word: Infinite guesses but beat the timer!")
        try:
            choice = input("Select a game (1, 2, or 3), or 'q' to quit: ")
            
            if choice == '1':
                guess_the_word(username)
            elif choice == '2':
                beat_the_shark(username)
            elif choice == '3':
                timed_guess_the_word(username)
            elif choice.lower() == 'q':
                print("Thank you for playing! Goodbye!")
                break
            else:
                print("Invalid choice. Please try again.")
        except KeyboardInterrupt:
            print("\nInput interrupted. Exiting the game.")
            break

if __name__ == "__main__":
    # Load and display high scores at the start
    high_scores = load_high_scores()
    display_high_scores(high_scores)

    # User login or registration
    username = user_login()

    # Start main menu
    start_menu() make a strucutre chart out of this code this is the marking critera Provides comprehensive and
detailed design models including
all the following: data dictionary,
structure chart, screen designs,
and algorithms that effectively
meet the requirements of guess
the word.