89 lines
3.0 KiB
Python
89 lines
3.0 KiB
Python
import pygame
|
|
|
|
|
|
class Game:
|
|
def __init__(self):
|
|
pygame.init()
|
|
self.screen = pygame.display.set_mode((800, 600))
|
|
pygame.display.set_caption("Undo Doodle")
|
|
self.clock = pygame.time.Clock()
|
|
|
|
# Der Zustand ist eine Liste von Strichen.
|
|
# Jeder Strich ist eine Liste von Punkten (tuples).
|
|
initial_state = []
|
|
|
|
# Die Historie speichert die aufeinanderfolgenden, immutablen Zustände
|
|
self.history = [initial_state]
|
|
|
|
self.drawing = False
|
|
self.current_stroke = []
|
|
|
|
@property
|
|
def current_state(self):
|
|
"""Liefert den aktuellen Zustand (oberstes Element der Historie)."""
|
|
return self.history[-1]
|
|
|
|
def run(self):
|
|
running = True
|
|
while running:
|
|
running = self.handle_events()
|
|
self.update()
|
|
self.draw()
|
|
self.clock.tick(60)
|
|
pygame.quit()
|
|
|
|
def handle_events(self):
|
|
for event in pygame.event.get():
|
|
if event.type == pygame.QUIT:
|
|
return False
|
|
|
|
elif event.type == pygame.KEYDOWN:
|
|
# Mit 'u' oder Strg+Z einen Schritt zurückgehen (Undo)
|
|
if event.key == pygame.K_u or (event.key == pygame.K_z and (pygame.key.get_mods() & pygame.KMOD_CTRL)):
|
|
if len(self.history) > 1:
|
|
self.history.pop()
|
|
print("Undo ausgeführt!")
|
|
|
|
elif event.type == pygame.MOUSEBUTTONDOWN:
|
|
if event.button == 1: # Linke Maustaste gedrückt
|
|
self.drawing = True
|
|
self.current_stroke = [event.pos]
|
|
|
|
elif event.type == pygame.MOUSEMOTION:
|
|
if self.drawing:
|
|
self.current_stroke.append(event.pos)
|
|
|
|
elif event.type == pygame.MOUSEBUTTONUP:
|
|
if event.button == 1 and self.drawing:
|
|
self.drawing = False
|
|
if self.current_stroke:
|
|
# IMMUTABLE ANSATZ:
|
|
# Erstelle einen völlig neuen Zustand (neue Liste),
|
|
# anstatt den alten Zustand direkt zu verändern.
|
|
new_strokes = self.current_state + [self.current_stroke]
|
|
self.history.append(new_strokes)
|
|
self.current_stroke = []
|
|
|
|
return True
|
|
|
|
def update(self):
|
|
pass
|
|
|
|
def draw(self):
|
|
self.screen.fill((255, 255, 255)) # Hintergrund weiß füllen
|
|
|
|
# 1. Zeichne alle fertigen Striche aus dem aktuellen Zustand
|
|
for stroke in self.current_state:
|
|
if len(stroke) > 1:
|
|
pygame.draw.lines(self.screen, (0, 0, 0), False, stroke, 3)
|
|
|
|
# 2. Zeichne den aktuellen Strich während des Ziehens in einer Vorschau-Farbe
|
|
if self.drawing and len(self.current_stroke) > 1:
|
|
pygame.draw.lines(self.screen, (120, 120, 120), False, self.current_stroke, 3)
|
|
|
|
pygame.display.flip()
|
|
|
|
|
|
if __name__ == "__main__":
|
|
game = Game()
|
|
game.run() |