Compare commits

..

11 Commits

Author SHA1 Message Date
3046af13e5 Fixed character placement 2025-07-16 09:46:11 +01:00
ae8b0c77a5 Added text timer 2025-07-06 20:16:46 +01:00
afd1fcd6be Added comments 2025-07-06 20:16:33 +01:00
3cd2ddbd46 Changed when timer is drawn 2025-07-06 20:16:22 +01:00
f36bce66e2 Updated random timer range 2025-07-06 20:07:03 +01:00
f625c80fd3 Added captcha progress bar 2025-07-06 20:06:49 +01:00
db7faca3d9 Added red flash when wrong 2025-07-06 20:06:13 +01:00
11b1dad78b Changed order of upper() 2025-07-06 20:05:39 +01:00
3471e41272 Refined fonts 2025-07-06 20:05:14 +01:00
ae6c23b6b7 Added basic timer 2025-07-06 19:34:07 +01:00
6e70f74874 Removed all letters from Flame on Black
They all seem to be broken
2025-07-06 19:33:55 +01:00
3 changed files with 36 additions and 7 deletions

View File

@ -5,11 +5,10 @@
{"file": "Vampire Wars.ttf", "alphabet": "abcdefghijklmnopqrstuvwxyz0123456789", "difficulty": 0.1}, {"file": "Vampire Wars.ttf", "alphabet": "abcdefghijklmnopqrstuvwxyz0123456789", "difficulty": 0.1},
{"file": "CloisterBlack.ttf", "alphabet": "0123456789", "difficulty": 0.1}, {"file": "CloisterBlack.ttf", "alphabet": "0123456789", "difficulty": 0.1},
{"file": "Noxlock-Free.otf", "alphabet": "ABCDEFGHIJKLMNOPQRSTUVWXYZ", "difficulty": 0.2}, {"file": "Noxlock-Free.otf", "alphabet": "ABCDEFGHIJKLMNOPQRSTUVWXYZ", "difficulty": 0.2},
{"file": "CloisterBlack.ttf", "alphabet": "abcdefghijklmnopqrstuvwxyz", "difficulty": 0.3}, {"file": "CloisterBlack.ttf", "alphabet": "abcdefghijklmnopqrstuvwxyz", "difficulty": 0.5},
{"file": "LEDLIGHT.otf", "alphabet": "abcdefghijklmnopqrstuvwxyz", "difficulty": 0.4}, {"file": "LEDLIGHT.otf", "alphabet": "abcdefghijklmnopqrstuvwxyz", "difficulty": 0.4},
{"file": "Flame on Black.ttf", "alphabet": "abcdefghijklmnopqrstuvwxyz0123456789!?/#<>", "difficulty": 0.5}, {"file": "Flame on Black.ttf", "alphabet": "0123456789!?/#<>", "difficulty": 0.5},
{"file": "CloisterBlack.ttf", "alphabet": "ABCDEFGHIJKLMNOPQRSTUVWXYZ", "difficulty": 0.6}, {"file": "CloisterBlack.ttf", "alphabet": "ABCDEFGHIJKLMNOPQRSTUVWXYZ", "difficulty": 0.6},
{"file": "mevno2.ttf", "alphabet": "abcdefghijklmnopqrstuvwxyz", "difficulty": 0.8},
{"file": "CloisterBlack.ttf", "alphabet": "ABCDEFGHIJKLMNOPQRSTUVWXYZ", "difficulty": 0.8}, {"file": "CloisterBlack.ttf", "alphabet": "ABCDEFGHIJKLMNOPQRSTUVWXYZ", "difficulty": 0.8},
{"file": "RoyalInitialen.ttf", "alphabet": "abcdefghijklmnopqrstuvwxyz", "difficulty": 0.8}, {"file": "RoyalInitialen.ttf", "alphabet": "abcdefghijklmnopqrstuvwxyz", "difficulty": 0.8},
{"file": "DeathMohawk_PERSONAL_USE_ONLY.otf", "alphabet": "ABCDEFGHIJKLMNOPQRSTUVWXYZ", "difficulty": 1.0} {"file": "DeathMohawk_PERSONAL_USE_ONLY.otf", "alphabet": "ABCDEFGHIJKLMNOPQRSTUVWXYZ", "difficulty": 1.0}

Binary file not shown.

38
game.py
View File

@ -1,5 +1,6 @@
from PIL import Image, ImageDraw, ImageFont from PIL import Image, ImageDraw, ImageFont
import math as maths import math as maths
import numpy as np
import logging import logging
import pygame import pygame
import gameUtils import gameUtils
@ -57,14 +58,14 @@ class Captcha:
# anthing below this index should appear green. # anthing below this index should appear green.
def addChar(self, char, font): def addChar(self, char, font):
self.chars.append(char.upper()) self.chars.append(char)
self.fonts.append(font) self.fonts.append(font)
def match(self, char): def match(self, char):
if self.charIdx == len(self.chars): if self.charIdx == len(self.chars):
return True, True return True, True
matches = char.upper() == self.chars[self.charIdx] matches = char.upper() == self.chars[self.charIdx].upper()
print(f'{char.upper()} == {self.chars[self.charIdx]}') print(f'{char.upper()} == {self.chars[self.charIdx]}')
if matches: if matches:
self.charIdx += 1 self.charIdx += 1
@ -96,6 +97,10 @@ class Game(gameUtils.Game):
self.timerStart = 0 self.timerStart = 0
# Holds how much time the user has in total (not updated) # Holds how much time the user has in total (not updated)
self.timerLength = 0 self.timerLength = 0
# The font used for the timer
self.timerFont = pygame.font.SysFont('', 100)
# Used for animating the red flash on the current character if the users enters it wrong.
self.lastWrong = 0
self.fonts = [] self.fonts = []
self.Drawsurface = Image.new("RGB",(800,220),(255,255,255)) self.Drawsurface = Image.new("RGB",(800,220),(255,255,255))
@ -138,7 +143,7 @@ class Game(gameUtils.Game):
for i in range(capLength): for i in range(capLength):
# Calculate the base X position of this character # Calculate the base X position of this character
# TODO: Make this better, I'm not too happy with my implementation here. # TODO: Make this better, I'm not too happy with my implementation here.
x = self.size[0] / (capLength + 3) x = drawSurface.size[0] / capLength
x *= i x *= i
# Get the selected difficulty for this character # Get the selected difficulty for this character
charDiff = normalDist(self.gameDifficulty) charDiff = normalDist(self.gameDifficulty)
@ -160,6 +165,10 @@ class Game(gameUtils.Game):
for char, font in zip(captcha.chars, captcha.fonts): for char, font in zip(captcha.chars, captcha.fonts):
print(f'{char}: {font.path}') print(f'{char}: {font.path}')
# Start the timer
self.timerStart = time.perf_counter()
self.timerLength = random.randint(7, 15)
def onEvent(self, event): def onEvent(self, event):
""" """
Ran when an event is fired. Ran when an event is fired.
@ -179,6 +188,8 @@ class Game(gameUtils.Game):
elif event.unicode != '' and event.unicode in alphabet: elif event.unicode != '' and event.unicode in alphabet:
correct, finished = self.currentCaptcha.match(event.unicode) correct, finished = self.currentCaptcha.match(event.unicode)
if not correct:
self.lastWrong = time.perf_counter()
print(correct) print(correct)
if finished: if finished:
self.createCaptcha() self.createCaptcha()
@ -189,9 +200,28 @@ class Game(gameUtils.Game):
game logic that should be ran once per frame in here. game logic that should be ran once per frame in here.
""" """
self.surf.fill((0, 0, 0)) #sets the background colour r = 1 - min(time.perf_counter() - self.lastWrong, 1)
self.surf.fill((r * 255, 0, 0)) #sets the background colour
self.surf.blit(gameUtils.centre(self.currentCaptchaImg, self.size)) #draws the text to center of the screen self.surf.blit(gameUtils.centre(self.currentCaptchaImg, self.size)) #draws the text to center of the screen
#TODO: actually scale the text, however, more work needs to be done on the actual function of the game first #TODO: actually scale the text, however, more work needs to be done on the actual function of the game first
# Draw the captcha progerss if there is a captcha
if self.currentCaptcha is not None:
x1 = self.size[0] / 2 - self.currentCaptchaImg.size[0] / 2
y = self.size[1] / 2 + self.currentCaptchaImg.size[1] / 2
x2 = x1 + (self.currentCaptcha.charIdx / len(self.currentCaptcha.chars)) * self.currentCaptchaImg.size[0]
pygame.draw.line(self.surf, (0, 255, 0), (x1, y), (x2, y), 5)
# Draw the timer if there's any time left
timeLeft = self.timerLength - (time.perf_counter() - self.timerStart)
if timeLeft > 0:
normalisedTimeLeft = max(timeLeft / self.timerLength, 0)
x = round((1-normalisedTimeLeft) * (self.size[0] // 2))
w = normalisedTimeLeft * self.size[0]
c = np.round((255, 255*normalisedTimeLeft, 255*normalisedTimeLeft))
pygame.draw.rect(self.surf, c, (x, 0, w, 10))
self.surf.blit(self.timerFont.render(str(round(timeLeft, 1)), True, c), (0, 10))
def close(self): def close(self):
""" """