pygame-tetris/scratch.py
2024-01-19 16:39:03 +08:00

89 lines
2.4 KiB
Python

import pygame
import math
import itertools
# Define constants
WHITE = (255, 255, 255)
BLACK = (0, 0, 0)
WIDTH, HEIGHT = 800, 600
CENTER = (WIDTH // 2, HEIGHT // 2)
# Define the tesseract vertices in 4D space
vertices = [-1, 1]
tesseract_vertices = [[x, y, z, w] for x in vertices for y in vertices
for z in vertices for w in vertices]
# Define the edges between vertices
edges = [(n, n ^ 1) for n in range(16) for bit in range(4) if n & (1 << bit)]
# Initialize Pygame
pygame.init()
screen = pygame.display.set_mode((WIDTH, HEIGHT))
clock = pygame.time.Clock()
running = True
# Projection functions
def project_4D_to_3D(x, y, z, w, rotation_xy, rotation_xz, rotation_xw):
# Rotate in 4D space
xz = x * math.cos(rotation_xz) - z * math.sin(rotation_xz)
zx = z * math.cos(rotation_xz) + x * math.sin(rotation_xz)
xy = xz * math.cos(rotation_xy) - y * math.sin(rotation_xy)
yx = y * math.cos(rotation_xy) + xz * math.sin(rotation_xy)
xw = xy * math.cos(rotation_xw) - w * math.sin(rotation_xw)
wx = w * math.cos(rotation_xw) + xy * math.sin(rotation_xw)
# 4D to 3D projection
distance = 2
factor = distance / (distance + wx)
x3d = factor * yx
y3d = factor * zx
z3d = factor * w
return x3d, y3d, z3d
def project_3D_to_2D(x, y, z):
# 3D to 2D projection (ignoring z for simple orthographic projection)
return int(CENTER[0] + x * 100), int(CENTER[1] + y * 100)
# Main loop
angle_xy = angle_xz = angle_xw = 0.0
while running:
# Handle events
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
# Update the rotation angles
angle_xy += 0.01
angle_xz += 0.01
angle_xw += 0.01
# Clear screen
screen.fill(BLACK)
# Draw the tesseract
projected_2d_points: list = []
for vertex in tesseract_vertices:
x, y, z, w = vertex
# Project the 4D point to 3D
x3d, y3d, z3d = project_4D_to_3D(x, y, z, w, angle_xy, angle_xz,
angle_xw)
# Project the 3D point to 2D and store it
projected_2d_points.append(project_3D_to_2D(x3d, y3d, z3d))
# Draw the edges
for edge in edges:
start_pos = projected_2d_points[edge[0]]
end_pos = projected_2d_points[edge[1]]
pygame.draw.line(screen, WHITE, start_pos, end_pos, 1)
# Update display
pygame.display.flip()
# Cap the frame rate
clock.tick(30)
pygame.quit()