diff --git a/raycaster.py b/raycaster.py index b428eb6..9aa4a66 100755 --- a/raycaster.py +++ b/raycaster.py @@ -10,10 +10,12 @@ import sdl2.ext import math from time import time -WIN_WIDTH = 640 -WIN_HEIGHT = 640 -DUNGEON_WIDTH = WIN_WIDTH -DUNGEON_HEIGHT = WIN_HEIGHT +MAP_WIN_WIDTH = 640 +MAP_WIN_HEIGHT = 640 +RAYCAST_WIN_WIDTH = MAP_WIN_WIDTH +RAYCAST_WIN_HEIGHT = MAP_WIN_HEIGHT +DUNGEON_WIDTH = MAP_WIN_WIDTH +DUNGEON_HEIGHT = MAP_WIN_HEIGHT PLAYER_SPEED = 10 RAY_LENGTH = 100 MAP_SCALE = 80 @@ -42,10 +44,14 @@ class Main: # Graphics sdl2.ext.init() - self.mapWindow = sdl2.ext.Window("2D Map", size=(WIN_WIDTH, WIN_HEIGHT)) + self.mapWindow = sdl2.ext.Window("2D Map", size=(MAP_WIN_WIDTH, MAP_WIN_HEIGHT)) self.mapWindow.show() self.mapSurface = self.mapWindow.get_surface() + self.raycastWindow = sdl2.ext.Window("3D View", size=(RAYCAST_WIN_WIDTH, RAYCAST_WIN_HEIGHT)) + self.raycastWindow.show() + self.raycastSurface = self.raycastWindow.get_surface() + # Player self.player_position = {"x": int(DUNGEON_WIDTH/2), "y": int(DUNGEON_HEIGHT/2), "r": 0} # r is rotation in radiants @@ -93,8 +99,10 @@ class Main: self.player_position["r"] = 2*math.pi sdl2.ext.draw.fill(self.mapSurface, sdl2.ext.Color(0,0,0,0)) # Clears screen + sdl2.ext.draw.fill(self.raycastSurface, sdl2.ext.Color(0,0,0,0)) # Clears screen self.draw() self.mapWindow.refresh() + self.raycastWindow.refresh() return 0 def draw(self): @@ -128,8 +136,8 @@ class Main: playerAngle = self.player_position["r"] # Cast 60 rays from -30° to +30° (60° viewing angle) - for r in range(60): - rayAngle = playerAngle - (r - 30)*DEGREE_IN_RADIANTS + for i in range(60): + rayAngle = playerAngle - (i - 30)*DEGREE_IN_RADIANTS # Check horizontal lines dof = 0 # Depth of field @@ -207,12 +215,30 @@ class Main: rayY = rayY + yOffset dof = dof + 1 - if self.dist(self.player_position["x"], self.player_position["y"], rayX, rayY) > self.dist(self.player_position["x"], self.player_position["y"], horizRayX, horizRayY): + horizDist = self.dist(self.player_position["x"], self.player_position["y"], horizRayX, horizRayY) + vertDist = self.dist(self.player_position["x"], self.player_position["y"], rayX, rayY) + shortestDist = vertDist + if vertDist > horizDist: rayX = horizRayX rayY = horizRayY + shortestDist = horizDist + # Draw rays in 2D view sdl2.ext.draw.line(self.mapSurface, sdl2.ext.Color(0,0,255,255), (self.player_position["x"], self.player_position["y"], rayX, rayY)) + + # ------ Draw 3D view ------ + + # Calculate line height based on distance + lineHeight = MAP_SCALE * RAYCAST_WIN_HEIGHT / shortestDist + if lineHeight > RAYCAST_WIN_HEIGHT: + lineHeight = RAYCAST_WIN_HEIGHT + # Center line vertically in window + lineOffset = RAYCAST_WIN_HEIGHT / 2 - lineHeight / 2 + # Draw line + for x in range(i*10, i*10+10): + sdl2.ext.draw.line(self.raycastSurface, sdl2.ext.Color(255,255,255,255), (x, int(lineOffset), x, int(lineOffset + lineHeight))) + def dist(self, ax, ay, bx, by): return math.sqrt((bx-ax)*(bx-ax) + (by-ay)*(by-ay))