├── .gitignore
├── README.md
├── src
├── day_1
│ ├── README.md
│ └── username_generator.py
├── day_10
│ ├── README.md
│ ├── calculator.py
│ ├── logo.py
│ └── main.py
├── day_11
│ ├── README.md
│ ├── blackjack.py
│ └── logo.py
├── day_12
│ ├── README.md
│ ├── logo.py
│ └── number_guess.py
├── day_13
│ ├── README.md
│ ├── fizzbuzz.py
│ └── logo.py
├── day_14
│ ├── README.md
│ ├── game_data.py
│ ├── higher_lower.py
│ └── logo.py
├── day_15
│ ├── README.md
│ ├── coffee.py
│ └── main.py
├── day_16
│ ├── README.md
│ ├── main.py
│ ├── tic_tac_toe.py
│ └── user_interface.py
├── day_17
│ ├── README.md
│ ├── main.py
│ ├── question.py
│ └── quiz.py
├── day_18
│ ├── README.md
│ ├── art.py
│ └── images
│ │ └── dots.jpg
├── day_19
│ ├── README.md
│ ├── images
│ │ └── race.gif
│ ├── main.py
│ └── player.py
├── day_2
│ ├── README.md
│ └── tip_calculator.py
├── day_20
│ ├── README.md
│ ├── food.py
│ ├── main.py
│ └── snake.py
├── day_21
│ ├── README.md
│ ├── ball.py
│ ├── main.py
│ ├── paddle.py
│ └── score.py
├── day_22
│ ├── README.md
│ ├── car.py
│ ├── display.py
│ ├── frog.py
│ ├── images
│ │ ├── bg0.png
│ │ ├── bg1.png
│ │ ├── bg2.png
│ │ ├── cars
│ │ │ ├── blue_car.gif
│ │ │ ├── green_car.gif
│ │ │ ├── red_car.gif
│ │ │ └── yellow_car.gif
│ │ ├── frog.gif
│ │ ├── frog3.gif
│ │ └── frog4.gif
│ └── main.py
├── day_23
│ ├── README.md
│ ├── data
│ │ ├── 50_states.csv
│ │ └── blank_states_img.gif
│ └── main.py
├── day_24
│ ├── README.md
│ ├── data
│ │ └── nato_phonetic_alphabet.csv
│ └── main.py
├── day_25
│ ├── README.md
│ └── main.py
├── day_26
│ ├── README.md
│ ├── images
│ │ └── pomodoro.png
│ ├── main.py
│ ├── pomodoro.py
│ └── pomodoro_settings.py
├── day_27
│ ├── README.md
│ ├── data
│ │ └── passwords.txt
│ ├── file_handler.py
│ ├── images
│ │ └── pass.png
│ ├── main.py
│ ├── password_generator.py
│ └── password_manager.py
├── day_28
│ ├── README.md
│ ├── data
│ │ └── french_words.csv
│ ├── flash_card.py
│ ├── images
│ │ ├── back_flash_card.png
│ │ ├── flash_card.png
│ │ ├── right.png
│ │ └── wrong.png
│ └── main.py
├── day_29
│ ├── README.md
│ └── main.py
├── day_3
│ ├── README.md
│ └── treasure_island.py
├── day_30
│ ├── README.md
│ ├── main.py
│ └── movies.txt
├── day_31
│ ├── README.md
│ └── main.py
├── day_4
│ ├── README.md
│ └── rock_paper_scissors.py
├── day_5
│ ├── README.md
│ ├── password_generator.py
│ └── user_interface.py
├── day_6
│ ├── README.md
│ ├── dice.py
│ ├── main.py
│ └── user_interface.py
├── day_7
│ ├── README.md
│ ├── hangman.py
│ ├── players-scores
│ ├── requirements.txt
│ └── words.txt
├── day_8
│ ├── README.md
│ ├── caesar_cipher.py
│ └── logo.py
└── day_9
│ ├── README.md
│ ├── auction.py
│ ├── auction_program.py
│ └── logo.py
└── utility.py
/.gitignore:
--------------------------------------------------------------------------------
1 | test.py
2 | .vscode
3 |
4 |
5 | # Byte-compiled / optimized / DLL files
6 | __pycache__/
7 | *.py[cod]
8 | *$py.class
9 |
10 | # C extensions
11 | *.so
12 |
13 | # Distribution / packaging
14 | .Python
15 | build/
16 | develop-eggs/
17 | dist/
18 | downloads/
19 | eggs/
20 | .eggs/
21 | lib/
22 | lib64/
23 | parts/
24 | sdist/
25 | var/
26 | wheels/
27 | pip-wheel-metadata/
28 | share/python-wheels/
29 | *.egg-info/
30 | .installed.cfg
31 | *.egg
32 | MANIFEST
33 |
34 | # PyInstaller
35 | # Usually these files are written by a python script from a template
36 | # before PyInstaller builds the exe, so as to inject date/other infos into it.
37 | *.manifest
38 | *.spec
39 |
40 | # Installer logs
41 | pip-log.txt
42 | pip-delete-this-directory.txt
43 |
44 | # Unit test / coverage reports
45 | htmlcov/
46 | .tox/
47 | .nox/
48 | .coverage
49 | .coverage.*
50 | .cache
51 | nosetests.xml
52 | coverage.xml
53 | *.cover
54 | *.py,cover
55 | .hypothesis/
56 | .pytest_cache/
57 |
58 | # Translations
59 | *.mo
60 | *.pot
61 |
62 | # Django stuff:
63 | *.log
64 | local_settings.py
65 | db.sqlite3
66 | db.sqlite3-journal
67 |
68 | # Flask stuff:
69 | instance/
70 | .webassets-cache
71 |
72 | # Scrapy stuff:
73 | .scrapy
74 |
75 | # Sphinx documentation
76 | docs/_build/
77 |
78 | # PyBuilder
79 | target/
80 |
81 | # Jupyter Notebook
82 | .ipynb_checkpoints
83 |
84 | # IPython
85 | profile_default/
86 | ipython_config.py
87 |
88 | # pyenv
89 | .python-version
90 |
91 | # pipenv
92 | # According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
93 | # However, in case of collaboration, if having platform-specific dependencies or dependencies
94 | # having no cross-platform support, pipenv may install dependencies that don't work, or not
95 | # install all needed dependencies.
96 | #Pipfile.lock
97 |
98 | # PEP 582; used by e.g. github.com/David-OConnor/pyflow
99 | __pypackages__/
100 |
101 | # Celery stuff
102 | celerybeat-schedule
103 | celerybeat.pid
104 |
105 | # SageMath parsed files
106 | *.sage.py
107 |
108 | # Environments
109 | .env
110 | .venv
111 | env/
112 | venv/
113 | ENV/
114 | env.bak/
115 | venv.bak/
116 |
117 | # Spyder project settings
118 | .spyderproject
119 | .spyproject
120 |
121 | # Rope project settings
122 | .ropeproject
123 |
124 | # mkdocs documentation
125 | /site
126 |
127 | # mypy
128 | .mypy_cache/
129 | .dmypy.json
130 | dmypy.json
131 |
132 | # Pyre type checker
133 | .pyre/
134 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # 31 Days Of Code
2 |
3 | I took on a challenge to build 31 mini-projects using Python. These projects included a variety of applications and features, such as a hangman game, a tic-tac-toe game, a quiz program, and a flash cards app.
4 |
5 | # Overview:
6 |
7 | | Day | Project | Demo | Code |
8 | | --- | ---------------------- | -------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------- |
9 | | 1 | Username Generator | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_1#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_1/username_generator.py) |
10 | | 2 | Tip Calculator | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_2#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_2/tip_calculator.py) | |
11 | | 3 | Treasure Island | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_3#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_3/treasure_island.py) | |
12 | | 4 | Rock Paper Scissors | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_4#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_4/rock_paper_scissors.py) | |
13 | | 5 | Password Generator | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_5#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_5/password_generator.py) | |
14 | | 6 | Dice Rolling Simulator | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_6#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_6/user_interface.py) | |
15 | | **7** | **Hangman Game** | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_7#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_7/hangman.py) | |
16 | | 8 | Caesar Cipher | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_8#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_8/caesar_cipher.py) | |
17 | | 9 | Auction Program | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_9#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_9/auction_program.py) | |
18 | | 10 | Calculator | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_10#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_10/main.py) | |
19 | | **11** | **BlackJack** | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_11#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_11/blackjack.py) | |
20 | | 12 | Number Guessing Game | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_12#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_12/number_guess.py) | |
21 | | 13 | FizzBuzz | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_13#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_13/fizzbuzz.py) | |
22 | | 14 | Higher Lower Game | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_14#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_14/higher_lower.py) | |
23 | | **15** |**Coffee Machine** | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_15#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_15/main.py) | |
24 | | **16** |**Tic Tac Toe** | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_16#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_16/main.py) | |
25 | | **17** |**Quiz Program** | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_17#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_17/main.py) | |
26 | | 18 | Dot Painting | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_18#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_18/art.py) | |
27 | | **19** | **Turtle Race Game** | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_19#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_19/main.py) | |
28 | | **20** | **Snake Game** | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_20#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_20/main.py) | |
29 | | **21** | **Pong Game** | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_21#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_21/main.py) | |
30 | | **22** | **Crossy Road Game** | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_22#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_22/main.py) | |
31 | | 23 | US Map Quiz | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_23#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_23/main.py) | |
32 | | 24 |NATO Phonetic Alphabet | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_24#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_24/main.py) | |
33 | | 25 |Miles to Km Converter | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_25#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_25/main.py) | |
34 | | **26** |**Pomodoro Timer App** | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_26#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_26/pomodoro.py) | |
35 | | **27** |**Password Manager App** | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_27#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_27/password_manager.py) | |
36 | | **28** |**FlashCards App** | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_28#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_28/flash_card.py) | |
37 | | 29 |Weather Forecast via SMS | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_29#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_29/main.py) | |
38 | | 30 |Best Movies To Watch App | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_30#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_30/main.py) | |
39 | | 31 |WallPaper Bot | [demo](https://github.com/dylanbuchi/100-days-of-code/tree/main/src/day_31#demo) | [code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_31/main.py) | |
40 |
41 |
--------------------------------------------------------------------------------
/src/day_1/README.md:
--------------------------------------------------------------------------------
1 | # Username Generator
2 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_1/username_generator.py)
3 | ## Demo:
4 |
5 |
6 |
--------------------------------------------------------------------------------
/src/day_1/username_generator.py:
--------------------------------------------------------------------------------
1 | # Username Generator
2 |
3 |
4 | def print_welcome(name: str):
5 | print(f"Welcome to {name}.")
6 |
7 |
8 | def get_username() -> str:
9 | user_color = ask_user_favorite('color')
10 | user_food = ask_user_favorite('food')
11 | username = create_username_from(user_color, user_food)
12 |
13 | return username
14 |
15 |
16 | def ask_user_favorite(item: str) -> str:
17 | return input(f"What's your favorite {item}?\n")
18 |
19 |
20 | def create_username_from(*args: str):
21 | if not args:
22 | raise ValueError("Cant create an empty username")
23 |
24 | username_parts = []
25 | username_number = 0
26 |
27 | for arg in args:
28 | username_parts.append(title_string_and_replace_spaces(arg, '-'))
29 | username_number += len(arg)
30 |
31 | username_number *= len(args)
32 |
33 | username_parts.append(str(username_number))
34 | username = format_username(username_parts)
35 |
36 | return username
37 |
38 |
39 | def title_string_and_replace_spaces(string: str, replacement: str):
40 | result = string.replace(" ", replacement)
41 | return result.title()
42 |
43 |
44 | def format_username(username_parts):
45 | username = f"{'-'.join(username_parts[:-1])}{username_parts[-1]}"
46 | return username
47 |
48 |
49 | def main():
50 | print_welcome("to the username generator")
51 | username = get_username()
52 |
53 | print(f"Your new username is {username}")
54 |
55 |
56 | if __name__ == "__main__":
57 | main()
--------------------------------------------------------------------------------
/src/day_10/README.md:
--------------------------------------------------------------------------------
1 | # Calculator
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_10/main.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_10/calculator.py:
--------------------------------------------------------------------------------
1 | # Calculator
2 | import sys
3 |
4 |
5 | class Calculator:
6 | def __init__(self):
7 | self.operations = {
8 | '+': self.add,
9 | '-': self.substract,
10 | '*': self.multiply,
11 | '/': self.divide,
12 | }
13 |
14 | def get_operations(self):
15 | return self.operations
16 |
17 | def add(self, n1, n2):
18 | return n1 + n2
19 |
20 | def substract(self, n1, n2):
21 | return n1 - n2
22 |
23 | def multiply(self, n1, n2):
24 | return n1 * n2
25 |
26 | def divide(self, n1, n2):
27 | try:
28 | return n1 / n2
29 | except ZeroDivisionError as err:
30 | print("Error, Can't divide by zero")
31 | sys.exit()
32 |
--------------------------------------------------------------------------------
/src/day_10/logo.py:
--------------------------------------------------------------------------------
1 | LOGO = """ _____________________
2 | | _________________ |
3 | | | JO 0. | |
4 | | |_________________| |
5 | | ___ ___ ___ ___ |
6 | | | 7 | 8 | 9 | | + | |
7 | | |___|___|___| |___| |
8 | | | 4 | 5 | 6 | | - | |
9 | | |___|___|___| |___| |
10 | | | 1 | 2 | 3 | | x | |
11 | | |___|___|___| |___| |
12 | | | . | 0 | = | | / | |
13 | | |___|___|___| |___| |
14 | |_____________________|"""
--------------------------------------------------------------------------------
/src/day_10/main.py:
--------------------------------------------------------------------------------
1 | import sys
2 | import os
3 |
4 | sys.path.append(os.getcwd())
5 |
6 | from calculator import Calculator
7 | from logo import LOGO
8 |
9 |
10 | def print_operations():
11 | print("""
12 | +
13 | -
14 | *
15 | /
16 | """)
17 |
18 |
19 | def get_user_operation(operations):
20 | print_operations()
21 | try:
22 | operator = input("Pick an operation: ").lower().strip()
23 | assert operator in operations.keys()
24 | except AssertionError:
25 | print("Select a valid operation")
26 | return get_user_operation(operations)
27 | else:
28 | return operator
29 |
30 |
31 | def get_user_number(string):
32 | try:
33 | number = float(input(f"\nPick the {string} number: "))
34 |
35 | except ValueError:
36 | print("Error, only numbers allowed")
37 | return get_user_number(string)
38 |
39 | else:
40 | return int(number) if (str(number)[-1] == '0') else number
41 |
42 |
43 | def get_user_inputs(operations):
44 |
45 | number_1 = get_user_number('first')
46 | operation = get_user_operation(operations)
47 | number_2 = get_user_number('second')
48 |
49 | return number_1, number_2, operation
50 |
51 |
52 | def print_result(n1, n2, operator, result):
53 | print(f"{n1} {operator} {n2} = {result}")
54 |
55 |
56 | def calculate_user_numbers(n1, n2, operator, operations):
57 | calculate = operations[operator]
58 | result = calculate(n1, n2)
59 | return result
60 |
61 |
62 | def user_interface():
63 | calculator = Calculator()
64 | operations = calculator.get_operations()
65 | number_1, number_2, operator = get_user_inputs(operations)
66 |
67 | result = calculate_user_numbers(number_1, number_2, operator, operations)
68 | print_result(number_1, number_2, operator, result)
69 | current_num = result
70 |
71 | choice = ''
72 |
73 | while choice == '':
74 |
75 | choice = input(
76 | f"Press enter to keep calculating with the number {current_num}\n")
77 | if not choice:
78 | operation = get_user_operation(operations)
79 | next_num = get_user_number('next')
80 | result = calculate_user_numbers(current_num, next_num, operation,
81 | operations)
82 | print_result(current_num, next_num, operation, result)
83 | current_num = result
84 |
85 | run_again("\nPress enter to use the calculator again\n", main)
86 |
87 |
88 | def run_again(string, func):
89 | choice = input(string).lower().strip()
90 | if not choice:
91 | func()
92 |
93 |
94 | def main():
95 | print(LOGO)
96 | try:
97 | user_interface()
98 | except KeyboardInterrupt:
99 | sys.exit()
100 |
101 |
102 | if __name__ == "__main__":
103 | main()
--------------------------------------------------------------------------------
/src/day_11/README.md:
--------------------------------------------------------------------------------
1 | # BlackJack
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_11/blackjack.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_11/blackjack.py:
--------------------------------------------------------------------------------
1 | # Blackjack
2 | import sys
3 | import os
4 | import random
5 | from colorama import init, Fore
6 | from time import sleep
7 |
8 | from logo import LOGO
9 |
10 |
11 | def create_standard_deck():
12 | """Create a deck of cards with 8 packs"""
13 | deck = []
14 | for _ in range(8):
15 | cards = {i: i for (i) in range(2, 11)}
16 | cards.update({'J': 10, 'Q': 10, 'K': 10, 'A': [11, 1]})
17 | deck.append(cards)
18 | return deck
19 |
20 |
21 | def refill_deck(deck):
22 | if not deck:
23 | temp = create_standard_deck()
24 | deck.extend(temp)
25 |
26 |
27 | def get_a_card(card_names, card_values, cards_count):
28 | """get a random card with it's value and remove it from deck"""
29 | index = random.randrange(0, len(card_names))
30 | card_name, card_value = card_names[index], card_values[index]
31 |
32 | cards_count[card_name] += 1
33 |
34 | if cards_count[card_name] == 4:
35 | card_names.pop(index)
36 | card_values.pop(index)
37 |
38 | return card_name, card_value
39 |
40 |
41 | def clear_console():
42 | os.system('cls' if os.name == 'nt' else 'clear')
43 |
44 |
45 | def get_value_for_Ace_card(player_name, player_card, card_values, total=0):
46 | """return 1 or 11 if card is As"""
47 | if (player_card != 'A'):
48 | return
49 |
50 | if player_name == 'You':
51 | try:
52 |
53 | choice = int(
54 | input("Your card is an Ace Do you want 1 or 11?:\n ").lower().
55 | strip())
56 | assert choice == 1 or choice == 11
57 |
58 | except (ValueError, AssertionError):
59 | print("Error, pick 1 or 11!")
60 | return get_value_for_Ace_card(player_name, player_card,
61 | card_values)
62 |
63 | else:
64 | clear_console()
65 | return choice
66 | else:
67 | bot_choice = 11 if total < 17 else 1
68 | return bot_choice
69 |
70 |
71 | def print_result(player_name, current_hand, total):
72 | total_color = Fore.RED if total > 21 else Fore.YELLOW
73 |
74 | print("*" * 80, end="\n")
75 | print(f"{Fore.GREEN} {player_name.upper()}:\n")
76 |
77 | print(f"Cards: {Fore.YELLOW + ', '.join(current_hand)}\n")
78 | print(f"Total: {total_color + str(total)}\n")
79 |
80 |
81 | def draw_card(player_name,
82 | card_names,
83 | card_values,
84 | current_hand,
85 | total,
86 | cards_count,
87 | balance=0):
88 | """A player draws a card, prints their hand and return the total points"""
89 | card, card_value = get_a_card(card_names, card_values, cards_count)
90 | if card != 'A':
91 | total += card_value
92 | else:
93 | if player_name != 'The dealer':
94 | if (total):
95 | print_result(player_name, current_hand, total)
96 |
97 | total += get_value_for_Ace_card(player_name, card, card_value, total)
98 | # if player_name == 'The dealer':
99 | # print_result(player_name, current_hand, total)
100 |
101 | # print("*" * 80, end="\n")
102 | # print(f"{player_name.upper()}:\n")
103 |
104 | current_hand.append(f"[{str(card)}]")
105 |
106 | # print_result(player_name, current_hand, total)
107 |
108 | return total
109 |
110 |
111 | def print_player_balance(balance):
112 | print(f"you have ${Fore.GREEN + str(balance)}")
113 |
114 |
115 | def rules(player_total, dealer_total, player_stop_draw):
116 | win = None
117 | if (player_total == 21):
118 | win = True
119 | elif (dealer_total == 21):
120 | win = False
121 | elif dealer_total >= 22:
122 | win = True
123 | elif player_total >= 22:
124 | win = False
125 |
126 | if player_stop_draw:
127 | if (player_total >= dealer_total and player_total < 21):
128 | win = True
129 | elif (dealer_total > player_total and dealer_total < 21):
130 | win = False
131 | return win
132 |
133 |
134 | def place_bet(max):
135 |
136 | try:
137 | bet = int(input("Place your bet\n:$"))
138 | assert bet > 0 and bet <= max
139 | except (AssertionError, ValueError):
140 | print("Place a correct bet amount")
141 | return place_bet(max)
142 | else:
143 | clear_console()
144 | return bet
145 |
146 |
147 | def dealer_plays(dealer_name, card_names, card_values, dealer_hand,
148 | dealer_total, player_total, cards_count):
149 |
150 | while True:
151 | if dealer_total >= 17 and player_total <= 17:
152 | return dealer_total
153 | else:
154 | if dealer_total > 21:
155 | break
156 | dealer_total = draw_card(dealer_name, card_names, card_values,
157 | dealer_hand, dealer_total, cards_count)
158 |
159 | print_result(dealer_name, dealer_hand, dealer_total)
160 | sleep(1.2)
161 | clear_console()
162 | return dealer_total
163 |
164 |
165 | def hit_or_stand():
166 | try:
167 | answer = int(input(" Hit (1) or Stand (2)\n:").lower().strip())
168 | assert 1 <= answer <= 2
169 | except (AssertionError, ValueError):
170 | print(f"Enter 1 to Hit or 2 to Stand")
171 | return hit_or_stand()
172 | return answer
173 |
174 |
175 | def get_cards():
176 | cards = {i: i for (i) in range(1, 11)}
177 | cards.update({'J': 10, 'Q': 10, 'K': 10, 'A': [11, 1]})
178 | return cards
179 |
180 |
181 | def play_black_jack(decks):
182 |
183 | # variables
184 | game_ended = False
185 | only_dealer_plays = False
186 | player_stop_draw = False
187 | new_game = True
188 |
189 | player_name = 'You'
190 | balance = 100
191 | dealer_name = 'The dealer'
192 |
193 | player_hand = []
194 | dealer_hand = []
195 | cards_count = get_cards()
196 | for k, v in cards_count.items():
197 | cards_count[k] = 0
198 |
199 | player_total = dealer_total = bet = 0
200 |
201 | while (len(decks)):
202 | current_deck = decks.pop()
203 |
204 | card_names = list(current_deck.keys())
205 | card_values = list(current_deck.values())
206 |
207 | # while current deck has cards
208 | while (len(card_names) and len(card_values)):
209 | if (balance <= 0):
210 | print("You have $0, deposit more to play again!")
211 | sys.exit()
212 |
213 | if new_game:
214 | new_game = False
215 | print_player_balance(balance)
216 | bet = place_bet(balance)
217 | dealer_total = draw_card(dealer_name, card_names, card_values,
218 | dealer_hand, dealer_total,
219 | cards_count)
220 |
221 | if only_dealer_plays:
222 |
223 | dealer_total = dealer_plays(dealer_name, card_names,
224 | card_values, dealer_hand,
225 | dealer_total, player_total,
226 | cards_count)
227 | else:
228 |
229 | print_result(dealer_name, dealer_hand, dealer_total)
230 | player_total = draw_card(player_name, card_names, card_values,
231 | player_hand, player_total,
232 | cards_count, balance)
233 |
234 | print_result(player_name, player_hand, player_total)
235 |
236 | has_winner = rules(player_total, dealer_total, player_stop_draw)
237 |
238 | if (has_winner == None):
239 | answer = ''
240 |
241 | if (not only_dealer_plays):
242 | answer = hit_or_stand()
243 |
244 | if answer == 1:
245 | clear_console()
246 | continue
247 | else:
248 | clear_console()
249 | player_stop_draw = True
250 | only_dealer_plays = True
251 | continue
252 |
253 | elif (has_winner):
254 | clear_console()
255 |
256 | balance += bet * 2
257 |
258 | print_result(dealer_name, dealer_hand, dealer_total)
259 | print_result(player_name, player_hand, player_total)
260 | if player_total == 21:
261 | print(f"{Fore.CYAN} BLACKJACK ", end='')
262 | print(f"You Win! {Fore.GREEN}+${bet * 2}")
263 | game_ended = True
264 | break
265 | elif (has_winner == False):
266 | clear_console()
267 |
268 | game_ended = True
269 | balance -= bet
270 | print_result(dealer_name, dealer_hand, dealer_total)
271 | print_result(player_name, player_hand, player_total)
272 | if (dealer_total == 21):
273 | print(f"{Fore.CYAN} BLACKJACK ", end='')
274 | print(f"Dealer wins! {Fore.RED} -${bet}\n")
275 | break
276 |
277 | # clear the current deck adn count when cards are empty
278 | if (not len(card_names) and not len(card_values)):
279 | current_deck.clear()
280 | cards_count.clear()
281 |
282 | # check if it's the end game
283 | if (game_ended):
284 | player_total, dealer_total = reset_points()
285 | reset_player_hand(player_hand)
286 | reset_player_hand(dealer_hand)
287 |
288 | ans = input("play again ? (y/n)\n:")
289 |
290 | if (ans == 'y'):
291 | game_ended = False
292 | only_dealer_plays = False
293 | player_stop_draw = False
294 | new_game = True
295 | clear_console()
296 | continue
297 | else:
298 | return
299 | # refill if no more cards in the decks
300 | if (not decks):
301 | refill_deck(decks)
302 | play_black_jack()
303 |
304 |
305 | def reset_player_hand(player_hand):
306 | player_hand.clear()
307 |
308 |
309 | def reset_points():
310 | return 0, 0
311 |
312 |
313 | def user_interface():
314 | decks = create_standard_deck()
315 | play_black_jack(decks)
316 |
317 |
318 | def main():
319 | init(autoreset=True)
320 | print(LOGO)
321 |
322 | try:
323 | user_interface()
324 | except KeyboardInterrupt:
325 | sys.exit()
326 |
327 |
328 | if __name__ == "__main__":
329 | main()
--------------------------------------------------------------------------------
/src/day_11/logo.py:
--------------------------------------------------------------------------------
1 | LOGO = """
2 | 88 88 88 88 88
3 | 88 88 88 "" 88
4 | 88 88 88 88
5 | 88,dPPYba, 88 ,adPPYYba, ,adPPYba, 88 ,d8 88 ,adPPYYba, ,adPPYba, 88 ,d8
6 | 88P' "8a 88 "" `Y8 a8" "" 88 ,a8" 88 "" `Y8 a8" "" 88 ,a8"
7 | 88 d8 88 ,adPPPPP88 8b 8888[ 88 ,adPPPPP88 8b 8888[
8 | 88b, ,a8" 88 88, ,88 "8a, ,aa 88`"Yba, 88 88, ,88 "8a, ,aa 88`"Yba,
9 | 8Y"Ybbd8"' 88 `"8bbdP"Y8 `"Ybbd8"' 88 `Y8a 88 `"8bbdP"Y8 `"Ybbd8"' 88 `Y8a
10 | ,88
11 | 888P"
12 | """
--------------------------------------------------------------------------------
/src/day_12/README.md:
--------------------------------------------------------------------------------
1 | # Number Guessing Game
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_12/number_guess.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_12/logo.py:
--------------------------------------------------------------------------------
1 | LOGO = """
2 | .__ __. __ __ .___ ___. .______ _______ .______
3 | | \ | | | | | | | \/ | | _ \ | ____|| _ \
4 | | \| | | | | | | \ / | | |_) | | |__ | |_) |
5 | | . ` | | | | | | |\/| | | _ < | __| | /
6 | | |\ | | `--' | | | | | | |_) | | |____ | |\ \-
7 | |__| \__| \______/ |__| |__| |______/ |_______|| _| `.__
8 |
9 | """
--------------------------------------------------------------------------------
/src/day_12/number_guess.py:
--------------------------------------------------------------------------------
1 | # Number Guessing Game
2 | import sys
3 | import random
4 |
5 | sys.path.append('src/day_9')
6 |
7 | from logo import LOGO
8 | from auction_program import clear_console
9 | from colorama import init, Fore
10 |
11 |
12 | def handle_exception(func, error_message):
13 | try:
14 | return func()
15 | except (AssertionError, ValueError):
16 | clear_console()
17 | print(Fore.RED + error_message)
18 | return handle_exception(func, error_message)
19 |
20 |
21 | def get_player_guess():
22 | player_guess = int(input("Make a guess: ").strip())
23 | assert 1 <= player_guess <= 100
24 | return player_guess
25 |
26 |
27 | def choose_difficulty():
28 |
29 | print(
30 | f"Choose a mode: {Fore.BLUE} (1) Easy - {Fore.LIGHTGREEN_EX} (2) Hard - {Fore.RED} (3) Expert: "
31 | )
32 | choice = int(input().strip())
33 | mode = "Easy" if choice == 1 else "Hard" if choice == 2 else "Expert"
34 | print(f"{mode} mode activated! Good luck!\n")
35 |
36 | assert choice == 1 or choice == 2 or choice == 3
37 | return choice
38 |
39 |
40 | def computer_picks_random_number(start, end):
41 | return random.randint(start, end)
42 |
43 |
44 | def welcome():
45 | print("Welcome to the Number Guessing Game\n")
46 |
47 |
48 | def get_player_attempts_by_difficulty(mode):
49 | # key: user difficulty choice choice, value: total attempts
50 | modes = {1: 10, 2: 5, 3: 3}
51 | return modes[mode]
52 |
53 |
54 | def print_user_attempts(player_attempts):
55 | color = Fore.RED if player_attempts <= 3 else Fore.YELLOW
56 | word = 'attempts' if player_attempts > 1 else 'attempt'
57 | print(
58 | color +
59 | f"You have {str(player_attempts)} {word} remaining to guess the number\n"
60 | )
61 |
62 |
63 | def play_again():
64 | choice = input("Press enter to play again!").strip()
65 | play_number_guessing_game() if not choice else sys.exit()
66 |
67 |
68 | def play_number_guessing_game():
69 | start, end, count = 1, 100, 0
70 |
71 | welcome()
72 | target = computer_picks_random_number(start, end)
73 | mode = handle_exception(choose_difficulty, "Please enter a valid mode")
74 | player_attempts = get_player_attempts_by_difficulty(mode)
75 | print(f"I'm thinking of a number from {start} to {end}\n")
76 |
77 | while True:
78 | if player_attempts == 0:
79 | print(
80 | f"No more attempts left, the number was {Fore.BLUE + str(target)}"
81 | )
82 | break
83 | player_guess = handle_exception(
84 | get_player_guess, f"Please enter a valid number ({start} - {end})")
85 |
86 | if target > player_guess:
87 | print(Fore.GREEN + "Too Low")
88 | elif target < player_guess:
89 | print(Fore.YELLOW + "Too High")
90 | else:
91 | print(f"Correct! The number was {target}")
92 | break
93 |
94 | count += 1
95 | player_attempts -= 1
96 | print_user_attempts(player_attempts)
97 |
98 | play_again()
99 |
100 |
101 | def main():
102 | init(autoreset=True)
103 | print(Fore.RED + LOGO)
104 | try:
105 | play_number_guessing_game()
106 | except KeyboardInterrupt:
107 | sys.exit()
108 |
109 |
110 | if __name__ == "__main__":
111 | main()
112 |
--------------------------------------------------------------------------------
/src/day_13/README.md:
--------------------------------------------------------------------------------
1 | # FizzBuzz
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_13/fizzbuzz.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_13/fizzbuzz.py:
--------------------------------------------------------------------------------
1 | # Fizz Buzz
2 | import sys
3 | import pyttsx3
4 |
5 | from colorama import init, Fore
6 | from logo import LOGO
7 |
8 |
9 | def play_fizz_buzz(limit):
10 | fizzBuzz = 'FizzBuzz'
11 | fizz = 'Fizz'
12 | buzz = 'Buzz'
13 |
14 | engine = pyttsx3.init()
15 |
16 | for i in range(1, limit + 1):
17 | end_line = ', ' if i < limit else '.\n'
18 | if i % 15 == 0:
19 | print(Fore.CYAN + fizzBuzz, end=end_line)
20 | engine.say(fizzBuzz)
21 | elif i % 5 == 0:
22 | print(Fore.YELLOW + buzz, end=end_line)
23 | engine.say(buzz)
24 | elif i % 3 == 0:
25 | print(Fore.GREEN + fizz, end=end_line)
26 | engine.say(fizz)
27 | else:
28 | print(i, end=end_line)
29 | engine.say(i)
30 | engine.runAndWait()
31 |
32 |
33 | def main():
34 | init(autoreset=True)
35 | print(Fore.RED + LOGO)
36 | try:
37 | play_fizz_buzz(15)
38 | except KeyboardInterrupt:
39 | sys.exit()
40 |
41 |
42 | if __name__ == "__main__":
43 | main()
44 |
--------------------------------------------------------------------------------
/src/day_13/logo.py:
--------------------------------------------------------------------------------
1 | LOGO = """
2 | _____ ____ _____ _____ ____ __ __ _____ _____
3 | | || || || || \ | | || || |
4 | | __| | | |__/ ||__/ || o )| | ||__/ ||__/ |
5 | | |_ | | | __|| __|| || | || __|| __|
6 | | _] | | | / || / || O || : || / || / |
7 | | | | | | || || || || || |
8 | |__| |____||_____||_____||_____| \__,_||_____||_____|
9 | """
--------------------------------------------------------------------------------
/src/day_14/README.md:
--------------------------------------------------------------------------------
1 | # Higher Lower Game
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_14/higher_lower.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/src/day_14/game_data.py:
--------------------------------------------------------------------------------
1 | GAME_DATA = [{
2 | 'name': 'Instagram',
3 | 'follower_count': 346,
4 | 'description': 'Social media platform',
5 | 'country': 'United States'
6 | }, {
7 | 'name': 'Cristiano Ronaldo',
8 | 'follower_count': 215,
9 | 'description': 'Footballer',
10 | 'country': 'Portugal'
11 | }, {
12 | 'name': 'Ariana Grande',
13 | 'follower_count': 183,
14 | 'description': 'Musician and actress',
15 | 'country': 'United States'
16 | }, {
17 | 'name': 'Dwayne Johnson',
18 | 'follower_count': 181,
19 | 'description': 'Actor and professional wrestler',
20 | 'country': 'United States'
21 | }, {
22 | 'name': 'Selena Gomez',
23 | 'follower_count': 174,
24 | 'description': 'Musician and actress',
25 | 'country': 'United States'
26 | }, {
27 | 'name': 'Kylie Jenner',
28 | 'follower_count': 172,
29 | 'description':
30 | 'Reality TV personality and businesswoman and Self-Made Billionaire',
31 | 'country': 'United States'
32 | }, {
33 | 'name': 'Kim Kardashian',
34 | 'follower_count': 167,
35 | 'description': 'Reality TV personality and businesswoman',
36 | 'country': 'United States'
37 | }, {
38 | 'name': 'Lionel Messi',
39 | 'follower_count': 149,
40 | 'description': 'Footballer',
41 | 'country': 'Argentina'
42 | }, {
43 | 'name': 'Beyoncé',
44 | 'follower_count': 145,
45 | 'description': 'Musician',
46 | 'country': 'United States'
47 | }, {
48 | 'name': 'Neymar',
49 | 'follower_count': 138,
50 | 'description': 'Footballer',
51 | 'country': 'Brasil'
52 | }, {
53 | 'name': 'National Geographic',
54 | 'follower_count': 135,
55 | 'description': 'Magazine',
56 | 'country': 'United States'
57 | }, {
58 | 'name': 'Justin Bieber',
59 | 'follower_count': 133,
60 | 'description': 'Musician',
61 | 'country': 'Canada'
62 | }, {
63 | 'name': 'Taylor Swift',
64 | 'follower_count': 131,
65 | 'description': 'Musician',
66 | 'country': 'United States'
67 | }, {
68 | 'name': 'Kendall Jenner',
69 | 'follower_count': 127,
70 | 'description': 'Reality TV personality and Model',
71 | 'country': 'United States'
72 | }, {
73 | 'name': 'Jennifer Lopez',
74 | 'follower_count': 119,
75 | 'description': 'Musician and actress',
76 | 'country': 'United States'
77 | }, {
78 | 'name': 'Nicki Minaj',
79 | 'follower_count': 113,
80 | 'description': 'Musician',
81 | 'country': 'Trinidad and Tobago'
82 | }, {
83 | 'name': 'Nike',
84 | 'follower_count': 109,
85 | 'description': 'Sportswear multinational',
86 | 'country': 'United States'
87 | }, {
88 | 'name': 'Khloé Kardashian',
89 | 'follower_count': 108,
90 | 'description': 'Reality TV personality and businesswoman',
91 | 'country': 'United States'
92 | }, {
93 | 'name': 'Miley Cyrus',
94 | 'follower_count': 107,
95 | 'description': 'Musician and actress',
96 | 'country': 'United States'
97 | }, {
98 | 'name': 'Katy Perry',
99 | 'follower_count': 94,
100 | 'description': 'Musician',
101 | 'country': 'United States'
102 | }, {
103 | 'name': 'Kourtney Kardashian',
104 | 'follower_count': 90,
105 | 'description': 'Reality TV personality',
106 | 'country': 'United States'
107 | }, {
108 | 'name': 'Kevin Hart',
109 | 'follower_count': 89,
110 | 'description': 'Comedian and actor',
111 | 'country': 'United States'
112 | }, {
113 | 'name': 'Ellen DeGeneres',
114 | 'follower_count': 87,
115 | 'description': 'Comedian',
116 | 'country': 'United States'
117 | }, {
118 | 'name': 'Real Madrid CF',
119 | 'follower_count': 86,
120 | 'description': 'Football club',
121 | 'country': 'Spain'
122 | }, {
123 | 'name': 'FC Barcelona',
124 | 'follower_count': 85,
125 | 'description': 'Football club',
126 | 'country': 'Spain'
127 | }, {
128 | 'name': 'Rihanna',
129 | 'follower_count': 81,
130 | 'description': 'Musician and businesswoman',
131 | 'country': 'Barbados'
132 | }, {
133 | 'name': 'Demi Lovato',
134 | 'follower_count': 80,
135 | 'description': 'Musician and actress',
136 | 'country': 'United States'
137 | }, {
138 | 'name': "Victoria's Secret",
139 | 'follower_count': 69,
140 | 'description': 'Lingerie brand',
141 | 'country': 'United States'
142 | }, {
143 | 'name': 'Zendaya',
144 | 'follower_count': 68,
145 | 'description': 'Actress and musician',
146 | 'country': 'United States'
147 | }, {
148 | 'name': 'Shakira',
149 | 'follower_count': 66,
150 | 'description': 'Musician',
151 | 'country': 'Colombia'
152 | }, {
153 | 'name': 'Drake',
154 | 'follower_count': 65,
155 | 'description': 'Musician',
156 | 'country': 'Canada'
157 | }, {
158 | 'name': 'Chris Brown',
159 | 'follower_count': 64,
160 | 'description': 'Musician',
161 | 'country': 'United States'
162 | }, {
163 | 'name': 'LeBron James',
164 | 'follower_count': 63,
165 | 'description': 'Basketball player',
166 | 'country': 'United States'
167 | }, {
168 | 'name': 'Vin Diesel',
169 | 'follower_count': 62,
170 | 'description': 'Actor',
171 | 'country': 'United States'
172 | }, {
173 | 'name': 'Cardi B',
174 | 'follower_count': 67,
175 | 'description': 'Musician',
176 | 'country': 'United States'
177 | }, {
178 | 'name': 'David Beckham',
179 | 'follower_count': 82,
180 | 'description': 'Footballer',
181 | 'country': 'United Kingdom'
182 | }, {
183 | 'name': 'Billie Eilish',
184 | 'follower_count': 61,
185 | 'description': 'Musician',
186 | 'country': 'United States'
187 | }, {
188 | 'name': 'Justin Timberlake',
189 | 'follower_count': 59,
190 | 'description': 'Musician and actor',
191 | 'country': 'United States'
192 | }, {
193 | 'name': 'UEFA Champions League',
194 | 'follower_count': 58,
195 | 'description': 'Club football competition',
196 | 'country': 'Europe'
197 | }, {
198 | 'name': 'NASA',
199 | 'follower_count': 56,
200 | 'description': 'Space agency',
201 | 'country': 'United States'
202 | }, {
203 | 'name': 'Emma Watson',
204 | 'follower_count': 56,
205 | 'description': 'Actress',
206 | 'country': 'United Kingdom'
207 | }, {
208 | 'name': 'Shawn Mendes',
209 | 'follower_count': 57,
210 | 'description': 'Musician',
211 | 'country': 'Canada'
212 | }, {
213 | 'name': 'Virat Kohli',
214 | 'follower_count': 55,
215 | 'description': 'Cricketer',
216 | 'country': 'India'
217 | }, {
218 | 'name': 'Gigi Hadid',
219 | 'follower_count': 54,
220 | 'description': 'Model',
221 | 'country': 'United States'
222 | }, {
223 | 'name': 'Priyanka Chopra Jonas',
224 | 'follower_count': 53,
225 | 'description': 'Actress and musician',
226 | 'country': 'India'
227 | }, {
228 | 'name': '9GAG',
229 | 'follower_count': 52,
230 | 'description': 'Social media platform',
231 | 'country': 'China'
232 | }, {
233 | 'name': 'Ronaldinho',
234 | 'follower_count': 51,
235 | 'description': 'Footballer',
236 | 'country': 'Brasil'
237 | }, {
238 | 'name': 'Maluma',
239 | 'follower_count': 50,
240 | 'description': 'Musician',
241 | 'country': 'Colombia'
242 | }, {
243 | 'name': 'Camila Cabello',
244 | 'follower_count': 49,
245 | 'description': 'Musician',
246 | 'country': 'Cuba'
247 | }, {
248 | 'name': 'NBA',
249 | 'follower_count': 47,
250 | 'description': 'Club Basketball Competition',
251 | 'country': 'United States'
252 | }]
253 |
--------------------------------------------------------------------------------
/src/day_14/higher_lower.py:
--------------------------------------------------------------------------------
1 | # Higher Lower Game
2 | import sys
3 | import random
4 | import os
5 |
6 | from colorama import init, Fore
7 | from typing_extensions import IntVar
8 | from logo import LOGO, VS_LOGO
9 | from game_data import GAME_DATA
10 |
11 |
12 | def clear_console():
13 | os.system('cls' if os.name == 'nt' else 'clear')
14 |
15 |
16 | def get_user_answer(string):
17 | try:
18 | answer = input(string).upper().strip()[:1]
19 | assert answer in 'AB' and answer
20 |
21 | except (AssertionError):
22 | print(Fore.RED + 'Please enter a valid answer')
23 | return get_user_answer(string)
24 |
25 | else:
26 | return answer
27 |
28 |
29 | def get_random_choices(data):
30 | compared_data = random.choice(data)
31 | against_data = random.choice(data)
32 |
33 | # to not compare the same data
34 | while compared_data == against_data:
35 | compared_data = random.choice(data)
36 | against_data = random.choice(data)
37 |
38 | return compared_data, against_data
39 |
40 |
41 | def get_game_data():
42 | return GAME_DATA.copy()
43 |
44 |
45 | def play_again():
46 | choice = input("Press enter to play again")
47 | return main() if not choice else sys.exit()
48 |
49 |
50 | def get_highest_followers_count(data_1, data_2):
51 | return max(data_1, data_2)
52 |
53 |
54 | def play_higher_lower():
55 | score = 0
56 | player_is_right = True
57 | starting = True
58 | compared_data = against_data = ''
59 | game_data = get_game_data()
60 |
61 | while player_is_right:
62 | if (starting):
63 | compared_data, against_data = get_random_choices(game_data)
64 | else:
65 | while compared_data == against_data:
66 | against_data = random.choice(game_data)
67 |
68 | compared_info = get_data_info(compared_data)
69 | against_info = get_data_info(against_data)
70 |
71 | compared_followers = compared_info.pop()
72 | against_followers = against_info.pop()
73 |
74 | results = {'A': compared_followers, 'B': against_followers}
75 |
76 | print_data_info(compared_info, 'Compare A: ')
77 | print(VS_LOGO)
78 | print_data_info(against_info, 'Compare B: ')
79 |
80 | user_answer = get_user_answer(
81 | f"\nWho has more followers? Type 'A ' or 'B': ")
82 |
83 | correct_answer = get_highest_followers_count(compared_followers,
84 | against_followers)
85 | user_result = results[user_answer]
86 |
87 | if (user_result) == correct_answer:
88 | clear_console()
89 | print()
90 | score += user_result
91 | compared_data = against_data
92 | starting = False
93 | print(Fore.CYAN + "Correct!")
94 | print(f"\nScore: {score}\n")
95 |
96 | else:
97 | clear_console()
98 | print(Fore.RED + f"Wrong Answer!")
99 | print(f"Score: {str(score)}")
100 | play_again()
101 | break
102 |
103 |
104 | def get_data_info(data):
105 | name = data['name']
106 | description = data['description']
107 | country = data['country']
108 | follower_count = data['follower_count']
109 |
110 | return [name, description, country, follower_count]
111 |
112 |
113 | def print_data_info(data, string):
114 | name, description, country = data
115 | an_or_a = 'an' if description[0][0] in 'AEIOU' else 'a'
116 | color_string = Fore.RED if 'A' in string else Fore.CYAN
117 | print(
118 | f"{color_string + string} {Fore.YELLOW + name}, {an_or_a} {description}, from {country}."
119 | )
120 |
121 |
122 | def main():
123 | init(autoreset=True)
124 | print(Fore.MAGENTA + LOGO)
125 | try:
126 | play_higher_lower()
127 | except KeyboardInterrupt:
128 | sys.exit()
129 |
130 |
131 | if __name__ == "__main__":
132 | print(os.getcwd())
133 | main()
134 |
--------------------------------------------------------------------------------
/src/day_14/logo.py:
--------------------------------------------------------------------------------
1 | LOGO = """
2 | __ ___ __
3 | / / / (_)___ _/ /_ ___ _____
4 | / /_/ / / __ `/ __ \/ _ \/ ___/
5 | / __ / / /_/ / / / / __/ /
6 | /_/ ///_/\__, /_/ /_/\___/_/
7 | / / /____/_ _____ _____
8 | / / / __ \ | /| / / _ \/ ___/
9 | / /___/ /_/ / |/ |/ / __/ /
10 | /_____/\____/|__/|__/\___/_/
11 | """
12 |
13 | VS_LOGO = """
14 | _ __
15 | | | / /____
16 | | | / / ___/
17 | | |/ (__ )
18 | |___/____(_)
19 | """
--------------------------------------------------------------------------------
/src/day_15/README.md:
--------------------------------------------------------------------------------
1 | # Coffee Machine
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_15/main.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/src/day_15/coffee.py:
--------------------------------------------------------------------------------
1 | import sys
2 | import time
3 | from colorama import init, Fore
4 |
5 |
6 | class CoffeeIngredients:
7 | def __init__(self, water: int, milk: int, coffee_beans: int):
8 | self._water = water
9 | self._milk = milk
10 | self._coffee_beans = coffee_beans
11 |
12 | @property
13 | def water(self):
14 | return self._water
15 |
16 | @water.setter
17 | def water(self, new_value):
18 | if (new_value <= 0):
19 | self._water = 0
20 | else:
21 | self._water = new_value
22 |
23 | @property
24 | def milk(self):
25 | return self._milk
26 |
27 | @milk.setter
28 | def milk(self, new_value):
29 | if (new_value <= 0):
30 | self._milk = 0
31 | else:
32 | self._milk = new_value
33 |
34 | @property
35 | def coffee_beans(self):
36 | return self._coffee_beans
37 |
38 | @coffee_beans.setter
39 | def coffee_beans(self, new_value):
40 | if (new_value <= 0):
41 | self._coffee_beans = 0
42 | else:
43 | self._coffee_beans = new_value
44 |
45 | def __repr__(self):
46 | return f"""{Fore.BLUE}Water: {self.water:>12}ml
47 | {Fore.WHITE}Milk: {self.milk:>13}ml
48 | {Fore.LIGHTYELLOW_EX}Coffee beans: {self.coffee_beans:>5}g
49 | """
50 |
51 |
52 | class Coffee:
53 | def __init__(self, ingredients: CoffeeIngredients, price: float):
54 | self.ingredients = ingredients
55 | self.price = price
56 |
57 | def __repr__(self):
58 | return f"{self.ingredients}{Fore.GREEN}Money: {'$'+ str(self.price):>9}"
59 |
60 | def get_water(self):
61 | return self.ingredients.water
62 |
63 | def get_milk(self):
64 | return self.ingredients.milk
65 |
66 | def get_coffee_beans(self):
67 | return self.ingredients.coffee_beans
68 |
69 |
70 | class Latte(Coffee):
71 | def __init__(self, water, milk, coffee_beans, price):
72 | super().__init__(CoffeeIngredients(water, milk, coffee_beans), price)
73 | self.name = 'Latte'
74 |
75 | def __repr__(self):
76 | return f"Latte:\n\n{Coffee.__repr__(self)}"
77 |
78 |
79 | class Cappuccino(Coffee):
80 | def __init__(self, water, milk, coffee_beans, price):
81 | super().__init__(CoffeeIngredients(water, milk, coffee_beans), price)
82 | self.name = 'Cappuccino'
83 |
84 | def __repr__(self):
85 | return f"Cappuccino:\n\n{Coffee.__repr__(self)}"
86 |
87 |
88 | class Espresso(Coffee):
89 | def __init__(self, water, milk, coffee_beans, price):
90 | super().__init__(CoffeeIngredients(water, milk, coffee_beans), price)
91 | self.name = 'Espresso'
92 |
93 | def __repr__(self):
94 | return f"Espresso:\n\n{Coffee.__repr__(self)}"
95 |
96 |
97 | class CoffeeMachine:
98 | def __init__(self, ingredients: CoffeeIngredients, coffees: list,
99 | total_money: float):
100 | self.ingredients = ingredients
101 | self._total_money = total_money
102 | self.coffees = coffees
103 |
104 | def get_logo(self):
105 | return """ ) (
106 | ( ) )
107 | ) ( (
108 | _______)_
109 | .-'---------|
110 | ( C|/\/\/\/\/|
111 | '-./\/\/\/\/|
112 | '_________'
113 | '-------'
114 | """
115 |
116 | def shut_down_coffee_machine(self):
117 | print("The coffee machine is shutting down..")
118 | sys.exit()
119 |
120 | def ask_user_to_pay_coffee(self, coffee_name, price):
121 | try:
122 | user_money = float(
123 | input(
124 | f"{coffee_name} costs ${price:.2f}, please insert the money here: $"
125 | ))
126 | assert user_money >= price
127 |
128 | if (user_money > self.total_money):
129 | print(
130 | Fore.RED +
131 | f"Sorry! I only have ${self.total_money}, please enter a correct amount"
132 | )
133 | return self.ask_user_to_pay_coffee(coffee_name, price)
134 | except (ValueError, AssertionError):
135 | print(Fore.RED + "Error, please enter a correct amount")
136 | return self.ask_user_to_pay_coffee(coffee_name, price)
137 |
138 | else:
139 | return user_money
140 |
141 | def prepare_coffee(self, coffee_name: str):
142 | for coffee in self.coffees:
143 | if coffee.name == coffee_name:
144 | can_make_coffee = self.check_enough_ingredients_to_make_a_coffee(
145 | coffee)
146 |
147 | if can_make_coffee:
148 | user_money = self.ask_user_to_pay_coffee(
149 | coffee.name, coffee.price)
150 |
151 | user_has_money = self.check_user_has_enough_money(
152 | user_money,
153 | coffee.price,
154 | )
155 | machine_has_money = self.check_machine_has_enough_money(
156 | user_money)
157 |
158 | if (user_has_money and machine_has_money):
159 | self.make_coffee(coffee, coffee_name)
160 | return self.give_user_change(user_money, coffee)
161 |
162 | else:
163 | return False
164 |
165 | def pause_coffee_machine(self, seconds):
166 | print('...')
167 | time.sleep(seconds)
168 |
169 | def check_machine_has_enough_money(self, user_money):
170 | return self.total_money >= user_money
171 |
172 | def check_user_has_enough_money(self, user_money: float,
173 | coffee_price: float):
174 | return user_money >= coffee_price
175 |
176 | def give_user_change(self, user_money: float, coffee: Coffee):
177 | coffee_price = coffee.price
178 | change = user_money - coffee_price
179 | self.total_money += coffee_price
180 | return change
181 |
182 | def make_coffee(self, coffee: Coffee, coffee_name: str):
183 | print(f"Preparing your {coffee_name}!")
184 | self.pause_coffee_machine(1.5)
185 | print(f"\nHere is your {coffee.name} ☕. Enjoy!")
186 |
187 | coffee_water = coffee.get_water()
188 | coffee_milk = coffee.get_milk()
189 | coffee_beans = coffee.get_coffee_beans()
190 |
191 | self.ingredients.water = self.ingredients.water - coffee_water
192 | self.ingredients.milk = self.ingredients.milk - coffee_milk
193 | self.ingredients.coffee_beans = self.ingredients._coffee_beans - coffee_beans
194 |
195 | def check_enough_ingredients_to_make_a_coffee(self, coffee: Coffee):
196 | total_water = self.ingredients.water
197 | total_milk = self.ingredients.milk
198 | total_coffee_beans = self.ingredients.coffee_beans
199 |
200 | if (total_water < coffee.get_water() or total_water <= 1):
201 | print(Fore.RED + f"Not enough water to make a {coffee.name}")
202 | return False
203 | elif (total_milk < coffee.get_milk() or total_milk <= 1):
204 | print(Fore.RED + f"Not enough milk to make a {coffee.name}")
205 | return False
206 | elif total_coffee_beans < coffee.get_coffee_beans(
207 | ) or total_coffee_beans <= 1:
208 | print(Fore.RED +
209 | f"Not enough coffee beans to make a {coffee.name}")
210 | return False
211 | else:
212 | return True
213 |
214 | def print_report(self):
215 | print("Coffee Machine: \n")
216 | print(
217 | f"{self.ingredients}{Fore.GREEN}Money: {'$'+ str(self.total_money):>12}"
218 | )
219 |
220 | @property
221 | def total_money(self):
222 | return self._total_money
223 |
224 | @total_money.setter
225 | def total_money(self, new_value):
226 | self._total_money = new_value
227 |
--------------------------------------------------------------------------------
/src/day_15/main.py:
--------------------------------------------------------------------------------
1 | import sys
2 | import os
3 | import time
4 | from colorama import init, Fore
5 |
6 | from coffee import CoffeeIngredients, CoffeeMachine, Latte, Cappuccino, Espresso
7 |
8 |
9 | def clear_console():
10 | os.system('cls' if os.name == 'nt' else 'clear')
11 |
12 |
13 | def ask_user_coffee_machine_commands(string, error_msg):
14 | commands = ['1', '2', '3', 'off', 'report']
15 |
16 | try:
17 | choice = input(string).strip().lower()
18 | assert choice in commands
19 | except (AssertionError, ValueError):
20 | clear_console()
21 | print(Fore.RED + error_msg)
22 | return ask_user_coffee_machine_commands(string, error_msg)
23 | else:
24 | return choice
25 |
26 |
27 | def get_default_coffees():
28 | coffees = [
29 | Latte(water=200, milk=150, coffee_beans=24, price=2.5),
30 | Cappuccino(water=250, milk=100, coffee_beans=24, price=3.0),
31 | Espresso(water=50, milk=0, coffee_beans=18, price=1.5),
32 | ]
33 | return coffees
34 |
35 |
36 | def get_default_coffee_ingredients():
37 | return CoffeeIngredients(water=500, milk=500, coffee_beans=500)
38 |
39 |
40 | def print_coffee_machine_report(coffee_machine):
41 | coffee_machine.print_report()
42 |
43 |
44 | def get_coffee(coffee_machine, coffee_name):
45 | for coffee in coffee_machine.coffees:
46 | if coffee.name == coffee_name:
47 | coffee_machine.check_enough_ingredients_to_make_a_coffee(coffee)
48 |
49 |
50 | def make_user_coffee(coffee_machine: CoffeeMachine, user_choice):
51 | choices_coffees = {'1': 'Latte', '2': 'Espresso', '3': 'Cappuccino'}
52 | change = coffee_machine.prepare_coffee(choices_coffees[user_choice])
53 |
54 | time.sleep(1.2)
55 | if change:
56 | print(f"\nHere is your change: ${change:.2f}!\n")
57 |
58 | elif change == False:
59 | coffee_name = choices_coffees[user_choice]
60 | if not coffee_machine.ingredients.water:
61 | print(Fore.RED + f"No more water to make a coffee!")
62 | elif not coffee_machine.ingredients.milk:
63 | print(Fore.RED + f"No more milk to make a coffee!")
64 | elif not coffee_machine.ingredients._coffee_beans:
65 | print(Fore.RED + f"No more coffee beans to make a coffee!")
66 |
67 | coffee_machine.print_report()
68 | print("\nSomeone will come to refill the machine, come back later!")
69 | coffee_machine.shut_down_coffee_machine()
70 | else:
71 | return False
72 |
73 |
74 | def ask_user_another_coffee(coffee_machine):
75 | try:
76 |
77 | choice = input(
78 | "Do you want to buy another coffee ? (y/n)").strip().lower()[:1]
79 | assert choice in 'yn'
80 | except AssertionError:
81 | print(Fore.RED + "PLease enter 'y' for yes or 'n' for no\n")
82 | return ask_user_another_coffee(coffee_machine)
83 | else:
84 | return choice
85 |
86 |
87 | def user_interface(coffee_machine):
88 |
89 | clear_console()
90 |
91 | print(Fore.YELLOW + coffee_machine.get_logo())
92 |
93 | while True:
94 | special_commands = {
95 | 'off': coffee_machine.shut_down_coffee_machine,
96 | 'report': coffee_machine.print_report
97 | }
98 |
99 | choice = ask_user_coffee_machine_commands(
100 | "Choose a coffee to buy: (1) Latte - (2) Espresso - (3) Cappuccino: ",
101 | "Please enter a valid command")
102 | clear_console()
103 |
104 | if choice not in special_commands:
105 | make_user_coffee(coffee_machine, choice)
106 | another_coffee = ask_user_another_coffee(coffee_machine)
107 | if another_coffee == 'y':
108 | clear_console()
109 | user_interface(coffee_machine)
110 | else:
111 | print('Ok bye')
112 | sys.exit()
113 | else:
114 | special_function = special_commands[choice]
115 | special_function()
116 |
117 |
118 | def main():
119 | coffee_machine = CoffeeMachine(
120 | ingredients=get_default_coffee_ingredients(),
121 | total_money=12,
122 | coffees=get_default_coffees())
123 |
124 | init(autoreset=True)
125 | try:
126 | user_interface(coffee_machine)
127 | except KeyboardInterrupt:
128 | sys.exit()
129 |
130 |
131 | if __name__ == "__main__":
132 | main()
--------------------------------------------------------------------------------
/src/day_16/README.md:
--------------------------------------------------------------------------------
1 | # Tic Tac Toe
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_16/main.py)
4 |
5 | ## Demo:
6 |
7 |
--------------------------------------------------------------------------------
/src/day_16/main.py:
--------------------------------------------------------------------------------
1 | import random
2 | import os
3 | import sys
4 |
5 | from functools import partial
6 | from colorama import Fore, init
7 |
8 | from tic_tac_toe import TicTacToe
9 | from user_interface import UserInterface
10 |
11 |
12 | def clear_console():
13 | os.system('cls' if os.name == 'nt' else 'clear')
14 |
15 |
16 | def get_player_pos(player, ui):
17 | error_message = ui.create_error_message('Please enter a correct position!')
18 | return ui.handle_exception(partial(ui.ask_player_a_position, player),
19 | error_message)
20 |
21 |
22 | def get_player_symbol(player, ui):
23 | clear_console()
24 | error_message = ui.create_error_message(
25 | 'Please enter a correct symbol! Numbers are not allowed')
26 | return ui.handle_exception(partial(ui.ask_player_to_choose_symbol, player),
27 | error_message)
28 |
29 |
30 | def get_player_name(ui):
31 | clear_console()
32 | error_message = ui.create_error_message(
33 | 'Please enter a correct symbol! Numbers are not allowed')
34 | return ui.handle_exception(ui.ask_player_name, error_message)
35 |
36 |
37 | def player_plays(player, player_symbol, game_board, userinterface, rounds):
38 | clear_console()
39 | print(f"Round {rounds}:\n")
40 | game_board.print_board()
41 | print(f"\n{player}, It's your turn: \n")
42 | p1_pos = get_player_pos(player, userinterface)
43 |
44 | while game_board.check_position_is_taken(p1_pos):
45 | clear_console()
46 | print(Fore.RED + "This position is already taken")
47 | game_board.print_board()
48 | p1_pos = get_player_pos(player, userinterface)
49 |
50 | game_board.put_player_symbol(player_symbol, p1_pos)
51 |
52 |
53 | def get_winner(game_board, scores):
54 | if (game_board.check_winner()):
55 | winner = game_board.get_winner_name_by_symbol()
56 | scores[winner] += 1
57 | print(f"\n{winner} wins!")
58 | return
59 |
60 |
61 | def play_game(p1_name, p2_name, userinterface, scores, rounds):
62 | clear_console()
63 |
64 | players_symbols = userinterface.players_symbols
65 |
66 | has_won = False
67 | game_board = TicTacToe(players_symbols)
68 |
69 | players = [p1_name, p2_name]
70 | index = random.randint(0, 1)
71 |
72 | first_player = players.pop(index)
73 | other_player = players.pop()
74 |
75 | p1_symbol = players_symbols[first_player]
76 | p2_symbol = players_symbols[other_player]
77 |
78 | while True:
79 | player_plays(first_player, p1_symbol, game_board, userinterface,
80 | rounds)
81 | has_won = game_board.check_winner()
82 |
83 | if has_won:
84 | clear_console()
85 | game_board.print_board()
86 | get_winner(game_board, scores)
87 | break
88 |
89 | if (game_board.is_board_full()):
90 | clear_console()
91 | game_board.print_board()
92 | print("\nIt's a draw!")
93 | break
94 |
95 | player_plays(other_player, p2_symbol, game_board, userinterface,
96 | rounds)
97 | has_won = game_board.check_winner()
98 |
99 | if has_won:
100 | clear_console()
101 | game_board.print_board()
102 | get_winner(game_board, scores)
103 | break
104 |
105 | if (game_board.is_board_full()):
106 | print("\nIt's a draw!")
107 | break
108 |
109 | clear_console()
110 | print_scores(scores)
111 | rounds += 1
112 | play_again(p1_name, p2_name, userinterface, scores, rounds)
113 |
114 |
115 | def play_again(p1_name, p2_name, userinterface, scores, rounds):
116 | choice = input("\nPress enter to play again!").strip()
117 | if not choice:
118 | play_game(p1_name, p2_name, userinterface, scores, rounds)
119 | else:
120 | sys.exit()
121 |
122 |
123 | def print_scores(scores):
124 | for k, v in scores.items():
125 | print(f"\n{k}, score: {Fore.BLUE} {v}")
126 |
127 |
128 | def user_interface():
129 | user_interface = UserInterface()
130 |
131 | p1_name = get_player_name(user_interface)
132 | p2_name = get_player_name(user_interface)
133 |
134 | p1_symbol = get_player_symbol(p1_name, user_interface)
135 | p2_symbol = get_player_symbol(p2_name, user_interface)
136 |
137 | user_interface.print_symbol(p1_name, p1_symbol)
138 | user_interface.print_symbol(p2_name, p2_symbol)
139 |
140 | scores = {p1_name: 0, p2_name: 0}
141 | rounds = 1
142 | play_game(p1_name, p2_name, user_interface, scores, rounds)
143 |
144 |
145 | def main():
146 | try:
147 | user_interface()
148 | except KeyboardInterrupt:
149 | pass
150 |
151 |
152 | if __name__ == "__main__":
153 | init(autoreset=True)
154 | main()
155 |
--------------------------------------------------------------------------------
/src/day_16/tic_tac_toe.py:
--------------------------------------------------------------------------------
1 | import sys
2 | from colorama import Fore, init
3 |
4 |
5 | class TicTacToe:
6 | def __init__(self, player_symbols):
7 | self.board = self.create_board()
8 | self.player_symbols = player_symbols
9 | self.symbols_counts = {k: 0 for k in self.player_symbols.values()}
10 | self.symbol_winner = 'None'
11 | self.board_positions = {
12 | 1: [0, 0],
13 | 2: [0, 1],
14 | 3: [0, 2],
15 | 4: [1, 0],
16 | 5: [1, 1],
17 | 6: [1, 2],
18 | 7: [2, 0],
19 | 8: [2, 1],
20 | 9: [2, 2]
21 | }
22 |
23 | self.winning_positions = [
24 | # rows
25 | [[0, 0], [0, 1], [0, 2]],
26 | [[1, 0], [1, 1], [1, 2]],
27 | [[2, 0], [2, 1], [2, 2]],
28 | # cols
29 | [[0, 0], [1, 0], [2, 0]],
30 | [[0, 1], [1, 1], [2, 1]],
31 | [[0, 2], [1, 2], [2, 2]],
32 | # diagonals
33 | [[0, 0], [1, 1], [2, 2]],
34 | [[2, 0], [1, 1], [0, 2]],
35 | ]
36 |
37 | def create_board(self):
38 | return [[' ', ' ', ' '], [' ', ' ', ' '], [' ', ' ', ' ']]
39 |
40 | def get_board(self, board):
41 | return (Fore.YELLOW +
42 | "\n---------\n".join([" | ".join(i) for i in board]))
43 |
44 | def check_position_is_taken(self, pos):
45 | row, col = self.board_positions[pos]
46 | return not self.board[row][col] == ' '
47 |
48 | def put_player_symbol(self, player_symbol, pos):
49 | row, col = self.board_positions[pos]
50 | self.board[row][col] = player_symbol
51 |
52 | def is_board_full(self):
53 | for row, col in self.board_positions.values():
54 | board_item = self.board[row][col]
55 | if (board_item.isspace()):
56 | return False
57 | return True
58 |
59 | def print_board(self):
60 | print(self.get_board(self.board))
61 |
62 | def get_winner_name_by_symbol(self):
63 | symbols_players = {k: v for (v, k) in self.player_symbols.items()}
64 | if self.symbol_winner in symbols_players:
65 | winner = symbols_players[self.symbol_winner]
66 | return winner
67 |
68 | def check_winner(self):
69 | p1_list = []
70 | p2_list = []
71 |
72 | p1_symbol, p2_symbol = self.player_symbols.values()
73 |
74 | for winning_position in self.winning_positions:
75 | for pos in winning_position:
76 | row, col = pos
77 | item = self.board[row][col]
78 | if item == p1_symbol:
79 | p1_list.append(1)
80 | elif item == p2_symbol:
81 | p2_list.append(1)
82 |
83 | if len(p1_list) == 3:
84 | self.symbol_winner = p1_symbol
85 | return True
86 |
87 | if len(p2_list) == 3:
88 | self.symbol_winner = p2_symbol
89 | return True
90 |
91 | p1_list.clear()
92 | p2_list.clear()
93 |
94 | return False
95 |
--------------------------------------------------------------------------------
/src/day_16/user_interface.py:
--------------------------------------------------------------------------------
1 | from colorama import Fore, init
2 | from tic_tac_toe import TicTacToe
3 | import random
4 |
5 |
6 | class UserInterface:
7 | def __init__(self):
8 | self.players_symbols = {}
9 | self.player_count = 1
10 |
11 | def ask_player_name(self):
12 | player_name = input(f"Player {self.player_count}: ").strip().title()
13 | assert len(player_name)
14 |
15 | if player_name in self.players_symbols:
16 | print(Fore.RED +
17 | "This name is already taken! Please choose another one")
18 | return self.ask_player_name()
19 |
20 | self.players_symbols[player_name] = ''
21 | self.player_count += 1
22 | return player_name
23 |
24 | def check_player_names(self, player):
25 | return player in self.players_symbols
26 |
27 | def create_error_message(self, error_message):
28 | return Fore.RED + error_message
29 |
30 | def handle_exception(self, function, error_message):
31 | try:
32 | return function()
33 | except (AssertionError, ValueError):
34 | print(error_message)
35 | return self.handle_exception(function, error_message)
36 |
37 | def ask_player_to_choose_symbol(self, player):
38 | symbol = ''
39 | if player == 'Bot':
40 | symbol = random.choice(['o', 'x']).upper()
41 | else:
42 | symbol = input(
43 | f"\n{player}, Choose a symbol for the game: ").upper().strip()
44 | assert not symbol.isdigit() and len(symbol) == 1
45 | if (self.check_symbols(symbol)):
46 | print(Fore.RED +
47 | "This symbol is taken, please choose another one\n")
48 | return self.ask_player_to_choose_symbol(player)
49 | else:
50 | self.players_symbols[player] = symbol
51 | return symbol
52 |
53 | def ask_player_a_position(self, player):
54 | if player == 'Bot':
55 | return random.randint(1, 9)
56 | else:
57 | pos = input(f"Choose a position: ").strip()
58 | assert 1 <= int(pos) <= 9
59 | return int(pos)
60 |
61 | def print_symbol(self, player, symbol):
62 | print(f"{player} plays with {symbol}\n")
63 |
64 | def check_symbols(self, symbol):
65 | return symbol in self.players_symbols.values()
66 |
--------------------------------------------------------------------------------
/src/day_17/README.md:
--------------------------------------------------------------------------------
1 | # Quiz Program
2 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_17/main.py)
3 |
4 | ## Demo:
5 |
6 |
7 |
--------------------------------------------------------------------------------
/src/day_17/main.py:
--------------------------------------------------------------------------------
1 | # Quiz
2 | import os
3 | import sys
4 | import requests
5 |
6 | from colorama import Fore, init
7 |
8 | from question import Question
9 | from quiz import Quiz
10 |
11 |
12 | def get_questions_data_from(url):
13 | response = requests.get(url)
14 | return response.json()['results']
15 |
16 |
17 | def clear_console():
18 | os.system('cls' if os.name == 'nt' else 'clear')
19 |
20 |
21 | def get_questions_from(questions_dict):
22 | question_objects = []
23 |
24 | for q in questions_dict:
25 | question = remove_unreadable_parts(q['question'])
26 | correct_answer = remove_unreadable_parts(q['correct_answer'])
27 | incorrect_answers = remove_unreadable_parts(q['incorrect_answers'])
28 |
29 | question_objects.append(
30 | Question(question, correct_answer, incorrect_answers))
31 | return question_objects
32 |
33 |
34 | def run_quiz(quiz: Quiz):
35 | clear_console()
36 | print(quiz)
37 |
38 | while True:
39 | question_object = quiz.get_user_a_question()
40 | correct_answer = question_object.correct_answer
41 | # question = question_object.question
42 | incorrect_answers = question_object.incorrect_answers
43 | quiz.display_list_of_possible_answers(incorrect_answers,
44 | correct_answer)
45 | user_answer = quiz.ask_user_an_answer("Answer: ")
46 | result = quiz.get_result_from_user_answer(user_answer, correct_answer)
47 |
48 | string_false_answer = f"{Fore.RED}False!\n{Fore.WHITE}The correct answer is:{Fore.GREEN} {correct_answer}\n"
49 | string_correct_answer = f"{Fore.GREEN}Correct!\n"
50 |
51 | if result:
52 | clear_console()
53 | print("*" * 55)
54 | print(string_correct_answer)
55 | quiz.player_score += 1
56 |
57 | else:
58 | clear_console()
59 | print(string_false_answer)
60 | quiz.player_lives -= 1
61 | print("*" * 55)
62 |
63 | if quiz.check_user_has_done_every_question():
64 | clear_console()
65 | print(
66 | f"{Fore.BLUE} Congratulations! You finished the whole Quiz without losing!!"
67 | )
68 | quiz.print_player_score()
69 | break
70 |
71 | if not quiz.player_lives:
72 | quiz.print_player_score()
73 | print(
74 | f"{Fore.RED}No more lives left...{Fore.RESET} Do you want to try again? (y/n)"
75 | )
76 | play_again()
77 | quiz.print_player_score()
78 |
79 |
80 | def play_again():
81 | choice = input().strip().lower()
82 | return main() if choice == 'y' else sys.exit()
83 |
84 |
85 | def remove_unreadable_parts(string):
86 | if '&' in string and ';' in string:
87 | start = string.index('&')
88 | end = string.index(';')
89 | word = string[start:end + 1]
90 | result = string.replace(word, '')
91 | return result
92 | else:
93 | return string
94 |
95 |
96 | def remove_unreadable_parts_from_list(question_objects):
97 | for q in question_objects:
98 | for string in q.incorrect_answers:
99 | index = q.incorrect_answers.index(string)
100 | q.incorrect_answers[index] = remove_unreadable_parts(string)
101 |
102 |
103 | def main():
104 | init(autoreset=True)
105 | # file_path = os.path.join(os.getcwd(), 'src', 'day_17', 'data.txt')
106 | quiz_data = get_questions_data_from(
107 | "https://opentdb.com/api.php?amount=48&category=18")
108 |
109 | question_objects = get_questions_from(quiz_data)
110 | remove_unreadable_parts_from_list(question_objects)
111 |
112 | quiz = Quiz(question_objects)
113 | run_quiz(quiz)
114 |
115 |
116 | if __name__ == "__main__":
117 | main()
--------------------------------------------------------------------------------
/src/day_17/question.py:
--------------------------------------------------------------------------------
1 | class Question:
2 | def __init__(self, question: str, correct_answer: str,
3 | incorrect_answers: list):
4 | self._question = question
5 | self._correct_answer = correct_answer
6 | self._incorrect_answers = incorrect_answers
7 |
8 | def __repr__(self):
9 | return f"\nQuestion: {str(self._question)}\nAnswer: {str(self._correct_answer)}\nIncorrect Answers{self._incorrect_answers}"
10 |
11 | @property
12 | def question(self):
13 | return str(self._question)
14 |
15 | @property
16 | def correct_answer(self):
17 | return str(self._correct_answer)
18 |
19 | @property
20 | def incorrect_answers(self):
21 | return self._incorrect_answers
22 |
--------------------------------------------------------------------------------
/src/day_17/quiz.py:
--------------------------------------------------------------------------------
1 | import random
2 | from colorama import Fore, init
3 |
4 |
5 | class Quiz:
6 | def __init__(self, question_objects: list):
7 | self.question_objects = question_objects
8 | self.track_questions = []
9 | self.question_counter = 0
10 | self.player_score = 0
11 | self.random_string_colors = [
12 | Fore.BLUE, Fore.GREEN, Fore.MAGENTA, Fore.WHITE, Fore.YELLOW
13 | ]
14 | self.numbers_answers = {}
15 | self.player_lives = 3
16 |
17 | init(autoreset=True)
18 |
19 | def display_list_of_possible_answers(self, incorrect_answers,
20 | correct_answer):
21 | possible_answers = incorrect_answers.copy()
22 | possible_answers.append(correct_answer)
23 |
24 | random.shuffle(possible_answers)
25 |
26 | for index, answer in enumerate(possible_answers):
27 | index += 1
28 | print(f"\n{Fore.WHITE}{str(index)} - {Fore.YELLOW}{answer}")
29 | self.numbers_answers[index] = answer
30 | print()
31 |
32 | def __repr__(self):
33 | return """
34 | 88
35 | ""
36 |
37 | ,adPPYb,d8 88 88 88 888888888
38 | a8" `Y88 88 88 88 a8P"
39 | 8b 88 88 88 88 ,d8P'
40 | "8a ,d88 "8a, ,a88 88 ,d8"
41 | `"YbbdP'88 `"YbbdP'Y8 88 888888888
42 | 88
43 | 88 """
44 |
45 | def get_random_question(self):
46 | question = None
47 | while question is None or question in self.track_questions:
48 | if (self.check_user_has_done_every_question()):
49 | break
50 | question = random.choice(self.question_objects)
51 |
52 | self.track_questions.append(question)
53 | return question
54 |
55 | def check_user_has_done_every_question(self):
56 | return len(self.track_questions) == len(self.question_objects)
57 |
58 | def get_random_color_for_string(self):
59 | return random.choice(self.random_string_colors)
60 |
61 | def get_user_a_question(self):
62 | self.question_counter += 1
63 | color = self.get_random_color_for_string()
64 | question_object = self.get_random_question()
65 | question = question_object.question
66 | print(f"\n{color}Question {self.question_counter}:")
67 | print(f"\n{question}\n")
68 | return question_object
69 |
70 | def get_number_key_from_correct_answer(self, correct_answer):
71 | for number, answer in self.numbers_answers.items():
72 | if answer == correct_answer:
73 | return number
74 |
75 | def get_result_from_user_answer(self, user_answer, correct_answer):
76 | answer_number = self.get_number_key_from_correct_answer(correct_answer)
77 | return True if answer_number == user_answer else False
78 |
79 | def ask_user_an_answer(self, message):
80 | try:
81 | answer = int(input(message).strip())
82 |
83 | assert answer in self.numbers_answers
84 | except (AssertionError, ValueError):
85 | print(Fore.RED + "Please choose a correct number")
86 | return self.ask_user_an_answer(message)
87 | else:
88 | return answer
89 |
90 | def print_player_score(self):
91 | print(f"Score: {self.player_score}/{self.question_counter}")
--------------------------------------------------------------------------------
/src/day_18/README.md:
--------------------------------------------------------------------------------
1 | # Dot Painting
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_18/art.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_18/art.py:
--------------------------------------------------------------------------------
1 | import random
2 | import colorgram
3 |
4 | from turtle import Turtle, Screen
5 |
6 |
7 | def create_pen(shape, color, speed):
8 | pen = Turtle()
9 | pen.shape(shape)
10 | pen.color(color)
11 | pen.speed(speed)
12 |
13 | return pen
14 |
15 |
16 | def get_colors_from_image(image_path, n_colors):
17 | colors_list = []
18 |
19 | for color_object in colorgram.extract(image_path, n_colors):
20 | r, g, b = color_object.rgb
21 | colors_list.append((r, g, b))
22 | return colors_list
23 |
24 |
25 | def get_random_unique_color(colors):
26 | color = random.choice(colors)
27 | return color
28 |
29 |
30 | def draw_art(pen):
31 | image_path = 'src/day_18/images/dots.jpg'
32 | n_colors = 35
33 | colors = get_colors_from_image(image_path, n_colors)
34 | n = 10
35 | x = -280
36 | y = -200
37 |
38 | move_pen(pen, x, y)
39 |
40 | while n:
41 | for _ in range(10):
42 | color = get_random_unique_color(colors)
43 | print(color)
44 | pen.color(color)
45 |
46 | move_forward(pen, 50)
47 | pen.dot(20)
48 | y += 50
49 | move_pen(pen, x, y)
50 | n -= 1
51 |
52 |
53 | def move_forward(pen, distance):
54 | pen.penup()
55 | pen.forward(distance)
56 | pen.pendown()
57 |
58 |
59 | def move_pen(pen, x, y):
60 | pen.penup()
61 | pen.goto(x, y)
62 | pen.pendown()
63 |
64 |
65 | def main():
66 | app = Screen()
67 | app.colormode(255)
68 |
69 | pen = create_pen('classic', 'black', 'fast')
70 | pen.hideturtle()
71 |
72 | draw_art(pen)
73 |
74 | app.mainloop()
75 |
76 |
77 | if __name__ == "__main__":
78 | main()
--------------------------------------------------------------------------------
/src/day_18/images/dots.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_18/images/dots.jpg
--------------------------------------------------------------------------------
/src/day_19/README.md:
--------------------------------------------------------------------------------
1 | # Turtle Race Game
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_19/main.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_19/images/race.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_19/images/race.gif
--------------------------------------------------------------------------------
/src/day_19/main.py:
--------------------------------------------------------------------------------
1 | import os
2 | import random
3 | import sys
4 | import time
5 |
6 | from turtle import Turtle, Screen
7 | from player import Player
8 |
9 |
10 | def get_player_bet_amount(player, app):
11 | player.set_player_bet(
12 | int(
13 | app.numinput(title="Place your bet!",
14 | prompt="Bet amount",
15 | minval=1,
16 | maxval=player.balance)))
17 |
18 |
19 | def get_player_turtle_color(player, app, colors):
20 | colors = get_colors()
21 | turtle_colors = ', '.join([i for i in colors])
22 |
23 | try:
24 | color = (app.textinput(
25 | title="Choose a turtle",
26 | prompt=f"Which turtle will win the race !?\n{turtle_colors}")
27 | ).lower().strip()
28 | assert color in colors
29 | player.set_player_turtle_color(color)
30 | except AssertionError:
31 | get_player_turtle_color(player, app, colors)
32 |
33 |
34 | def move_turtles(turtles, max_distance):
35 | for turtle in turtles:
36 | move_turtle_randomly(turtle, max_distance)
37 | if turtle_has_passed_finish_line(turtle):
38 | return turtle
39 | return False
40 |
41 |
42 | def move_turtle_randomly(turtle, max_distance):
43 | n = random.randint(0, max_distance)
44 | turtle.forward(n)
45 |
46 |
47 | def place_turtle_to_pos(turtle, x, y):
48 | turtle.penup()
49 | turtle.goto(x, y)
50 |
51 |
52 | def get_turtles(colors):
53 | turtles = []
54 | for color in colors:
55 | turtle = Turtle(shape='turtle')
56 | turtle.color(color)
57 | turtle.turtlesize(2)
58 | turtles.append(turtle)
59 | return turtles
60 |
61 |
62 | def get_colors():
63 | return [
64 | 'red',
65 | 'blue',
66 | 'yellow',
67 | 'green',
68 | 'orange',
69 | 'white',
70 | ]
71 |
72 |
73 | def setup_app(app):
74 | app.listen()
75 | app.title("Turtle Race")
76 | app.setup(width=600, height=600)
77 | app.bgpic("src/day_19/images/race.gif")
78 | app.bgcolor('black')
79 |
80 |
81 | def move_turtles_to_starting_positions(turtles):
82 | x = -230
83 | y = -200
84 |
85 | for turtle in turtles:
86 | place_turtle_to_pos(turtle, x, y)
87 | y += 80
88 |
89 |
90 | def check_user_won_bet(winner_color, player):
91 | if winner_color == player.turtle_color:
92 | player.player_wins()
93 | return True
94 | return False
95 |
96 |
97 | def play_again(app, player):
98 | app.reset()
99 | app.bgpic("src/day_19/images/race.gif")
100 | response = app.textinput(
101 | title="Play", prompt=f"Do you want to play again?").lower().strip()
102 | if response == 'yes':
103 | race(app, player)
104 | else:
105 | say_bye(app)
106 |
107 |
108 | def turtle_has_passed_finish_line(turtle):
109 | return turtle.xcor() >= 190
110 |
111 |
112 | def race(app, player):
113 | current_balance_coordinates = (130, 260)
114 | winner_coordinates = (-230, 200)
115 |
116 | balance_pen = set_pen('white', current_balance_coordinates)
117 | winner_pen = set_pen('white', winner_coordinates)
118 |
119 | display_user_balance(balance_pen, player)
120 |
121 | colors = get_colors()
122 | turtles = get_turtles(colors)
123 |
124 | get_player_turtle_color(player, app, colors)
125 | get_player_bet_amount(player, app)
126 |
127 | move_turtles_to_starting_positions(turtles)
128 |
129 | while True:
130 | winner = move_turtles(turtles, max_distance=20)
131 | if winner:
132 | balance_pen.clear()
133 | display_winner(winner_pen, winner)
134 | winner_color = winner.pencolor()
135 | check_user_won_bet(winner_color, player)
136 | display_user_balance(balance_pen, player)
137 | time.sleep(3)
138 | break
139 |
140 | if player.balance_is_zero():
141 | say_bye(app)
142 | else:
143 | play_again(app, player)
144 |
145 |
146 | def display_user_balance(pen, player):
147 | pen.write(f"Balance: ${player.balance}", font=("Arial", 10, "normal"))
148 |
149 |
150 | def say_bye(app):
151 | app.reset()
152 | pen = set_pen('white')
153 | pen.write('Bye bye', font=('Arial', 20, 'normal'))
154 | time.sleep(3)
155 | sys.exit()
156 |
157 |
158 | def set_pen(color, coordinates=(-230, 200)):
159 | x, y = coordinates
160 | pen = Turtle()
161 | pen.pendown
162 | pen.goto(x, y)
163 | pen.pendown
164 | pen.hideturtle()
165 | pen.color(color)
166 | return pen
167 |
168 |
169 | def get_winner_message(color):
170 | return f"{color.title()} turtle wins the race!"
171 |
172 |
173 | def display_winner(pen, winner, coordinates=(-230, 220)):
174 | color = winner.pencolor()
175 | pen = set_pen('white', coordinates)
176 | pen.write(get_winner_message(color), font=('Arial', 12, 'normal'))
177 |
178 |
179 | def main():
180 | try:
181 | player = Player(balance=100)
182 | app = Screen()
183 | setup_app(app)
184 | race(app, player)
185 | app.mainloop()
186 | except:
187 | sys.exit()
188 |
189 |
190 | if __name__ == "__main__":
191 | main()
--------------------------------------------------------------------------------
/src/day_19/player.py:
--------------------------------------------------------------------------------
1 | class Player:
2 | def __init__(self, balance):
3 | self.balance = balance
4 | self.turtle_color = None
5 | self.current_bet = 0
6 |
7 | def set_player_bet(self, bet_amount):
8 | self.current_bet = bet_amount
9 | self.balance -= bet_amount
10 | self.balance_is_zero()
11 |
12 | def balance_is_zero(self):
13 | if self.balance <= 0:
14 | self.balance = 0
15 | return True
16 | return False
17 |
18 | def set_player_turtle_color(self, color):
19 | self.turtle_color = color
20 |
21 | def player_wins(self):
22 | self.balance += self.current_bet * 2
23 |
--------------------------------------------------------------------------------
/src/day_2/README.md:
--------------------------------------------------------------------------------
1 | # Tip Calculator
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_2/tip_calculator.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_2/tip_calculator.py:
--------------------------------------------------------------------------------
1 | import sys
2 |
3 | # Tip Calculator
4 |
5 |
6 | def run_tip_calculator():
7 | print("Welcome to the tip calculator.")
8 |
9 | total_bill = float(input("What was the total bill?\n$"))
10 | check_bill(total_bill)
11 |
12 | percentage_tip = check_percentage(
13 | int(input("Choose a percentage tip you would like to give:\n")))
14 |
15 | total_people = check_people(
16 | int(input("How many people to split the bill?\n")))
17 |
18 | total_to_pay = calculate_tip(total_bill, percentage_tip, total_people)
19 |
20 | print(f"You have to pay ", end='') if total_people == 1 else print(
21 | f"Each person should pay ", end='')
22 |
23 | print(f"${total_to_pay:.2f}")
24 |
25 |
26 | def calculate_tip(total_bill, percentage_tip, total_people):
27 | percentage = percentage_tip / 100 * total_bill
28 | total = (total_bill + percentage) / total_people
29 | return total
30 |
31 |
32 | def check_bill(total):
33 | if total <= 0:
34 | print("It's on the house!")
35 | sys.exit()
36 |
37 |
38 | def check_people(total):
39 | return 1 if total <= 0 else total
40 |
41 |
42 | def check_percentage(total):
43 | return 0 if total <= 0 else total
44 |
45 |
46 | def main():
47 | run_tip_calculator()
48 |
49 |
50 | if __name__ == "__main__":
51 | main()
--------------------------------------------------------------------------------
/src/day_20/README.md:
--------------------------------------------------------------------------------
1 | # Snake Game
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_20/main.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_20/food.py:
--------------------------------------------------------------------------------
1 | import random
2 | from turtle import Turtle
3 |
4 |
5 | class Food(Turtle):
6 | def __init__(self):
7 | super().__init__()
8 | self.shape('square')
9 | self.color('red')
10 | self.penup()
11 | self.pensize(1)
12 | self.speed(0)
13 | self.got_to_random_pos()
14 |
15 | def got_to_random_pos(self):
16 | x, y = self.get_random_pos()
17 | self.goto(x, y)
18 |
19 | def get_random_pos(self):
20 | x = random.randint(-550, 550)
21 | y = random.randint(-350, 350)
22 | return x, y
23 |
--------------------------------------------------------------------------------
/src/day_20/main.py:
--------------------------------------------------------------------------------
1 | import sys
2 | import time
3 |
4 | from turtle import Turtle, Screen
5 | from snake import Snake
6 | from food import Food
7 |
8 | # Constants variables
9 | SCORE_X_Y_COORDINATES = (0, 270)
10 | GAME_OVER_X_Y_COORDINATES = (0, 100)
11 |
12 | FONT_PEN_SETTINGS = ('ROBOTO', 30, 'normal')
13 | FONT_SCORE_PEN_SETTINGS = ('ROBOTO', 15, 'normal')
14 |
15 |
16 | def play_again(app, snake):
17 | pen = create_pen(GAME_OVER_X_Y_COORDINATES)
18 | choice = app.textinput("Play again",
19 | "Do you want to play again?").lower().strip()
20 |
21 | snake.score = 0
22 |
23 | return main() if choice == 'yes' else pen.write(
24 | 'BYE!', align='center',
25 | font=FONT_PEN_SETTINGS), time.sleep(2), app.bye()
26 |
27 |
28 | def setup_app(app):
29 | app.setup(width=1200, height=800)
30 | app.bgcolor('#07470B')
31 | app.title('Snake Game')
32 |
33 |
34 | def play_game(app, snake: Snake):
35 | apple = Food()
36 | pen_score = create_pen(SCORE_X_Y_COORDINATES)
37 | pen_game_over = create_pen(GAME_OVER_X_Y_COORDINATES)
38 |
39 | while True:
40 | app.update()
41 | if snake.check_player_passed_game_boundaries((580, 380)):
42 | display_user_score(pen_score, snake)
43 | display_game_over(pen_game_over)
44 | time.sleep(1)
45 | pen_game_over.clear()
46 | play_again(app, snake)
47 | break
48 | display_user_score(pen_score, snake)
49 |
50 | pen_score.clear()
51 | speed_time = snake.speed
52 | snake.move(snake.get_player_key(app))
53 | time.sleep(speed_time)
54 | if (snake.eat(apple)):
55 | apple.got_to_random_pos()
56 |
57 |
58 | def ask_user_to_pick_snake_color_for(body_part, app):
59 | colors = [
60 | 'red',
61 | 'blue',
62 | 'green',
63 | 'white',
64 | 'pink',
65 | 'orange',
66 | 'purple',
67 | 'black',
68 | ]
69 | colors_text = ' - '.join(colors)
70 | try:
71 | color = app.textinput(
72 | title="Choose a color",
73 | prompt=
74 | f"Pick a color for the {body_part} of the snake\n{colors_text}"
75 | ).lower().strip()
76 |
77 | assert color in colors or color == ''
78 | except AssertionError:
79 | return ask_user_to_pick_snake_color_for(body_part, app)
80 | else:
81 | return color
82 |
83 |
84 | def create_pen(coords):
85 | x, y = coords
86 | pen = Turtle()
87 | pen.penup()
88 | pen.goto(x, y)
89 | pen.color('white')
90 | pen.hideturtle()
91 | return pen
92 |
93 |
94 | def display_user_score(pen, snake):
95 | pen.write(f"Score: {snake.score}",
96 | align="center",
97 | font=FONT_SCORE_PEN_SETTINGS)
98 |
99 |
100 | def display_game_over(pen):
101 | pen.write(f"GAME OVER", align="center", font=FONT_PEN_SETTINGS)
102 |
103 |
104 | def change_snake_colors(app, snake):
105 | body_color = ask_user_to_pick_snake_color_for('body', app)
106 | if body_color: snake.change_snake_body_color(body_color)
107 |
108 | head_color = ask_user_to_pick_snake_color_for('head', app)
109 | if head_color: snake.change_snake_head_color(head_color)
110 |
111 |
112 | def main():
113 | app = Screen()
114 | app.reset()
115 | app.clear()
116 |
117 | setup_app(app)
118 | app.tracer(0)
119 | snake = Snake()
120 |
121 | change_snake_colors(app, snake)
122 |
123 | app.listen()
124 | play_game(app, snake)
125 | app.mainloop()
126 |
127 |
128 | if __name__ == "__main__":
129 | try:
130 | main()
131 | except:
132 | sys.exit()
133 |
--------------------------------------------------------------------------------
/src/day_20/snake.py:
--------------------------------------------------------------------------------
1 | from tkinter.constants import LEFT
2 | from turtle import Turtle, down
3 | from functools import partial
4 |
5 | # Constant Variables
6 | DOWN_VAL = 270
7 | UP_VAL = 90
8 | LEFT_VAL = 180
9 | RIGHT_VAL = 0
10 |
11 | KEYS = 'wasd'
12 | PADDING = 23
13 | # -----------------------------------------------------------------------------------
14 |
15 |
16 | class Snake:
17 | def __init__(
18 | self,
19 | body_color='lime green',
20 | head_color='green yellow',
21 | shape='square',
22 | size=20,
23 | body_length=3,
24 | ):
25 | self.snake_body = []
26 | self.speed = 0.12
27 | self._create_snake_body(body_color, head_color, shape, size,
28 | body_length)
29 | self._place_snake_to_starting_position()
30 | self.snake_head = self.snake_body[0]
31 | self.count_eaten = 0
32 | self.score = 0
33 | self.play_again = False
34 |
35 | def change_snake_head_color(self, color='green yellow'):
36 | self.snake_head.color(color)
37 |
38 | def change_snake_body_color(self, color='lime green'):
39 | for body in self.snake_body[1:]:
40 | body.color(color)
41 |
42 | def _create_snake_body(self, color, head_color, shape, size, body_length):
43 | for i in range(body_length):
44 | turtle = self._create_body_part(shape, head_color, size, color, i)
45 | self.snake_body.append(turtle)
46 |
47 | def _create_body_part(self, shape, head_color, size, color, index=-1):
48 | turtle = Turtle(shape=shape)
49 | turtle.color(head_color) if index == 0 else turtle.color(color)
50 | turtle.pensize(size)
51 | turtle.speed(0)
52 | turtle.penup()
53 | return turtle
54 |
55 | def _place_snake_to_starting_position(self, coords=(0, 0)):
56 | x, y = coords
57 | for body in self.snake_body:
58 | body.goto(x, y)
59 | x -= PADDING
60 |
61 | def eat(self, food: Turtle):
62 | if self.snake_head.distance(food) <= 25:
63 | self.count_eaten += 1
64 | self.grow()
65 | self.score += 1
66 | print('Yummy!')
67 | return True
68 | return False
69 |
70 | def grow(self):
71 | body_part = self.snake_body[-1].clone()
72 | body_part2 = self.snake_body[-1].clone()
73 | self.snake_body.extend([body_part, body_part2])
74 |
75 | if self.count_eaten % 2 == 0:
76 | self.speed -= 0.02
77 | if self.speed <= 0.02:
78 | self.speed = 0.02
79 |
80 | def move(self, command, degree=0):
81 | for i in range(len(self.snake_body) - 1, 0, -1):
82 | pos = 0
83 | if (i >= 0):
84 | pos = self.snake_body[i - 1].pos()
85 | x, y = pos
86 | self.snake_body[i].goto(x, y)
87 | commands = {
88 | 'w': self.snake_head.setheading, # up
89 | 'a': self.snake_head.setheading, # left
90 | 's': self.snake_head.setheading, # down
91 | 'd': self.snake_head.setheading, # right
92 | }
93 | if (command in commands):
94 | move_function = commands[command]
95 | if command == 'w':
96 | if self.snake_head.heading() != DOWN_VAL:
97 | move_function(degree)
98 | elif command == 'a':
99 |
100 | if self.snake_head.heading() != RIGHT_VAL:
101 | move_function(degree)
102 | elif command == 's':
103 | if self.snake_head.heading() != UP_VAL:
104 | move_function(degree)
105 | elif command == 'd':
106 | if self.snake_head.heading() != LEFT_VAL:
107 | move_function(degree)
108 |
109 | self.snake_head.forward(PADDING)
110 |
111 | def get_player_key(self, app):
112 | W, A, S, D = KEYS
113 |
114 | app.onkey(partial(self.move, W, UP_VAL), W)
115 | app.onkey(partial(self.move, A, LEFT_VAL), A)
116 | app.onkey(partial(self.move, S, DOWN_VAL), S)
117 | app.onkey(partial(self.move, D, RIGHT_VAL), D)
118 |
119 | def check_player_passed_game_boundaries(self, coords):
120 | x, y = coords
121 | if self.snake_head.xcor() >= x or self.snake_head.xcor(
122 | ) <= -x or self.snake_head.ycor() >= y or self.snake_head.ycor() <= -y:
123 | return True
124 | for body in self.snake_body[1:]:
125 | if self.snake_head.distance(body) <= 20:
126 | return True
127 |
--------------------------------------------------------------------------------
/src/day_21/README.md:
--------------------------------------------------------------------------------
1 | # Pong Game
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_21/main.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_21/ball.py:
--------------------------------------------------------------------------------
1 | import random
2 | from turtle import Turtle
3 |
4 |
5 | class Ball(Turtle):
6 | def __init__(self):
7 | super().__init__()
8 | self.color('white')
9 | self.shape('circle')
10 | self.penup()
11 | self.x = 10
12 | self.y = 10
13 | self.speed = 0.04
14 |
15 | def move_ball(self):
16 | x, y = self.pos()
17 | x += self.x
18 | y += self.y
19 | self.goto(x, y)
20 |
21 | def bounce_of_wall(self, walls):
22 | up_wall, down_wall = walls
23 | if (self.ycor() >= up_wall + 30 or self.ycor() <= down_wall - 30):
24 | self.bounce_Y()
25 |
26 | def bounce_Y(self):
27 | self.y *= -1
28 |
29 | def bounce_X(self):
30 | self.x *= -1
31 | self.speed -= 0.005
32 | if self.speed <= 0.01:
33 | self.speed = 0.01
34 |
35 | def ball_scored(self, score, limits):
36 | right_limit, left_limit = limits
37 | if (self.xcor() >= right_limit + 30):
38 | self.reset_ball()
39 | return 'right'
40 | if (self.xcor() <= left_limit - 30):
41 | self.reset_ball()
42 | return 'left'
43 |
44 | def bounce_paddle(self, paddles):
45 | left_paddle, bot_paddle = paddles
46 |
47 | if self.distance(left_paddle) < 40 and self.xcor() < -340:
48 | self.bounce_X()
49 | elif self.distance(bot_paddle) < 40 and self.xcor() > 340:
50 | self.bounce_X()
51 |
52 | def is_ball_out_of_bounds(self, limits):
53 | right, left = limits
54 | if self.xcor() >= right or self.xcor() <= left:
55 | self.reset_ball()
56 | return True
57 | return False
58 |
59 | def reset_ball(self):
60 | self.goto(0, 0)
61 | self.speed = 0.04
62 | self.bounce_X()
63 |
--------------------------------------------------------------------------------
/src/day_21/main.py:
--------------------------------------------------------------------------------
1 | import time
2 | import sys
3 |
4 | from turtle import Turtle, Screen
5 | from tkinter import TclError
6 |
7 | from ball import Ball
8 | from score import Score
9 | from paddle import Paddle
10 |
11 | LIMITS_Y = (250, -250)
12 | LIMITS_X = (400, -400)
13 |
14 |
15 | def create_screen():
16 | game_screen = Screen()
17 | game_screen.setup(width=800, height=600)
18 | game_screen.bgcolor('black')
19 | game_screen.tracer(0)
20 | game_screen.listen()
21 | game_screen.title('Pong Game')
22 |
23 | return game_screen
24 |
25 |
26 | def move_bot(paddle):
27 | paddle.bot_move()
28 |
29 |
30 | def display_score(score):
31 | return score
32 |
33 |
34 | def check_winner(result, score):
35 | if result == 'right':
36 | score.left_score += 1
37 | elif result == 'left':
38 | score.right_score += 1
39 | score.update_score()
40 |
41 |
42 | def ball_moves(ball, left_paddle, bot_paddle, score):
43 | ball.move_ball()
44 | ball.bounce_of_wall(LIMITS_Y)
45 | ball.bounce_paddle((left_paddle, bot_paddle))
46 | result = ball.ball_scored(score, LIMITS_X)
47 | check_winner(result, score)
48 |
49 |
50 | def play_pong_game(game_screen):
51 | left_paddle = Paddle()
52 | bot_paddle = Paddle()
53 | ball = Ball()
54 | score = Score()
55 |
56 | bot_paddle.place_paddle_to((350, 0))
57 | left_paddle.place_paddle_to((-350, 0))
58 |
59 | while True:
60 | score
61 | left_paddle.move_up_down(game_screen, LIMITS_Y)
62 | bot_paddle.bot_move(ball, LIMITS_Y)
63 |
64 | ball_moves(ball, left_paddle, bot_paddle, score)
65 |
66 | time.sleep(ball.speed)
67 | game_screen.update()
68 |
69 |
70 | def main():
71 | game_screen = create_screen()
72 | play_pong_game(game_screen)
73 | game_screen.mainloop()
74 |
75 |
76 | if __name__ == "__main__":
77 | try:
78 | main()
79 | except TclError:
80 | sys.exit()
81 |
--------------------------------------------------------------------------------
/src/day_21/paddle.py:
--------------------------------------------------------------------------------
1 | from turtle import Turtle
2 | from functools import partial
3 | import random
4 | import time
5 |
6 | # constant variables
7 | KEYS = ('Up', 'Down')
8 |
9 |
10 | class Paddle(Turtle):
11 | def __init__(self):
12 | super().__init__()
13 | self.color('white')
14 | self.shape('square')
15 | self.shapesize(4, 0.2, 15)
16 | self.penup()
17 |
18 | def place_paddle_to(self, coords: tuple):
19 | x, y = coords
20 | self.goto(x, y)
21 |
22 | def bot_move(self, ball, limits_Y):
23 | n = random.randint(0, 20)
24 | ball_x, ball_y = ball.pos()
25 | x, y = self.pos()
26 | up_limit, down_limit = limits_Y
27 |
28 | if y >= ball_y:
29 | y -= n
30 | else:
31 | y += n
32 | self.goto(x, y)
33 |
34 | def move_up_down(self, game_screen, limits_Y):
35 | UP, DOWN = KEYS
36 | for key in KEYS:
37 | game_screen.onkey(partial(self._move, key, limits_Y), key)
38 |
39 | def _move(self, key, limits_Y):
40 | x, y = self.pos()
41 | up_limit, down_limit = limits_Y
42 | UP, DOWN = KEYS
43 |
44 | if key == UP:
45 | if y >= up_limit - 20:
46 | y -= 100
47 | self.goto(x, y)
48 | self.goto(x, y + 48)
49 | else:
50 | if y <= down_limit + 25:
51 | y += 100
52 | self.goto(x, y)
53 | self.goto(x, y - 48)
54 |
--------------------------------------------------------------------------------
/src/day_21/score.py:
--------------------------------------------------------------------------------
1 | from turtle import Turtle
2 |
3 |
4 | class Score(Turtle):
5 | def __init__(self, color='white'):
6 | super().__init__()
7 | self.color(color)
8 | self.penup()
9 | self.hideturtle()
10 | self.left_score = 0
11 | self.right_score = 0
12 | self.update_score()
13 |
14 | def update_score(self):
15 | self.clear()
16 | self.goto(-100, 200)
17 | self.write_score(self.left_score)
18 | self.goto(100, 200)
19 | self.write_score(self.right_score)
20 |
21 | def write_score(self, score):
22 | self.write(score, align='center', font=('Roboto', 20, 'normal'))
23 |
--------------------------------------------------------------------------------
/src/day_22/README.md:
--------------------------------------------------------------------------------
1 | # Crossy Road Game
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_22/main.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_22/car.py:
--------------------------------------------------------------------------------
1 | from turtle import Turtle
2 |
3 |
4 | class Car(Turtle):
5 | def __init__(self, shape, x, y):
6 | super().__init__()
7 | self.shape(shape)
8 | self.penup()
9 | self.goto(x, y)
10 | self.speed = 4
11 |
12 | def run_over_frog(self, frog: Turtle):
13 | if self.distance(frog) < 48:
14 | return True
15 | return False
16 |
--------------------------------------------------------------------------------
/src/day_22/display.py:
--------------------------------------------------------------------------------
1 | from turtle import Turtle
2 |
3 |
4 | class Display(Turtle):
5 | def __init__(self, color, x, y):
6 | super().__init__()
7 | self.color(color)
8 | self.penup()
9 | self.hideturtle()
10 | self.goto(x, y)
11 |
12 | def display_score(self, level):
13 | self.clear()
14 | self.write(f'Level: {level}', font=('Consolas', 15, 'normal'))
15 |
16 | def display_game_over(self):
17 | self.clear()
18 | self.write(f'Game Over',
19 | align='center',
20 | font=('Consolas', 20, 'normal'))
21 |
--------------------------------------------------------------------------------
/src/day_22/frog.py:
--------------------------------------------------------------------------------
1 | from turtle import Turtle
2 | from functools import partial
3 |
4 |
5 | class Frog(Turtle):
6 | def __init__(self, shape):
7 | super().__init__()
8 | self.shape(shape)
9 | self.penup()
10 | self.go_to_starting_position()
11 | self.lvl = 1
12 |
13 | def reset_lvl(self):
14 | self.lvl = 1
15 |
16 | def go_to_starting_position(self):
17 | self.goto(0, -350)
18 |
19 | def _move(self):
20 | y = self.ycor() + 20
21 | self.goto(0, y)
22 |
23 | def move(self, screen):
24 | """move the frog on up arrow key press"""
25 | screen.onkey(self._move, 'Up')
26 |
27 | def frog_passed_lvl(self, limit):
28 | if self.ycor() >= limit:
29 | self.go_to_starting_position()
30 | self.lvl += 1
31 | return True
32 | return False
33 |
--------------------------------------------------------------------------------
/src/day_22/images/bg0.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_22/images/bg0.png
--------------------------------------------------------------------------------
/src/day_22/images/bg1.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_22/images/bg1.png
--------------------------------------------------------------------------------
/src/day_22/images/bg2.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_22/images/bg2.png
--------------------------------------------------------------------------------
/src/day_22/images/cars/blue_car.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_22/images/cars/blue_car.gif
--------------------------------------------------------------------------------
/src/day_22/images/cars/green_car.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_22/images/cars/green_car.gif
--------------------------------------------------------------------------------
/src/day_22/images/cars/red_car.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_22/images/cars/red_car.gif
--------------------------------------------------------------------------------
/src/day_22/images/cars/yellow_car.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_22/images/cars/yellow_car.gif
--------------------------------------------------------------------------------
/src/day_22/images/frog.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_22/images/frog.gif
--------------------------------------------------------------------------------
/src/day_22/images/frog3.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_22/images/frog3.gif
--------------------------------------------------------------------------------
/src/day_22/images/frog4.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_22/images/frog4.gif
--------------------------------------------------------------------------------
/src/day_22/main.py:
--------------------------------------------------------------------------------
1 | import os
2 | import time
3 | import random
4 | from turtle import Screen
5 |
6 | from car import Car
7 | from frog import Frog
8 | from display import Display
9 |
10 | # constants
11 | IMAGES_PATH = os.path.join(os.getcwd(), 'src', 'day_22', 'images')
12 | BACKGROUND = f"{IMAGES_PATH}/bg2.png"
13 | CARS_IMAGE_PATH = f"{IMAGES_PATH}/cars/"
14 | FROG_IMAGE = f"{IMAGES_PATH}/frog3.gif"
15 |
16 | LIMIT_UP = 300
17 |
18 | # -----------------------------------------------------
19 |
20 |
21 | def get_cars_images_path():
22 | """return a list of the paths of every car image"""
23 | onlyfiles = [
24 | f"{CARS_IMAGE_PATH}{car_file}"
25 | for car_file in os.listdir(CARS_IMAGE_PATH)
26 | if os.path.isfile(os.path.join(CARS_IMAGE_PATH, car_file))
27 | ]
28 | return onlyfiles
29 |
30 |
31 | def create_screen(title='Crossy Road Game',
32 | width=600,
33 | height=600,
34 | color='white',
35 | bg_image=BACKGROUND):
36 | screen = Screen()
37 | screen.tracer(0)
38 | screen.bgcolor(color)
39 | screen.bgpic(bg_image)
40 | screen.listen()
41 | screen.setup()
42 | screen.title(title)
43 |
44 | return screen
45 |
46 |
47 | def set_screen_car_shapes(screen):
48 | """set the screen to add custom car images"""
49 | cars = get_cars_images_path()
50 | for car in cars:
51 | screen.addshape(car)
52 |
53 |
54 | def teleport(car):
55 | """teleport the car when it goes out of bounds"""
56 | if car.xcor() >= 600:
57 | y = car.ycor()
58 | x = car.xcor()
59 | car.goto(-x, y)
60 |
61 |
62 | def change_car_positions(cars):
63 | range_x_slots = [i for i in range(-280, 300, 80)]
64 | range_y_slots = [i for i in range(-280, 300, 120)]
65 |
66 | for car in cars:
67 | x = random.choice(range_x_slots)
68 | y = random.choice(range_y_slots)
69 | if range_y_slots:
70 | range_x_slots.remove(x)
71 |
72 | car.speed += 2
73 | car.goto(x, y)
74 |
75 |
76 | def play_game(screen):
77 | frog = Frog(FROG_IMAGE)
78 |
79 | cars = create_cars()
80 | cars_2 = create_cars()
81 | cars.extend(cars_2)
82 |
83 | score = Display(color='white', x=-450, y=350)
84 | game_over = Display('white', 0, 0)
85 |
86 | while True:
87 | score.display_score(frog.lvl)
88 |
89 | for car in cars:
90 | car.forward(car.speed)
91 | frog.move(screen)
92 | teleport(car)
93 |
94 | if (frog.frog_passed_lvl(LIMIT_UP)):
95 | random_car = random.choice(cars)
96 | random_car.speed += 1
97 |
98 | change_car_positions(cars)
99 | if car.run_over_frog(frog):
100 | game_over.display_game_over()
101 | return
102 |
103 | screen.update()
104 | time.sleep(0.01)
105 |
106 |
107 | def create_cars():
108 | car_paths = get_cars_images_path()
109 | cars = []
110 |
111 | range_x_slots = [i for i in range(-280, 280, 120)]
112 | range_y_slots = [i for i in range(-280, 300, 120)]
113 |
114 | for cp in car_paths:
115 | x = random.choice(range_x_slots)
116 | y = random.choice(range_y_slots)
117 |
118 | if range_y_slots:
119 | range_x_slots.remove(x)
120 |
121 | new_car = Car(cp, x, y)
122 |
123 | cars.append(new_car)
124 |
125 | return cars
126 |
127 |
128 | def main():
129 | screen = create_screen()
130 | set_screen_car_shapes(screen)
131 | screen.addshape(FROG_IMAGE)
132 | play_game(screen)
133 | screen.mainloop()
134 |
135 |
136 | if __name__ == "__main__":
137 | main()
--------------------------------------------------------------------------------
/src/day_23/README.md:
--------------------------------------------------------------------------------
1 | # US map Quiz
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_23/main.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_23/data/50_states.csv:
--------------------------------------------------------------------------------
1 | state,x,y
2 | Alabama,139,-77
3 | Alaska,-204,-170
4 | Arizona,-203,-40
5 | Arkansas,57,-53
6 | California,-297,13
7 | Colorado,-112,20
8 | Connecticut,297,96
9 | Delaware,275,42
10 | Florida,220,-145
11 | Georgia,182,-75
12 | Hawaii,-317,-143
13 | Idaho,-216,122
14 | Illinois,95,37
15 | Indiana,133,39
16 | Iowa,38,65
17 | Kansas,-17,5
18 | Kentucky,149,1
19 | Louisiana,59,-114
20 | Maine,319,164
21 | Maryland,288,27
22 | Massachusetts,312,112
23 | Michigan,148,101
24 | Minnesota,23,135
25 | Mississippi,94,-78
26 | Missouri,49,6
27 | Montana,-141,150
28 | Nebraska,-61,66
29 | Nevada,-257,56
30 | New Hampshire,302,127
31 | New Jersey,282,65
32 | New Mexico,-128,-43
33 | New York,236,104
34 | North Carolina,239,-22
35 | North Dakota,-44,158
36 | Ohio,176,52
37 | Oklahoma,-8,-41
38 | Oregon,-278,138
39 | Pennsylvania,238,72
40 | Rhode Island,318,94
41 | South Carolina,218,-51
42 | South Dakota,-44,109
43 | Tennessee,131,-34
44 | Texas,-38,-106
45 | Utah,-189,34
46 | Vermont,282,154
47 | Virginia,234,12
48 | Washington,-257,193
49 | West Virginia,200,20
50 | Wisconsin,83,113
51 | Wyoming,-134,90
--------------------------------------------------------------------------------
/src/day_23/data/blank_states_img.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_23/data/blank_states_img.gif
--------------------------------------------------------------------------------
/src/day_23/main.py:
--------------------------------------------------------------------------------
1 | import pandas
2 | import os
3 | import time
4 |
5 | from functools import partial
6 | from turtle import Turtle, Screen
7 |
8 | IMAGE_PATH = os.path.abspath('./src/day_23/data/blank_states_img.gif')
9 | DATA_PATH = os.path.abspath('./src/day_23/data/50_states.csv')
10 |
11 |
12 | def display_score(pen, score):
13 | pen.goto(-200, 210)
14 | pen.write(f"Score: {score}/50", font=('Arial', 12, 'normal'))
15 |
16 |
17 | def display_lives(pen, lives):
18 | pen.goto(80, 220)
19 | pen.write(f"Lives left: {lives} ", font=('Arial', 8, 'normal'))
20 |
21 |
22 | def get_states_data():
23 | return pandas.read_csv(DATA_PATH)
24 |
25 |
26 | def create_screen():
27 | screen = Screen()
28 | screen.bgpic(IMAGE_PATH)
29 | screen.setup(width=700, height=500)
30 | screen.title("US States Quiz")
31 | screen.listen()
32 | return screen
33 |
34 |
35 | def get_state_name_coordinate_dict(states_data):
36 | state_name_coordinates = {}
37 |
38 | states_names = states_data['state'].tolist()
39 | states_x = states_data['x'].tolist()
40 | states_y = states_data['y'].tolist()
41 |
42 | for i in range(len(states_names)):
43 | state_name_coordinates[states_names[i]] = (states_x[i], states_y[i])
44 |
45 | return state_name_coordinates
46 |
47 |
48 | def get_state_names(states_data):
49 | states_names = states_data['state'].tolist()
50 | return states_names
51 |
52 |
53 | def create_pen():
54 | pen = Turtle()
55 | pen.penup()
56 | pen.hideturtle()
57 | pen.speed(0)
58 | return pen
59 |
60 |
61 | def play_US_state_quiz(screen):
62 | score = 0
63 | lives = 3
64 |
65 | pen = create_pen()
66 | pen_score = create_pen()
67 | pen_game_over = create_pen()
68 | pen_lives = create_pen()
69 |
70 | states_data = get_states_data()
71 | states_names = get_state_names(states_data)
72 | state_name_coordinates = get_state_name_coordinate_dict(states_data)
73 |
74 | while states_names and lives:
75 | pen_lives.clear()
76 | display_lives(pen_lives, lives)
77 |
78 | user_state_name = ask_user_to_guess_state(screen)
79 |
80 | if check_user_response(user_state_name, states_names):
81 | screen.onclick(partial(write_to_map, pen, user_state_name))
82 | x, y = state_name_coordinates[user_state_name]
83 | write_to_map(pen, user_state_name, x, y)
84 | states_names.remove(user_state_name)
85 | score += 1
86 | else:
87 | lives -= 1
88 |
89 | pen_score.clear()
90 |
91 | display_score(pen_score, score)
92 |
93 | if not lives:
94 | pen_lives.clear()
95 | display_lives(pen_lives, lives)
96 |
97 | pen_score.clear()
98 | display_game_over(pen_game_over)
99 | display_score(pen_score, score)
100 | time.sleep(2)
101 | pen_game_over.clear()
102 | display_remaining_states(pen, states_names, state_name_coordinates)
103 |
104 |
105 | def display_remaining_states(pen, states_names, state_name_coordinate):
106 | for name in states_names:
107 | x, y = state_name_coordinate[name]
108 | write_to_map(pen, name, x, y)
109 |
110 |
111 | def display_game_over(pen):
112 | pen.goto(0, 0)
113 | pen.write('Game Over', align='center', font=("Arial", 20, 'normal'))
114 |
115 |
116 | def check_user_response(user_state, states):
117 | return user_state in states
118 |
119 |
120 | def main():
121 | screen = create_screen()
122 | play_US_state_quiz(screen)
123 | screen.mainloop()
124 |
125 |
126 | def ask_user_to_guess_state(screen):
127 | user_choice = screen.textinput(title="",
128 | prompt="Enter state name:").title().strip()
129 | return user_choice
130 |
131 |
132 | def write_to_map(pen, user_state_name, x, y):
133 | pen.goto(x, y)
134 | pen.write(user_state_name, font=('Arial', 5, 'normal'))
135 |
136 |
137 | if __name__ == "__main__":
138 | main()
--------------------------------------------------------------------------------
/src/day_24/README.md:
--------------------------------------------------------------------------------
1 | # NATO phonetic alphabet
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_24/main.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_24/data/nato_phonetic_alphabet.csv:
--------------------------------------------------------------------------------
1 | letter,code
2 | A,Alfa
3 | B,Bravo
4 | C,Charlie
5 | D,Delta
6 | E,Echo
7 | F,Foxtrot
8 | G,Golf
9 | H,Hotel
10 | I,India
11 | J,Juliet
12 | K,Kilo
13 | L,Lima
14 | M,Mike
15 | N,November
16 | O,Oscar
17 | P,Papa
18 | Q,Quebec
19 | R,Romeo
20 | S,Sierra
21 | T,Tango
22 | U,Uniform
23 | V,Victor
24 | W,Whiskey
25 | X,X-ray
26 | Y,Yankee
27 | Z,Zulu
28 | ,
--------------------------------------------------------------------------------
/src/day_24/main.py:
--------------------------------------------------------------------------------
1 | import pandas
2 | import os
3 | import random
4 | import sys
5 | import re
6 |
7 | from functools import partial
8 | from tkinter import TclError
9 | from colorama import Fore, init
10 | from turtle import Turtle, Screen
11 |
12 | FILE_PATH = os.path.abspath(
13 | os.path.join(os.getcwd(), 'src/day_24/data/nato_phonetic_alphabet.csv'))
14 |
15 |
16 | def get_phonetic_alphabet_data_dict_dict_from(file_path):
17 | return pandas.read_csv(file_path, index_col=0, squeeze=True).to_dict()
18 |
19 |
20 | def get_phonetic_alphabet_list(screen):
21 | user_word = get_user_input(screen)
22 | phonetic_alphabet_data_dict = get_phonetic_alphabet_data_dict_dict_from(
23 | FILE_PATH)
24 | words = create_phonetic_alphabet_words_list_from(
25 | user_word, phonetic_alphabet_data_dict)
26 | return words
27 |
28 |
29 | def main():
30 | try:
31 | init(autoreset=True)
32 | screen = create_screen()
33 | pen = create_pen()
34 |
35 | phonetic_alphabet_list = get_phonetic_alphabet_list(screen)
36 | display_phonetic_alphabet(pen, phonetic_alphabet_list)
37 |
38 | screen.listen()
39 | screen.onclick(partial(run_again, pen))
40 | screen.mainloop()
41 |
42 | except (TclError):
43 | sys.exit()
44 |
45 |
46 | def run_again(pen, x, y):
47 | pen.goto(x, y)
48 | pen.clear()
49 | main()
50 |
51 |
52 | def write_to_screen(word, directions, pen, pen_color, font_specs):
53 | x, y = directions
54 | font, size, style = font_specs
55 | pen.goto(x, y)
56 | pen.color(pen_color)
57 | pen.write(f"{word}", font=(font, size, style))
58 |
59 |
60 | def display_phonetic_alphabet(pen, phonetic_alphabet_list):
61 | y = 150
62 | x = -380
63 | white_color = 255, 255, 255
64 |
65 | for word in phonetic_alphabet_list:
66 |
67 | if check_word_passed_y_screen_limit(y) or word == ' ':
68 | x, y = change_directions(x, y)
69 |
70 | colors = get_random_rgb_colors()
71 | first_letter = word[0]
72 |
73 | write_to_screen(word=first_letter,
74 | directions=(x, y),
75 | pen=pen,
76 | pen_color=white_color,
77 | font_specs=('Consolas', 21, 'bold'))
78 |
79 | temp_x = x + 30
80 |
81 | write_to_screen(word=word[1:],
82 | directions=(temp_x, y),
83 | pen=pen,
84 | pen_color=colors,
85 | font_specs=('Consolas', 20, 'italic'))
86 |
87 | y -= 50
88 |
89 |
90 | def check_word_passed_y_screen_limit(y):
91 | return y < -300
92 |
93 |
94 | def change_directions(x, y):
95 | """change (x, y) coordinates"""
96 | x += 200
97 | y = 200
98 | return x, y
99 |
100 |
101 | def create_pen():
102 | """Create a Turtle object to write on the screen"""
103 | pen = Turtle()
104 | pen.penup()
105 | pen.hideturtle()
106 | pen.speed(0)
107 | return pen
108 |
109 |
110 | def clear_pen(pen):
111 | pen.clear()
112 |
113 |
114 | def create_screen():
115 | screen = Screen()
116 | screen.setup(width=900, height=600)
117 | screen.title("NATO Phonetic Alphabet")
118 | screen.bgcolor('black')
119 | screen.colormode(255)
120 | return screen
121 |
122 |
123 | def get_random_rgb_colors():
124 | rgb = []
125 | for _ in range(3):
126 | color = random.randint(50, 250)
127 | rgb.append(color)
128 | return tuple(rgb)
129 |
130 |
131 | def get_user_input(screen):
132 | user_word = None
133 | try:
134 | user_word = screen.textinput(title="",
135 | prompt="Enter a word").upper().strip()
136 | assert re.match(r'^[a-z A-Z]+$', user_word) is not None
137 |
138 | except (AssertionError, AttributeError):
139 | if user_word is None:
140 | # when the user clicks the Cancel button it will exit without error
141 | sys.exit()
142 |
143 | print(f"{Fore.RED}Only letters allowed!\n")
144 | return get_user_input(screen)
145 | else:
146 | return user_word
147 |
148 |
149 | def create_phonetic_alphabet_words_list_from(user_input, data_dict):
150 | words = [data_dict[i] for i in list(user_input)]
151 | return words
152 |
153 |
154 | if __name__ == "__main__":
155 | main()
156 |
--------------------------------------------------------------------------------
/src/day_25/README.md:
--------------------------------------------------------------------------------
1 | # Miles to Km Converter
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_25/main.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_25/main.py:
--------------------------------------------------------------------------------
1 | import tkinter as tk
2 |
3 | MILES_TO_KM_VALUE = 1.60934
4 |
5 |
6 | def create_screen(title):
7 | screen = tk.Tk()
8 | screen.title(title)
9 | screen.minsize(width=400, height=200)
10 | screen.config(padx=100, pady=20)
11 | return screen
12 |
13 |
14 | def convert_miles_to_km(miles):
15 | return miles * MILES_TO_KM_VALUE
16 |
17 |
18 | def clear_text_area(text_area):
19 | """clears input text area """
20 | text_area.delete(0, tk.END)
21 |
22 |
23 | def click_calculate_button(result_label, text_area):
24 | try:
25 | miles = float(text_area.get())
26 | except Exception:
27 | text_area.delete(0, tk.END)
28 | return
29 | else:
30 | result = convert_miles_to_km(miles)
31 | result_label['text'] = f"{result:.2f}"
32 |
33 |
34 | def main():
35 | screen = create_screen('Mile to Km')
36 |
37 | # text area
38 | text_area = tk.Entry(width=6)
39 | text_area.focus()
40 | text_area.grid(row=0, column=2, padx=20)
41 |
42 | # bind the enter key to the calculate button
43 | text_area.bind(
44 | "",
45 | lambda event: click_calculate_button(result_label, text_area))
46 |
47 | # bind the backspace key to the calculate button
48 | text_area.bind("", lambda event: clear_text_area(text_area))
49 |
50 | # miles label
51 | miles_label = tk.Label(text="Mile")
52 | miles_label.grid(row=0, column=3)
53 |
54 | # converter result label
55 | result_label = tk.Label(text='0')
56 | result_label.grid(row=1, column=2)
57 |
58 | # calculate button
59 | calculate_button = tk.Button(
60 | text="Calculate",
61 | command=lambda: click_calculate_button(result_label, text_area))
62 | calculate_button.grid(row=2, column=2)
63 |
64 | # km label
65 | km_label = tk.Label(text='Km')
66 | km_label.grid(row=1, column=3)
67 |
68 | screen.mainloop()
69 |
70 |
71 | if __name__ == "__main__":
72 | main()
73 |
--------------------------------------------------------------------------------
/src/day_26/README.md:
--------------------------------------------------------------------------------
1 | # Pomodoro Timer App
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_26/pomodoro.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_26/images/pomodoro.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_26/images/pomodoro.png
--------------------------------------------------------------------------------
/src/day_26/main.py:
--------------------------------------------------------------------------------
1 | from pomodoro import PomodoroTimerApp
2 |
3 |
4 | def main():
5 | pomodoro_app = PomodoroTimerApp()
6 | pomodoro_app.mainloop()
7 |
8 |
9 | if __name__ == "__main__":
10 | main()
11 |
--------------------------------------------------------------------------------
/src/day_26/pomodoro.py:
--------------------------------------------------------------------------------
1 | import pyttsx3 as text_to_speech
2 |
3 | from tkinter import Button, Canvas, Label, Tk, PhotoImage
4 | from tkinter.constants import LEFT, TOP
5 |
6 | from pomodoro_settings import PomodoroAppSettings
7 |
8 |
9 | class PomodoroTimerApp(Tk):
10 | def __init__(self):
11 | super().__init__()
12 | self.repetition_number = 0
13 | self.clicked_started_button_count = 0
14 | self.timer_count = None
15 | self.settings = PomodoroAppSettings()
16 | self.tomato_image = PhotoImage(file=self.settings.TOMATO_IMAGE_PATH)
17 | self.work_break_label = Label(text='',
18 | fg=self.settings.GREEN,
19 | bg=self.settings.LIGHT_RED,
20 | font=self.settings.WORK_BREAK_LABEL)
21 | self.work_break_label.pack(side=TOP, pady=0)
22 |
23 | self.canvas = Canvas(width=600, height=600)
24 | self.setup_text_to_speech()
25 | self.setup_pomodoro_screen()
26 | self.setup_canvas_screen()
27 | self.timer_label = self.add_timer_label_for_canvas(
28 | 300, 330, text='25:00', fill='#FFF', font=self.settings.TIMER_FONT)
29 | self.setup_buttons()
30 |
31 | def setup_text_to_speech(self):
32 | self.engine = text_to_speech.init()
33 | voices = self.engine.getProperty('voices')
34 | self.engine.setProperty('voice', voices[1].id)
35 |
36 | def click_start_button(self):
37 | # break out if user clicks the start button multiples times
38 | if self.clicked_started_button_count == 1:
39 | return
40 | self.clicked_started_button_count += 1
41 |
42 | self.start_timer()
43 |
44 | def setup_buttons(self):
45 | self.add_start_button()
46 | self.add_reset_button()
47 |
48 | def add_start_button(self):
49 | button = Button(self,
50 | text="Start",
51 | borderwidth=0,
52 | activeforeground=self.settings.LIGHT_RED,
53 | background='white',
54 | font=self.settings.START_BUTTON_FONT,
55 | command=self.click_start_button)
56 | button.pack(side=LEFT, padx=100)
57 |
58 | def add_reset_button(self):
59 | button = Button(self,
60 | text="Reset",
61 | borderwidth=0,
62 | activeforeground=self.settings.LIGHT_RED,
63 | background='white',
64 | font=self.settings.START_BUTTON_FONT,
65 | command=self.reset_timer)
66 | button.pack(side=TOP)
67 |
68 | def setup_pomodoro_screen(self):
69 | width = self.winfo_screenwidth()
70 | add_spaces = (" " * (int(width) // 50))
71 |
72 | self.title(f"{add_spaces}Big Pomodoro Timer")
73 | self.config(padx=100, pady=50, background='#F6CFCF')
74 | self.resizable(width=False, height=False)
75 |
76 | def reset_timer(self):
77 | if self.timer_count:
78 | self.after_cancel(self.timer_count)
79 |
80 | self.canvas.itemconfigure(self.timer_label, text="25:00")
81 | self.work_break_label.config(text="")
82 |
83 | self.repetition_number = 0
84 | self.clicked_started_button_count = 0
85 | self.timer_count = None
86 |
87 | def start_timer(self):
88 | self.repetition_number += 1
89 | rep_num = self.repetition_number
90 |
91 | # long break of 25 min
92 | if rep_num % 8 == 0:
93 | text = "It's time for a big break!"
94 | self.work_break_label.config(text="It's time for a big break!",
95 | fg=self.settings.RED)
96 | self.count_down(self.settings.LONG_BREAK_MINUTES)
97 | text_to_speech.speak(text)
98 |
99 | # short break 5 min
100 | elif rep_num % 2 == 0:
101 | text = "It's time for a break!"
102 | self.work_break_label.config(text=text, fg=self.settings.RED)
103 | self.count_down(self.settings.SHORT_BREAK_MINUTES)
104 | text_to_speech.speak(text)
105 | else:
106 | # work time
107 | text = "It's time to work!"
108 | text_to_speech.speak(text)
109 | self.work_break_label.config(text=text, fg=self.settings.GREEN)
110 | self.count_down(self.settings.WORK_MINUTES)
111 |
112 | def count_down(self, count):
113 | if count == -1:
114 | self.start_timer()
115 | else:
116 | minutes = count // 60
117 | seconds = count % 60
118 |
119 | if count < 10:
120 | seconds = f"0{seconds}"
121 | elif int(seconds) < 10:
122 | seconds = f"0{seconds}"
123 |
124 | timer = f"{minutes}:{seconds}"
125 |
126 | self.canvas.itemconfigure(self.timer_label, text=timer)
127 | self.timer_count = self.after(1000, self.count_down, count - 1)
128 |
129 | def setup_canvas_screen(self):
130 | self.canvas.config(background=self.settings.LIGHT_RED,
131 | highlightthickness=0)
132 | self.pack_items_to_canvas()
133 |
134 | def pack_items_to_canvas(self):
135 | self.add_tomato_image_to_canvas()
136 | self.canvas.pack()
137 |
138 | def add_timer_label_for_canvas(self, x, y, text, fill, font):
139 | return self.canvas.create_text(x, y, text=text, fill=fill, font=font)
140 |
141 | def kill_app(self):
142 | self.destroy()
143 |
144 | def add_tomato_image_to_canvas(self):
145 | self.canvas.create_image(300, 300, image=self.tomato_image)
146 |
--------------------------------------------------------------------------------
/src/day_26/pomodoro_settings.py:
--------------------------------------------------------------------------------
1 | import os
2 |
3 |
4 | class PomodoroAppSettings():
5 | # files
6 | TOMATO_IMAGE_PATH = os.path.join(os.getcwd(),
7 | 'src/day_26/images/pomodoro.png')
8 | # colors
9 | LIGHT_RED = "#F6CFCF"
10 | RED = "#e7305b"
11 | GREEN = "#00a130"
12 | YELLOW = "#f7f5dd"
13 |
14 | # fonts
15 | FONT_NAME = "Ubuntu Mono"
16 |
17 | TIMER_FONT = (FONT_NAME, 35, 'bold')
18 | START_BUTTON_FONT = (FONT_NAME, 15, 'normal')
19 | WORK_BREAK_LABEL = (FONT_NAME, 20, 'bold')
20 |
21 | # timers
22 | WORK_MINUTES = 25 * 60
23 | SHORT_BREAK_MINUTES = 5 * 60
24 | LONG_BREAK_MINUTES = 20 * 60
25 |
--------------------------------------------------------------------------------
/src/day_27/README.md:
--------------------------------------------------------------------------------
1 | # Password Manager App
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_27/password_manager.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_27/data/passwords.txt:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_27/data/passwords.txt
--------------------------------------------------------------------------------
/src/day_27/file_handler.py:
--------------------------------------------------------------------------------
1 | import os
2 | import json
3 |
4 | PASSWORDS_DATA_FILE_PATH = os.path.join(os.getcwd(),
5 | 'src/day_27/data/passwords.txt')
6 |
7 |
8 | class PasswordsDataFileHandler:
9 | def __init__(self):
10 | pass
11 |
12 | def save_passwords_data_to_file(self, passwords_data):
13 | """save passwords_data to the passwords file in a JSON format"""
14 | data_to_write = None
15 | website, email, password = passwords_data
16 | new_passwords_data = {website: {"email": email, "password": password}}
17 |
18 | updated_passwords_data = self.update_passwords_data_file(
19 | new_passwords_data)
20 |
21 | if updated_passwords_data:
22 | data_to_write = updated_passwords_data
23 | else:
24 | data_to_write = new_passwords_data
25 |
26 | with open(PASSWORDS_DATA_FILE_PATH, 'w') as password_data_file:
27 | json.dump(data_to_write, password_data_file, indent=4)
28 |
29 | def update_passwords_data_file(self, new_passwords_data):
30 | try:
31 | with open(PASSWORDS_DATA_FILE_PATH) as password_data_file:
32 | password_data = json.load(password_data_file)
33 | password_data.update(new_passwords_data)
34 | except:
35 | return False
36 | else:
37 | return password_data
38 |
--------------------------------------------------------------------------------
/src/day_27/images/pass.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_27/images/pass.png
--------------------------------------------------------------------------------
/src/day_27/main.py:
--------------------------------------------------------------------------------
1 | from password_manager import PasswordManager
2 |
3 |
4 | def main():
5 | PasswordManager()
6 |
7 |
8 | if __name__ == "__main__":
9 | main()
10 |
--------------------------------------------------------------------------------
/src/day_27/password_generator.py:
--------------------------------------------------------------------------------
1 | import random
2 |
3 |
4 | class PasswordGenerator:
5 | def __init__(self):
6 |
7 | self.lower_letters_list = [chr(i) for i in range(97, 123)]
8 | self.letters_list = [i.upper() for i in self.lower_letters_list
9 | ] + self.lower_letters_list
10 |
11 | self.numbers_list = [i for i in range(10)]
12 | self.symbols_list = [
13 | '!',
14 | '#',
15 | '$',
16 | '%',
17 | '&',
18 | '(',
19 | ')',
20 | '*',
21 | '+',
22 | '.',
23 | '-',
24 | '=',
25 | ]
26 |
27 | def append_random_character_to_password_from(self, lst, random_number,
28 | password_list):
29 | for _ in range(random_number):
30 | password_list.append(str(random.choice(lst)))
31 |
32 | def generate_password(self):
33 | password_list = []
34 |
35 | letters_count = random.randint(8, 10)
36 | symbols_count = random.randint(2, 4)
37 | numbers_count = random.randint(2, 4)
38 |
39 | self.append_random_character_to_password_from(self.letters_list,
40 | letters_count,
41 | password_list)
42 | self.append_random_character_to_password_from(self.symbols_list,
43 | symbols_count,
44 | password_list)
45 | self.append_random_character_to_password_from(self.numbers_list,
46 | numbers_count,
47 | password_list)
48 |
49 | random.shuffle(password_list)
50 |
51 | return ''.join(password_list)
52 |
--------------------------------------------------------------------------------
/src/day_27/password_manager.py:
--------------------------------------------------------------------------------
1 | import os
2 | import tkinter as tk
3 | import tkinter.messagebox as messagebox
4 |
5 | from tkinter import PhotoImage, Tk, Canvas
6 | from PIL import Image, ImageTk
7 | from password_generator import PasswordGenerator
8 | from file_handler import PasswordsDataFileHandler
9 |
10 | PASSWORD_IMAGE_PATH = os.path.join(os.getcwd(), 'src/day_27/images/pass.png')
11 | PASSWORDS_DATA_FILE_PATH = os.path.join(os.getcwd(),
12 | 'src/day_27/data/passwords.txt')
13 |
14 |
15 | class PasswordManager(Tk):
16 | def __init__(self):
17 | super().__init__()
18 | self.canvas = Canvas(width=200, height=150)
19 | self.password_generator = PasswordGenerator()
20 | self.file_handler = PasswordsDataFileHandler()
21 | self.website = None
22 | self.email = None
23 | self.password = None
24 | self.password_entry = None
25 | self.entries = []
26 | self.passwords_data = []
27 | self.config_app()
28 | self.mainloop()
29 |
30 | def generate_password(self):
31 | self.password_entry.delete(0, tk.END)
32 | password = self.password_generator.generate_password()
33 | self.password_entry.insert(0, string=password)
34 | return password
35 |
36 | def ask_user_to_save_current_data(self):
37 | try:
38 | website, email, password = self.passwords_data
39 | assert website and email and password
40 | except (AssertionError):
41 | messagebox.showerror(title="Error",
42 | message='Some fields are empty!')
43 | return
44 | else:
45 | is_ok = messagebox.askokcancel(
46 | title="Save",
47 | message=
48 | f"Website: {website}\nEmail: {email}\nPassword: {password}\n\nDo you want to save?"
49 | )
50 | return is_ok
51 |
52 | def delete_entry_inputs(self):
53 | for entry in self.entries:
54 | entry.delete(0, tk.END)
55 |
56 | def click_submit_button(self):
57 | self.append_data_to_passwords_data()
58 | if self.ask_user_to_save_current_data():
59 | self.append_passwords_data_to_file()
60 | self.delete_entry_inputs()
61 |
62 | self.passwords_data.clear()
63 |
64 | def append_passwords_data_to_file(self):
65 | self.file_handler.save_data_to_file(self.passwords_data)
66 |
67 | def append_data_to_passwords_data(self):
68 | for entry in self.entries:
69 | data = entry.get()
70 | self.passwords_data.append(data)
71 |
72 | def config_app(self):
73 | self.set_screen()
74 | self.add_password_image()
75 | self.add_labels()
76 | self.add_text_areas()
77 | self.add_buttons()
78 |
79 | def add_labels(self):
80 | website_label = tk.Label(text='Website:', bg='white')
81 | website_label.grid(row=1, column=0)
82 |
83 | email_label = tk.Label(text='Email:', bg='white')
84 | email_label.grid(row=2, column=0, padx=0)
85 |
86 | password_label = tk.Label(text='Password:', bg='white')
87 | password_label.grid(row=3, column=0)
88 |
89 | def add_text_areas(self):
90 | website_entry = tk.Entry()
91 | website_entry.focus()
92 | website_entry.insert(0, 'https://www.google.com/')
93 | website_entry.grid(row=1, column=1)
94 |
95 | email_entry = tk.Entry()
96 | email_entry.insert(0, 'test@gmail.com')
97 | email_entry.grid(row=2, column=1)
98 |
99 | self.password_entry = tk.Entry()
100 | self.password_entry.grid(row=3, column=1)
101 |
102 | self.entries.extend([website_entry, email_entry, self.password_entry])
103 |
104 | def add_buttons(self):
105 | submit_button = tk.Button(text="Submit",
106 | borderwidth=1,
107 | command=self.click_submit_button)
108 | submit_button.grid(row=4, column=1, pady=20)
109 |
110 | generate_password = tk.Button(text="Generate Password",
111 | borderwidth=1,
112 | command=self.generate_password)
113 | generate_password.grid(row=4, column=0, pady=20)
114 |
115 | def add_password_image(self):
116 | image = Image.open(PASSWORD_IMAGE_PATH)
117 | image = image.resize((150, 150), Image.ANTIALIAS)
118 | self.password_image = ImageTk.PhotoImage(image)
119 | self.canvas.create_image(100, 80, image=self.password_image)
120 | self.canvas.config(bg='white', borderwidth=0, highlightthickness=0)
121 | self.canvas.grid(row=0, column=1, pady=20)
122 |
123 | def set_screen(self):
124 | self.title(f"Password Manager")
125 | self.config(padx=20, pady=20, background='#FFF')
126 | self.geometry('500x400')
127 | self.resizable(width=False, height=False)
128 |
129 |
130 | def main():
131 | pm = PasswordManager()
132 |
133 |
134 | if __name__ == "__main__":
135 | main()
--------------------------------------------------------------------------------
/src/day_28/README.md:
--------------------------------------------------------------------------------
1 | # FlashCards App
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_28/flash_card.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_28/data/french_words.csv:
--------------------------------------------------------------------------------
1 | French,English
2 | partir,leave
3 | histoire,history
4 | chercher,search
5 | seulement,only
6 | police,police
7 | pensée,thought
8 | aide,help
9 | demande,request
10 | genre,kind
11 | mois,month
12 | frère,brother
13 | laisser,let
14 | car,because
15 | mettre,to put
16 | aucun,no
17 | laisse,leash
18 | eux,them
19 | ville,city
20 | chaque,each
21 | parlé,speak
22 | arrivé,come
23 | devrait,should
24 | bébé,baby
25 | longtemps,long time
26 | heures,hours
27 | vont,will
28 | pendant,while
29 | revoir,meet again
30 | aucune,any
31 | place,square
32 | parler,speak
33 | compris,understood
34 | savais,knew
35 | étaient,were
36 | attention,Warning
37 | voici,here is
38 | pourrais,could
39 | affaire,case
40 | donner,give
41 | type,type
42 | leurs,their
43 | donné,given
44 | train,train
45 | corps,body
46 | endroit,place
47 | yeux,eyes
48 | façon,way
49 | écoute,listen
50 | dont,whose
51 | trouver,find
52 | premier,first
53 | perdu,lost
54 | main,hand
55 | première,first
56 | côté,side
57 | pouvoir,power
58 | vieux,old
59 | sois,be
60 | tiens,here
61 | matin,morning
62 | tellement,so much
63 | enfant,child
64 | point,point
65 | venu,came
66 | suite,after
67 | pardon,sorry
68 | venez,come
69 | devant,in front of
70 | vers,towards
71 | minutes,minutes
72 | demandé,request
73 | chambre,bedroom
74 | mis,placed
75 | belle,beautiful
76 | droit,law
77 | aimerais,would like to
78 | aujourd'hui,today
79 | mari,husband
80 | cause,cause
81 | enfin,finally
82 | espère,hope
83 | eau,water
84 | attendez,Wait
85 | parti,left
86 | nouvelle,new
87 | boulot,job
88 | arrêter,Stop
89 | dirait,would say
90 | terre,Earth
91 | compte,account
92 | donne,given
93 | loin,far
94 | fin,end
95 | croire,believe
96 | chérie,sweetheart
97 | gros,large
98 | plutôt,rather
99 | aura,will have
100 | filles,girls
101 | jouer,to play
102 | bureau,office
--------------------------------------------------------------------------------
/src/day_28/flash_card.py:
--------------------------------------------------------------------------------
1 | import os
2 | import sys
3 | import pandas
4 | import random
5 | import tkinter as tk
6 |
7 | CSV_FRENCH_WORDS_FILE_PATH = os.path.join(os.getcwd(),
8 | "src/day_28/data/french_words.csv")
9 | IMAGES_PATH = os.path.join(os.getcwd(), "src/day_28/images/")
10 |
11 | FLASHCARD_IMAGE_PATH = f"{IMAGES_PATH}flash_card.png"
12 | BACK_FLASHCARD_IMAGE_PATH = f"{IMAGES_PATH}back_flash_card.png"
13 |
14 | WRONG_IMAGE_PATH = f"{IMAGES_PATH}wrong.png"
15 | RIGHT_IMAGE_PATH = f"{IMAGES_PATH}right.png"
16 |
17 | BG_COLOR = '#a4dea0'
18 | FONT_NAME = 'MonoLisa-Medium'
19 | FONT_NAME_ITALIC = 'MonoLisa-MediumItalic'
20 |
21 |
22 | class Flashcard(tk.Tk):
23 | def __init__(self):
24 | super().__init__()
25 | # fields
26 | self.french_word = None
27 | self.english_word = None
28 | self.card_title = None
29 | self.card_word = None
30 |
31 | self.change_card_canvas_image = None
32 |
33 | self.french_english_words_dict = pandas.read_csv(
34 | CSV_FRENCH_WORDS_FILE_PATH).to_dict(orient='records')
35 | self.right_or_wrong_button_is_clicked = False
36 | self.clicked_on_canvas_image = False
37 | self.canvas = tk.Canvas(width=700, height=500)
38 | # images
39 | self.flash_card_image = tk.PhotoImage(file=f"{FLASHCARD_IMAGE_PATH}")
40 | self.back_flash_card_image = tk.PhotoImage(
41 | file=f"{BACK_FLASHCARD_IMAGE_PATH}")
42 | self.wrong_card_image = tk.PhotoImage(file=f"{WRONG_IMAGE_PATH}")
43 | self.right_card_image = tk.PhotoImage(file=f"{RIGHT_IMAGE_PATH}")
44 | # methods
45 | self.config_app_screen()
46 | self.add_flash_card_image_to_canvas()
47 | self.add_words_to_canvas()
48 | self.add_right_and_wrong_buttons()
49 | self.mainloop()
50 |
51 | def get_random_flashcard(self) -> dict:
52 | """get a random list of dicts: {French: word, English: word} and return it"""
53 | try:
54 | return random.choice(self.french_english_words_dict)
55 | except IndexError:
56 | sys.exit()
57 |
58 | def remove_known_card_from_french_english_words_dict(self):
59 | temp = self.french_english_words_dict[:]
60 | index = next((index for (index, dic) in enumerate(temp)
61 | if dic["French"] == self.french_word.lower()), None)
62 | if temp:
63 | temp.pop(index)
64 | else:
65 | sys.exit()
66 | self.french_english_words_dict = temp
67 |
68 | def click_right_button(self):
69 | self.right_or_wrong_button_is_clicked = True
70 | self.store_card_words()
71 | self.remove_from_known_card_from_french_english_words_dict()
72 | self.add_flashcard_to_canvas()
73 |
74 | def click_wrong_button(self):
75 | self.right_or_wrong_button_is_clicked = True
76 | self.store_card_words()
77 | self.add_flashcard_to_canvas()
78 |
79 | def click_on_canvas_image(self, event):
80 | self.clicked_on_canvas_image = True
81 | self.add_flashcard_to_canvas()
82 |
83 | def store_card_words(self):
84 | flash_card = self.get_random_flashcard()
85 | french_card_word = flash_card['French'].title()
86 | english_card_word = flash_card['English'].title()
87 | self.french_word = french_card_word
88 | self.english_word = english_card_word
89 |
90 | def add_flashcard_to_canvas(self):
91 | if self.right_or_wrong_button_is_clicked:
92 | self.canvas.itemconfig(self.card_title,
93 | text='French',
94 | fill='black')
95 | self.canvas.itemconfig(self.card_word,
96 | text=self.french_word,
97 | fill='black')
98 |
99 | self.config_canvas_french_card()
100 | self.right_or_wrong_button_is_clicked = False
101 |
102 | elif self.clicked_on_canvas_image:
103 | self.canvas.itemconfig(self.card_title,
104 | text='English',
105 | fill='white')
106 | self.canvas.itemconfig(self.card_word,
107 | text=self.english_word,
108 | fill='white')
109 | self.config_canvas_english_card()
110 | self.clicked_on_canvas_image = False
111 |
112 | def config_canvas_french_card(self):
113 | self.canvas.itemconfigure(self.change_card_canvas_image,
114 | image=self.flash_card_image)
115 |
116 | def config_canvas_english_card(self):
117 | self.canvas.itemconfigure(self.change_card_canvas_image,
118 | image=self.back_flash_card_image)
119 |
120 | def config_app_screen(self):
121 | space = ' ' * 25
122 | self.title(f"Flashcards { space} French - English ")
123 | self.config(padx=50, pady=70, background=BG_COLOR)
124 | self.geometry('800x800')
125 | self.resizable(width=False, height=False)
126 |
127 | def add_flash_card_image_to_canvas(self):
128 | self.change_card_canvas_image = self.canvas.create_image(
129 | 350, 250, image=self.flash_card_image)
130 | self.canvas.bind("", self.click_on_canvas_image)
131 | self.canvas.config(bg=BG_COLOR, highlightthickness=0)
132 | self.canvas.pack()
133 |
134 | def add_words_to_canvas(self):
135 | # Title
136 | cards = self.get_random_flashcard()
137 |
138 | french_word = cards["French"]
139 | english_word = cards["English"]
140 |
141 | self.french_word = french_word
142 | self.english_word = english_word
143 |
144 | self.card_title = self.canvas.create_text(350,
145 | 165,
146 | text="French",
147 | font=(FONT_NAME_ITALIC, 18))
148 | # Word
149 | self.card_word = self.canvas.create_text(350,
150 | 295,
151 | text=french_word,
152 | font=(FONT_NAME, 30, 'bold'))
153 |
154 | def add_right_and_wrong_buttons(self):
155 | # Right button
156 | right_button = tk.Button(image=self.right_card_image,
157 | highlightthickness=0,
158 | command=self.click_right_button)
159 | right_button.pack(side=tk.RIGHT, padx=100, pady=(50, 0))
160 |
161 | # Wrong button
162 | wrong_button = tk.Button(image=self.wrong_card_image,
163 | highlightthickness=0,
164 | command=self.click_wrong_button)
165 | wrong_button.pack(side=tk.LEFT, padx=100, pady=(50, 0))
166 |
--------------------------------------------------------------------------------
/src/day_28/images/back_flash_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_28/images/back_flash_card.png
--------------------------------------------------------------------------------
/src/day_28/images/flash_card.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_28/images/flash_card.png
--------------------------------------------------------------------------------
/src/day_28/images/right.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_28/images/right.png
--------------------------------------------------------------------------------
/src/day_28/images/wrong.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_28/images/wrong.png
--------------------------------------------------------------------------------
/src/day_28/main.py:
--------------------------------------------------------------------------------
1 | from flash_card import Flashcard
2 |
3 |
4 | def main():
5 | Flashcard()
6 |
7 |
8 | if __name__ == "__main__":
9 | main()
10 |
--------------------------------------------------------------------------------
/src/day_29/README.md:
--------------------------------------------------------------------------------
1 | # Weather Forecast via SMS
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_29/main.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_29/main.py:
--------------------------------------------------------------------------------
1 | import requests
2 | import os
3 |
4 | from twilio.rest import Client
5 | # loads .env secret variables
6 | from dotenv import load_dotenv
7 | load_dotenv()
8 |
9 | WEATHER_API_KEY = os.environ['WEATHER_API_KEY']
10 |
11 | # city location longitude and latitude
12 | LON = -43.9378
13 | LAT = -19.9208
14 |
15 | # weather API url
16 | URL = f"https://api.openweathermap.org/data/2.5/onecall?lat={LAT}&lon={LON}&appid={WEATHER_API_KEY}"
17 |
18 |
19 | def send_message_with_twilio(weather_msg):
20 | account_sid = os.environ['TWILIO_ACCOUNT_SID']
21 | auth_token = os.environ['TWILIO_AUTH_TOKEN']
22 | sender_number = os.environ['SENDER_PHONE_NUMBER']
23 | receiver_number = os.environ['RECEIVER_PHONE_NUMBER']
24 |
25 | client = Client(account_sid, auth_token)
26 | message = client.messages.create(body=f'{weather_msg}',
27 | from_=sender_number,
28 | to=receiver_number)
29 |
30 |
31 | def get_12_hours_weather_ids_data():
32 | """get only the 12 hours of weather data of the day"""
33 |
34 | response = requests.get(URL)
35 | weather_data = response.json()
36 | weather_data_12_hours = weather_data["hourly"][:12]
37 | weather_ids = [i['weather'][0]['id'] for i in weather_data_12_hours]
38 | return weather_ids
39 |
40 |
41 | def get_weather_string_message_from(id_num, weather_status):
42 |
43 | if id_num == 801:
44 | weather_status['is_clear'] = True
45 | return "Today will be a clear day! ☀︎"
46 |
47 | elif 800 <= id_num <= 804:
48 | weather_status['is_cloudy'] = True
49 | return "Today will be a cloudy day! ☁️"
50 |
51 | elif 600 <= id_num <= 622:
52 | weather_status['is_snow'] = True
53 | return "It's going to snow today! ❄️"
54 |
55 | elif 500 <= id_num <= 531:
56 | weather_status['is_rain'] = True
57 | return "It's going to rain today! ☔"
58 |
59 | elif 300 <= id_num <= 321:
60 | weather_status['is_drizzle'] = True
61 | return 'Today will be a drizzle day! 💧'
62 |
63 | elif 200 <= id_num <= 232:
64 | weather_status['is_thunderstorm'] = True
65 | return 'Today we will have a thunderstorm! ⛈'
66 |
67 |
68 | def main():
69 | weather_status = {
70 | 'is_clear': False,
71 | 'is_cloudy': False,
72 | 'is_snow': False,
73 | 'is_rain': False,
74 | 'is_drizzle': False,
75 | 'is_thunderstorm': False
76 | }
77 |
78 | weather_string_msg = None
79 |
80 | for weather_id in get_12_hours_weather_ids_data():
81 | weather_string_msg = get_weather_string_message_from(
82 | weather_id, weather_status)
83 | if True in weather_status.values():
84 | break
85 |
86 | send_message_with_twilio(weather_string_msg)
87 |
88 |
89 | if __name__ == "__main__":
90 | main()
91 |
--------------------------------------------------------------------------------
/src/day_3/README.md:
--------------------------------------------------------------------------------
1 | # Treasure Island
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_3/treasure_island.py)
4 |
5 | ## Demo:
6 |
7 | 
8 |
--------------------------------------------------------------------------------
/src/day_3/treasure_island.py:
--------------------------------------------------------------------------------
1 | # Treasure Island
2 |
3 |
4 | def start():
5 |
6 | print("\nWelcome to this mysterious Treasure Island.")
7 | print("\nYour mission is to find the hidden treasure.")
8 |
9 | user_choice = get_user_choice(
10 | '\nYou\'re at a cross road. Where do you want to go? - Type "left" or "right"'
11 | )
12 |
13 | if user_choice == 'left':
14 | go_left()
15 | elif user_choice == 'right':
16 | go_right()
17 | else:
18 | wrong_choice()
19 |
20 |
21 | def get_user_choice(question):
22 | choice = input(question).lower().strip()
23 | return choice
24 |
25 |
26 | def wait():
27 | # end game
28 | print(
29 | "\nYou arrive at the island and see a house with 3 doors. One red, one blue, and the last one is purple"
30 | )
31 | user_choice = get_user_choice(
32 | '\nWhich color do you choose? - Type "red", "green" or "purple"')
33 |
34 | if user_choice == 'red':
35 | print(
36 | "\nThere is a red button in the middle of the room, you press it. The door shuts and locks you inside, a fire starts and you're trapped..."
37 | )
38 | print_game_over()
39 | elif user_choice == 'green':
40 | print("\nYou found the hidden treasure!")
41 | print(get_treasure())
42 |
43 | elif user_choice == 'purple':
44 | print(
45 | '\nYou open the door, and a sudden explosion occurs inside the room...'
46 | )
47 | print_game_over()
48 | else:
49 | wrong_choice()
50 |
51 |
52 | def go_left():
53 | # go to lake
54 | user_choice = get_user_choice(
55 | '\nYou come to the lake and there\'s an island in the middle do you swim or wait for a boat? - Type "swim" or "wait"'
56 | )
57 | if user_choice == 'swim':
58 | swim()
59 | elif user_choice == 'wait':
60 | wait()
61 | else:
62 | wrong_choice()
63 |
64 |
65 | def swim():
66 | # game over
67 | print(
68 | "\nA white shark comes near and bites you in the stomach, you manage to reach the island but you pass out and die."
69 | )
70 |
71 |
72 | def wrong_choice():
73 | # game over
74 | print("\nYou don't feel so good and die...")
75 | print_game_over()
76 |
77 |
78 | def print_game_over():
79 | print("\nGame Over.")
80 |
81 |
82 | def go_right():
83 | # dies
84 | print(
85 | "\nThere's a giant hole in front of you, you slip... and fall to death"
86 | )
87 | print_game_over()
88 |
89 |
90 | def get_treasure():
91 | return """
92 | ****************B**************I**********I************I*********I*****G*************
93 | _.--.
94 | _.-'_:-'||
95 | _.-'_.-::::'||
96 | _.-:'_.-::::::' ||
97 | .'`-.-:::::::' ||
98 | /.'`;|:::::::' ||_
99 | || ||::::::' _.;._'-._
100 | || ||:::::' _.-!oo @.!-._'-.
101 | \'. ||:::::.-!()oo @!()@.-'_.|
102 | '.'-;|:.-'.&$@.& ()$%-'o.'\\U||
103 | `>'-.!@%()@'@_%-'_.-o _.|'||
104 | ||-._'-.@.-'_.-' _.-o |'||
105 | ||=[ '-._.-\\U/.-' o |'||
106 | || '-.]=|| |'| o |'||
107 | || || |'| _| ';
108 | || || |'| _.-'_.-'
109 | |'-._ || |'|_.-'_.-'
110 | '-._'-.|| |' `_.-'
111 | '-.||_/.-'
112 |
113 | ****************B**************I**********I************I*********I*****G*************
114 | """
115 |
116 |
117 | def main():
118 | start()
119 |
120 |
121 | if __name__ == "__main__":
122 | main()
--------------------------------------------------------------------------------
/src/day_30/README.md:
--------------------------------------------------------------------------------
1 | # Best Movies To Watch App
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_30/main.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_30/main.py:
--------------------------------------------------------------------------------
1 | import tkinter as tk
2 | import urllib.request
3 | import clipboard
4 | import requests
5 | import random
6 | import re
7 | import io
8 | import sys
9 |
10 | from urllib.error import HTTPError
11 | from bs4 import BeautifulSoup
12 | from PIL import Image, ImageTk
13 | from tkinter import messagebox
14 |
15 | MOVIE_FILE_PATH = 'src/day_30/movies.txt'
16 |
17 |
18 | def paste_movie_title_to_clipboard(movie_title):
19 | messagebox.showinfo(message="The movie title was copied to the clipboard!")
20 | clipboard.copy(movie_title)
21 |
22 |
23 | def ask_user_to_watch_or_skip(movies_and_images, image_label, movie_label):
24 | is_yes = messagebox.askyesno(message='Do you want to watch this movie?')
25 | if not is_yes:
26 | configure_image_and_movie_labels(movies_and_images, image_label,
27 | movie_label)
28 | return ask_user_to_watch_or_skip(movies_and_images, image_label,
29 | movie_label)
30 | else:
31 | return is_yes
32 |
33 |
34 | def configure_image_and_movie_labels(movies_and_images, image_label,
35 | movie_label):
36 | movie, image_url = get_random_movie_and_image(movies_and_images)
37 | image = get_formated_image(image_url)
38 | image_label.configure(image=image)
39 | image_label.image = image
40 | movie_label.configure(text=movie)
41 |
42 |
43 | def remove_unicode_characters_from(string):
44 | string_encode = string.encode("ascii", "ignore")
45 | string_decode = string_encode.decode()
46 | return string_decode
47 |
48 |
49 | def get_url_images(soup):
50 | images = soup.find_all('img')
51 | image_list = []
52 | prev = ''
53 |
54 | for image in images:
55 | image_src = (image['src'])
56 | if image_src and image_src.endswith('jpg'):
57 | if len(image_src) <= 52:
58 | # skip if the current image is equal to the previous one
59 | if image_list:
60 | prev = image_list[-1]
61 | if prev == image_src:
62 | continue
63 |
64 | image_list.append(image_src)
65 |
66 | return image_list[0:100]
67 |
68 |
69 | def get_movies(soup):
70 | movies = []
71 | movies_data = soup.find_all(name='a')
72 |
73 | for movie in movies_data:
74 | movie = movie.getText().strip()
75 | matches = re.match(r'[0-9]+', movie)
76 | if (matches):
77 | movie = remove_unicode_characters_from(movie)
78 | # format the string
79 | point_index = movie.index('.')
80 | movie = f"{movie[0:point_index]}. {movie[point_index+1:]}"
81 | movies.append(movie)
82 | return movies
83 |
84 |
85 | def get_soup_data():
86 | url = "https://www.timeout.com/newyork/movies/best-movies-of-all-time"
87 | try:
88 | response = requests.get(url)
89 | response.raise_for_status()
90 | html_text = response.text
91 | except HTTPError:
92 | sys.exit()
93 |
94 | soup = BeautifulSoup(html_text, 'html.parser')
95 | return soup
96 |
97 |
98 | def zip_movies_and_images():
99 | soup = get_soup_data()
100 | images = get_url_images(soup)
101 | movies = get_movies(soup)
102 |
103 | movies_and_images = zip(movies, images)
104 | return movies_and_images
105 |
106 |
107 | def get_app_screen():
108 | screen = tk.Tk()
109 | screen.title('Best Movies of all time')
110 | screen.geometry('800x600')
111 | return screen
112 |
113 |
114 | def get_formated_image(image_url):
115 | image_url_data = urllib.request.urlopen(image_url)
116 | raw_data = image_url_data.read()
117 |
118 | pilImage = Image.open(io.BytesIO(raw_data))
119 | pilImage = pilImage.resize((800, 600), Image.ANTIALIAS)
120 |
121 | image = ImageTk.PhotoImage(pilImage)
122 | return image
123 |
124 |
125 | def save_movies_to_file(movies_and_images, filename):
126 | with open(filename, 'w') as movie_file:
127 | for movie, _ in movies_and_images:
128 | movie_file.write(f"{movie}\n")
129 |
130 |
131 | def load_movies_from_file(filename):
132 | with open(filename) as movie_file:
133 | return movie_file.read().splitlines()
134 |
135 |
136 | def get_random_movie_and_image(movies_and_images):
137 | return random.choice(movies_and_images)
138 |
139 |
140 | def main():
141 | screen = get_app_screen()
142 | movies_and_images = list(zip_movies_and_images())
143 | save_movies_to_file(movies_and_images, MOVIE_FILE_PATH)
144 |
145 | movie, image_url = get_random_movie_and_image(movies_and_images)
146 |
147 | image = get_formated_image(image_url)
148 |
149 | movie_label = tk.Label(text=movie)
150 | movie_label.pack()
151 |
152 | image_label = tk.Label(image=image)
153 | image_label.pack()
154 |
155 | result = ask_user_to_watch_or_skip(movies_and_images, image_label,
156 | movie_label)
157 | if result:
158 | paste_movie_title_to_clipboard(movie)
159 | screen.after(3000, sys.exit)
160 |
161 | screen.mainloop()
162 |
163 |
164 | if __name__ == "__main__":
165 | main()
--------------------------------------------------------------------------------
/src/day_30/movies.txt:
--------------------------------------------------------------------------------
1 | 1. 2001: A Space Odyssey (1968)
2 | 2. The Godfather (1972)
3 | 3. Citizen Kane (1941)
4 | 4. Jeanne Dielman, 23, Quai du Commerce, 1080 Bruxelles (1975)
5 | 5. Raiders of the Lost Ark (1981)
6 | 6. La Dolce Vita (1960)
7 | 7. Seven Samurai (1954)
8 | 8. In the Mood for Love (2000)
9 | 9. There Will Be Blood (2007)
10 | 10. Singin in the Rain (1952)
11 | 11. Goodfellas (1990)
12 | 12. North by Northwest (1959)
13 | 13. Mulholland Drive (2001)
14 | 14. Bicycle Thieves (1948)
15 | 15. The Dark Knight (2008)
16 | 16. City Lights (1931)
17 | 17. Grand Illusion (1937)
18 | 18. His Girl Friday (1940)
19 | 19. The Red Shoes (1948)
20 | 20. Vertigo (1958)
21 | 21. Beau Travail (1999)
22 | 22. The Searchers (1956)
23 | 23. Persona (1966)
24 | 24. Do the Right Thing (1989)
25 | 25. Rashomon (1950)
26 | 26. The Rules of the Game (1939)
27 | 27. Jaws (1975)
28 | 28. Double Indemnity (1944)
29 | 29. The 400 Blows (1959)
30 | 30. Star Wars (1977)
31 | 31. The Passion of Joan of Arc (1928)
32 | 32. Once Upon a Time in the West (1968)
33 | 33. Alien (1979)
34 | 34. Tokyo Story (1951)
35 | 35. Pulp Fiction (1994)
36 | 36. The Truman Show (1998)
37 | 37. Lawrence of Arabia (1962)
38 | 38. Psycho (1960)
39 | 39. Sansho the Bailiff (1954)
40 | 40. Andrei Rublev (1966)
41 | 41. The Umbrellas of Cherbourg (1964)
42 | 42. Chinatown (1974)
43 | 43. The Seventh Seal (1957)
44 | 44. Lost in Translation (2003)
45 | 45. Taxi Driver (1976)
46 | 46. Spirited Away (2001)
47 | 47. Night of the Living Dead (1968)
48 | 48. Battleship Potemkin (1925)
49 | 49. Modern Times (1936)
50 | 50. Breathless (1960)
51 | 51. Dr. Strangelove or: How I Learned to Stop Worrying and Love the Bomb (1964)
52 | 52. M (1931)
53 | 53. Blade Runner
54 | 54. The Bitter Tears of Petra von Kant (1972)
55 | 55. Rome, Open City (1945)
56 | 56. Nosferatu (1922)
57 | 57. Airplane! (1980)
58 | 58. Under the Skin (2013)
59 | 59. Mad Max: Fury Road (2015)
60 | 60. Apocalypse Now (1979)
61 | 61. Brokeback Mountain (2005)
62 | 62. Duck Soup (1933)
63 | 63. The Blair Witch Project (1999)
64 | 64. All the Presidents Men (1976)
65 | 65. The Apu trilogy (1955, 1956, 1959)
66 | 66. The General (1926)
67 | 67. Eternal Sunshine of the Spotless Mind (2004)
68 | 68. The Texas Chain Saw Massacre (1974)
69 | 69. Come and See (1985)
70 | 70. Heat (1995)
71 | 71. The Shining (1980)
72 | 72. Toy Story (1995)
73 | 73. Killer of Sheep (1977)
74 | 74. A Woman Under the Influence (1974)
75 | 75. Annie Hall (1977)
76 | 76. Some Like It Hot (1959)
77 | 77. Metropolis (1927)
78 | 78. The Maltese Falcon (1941)
79 | 79. This Is Spinal Tap (1984)
80 | 80. It Happened One Night (1934)
81 | 81. Die Hard (1988)
82 | 82. The Conformist (1970)
83 | 83. The Thing (1982)
84 | 84. Daughters of the Dust (1991)
85 | 85. Barry Lyndon (1975)
86 | 86. Raging Bull (1980)
87 | 87. Seven (1995)
88 | 88. Aguirre, the Wrath of God (1972)
89 | 89. The Battle of Algiers (1966)
90 | 90. Women on the Verge of a Nervous Breakdown (1988)
91 | 91. Boyhood (2014)
92 | 92. The Discreet Charm of the Bourgeoisie (1972)
93 | 93. Paths of Glory (1957)
94 | 94. Secrets & Lies (1996)
95 | 95. Sweet Smell of Success (1957)
96 | 96. The Cabinet of Dr. Caligari (1920)
97 | 97. Nashville (1975)
98 | 98. Dont Look Now (1973)
99 | 99. Bonnie and Clyde (1967)
100 | 100. Get Out (2017)
101 |
--------------------------------------------------------------------------------
/src/day_31/README.md:
--------------------------------------------------------------------------------
1 | # Wallpaper Bot
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_31/main.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_31/main.py:
--------------------------------------------------------------------------------
1 | import pyautogui
2 |
3 | from selenium import webdriver
4 | from selenium.webdriver import ActionChains
5 | from selenium.webdriver.chrome.service import Service
6 | from selenium.webdriver.common.by import By
7 |
8 | from webdriver_manager.firefox import GeckoDriverManager
9 | from time import sleep
10 |
11 |
12 | WALLPAPERS_URL = "https://dailydevbytes.com/channel/wallpapers"
13 |
14 |
15 | class Keys:
16 | DOWN = "down"
17 | ENTER = "enter"
18 |
19 |
20 | def get_web_driver_for(url):
21 | driver = webdriver.Firefox(service=Service(GeckoDriverManager().install()))
22 | driver.get(url)
23 | return driver
24 |
25 |
26 | def press_key(key, press_count=1):
27 | for _ in range(press_count):
28 | pyautogui.press(key)
29 |
30 |
31 |
32 | def set_wallpaper(driver):
33 | first_image = driver.find_element(By.TAG_NAME, "img")
34 |
35 | action_chains = ActionChains(driver)
36 | action_chains.context_click(first_image).perform()
37 |
38 | press_key(Keys.DOWN, 13)
39 | press_key(Keys.ENTER)
40 |
41 | sleep(2.5)
42 |
43 | press_key(Keys.DOWN, 6)
44 | press_key(Keys.ENTER)
45 |
46 |
47 | def main():
48 | driver = get_web_driver_for(WALLPAPERS_URL)
49 | set_wallpaper(driver)
50 |
51 | driver.quit()
52 |
53 |
54 | if __name__ == "__main__":
55 | main()
56 |
57 |
--------------------------------------------------------------------------------
/src/day_4/README.md:
--------------------------------------------------------------------------------
1 | # Rock Paper Scissors
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_4/rock_paper_scissors.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
--------------------------------------------------------------------------------
/src/day_4/rock_paper_scissors.py:
--------------------------------------------------------------------------------
1 | import random
2 | import time
3 | import sys
4 |
5 |
6 | def get_game_images():
7 | rock = '''
8 | _______
9 | ---' ____)
10 | (_____)
11 | (_____)
12 | (____)
13 | ---.__(___)
14 | '''
15 | paper = '''
16 | _______
17 | ---' ____)____
18 | ______)
19 | _______)
20 | _______)
21 | ---.__________)
22 | '''
23 |
24 | scissors = '''
25 | _______
26 | ---' ____)____
27 | ______)
28 | __________)
29 | (____)
30 | ---.__(___)
31 | '''
32 | return (rock, paper, scissors)
33 |
34 |
35 | def get_index_from(user_choice):
36 | indexes = {'r': 0, 'p': 1, 's': 2}
37 | return indexes.get(user_choice.lower().strip()[:1], 0)
38 |
39 |
40 | def play_again(points):
41 | main(points) if (choice :=
42 | input("Press enter to play again or else to exit")
43 | == '') else sys.exit()
44 |
45 |
46 | def print_game_images(player, computer):
47 | print(f"You chose:")
48 | print(get_game_images()[player])
49 | time.sleep(1)
50 |
51 | print("Computer chose:")
52 | print(get_game_images()[computer])
53 | time.sleep(1)
54 |
55 |
56 | def get_game_result(player, computer, points):
57 |
58 | win_combs = {
59 | 0: 2,
60 | 1: 0,
61 | 2: 1,
62 | }
63 |
64 | print_game_images(player, computer)
65 |
66 | if (win_combs[player] == computer):
67 |
68 | points['You'] += 1
69 |
70 | return 'You win!'
71 |
72 | elif (win_combs[computer] == player):
73 | points['Computer'] += 1
74 |
75 | return 'You lose'
76 |
77 | else:
78 | return 'It\'s a Draw!'
79 |
80 |
81 | def print_points(points):
82 | print("TOTAL POINTS:", '\n')
83 |
84 | for player, score in points.items():
85 | print(f"{player}: {score}\n")
86 |
87 |
88 | def main(points):
89 |
90 | rules = ('Rock', 'Paper', 'Scissors')
91 |
92 | computer_choice = rules.index(random.choice(rules))
93 |
94 | try:
95 | player_choice = int(
96 | input("Choose Rock (1), Paper (2), or Scissors (3):\n").lower().
97 | strip()[:1]) - 1
98 |
99 | except (ValueError, IndexError):
100 | player_choice = random.randint(0, 2)
101 |
102 | result = get_game_result(player_choice, computer_choice, points)
103 |
104 | print(result, '\n')
105 | print_points(points)
106 | play_again(points)
107 |
108 |
109 | if __name__ == "__main__":
110 | points = {'You': 0, 'Computer': 0}
111 |
112 | try:
113 | main(points)
114 |
115 | except KeyboardInterrupt:
116 | print('Exit Program')
117 | sys.exit()
118 |
--------------------------------------------------------------------------------
/src/day_5/README.md:
--------------------------------------------------------------------------------
1 | # Password Generator
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_5/password_generator.py)
4 |
5 | ## Demo:
6 |
7 |
9 |
--------------------------------------------------------------------------------
/src/day_5/password_generator.py:
--------------------------------------------------------------------------------
1 | import random
2 | import string
3 |
4 |
5 | class PasswordGenerator:
6 | def __init__(
7 | self,
8 | letters_amount: int,
9 | symbols_amount: int,
10 | numbers_amount: int,
11 | ):
12 | self.letters_amount = letters_amount
13 | self.symbols_amount = symbols_amount
14 | self.numbers_amount = numbers_amount
15 |
16 | self.letters = list(string.ascii_letters)
17 | self.symbols = list(string.punctuation)
18 | self.numbers = [i for i in range(10)]
19 |
20 | self.password = []
21 |
22 | def generate_password(self):
23 | self._append_to_password_from(self.letters, self.letters_amount)
24 | self._append_to_password_from(self.symbols, self.symbols_amount)
25 | self._append_to_password_from(self.numbers, self.numbers_amount)
26 |
27 | random.shuffle(self.password)
28 | return ''.join(self.password)
29 |
30 | def _append_to_password_from(self, lst: list, amount: int):
31 | for _ in range(amount):
32 | ch = random.choice(lst)
33 | self.password.append(str(ch))
34 |
--------------------------------------------------------------------------------
/src/day_5/user_interface.py:
--------------------------------------------------------------------------------
1 | from password_generator import PasswordGenerator
2 |
3 |
4 | class UserInterface():
5 | def __init__(self):
6 | self.nb_letters = self.nb_symbols = self.nb_numbers = None
7 |
8 | def print_welcome(self):
9 | print("Welcome to BIGSECURE Password Generator!!")
10 |
11 | def ask_user_password_details(self):
12 | while True:
13 | try:
14 | self.nb_letters = int(
15 | input(
16 | "How many letters would you like in your password?\n"))
17 | assert self.nb_letters > 0
18 |
19 | self.nb_symbols = int(
20 | input(f"How many symbols would you like?\n"))
21 | assert self.nb_symbols > 0
22 |
23 | self.nb_numbers = int(
24 | input(f"How many numbers would you like?\n"))
25 | assert self.nb_numbers > 0
26 |
27 | except (ValueError, AssertionError):
28 | print("Please enter a valid number")
29 | continue
30 | else:
31 | break
32 |
33 | def generate_password(self):
34 | password = PasswordGenerator(self.nb_letters, self.nb_symbols,
35 | self.nb_numbers).generate_password()
36 | return password
37 |
38 | def run(self):
39 | self.print_welcome()
40 | self.ask_user_password_details()
41 |
42 | print("Here is your new password: ")
43 | print(self.generate_password())
44 |
45 |
46 | def main():
47 | ui = UserInterface()
48 | ui.run()
49 |
50 |
51 | if __name__ == "__main__":
52 | main()
--------------------------------------------------------------------------------
/src/day_6/README.md:
--------------------------------------------------------------------------------
1 | # Dice Rolling Simulator
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_6/dice_rolling.py)
4 |
5 | ## Demo:
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/src/day_6/dice.py:
--------------------------------------------------------------------------------
1 | import random
2 | import time
3 |
4 | from collections import Counter
5 |
6 |
7 | class Dice:
8 | def __init__(self, rolling_time=0):
9 | self.rolling_time = rolling_time
10 | self.stats = Counter()
11 |
12 | def print_dice(self, dice_value):
13 | number = 'o '
14 | string = '-----\n|' + number[dice_value < 1] + ' ' + number[
15 | dice_value < 3] + '|\n|' + number[dice_value < 5]
16 | print(string + number[dice_value & 1] + string[::-1])
17 |
18 | def roll_dices(self, dices_number):
19 | dices = dices_number
20 | self.rolling_a_dice(dices)
21 |
22 | def rolling_a_dice(self, dices):
23 | for dice in range(1, dices + 1):
24 | dice_value = random.randrange(6)
25 | self.stats[dice_value + 1] += 1
26 |
27 | print(f"Rolling dice number #{dice}...:\n")
28 | time.sleep(self.rolling_time)
29 | self.print_dice(dice_value)
30 |
31 | def get_dice_stats(self):
32 | return self.stats
--------------------------------------------------------------------------------
/src/day_6/main.py:
--------------------------------------------------------------------------------
1 | from user_interface import UserInterface
2 |
3 |
4 | def main():
5 | UserInterface().run_app()
6 |
7 |
8 | if __name__ == "__main__":
9 | main()
--------------------------------------------------------------------------------
/src/day_6/user_interface.py:
--------------------------------------------------------------------------------
1 | import sys
2 |
3 | from dice import Dice
4 |
5 |
6 | class UserInterface():
7 | def run_app(self):
8 | try:
9 | dice = Dice(rolling_time=1)
10 | dices_to_roll = self.ask_user_how_many_dices()
11 | dice_stats = dice.get_dice_stats()
12 |
13 | dice.roll_dices(dices_to_roll)
14 | self.print_stats(dice_stats)
15 | self.play_again()
16 |
17 | except (KeyboardInterrupt):
18 | print('Exit Program')
19 | sys.exit()
20 |
21 | def ask_user_how_many_dices(self):
22 | try:
23 | dices_to_roll = int(
24 | input("How many dices would you like to roll?\n"))
25 | except ValueError:
26 | # recursive calls until the user enters a correct input
27 | print('Please enter a valid number')
28 | self.ask_user_how_many_dices()
29 | else:
30 | return dices_to_roll
31 |
32 | def print_stats(self, results):
33 | sorted_dices = list(sorted(results.items()))
34 | print(" STATS ".center(20, '*'))
35 |
36 | for dice, total in sorted_dices:
37 | print(f"Dice {dice}:\ntotal: {total}\n")
38 |
39 | if len(results) > 3:
40 | lucky_numbers = self.get_lucky_numbers(results)
41 | numbers = self.make_word_plural('number', lucky_numbers)
42 | print(f"Your lucky {numbers} {str(lucky_numbers)}\n")
43 |
44 | def get_lucky_numbers(self, results):
45 | max_val = max(results.values())
46 | lucky_numbers = []
47 |
48 | # grab the keys from the max values
49 | for dice, total in results.items():
50 | if max_val == total:
51 | lucky_numbers.append(str(dice))
52 |
53 | return ' and '.join(lucky_numbers) if len(
54 | lucky_numbers) == 2 else ', '.join(lucky_numbers)
55 |
56 | def make_word_plural(self, word, condition):
57 | # make a word plural if condition is more than 1
58 | return f"{word}s are" if len(condition) > 1 else f"{word} is"
59 |
60 | def play_again(self):
61 | user_choice = input("Press enter to roll the dice again!")
62 | if user_choice != '':
63 | sys.exit()
64 | else:
65 | self.run_app()
66 |
67 |
68 | if __name__ == "__main__":
69 | ui = UserInterface()
70 | ui.run_app()
--------------------------------------------------------------------------------
/src/day_7/README.md:
--------------------------------------------------------------------------------
1 | # Hangman Game
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_7/hangman.py)
4 |
5 | ## Demo:
6 | 
7 |
--------------------------------------------------------------------------------
/src/day_7/hangman.py:
--------------------------------------------------------------------------------
1 | import random
2 | import pickle
3 | import sys
4 | import os
5 |
6 | from colorama import init, Fore
7 |
8 |
9 | def hangman_pic():
10 | return [
11 | '''
12 | +---+
13 | | |
14 | |
15 | |
16 | |
17 | |
18 | =========''', '''
19 | +---+
20 | | |
21 | O |
22 | |
23 | |
24 | |
25 | =========''', '''
26 | +---+
27 | | |
28 | O |
29 | | |
30 | |
31 | |
32 | =========''', '''
33 | +---+
34 | | |
35 | O |
36 | /| |
37 | |
38 | |
39 | =========''', '''
40 | +---+
41 | | |
42 | O |
43 | /|\\ |
44 | |
45 | |
46 | =========''', '''
47 | +---+
48 | | |
49 | O |
50 | /|\\ |
51 | / |
52 | |
53 | =========''', '''
54 | +---+
55 | | |
56 | O |
57 | /|\\ |
58 | / \\ |
59 | |
60 | ========='''
61 | ]
62 |
63 |
64 | def get_file_path(*paths):
65 | return os.path.join(os.getcwd(), ''.join(list(paths)))
66 |
67 |
68 | def save_player_score_to(file_name, player_name, score):
69 | scores = get_players_scores_from(file_name)
70 |
71 | with open(get_file_path(file_name), 'wb') as scores_file:
72 | scores[player_name] = score
73 | pickle.dump(scores, scores_file)
74 |
75 |
76 | def create_scores_file(file_name):
77 | if not os.path.isfile(file_name):
78 | with open(get_file_path(file_name), 'wb') as scores_file:
79 | pickle.dump({}, scores_file)
80 |
81 |
82 | def get_players_scores_from(file_name):
83 | with open(get_file_path(file_name), 'rb') as scores_file:
84 | try:
85 | data = pickle.load(scores_file)
86 | except EOFError as error:
87 | return {}
88 | return data
89 |
90 |
91 | def get_words_list():
92 | with open(os.path.join(os.getcwd(), 'words.txt')) as words_file:
93 | words = words_file.read().strip().split()
94 | return words
95 |
96 |
97 | def get_string_word(word):
98 | return ''.join(word).upper()
99 |
100 |
101 | # def check_keyboardInterrupt(callback):
102 | # # check if the player exits the terminal with (control + C) or other if true he can exit without error
103 | # try:
104 | # return callback()
105 | # except KeyboardInterrupt as error:
106 | # print("Exit program")
107 | # sys.exit()
108 |
109 |
110 | def remove_player(name, players_scores, file_name):
111 | del players_scores[name]
112 | with open(get_file_path(file_name), 'wb') as scores_file:
113 | pickle.dump(players_scores, scores_file)
114 |
115 |
116 | def remove_last_player(players_scores, file_name):
117 | players_scores.popitem()
118 | with open(get_file_path(file_name), 'wb') as scores_file:
119 | pickle.dump(players_scores, scores_file)
120 |
121 |
122 | def ask_player_letter():
123 | letter = input("Enter a letter:\n").strip().upper()[:1]
124 | return letter
125 |
126 |
127 | def make_word_plural_or_singular(condition, word):
128 | plural_word = word
129 |
130 | if word.endswith('s'):
131 | plural_word = word + 'es'
132 | else:
133 | plural_word = word + 's'
134 |
135 | word = plural_word if condition > 1 else word
136 | return word
137 |
138 |
139 | def print_guesses_left(player_guesses):
140 | guess_color = Fore.YELLOW if int(player_guesses) > 3 else Fore.RED
141 | print(
142 | f'You have {guess_color + str(player_guesses)} {make_word_plural_or_singular(player_guesses, "guess")} left!'
143 | )
144 |
145 |
146 | def play_again(file_name, player_name):
147 |
148 | choice = input(f"{player_name}, type 'y' to play again or 'n' to exit"
149 | ).lower().strip()
150 |
151 | if choice == 'y':
152 | play_game(file_name, player_name)
153 |
154 |
155 | def get_player_name():
156 | return input("Enter your name to save your score:\n").title().strip()
157 |
158 |
159 | def print_leaderboard(scores):
160 |
161 | if (scores):
162 | names_scores_sorted = sorted(scores.items(),
163 | key=lambda x: x[1],
164 | reverse=True)
165 | placement = 1
166 |
167 | print(Fore.YELLOW + "LEADERBOARD".center(40, '*'))
168 | print()
169 | print(Fore.YELLOW + "TOP 3 PLAYERS".center(40, '*'), "\n")
170 |
171 | for name, score in names_scores_sorted:
172 |
173 | score_color = Fore.CYAN if score > 0 else Fore.RED
174 | placement_color = Fore.YELLOW if placement <= 3 else Fore.WHITE
175 | name_color = Fore.GREEN if placement <= 3 else Fore.WHITE
176 |
177 | if placement == 4:
178 | print(Fore.YELLOW + "******".center(40, '*'))
179 |
180 | print(
181 | f"# {placement_color + str(placement)}: {name_color+ name} - {score_color + str(score)} {Fore.WHITE + make_word_plural_or_singular(score, 'point')}"
182 | )
183 |
184 | placement += 1
185 |
186 | print(Fore.YELLOW + "******".center(40, '*'))
187 |
188 |
189 | def play_game(file_name, player_name):
190 | players_scores = get_players_scores_from(file_name)
191 | print_leaderboard(players_scores)
192 |
193 | hangman_pic_index = 0
194 | wrong_letters = []
195 | score = 0
196 |
197 | if players_scores and player_name in players_scores:
198 | score = players_scores[player_name]
199 |
200 | words_list = get_words_list()
201 | correct_word = random.choice(words_list).upper()
202 |
203 | player_guesses = 6
204 | word_to_guess_list = ['_' for _ in range(len(correct_word))]
205 |
206 | print(f'The secret word has {len(correct_word)} letters\n')
207 |
208 | while player_guesses:
209 |
210 | player_letter = ask_player_letter()
211 |
212 | if player_letter and player_letter in correct_word:
213 | indexes = [
214 | i for i, letter in enumerate(correct_word)
215 | if letter == player_letter
216 | ]
217 | for i in indexes:
218 | word_to_guess_list[i] = player_letter
219 | else:
220 | wrong_letters.append((player_letter))
221 | wrong_letters = list(set(wrong_letters))
222 | player_guesses -= 1
223 | hangman_pic_index += 1
224 |
225 | word_to_guess_string = get_string_word(word_to_guess_list)
226 |
227 | for ch in word_to_guess_string:
228 | word_color = Fore.WHITE if ch == '_' else Fore.CYAN
229 | print(f" {word_color + ch} ".center(1), end='')
230 | print("\n")
231 | print(hangman_pic()[hangman_pic_index], '\n')
232 | print_guesses_left(player_guesses)
233 |
234 | print(f"Wrong letters: {Fore.RED + ' '.join(wrong_letters)}\n")
235 |
236 | if (word_to_guess_string == correct_word):
237 | print(f'You win! The word is {Fore.CYAN + correct_word}\n')
238 | break
239 |
240 | if (not player_guesses):
241 | print(
242 | f'Sorry! You lost! No more guesses left! The word was {Fore.CYAN + correct_word}\n'
243 | )
244 |
245 | score += player_guesses
246 |
247 | save_player_score_to(file_name, player_name, score)
248 |
249 | play_again(file_name, player_name)
250 |
251 |
252 | def main():
253 | os.chdir(os.getcwd() + "/src/day_7")
254 |
255 | try:
256 | file_name = 'players-scores'
257 | create_scores_file(file_name)
258 |
259 | player_name = get_player_name()
260 | play_game(file_name, player_name)
261 |
262 | except KeyboardInterrupt:
263 | print("Exit Program")
264 | sys.exit()
265 |
266 |
267 | if __name__ == "__main__":
268 | # for the color to reset at each print
269 |
270 | init(autoreset=True)
271 | main()
--------------------------------------------------------------------------------
/src/day_7/players-scores:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/dylanbuchi/31-days-of-code/216585d2402129da42bc17babce4ae444fc40dff/src/day_7/players-scores
--------------------------------------------------------------------------------
/src/day_7/requirements.txt:
--------------------------------------------------------------------------------
1 | colorama==0.4.4
--------------------------------------------------------------------------------
/src/day_7/words.txt:
--------------------------------------------------------------------------------
1 | able
2 | about
3 | account
4 | acid
5 | across
6 | act
7 | addition
8 | adjustment
9 | advertisement
10 | after
11 | again
12 | against
13 | agreement
14 | air
15 | all
16 | almost
17 | among
18 | amount
19 | amusement
20 | and
21 | angle
22 | angry
23 | animal
24 | answer
25 | ant
26 | any
27 | apparatus
28 | apple
29 | approval
30 | arch
31 | argument
32 | arm
33 | army
34 | art
35 | as
36 | at
37 | attack
38 | attempt
39 | attention
40 | attraction
41 | authority
42 | automatic
43 | awake
44 | baby
45 | back
46 | bad
47 | bag
48 | balance
49 | ball
50 | band
51 | base
52 | basin
53 | basket
54 | bath
55 | be
56 | beautiful
57 | because
58 | bed
59 | bee
60 | before
61 | behaviour
62 | belief
63 | bell
64 | bent
65 | berry
66 | between
67 | bird
68 | birth
69 | bit
70 | bite
71 | bitter
72 | black
73 | blade
74 | blood
75 | blow
76 | blue
77 | board
78 | boat
79 | body
80 | boiling
81 | bone
82 | book
83 | boot
84 | bottle
85 | box
86 | boy
87 | brain
88 | brake
89 | branch
90 | brass
91 | bread
92 | breath
93 | brick
94 | bridge
95 | bright
96 | broken
97 | brother
98 | brown
99 | brush
100 | bucket
101 | building
102 | bulb
103 | burn
104 | burst
105 | business
106 | biiiiiig
107 | but
108 | butter
109 | button
110 | by
111 | cake
112 | camera
113 | canvas
114 | card
115 | care
116 | carriage
117 | cart
118 | cat
119 | cause
120 | certain
121 | chain
122 | chalk
123 | chance
124 | change
125 | cheap
126 | cheese
127 | chemical
128 | chest
129 | chief
130 | chin
131 | church
132 | circle
133 | clean
134 | clear
135 | clock
136 | cloth
137 | cloud
138 | coal
139 | coat
140 | cold
141 | collar
142 | colour
143 | comb
144 | come
145 | comfort
146 | committee
147 | common
148 | company
149 | comparison
150 | competition
151 | complete
152 | complex
153 | condition
154 | connection
155 | conscious
156 | control
157 | cook
158 | copper
159 | copy
160 | cord
161 | cork
162 | cotton
163 | cough
164 | country
165 | cover
166 | cow
167 | crack
168 | credit
169 | crime
170 | cruel
171 | crush
172 | cry
173 | cup
174 | cup
175 | current
176 | curtain
177 | curve
178 | cushion
179 | damage
180 | danger
181 | dark
182 | daughter
183 | day
184 | dead
185 | dear
186 | death
187 | debt
188 | decision
189 | deep
190 | degree
191 | delicate
192 | dependent
193 | design
194 | desire
195 | destruction
196 | detail
197 | development
198 | different
199 | digestion
200 | direction
201 | dirty
202 | discovery
203 | discussion
204 | disease
205 | disgust
206 | distance
207 | distribution
208 | division
209 | do
210 | dog
211 | door
212 | doubt
213 | down
214 | drain
215 | drawer
216 | dress
217 | drink
218 | driving
219 | drop
220 | dry
221 | dust
222 | ear
223 | early
224 | earth
225 | east
226 | edge
227 | education
228 | effect
229 | egg
230 | elastic
231 | electric
232 | end
233 | engine
234 | enough
235 | equal
236 | error
237 | even
238 | event
239 | ever
240 | every
241 | example
242 | exchange
243 | existence
244 | expansion
245 | experience
246 | expert
247 | eye
248 | face
249 | fact
250 | fall
251 | false
252 | family
253 | far
254 | farm
255 | fat
256 | father
257 | fear
258 | feather
259 | feeble
260 | feeling
261 | female
262 | fertile
263 | fiction
264 | field
265 | fight
266 | finger
267 | fire
268 | first
269 | fish
270 | fixed
271 | flag
272 | flame
273 | flat
274 | flight
275 | floor
276 | flower
277 | fly
278 | fold
279 | food
280 | foolish
281 | foot
282 | for
283 | force
284 | fork
285 | form
286 | forward
287 | fowl
288 | frame
289 | free
290 | frequent
291 | friend
292 | from
293 | front
294 | fruit
295 | full
296 | future
297 | garden
298 | general
299 | get
300 | girl
301 | give
302 | glass
303 | glove
304 | go
305 | goat
306 | gold
307 | good
308 | government
309 | grain
310 | grass
311 | great
312 | green
313 | grey
314 | grip
315 | group
316 | growth
317 | guide
318 | gun
319 | hair
320 | hammer
321 | hand
322 | hanging
323 | happy
324 | harbour
325 | hard
326 | harmony
327 | hat
328 | hate
329 | have
330 | he
331 | head
332 | healthy
333 | hear
334 | hearing
335 | heart
336 | heat
337 | help
338 | high
339 | history
340 | hole
341 | hollow
342 | hook
343 | hope
344 | horn
345 | horse
346 | hospital
347 | hour
348 | house
349 | how
350 | humour
351 | I
352 | ice
353 | idea
354 | if
355 | ill
356 | important
357 | impulse
358 | in
359 | increase
360 | industry
361 | ink
362 | insect
363 | instrument
364 | insurance
365 | interest
366 | invention
367 | iron
368 | island
369 | jelly
370 | jewel
371 | join
372 | journey
373 | judge
374 | jump
375 | keep
376 | kettle
377 | key
378 | kick
379 | kind
380 | kiss
381 | knee
382 | knife
383 | knot
384 | knowledge
385 | land
386 | language
387 | last
388 | late
389 | laugh
390 | law
391 | lead
392 | leaf
393 | learning
394 | leather
395 | left
396 | leg
397 | let
398 | letter
399 | level
400 | library
401 | lift
402 | light
403 | like
404 | limit
405 | line
406 | linen
407 | lip
408 | liquid
409 | list
410 | little
411 | living
412 | lock
413 | long
414 | look
415 | loose
416 | loss
417 | loud
418 | love
419 | low
420 | machine
421 | make
422 | male
423 | man
424 | manager
425 | map
426 | mark
427 | market
428 | married
429 | mass
430 | match
431 | material
432 | may
433 | meal
434 | measure
435 | meat
436 | medical
437 | meeting
438 | memory
439 | metal
440 | middle
441 | military
442 | milk
443 | mind
444 | mine
445 | minute
446 | mist
447 | mixed
448 | money
449 | monkey
450 | month
451 | moon
452 | morning
453 | mother
454 | motion
455 | mountain
456 | mouth
457 | move
458 | much
459 | muscle
460 | music
461 | nail
462 | name
463 | narrow
464 | nation
465 | natural
466 | near
467 | necessary
468 | neck
469 | need
470 | needle
471 | nerve
472 | net
473 | new
474 | news
475 | night
476 | no
477 | noise
478 | normal
479 | north
480 | nose
481 | not
482 | note
483 | now
484 | number
485 | nut
486 | observation
487 | of
488 | off
489 | offer
490 | office
491 | oil
492 | old
493 | on
494 | only
495 | open
496 | operation
497 | opinion
498 | opposite
499 | or
500 | orange
501 | order
502 | organization
503 | ornament
504 | other
505 | out
506 | oven
507 | over
508 | owner
509 | page
510 | pain
511 | paint
512 | paper
513 | parallel
514 | parcel
515 | part
516 | past
517 | paste
518 | payment
519 | peace
520 | pen
521 | pencil
522 | person
523 | physical
524 | picture
525 | pig
526 | pin
527 | pipe
528 | place
529 | plane
530 | plant
531 | plate
532 | play
533 | please
534 | pleasure
535 | plough
536 | pocket
537 | point
538 | poison
539 | polish
540 | political
541 | poor
542 | porter
543 | position
544 | possible
545 | pot
546 | potato
547 | powder
548 | power
549 | present
550 | price
551 | print
552 | prison
553 | private
554 | probable
555 | process
556 | produce
557 | profit
558 | property
559 | prose
560 | protest
561 | public
562 | pull
563 | pump
564 | punishment
565 | purpose
566 | push
567 | put
568 | quality
569 | question
570 | quick
571 | quiet
572 | quite
573 | rail
574 | rain
575 | range
576 | rat
577 | rate
578 | ray
579 | reaction
580 | reading
581 | ready
582 | reason
583 | receipt
584 | record
585 | red
586 | regret
587 | regular
588 | relation
589 | religion
590 | representative
591 | request
592 | respect
593 | responsible
594 | rest
595 | reward
596 | rhythm
597 | rice
598 | right
599 | ring
600 | river
601 | road
602 | rod
603 | roll
604 | roof
605 | room
606 | root
607 | rough
608 | round
609 | rub
610 | rule
611 | run
612 | sad
613 | safe
614 | sail
615 | salt
616 | same
617 | sand
618 | say
619 | scale
620 | school
621 | science
622 | scissors
623 | screw
624 | sea
625 | seat
626 | second
627 | secret
628 | secretary
629 | see
630 | seed
631 | seem
632 | selection
633 | self
634 | send
635 | sense
636 | separate
637 | serious
638 | servant
639 | sex
640 | shade
641 | shake
642 | shame
643 | sharp
644 | sheep
645 | shelf
646 | ship
647 | shirt
648 | shock
649 | shoe
650 | short
651 | shut
652 | side
653 | sign
654 | silk
655 | silver
656 | simple
657 | sister
658 | size
659 | skin
660 |
661 | skirt
662 | sky
663 | sleep
664 | slip
665 | slope
666 | slow
667 | small
668 | smash
669 | smell
670 | smile
671 | smoke
672 | smooth
673 | snake
674 | sneeze
675 | snow
676 | so
677 | soap
678 | society
679 | sock
680 | soft
681 | solid
682 | some
683 |
684 | son
685 | song
686 | sort
687 | sound
688 | soup
689 | south
690 | space
691 | spade
692 | special
693 | sponge
694 | spoon
695 | spring
696 | square
697 | stage
698 | stamp
699 | star
700 | start
701 | statement
702 | station
703 | steam
704 | steel
705 | stem
706 | step
707 | stick
708 | sticky
709 | stiff
710 | still
711 | stitch
712 | stocking
713 | stomach
714 | stone
715 | stop
716 | store
717 | story
718 | straight
719 | strange
720 | street
721 | stretch
722 | strong
723 | structure
724 | substance
725 | such
726 | sudden
727 | sugar
728 | suggestion
729 | summer
730 | sun
731 | support
732 | surprise
733 | sweet
734 | swim
735 | system
736 | table
737 | tail
738 | take
739 | talk
740 | tall
741 | taste
742 | tax
743 | teaching
744 | tendency
745 | test
746 | than
747 | that
748 | the
749 | then
750 | theory
751 | there
752 | thick
753 | thin
754 | thing
755 | this
756 | thought
757 | thread
758 | throat
759 | through
760 | through
761 | thumb
762 | thunder
763 | ticket
764 | tight
765 | till
766 | time
767 | tin
768 | tired
769 | to
770 | toe
771 | together
772 | tomorrow
773 | tongue
774 | tooth
775 | top
776 | touch
777 | town
778 | trade
779 | train
780 | transport
781 | tray
782 | tree
783 | trick
784 | trouble
785 | trousers
786 | true
787 | turn
788 | twist
789 | umbrella
790 | under
791 | unit
792 | up
793 | use
794 | value
795 | verse
796 | very
797 | vessel
798 | view
799 | violent
800 | voice
801 | waiting
802 | walk
803 | wall
804 | war
805 | warm
806 | wash
807 | waste
808 | watch
809 | water
810 | wave
811 | wax
812 | way
813 | weather
814 | week
815 | weight
816 | well
817 | west
818 | wet
819 | wheel
820 | when
821 | where
822 | while
823 | whip
824 | whistle
825 | white
826 | who
827 | why
828 | wide
829 | will
830 | wind
831 | window
832 | wine
833 | wing
834 | winter
835 | wire
836 | wise
837 | with
838 | woman
839 | wood
840 | wool
841 | word
842 | work
843 | worm
844 | wound
845 | writing
846 | wrong
847 | year
848 | yellow
849 | yes
850 | yesterday
851 | you
852 | young
853 | Bernhard
854 | Breytenbach
855 | Android
--------------------------------------------------------------------------------
/src/day_8/README.md:
--------------------------------------------------------------------------------
1 | # Caesar Cipher
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_8/caesar_cipher.py)
4 |
5 | ## Demo:
6 |
7 | 
8 |
--------------------------------------------------------------------------------
/src/day_8/caesar_cipher.py:
--------------------------------------------------------------------------------
1 | # Caesar Cipher
2 | import sys
3 | import os
4 |
5 | # add this to import the logo and run the file here
6 | sys.path.append(os.getcwd())
7 |
8 | from src.day_8.logo import LOGO
9 |
10 | # Global constant variable
11 | ALPHABET = [chr(i) for i in range(97, 123)]
12 |
13 |
14 | def run_again():
15 | choice = input("Press enter to run again")
16 | if not choice:
17 | main()
18 |
19 |
20 | def ask_user_encryption_details():
21 | text = space = ' '
22 | shift = 5
23 |
24 | while True:
25 | try:
26 | text = input("Type your message:\n").lower()
27 | assert text.isalpha() or space in text
28 | shift = int(input("Type the shift number:\n"))
29 |
30 | except (ValueError, AssertionError):
31 | print("Error, please try again with valid inputs")
32 | continue
33 | else:
34 | return text, shift
35 |
36 |
37 | def choose_codec_mode(mode, text: str, shift):
38 | parts = []
39 |
40 | for ch in text:
41 | if not ch.isalpha():
42 | parts.append(ch)
43 |
44 | else:
45 | index = (ALPHABET.index(ch))
46 | index = index + shift if mode == 'encode' else index - shift
47 | parts.append(ALPHABET[index % 26])
48 |
49 | return ''.join(parts)
50 |
51 |
52 | def run_caesar_cipher(text, shift, mode):
53 | return choose_codec_mode(mode, text, shift)
54 |
55 |
56 | def user_interface():
57 | mode = input("Type 'encode' to encrypt or type 'decode' to decrypt:\n"
58 | ).lower().strip()
59 | text, shift = ask_user_encryption_details()
60 | result = run_caesar_cipher(text, shift, mode)
61 |
62 | print(f"The {mode}d message is: {result}")
63 |
64 |
65 | def main():
66 | print(LOGO)
67 | try:
68 | user_interface()
69 | run_again()
70 |
71 | except KeyboardInterrupt:
72 | sys.exit()
73 |
74 |
75 | if __name__ == "__main__":
76 | main()
--------------------------------------------------------------------------------
/src/day_8/logo.py:
--------------------------------------------------------------------------------
1 | LOGO = """
2 | ,adPPYba, ,adPPYYba, ,adPPYba, ,adPPYba, ,adPPYYba, 8b,dPPYba,
3 | a8" "" "" `Y8 a8P_____88 I8[ "" "" `Y8 88P' "Y8
4 | 8b ,adPPPPP88 8PP""" """" `"Y8ba, ,adPPPPP88 88
5 | "8a, ,aa 88, ,88 "8b, ,aa aa ]8I 88, ,88 88
6 | `"Ybbd8"' `"8bbdP"Y8 `"Ybbd8"' `"YbbdP"' `"8bbdP"Y8 88
7 | 88 88
8 | "" 88
9 | 88
10 | ,adPPYba, 88 8b,dPPYba, 88,dPPYba, ,adPPYba, 8b,dPPYba,
11 | a8" "" 88 88P' "8a 88P' "8a a8P_____88 88P' "Y8
12 | 8b 88 88 d8 88 88 8PP""" """" 88
13 | "8a, ,aa 88 88b, ,a8" 88 88 "8b, ,aa 88
14 | `"Ybbd8"' 88 88`YbbdP"' 88 88 `"Ybbd8"' 88
15 | 88
16 | 88
17 | """
--------------------------------------------------------------------------------
/src/day_9/README.md:
--------------------------------------------------------------------------------
1 | # Auction Program
2 |
3 | ## [Code](https://github.com/dylanbuchi/100-days-of-code/blob/main/src/day_9/auction_program.py)
4 |
5 | ## Demo:
6 |
7 | 
8 |
9 |
--------------------------------------------------------------------------------
/src/day_9/auction.py:
--------------------------------------------------------------------------------
1 | import re
2 |
3 | from colorama import Fore, init
4 |
5 |
6 | class Auction:
7 | def __init__(self) -> None:
8 | init(autoreset=True)
9 | self.name_with_bid_amount_map = {}
10 |
11 | def check_user_name(self, name):
12 | return name in self.name_with_bid_amount_map
13 |
14 | def get_welcome_message(self, message="Welcome to my auction program"):
15 | return message
16 |
17 | def print_error_message(self, message):
18 | print(Fore.RED + message)
19 |
20 | def get_user_name(self):
21 | try:
22 | name = input("What's your name?\n").title().strip()
23 | if self.check_user_name(name):
24 | self.print_error_message(
25 | "This name is already in our database. Please choose an username"
26 | )
27 | return self.get_user_name()
28 |
29 | assert re.match(r"^[a-z A-Z]+$", name) is not None
30 |
31 | except AssertionError:
32 | self.print_error_message("Please enter a valid name")
33 | return self.get_user_name()
34 |
35 | else:
36 | return name
37 |
38 | def get_user_bid_amount(self):
39 | try:
40 | bid = int(input("What's your bid?\n$").strip())
41 | assert bid > 0
42 |
43 | except (ValueError, AssertionError):
44 | # recursive calls until user enters a valid input
45 | self.print_error_message('Please enter a valid amount')
46 | return self.get_user_bid_amount()
47 |
48 | else:
49 | return bid
50 |
51 | def ask_user_more_biders(self):
52 | try:
53 | answer = input(
54 | "Are there any other bidders? (y/n)\n").lower().strip()[:1]
55 | assert answer == 'y' or answer == 'n'
56 |
57 | except AssertionError:
58 | self.print_error_message("Please enter 'yes' or 'no' (y/n)")
59 | return self.ask_user_more_biders()
60 | else:
61 | return answer
62 |
63 | def get_winner(self, name_bid_amount):
64 | max_amount = max(name_bid_amount.values())
65 |
66 | for name, amount in name_bid_amount.items():
67 | if max_amount == amount:
68 | return name, amount
69 |
70 | def print_current_bidders(self):
71 | print("\nCurrent bidders:\n")
72 |
73 | if self.name_with_bid_amount_map:
74 | for name, amount in sorted(self.name_with_bid_amount_map.items(),
75 | key=lambda x: x[1],
76 | reverse=True):
77 | print(f"{name:5}: ${amount:,}")
78 | print()
79 |
--------------------------------------------------------------------------------
/src/day_9/auction_program.py:
--------------------------------------------------------------------------------
1 | # Auction_Program
2 | import os
3 | import sys
4 | sys.path.extend([os.path.join(os.getcwd(), 'src'), os.path.join(os.getcwd())])
5 |
6 | import random
7 |
8 | from day_9.auction import Auction
9 | from day_9.logo import LOGO
10 |
11 | from utility import clear_console
12 |
13 |
14 | def get_random_bid(start=1, end=2000):
15 | return random.randint(start, end)
16 |
17 |
18 | def get_random_name_and_remove_it_from(names):
19 | name = random.choice(names)
20 | names.remove(name)
21 | return name
22 |
23 |
24 | def create_default_bidders():
25 | names = ["John", "Harry", "Joe", "Tony", "Emma", "Mia"]
26 |
27 | bidders_list = [{
28 | get_random_name_and_remove_it_from(names): get_random_bid()
29 | for i in range(6)
30 | }]
31 |
32 | return bidders_list
33 |
34 |
35 | def get_default_bidders():
36 | temp = {}
37 | for b in create_default_bidders():
38 | temp.update(b)
39 | return temp
40 |
41 |
42 | def user_interface():
43 | auction = Auction()
44 | print(auction.get_welcome_message())
45 |
46 | auction.name_with_bid_amount_map = get_default_bidders()
47 | name_bid_amount = auction.name_with_bid_amount_map
48 |
49 | while True:
50 | auction.print_current_bidders()
51 |
52 | user_name = auction.get_user_name()
53 | user_bid = auction.get_user_bid_amount()
54 |
55 | name_bid_amount[user_name] = user_bid
56 | answer = auction.ask_user_more_biders()
57 |
58 | if answer == 'n':
59 | break
60 |
61 | clear_console()
62 |
63 | winner, winner_bid = auction.get_winner(name_bid_amount)
64 | print(f"The winner is {winner} with a bid of ${winner_bid:,}")
65 |
66 |
67 | def main():
68 | print(LOGO)
69 |
70 | try:
71 | user_interface()
72 |
73 | except KeyboardInterrupt:
74 | print("Exit")
75 |
76 |
77 | if __name__ == "__main__":
78 | main()
--------------------------------------------------------------------------------
/src/day_9/logo.py:
--------------------------------------------------------------------------------
1 | LOGO = '''
2 | ___________
3 | \ /
4 | )_______(
5 | |"""""""|_.-._,.---------.,_.-._
6 | | | | | | | ''-.
7 | | |_| |_ _| |_..-'
8 | |_______| '-' `'---------'` '-'
9 | )"""""""(
10 | /_________\\
11 | .-------------.
12 | /_______________\\
13 | '''
--------------------------------------------------------------------------------
/utility.py:
--------------------------------------------------------------------------------
1 | import os
2 |
3 |
4 | def clear_console():
5 | os.system('cls' if os.name == 'nt' else 'clear')
--------------------------------------------------------------------------------