-
-
Save Aakash67/5d761cae69157cbdc383aa9e49469a16 to your computer and use it in GitHub Desktop.
Minecraft with Pygame using Grok 3 Think
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| import pygame | |
| import math | |
| # Initialize Pygame | |
| pygame.init() | |
| pygame.mixer.init() # For sound effects | |
| # Constants | |
| SCREEN_WIDTH = 800 | |
| SCREEN_HEIGHT = 600 | |
| TILE_SIZE = 32 | |
| WORLD_WIDTH = 100 | |
| WORLD_HEIGHT = 100 | |
| CAMERA_SPEED = 200 # Pixels per second | |
| FPS = 60 | |
| # Colors | |
| SKY_COLOR = (135, 206, 235) # Sky blue | |
| BLOCK_COLORS = { | |
| 1: (139, 69, 19), # Dirt: brown | |
| 2: (169, 169, 169), # Stone: gray | |
| 3: (205, 133, 63) # Wood: dark brown | |
| } | |
| HIGHLIGHT_COLOR = (255, 255, 255) # White for block highlight | |
| # Set up display and clock | |
| screen = pygame.display.set_mode((SCREEN_WIDTH, SCREEN_HEIGHT)) | |
| pygame.display.set_caption("2D Minecraft-style Game") | |
| clock = pygame.time.Clock() | |
| # Generate initial world (0 = empty, 1 = dirt, etc.) | |
| world = [[0 for _ in range(WORLD_HEIGHT)] for _ in range(WORLD_WIDTH)] | |
| for x in range(WORLD_WIDTH): | |
| for y in range(70, WORLD_HEIGHT): | |
| world[x][y] = 1 # Ground level with dirt | |
| # Camera position (top-left corner in world coordinates) | |
| camera_x = 0 | |
| camera_y = (70 - 15) * TILE_SIZE # Start with ground near bottom | |
| # Selected block type (1=dirt, 2=stone, 3=wood) | |
| selected_block = 1 | |
| # Animation storage: (tile_x, tile_y, scale, timer) | |
| animations = [] | |
| # Load sound effects (uncomment and provide your own .wav files) | |
| # place_sound = pygame.mixer.Sound('place.wav') | |
| # break_sound = pygame.mixer.Sound('break.wav') | |
| # Main game loop | |
| running = True | |
| while running: | |
| dt = clock.tick(FPS) / 1000.0 # Delta time in seconds | |
| # Event handling | |
| for event in pygame.event.get(): | |
| if event.type == pygame.QUIT: | |
| running = False | |
| elif event.type == pygame.MOUSEBUTTONDOWN: | |
| mouse_x, mouse_y = pygame.mouse.get_pos() | |
| world_x = camera_x + mouse_x | |
| world_y = camera_y + mouse_y | |
| tile_x = int(world_x / TILE_SIZE) | |
| tile_y = int(world_y / TILE_SIZE) | |
| if 0 <= tile_x < WORLD_WIDTH and 0 <= tile_y < WORLD_HEIGHT: | |
| if event.button == 1 and world[tile_x][tile_y] == 0: # Left-click: place | |
| world[tile_x][tile_y] = selected_block | |
| animations.append([tile_x, tile_y, 0.1, 0.3]) # Start animation (scale, duration) | |
| # place_sound.play() | |
| elif event.button == 3 and world[tile_x][tile_y] != 0: # Right-click: break | |
| world[tile_x][tile_y] = 0 | |
| # break_sound.play() | |
| elif event.type == pygame.KEYDOWN: | |
| if event.key == pygame.K_1: | |
| selected_block = 1 | |
| elif event.key == pygame.K_2: | |
| selected_block = 2 | |
| elif event.key == pygame.K_3: | |
| selected_block = 3 | |
| # Camera movement | |
| keys = pygame.key.get_pressed() | |
| if keys[pygame.K_w]: | |
| camera_y -= CAMERA_SPEED * dt | |
| if keys[pygame.K_s]: | |
| camera_y += CAMERA_SPEED * dt | |
| if keys[pygame.K_a]: | |
| camera_x -= CAMERA_SPEED * dt | |
| if keys[pygame.K_d]: | |
| camera_x += CAMERA_SPEED * dt | |
| # Clamp camera to world bounds | |
| camera_x = max(0, min(camera_x, WORLD_WIDTH * TILE_SIZE - SCREEN_WIDTH)) | |
| camera_y = max(0, min(camera_y, WORLD_HEIGHT * TILE_SIZE - SCREEN_HEIGHT)) | |
| # Update animations | |
| for anim in animations[:]: | |
| anim[3] -= dt # Decrease timer | |
| anim[2] += (1.0 - anim[2]) * (dt / 0.3) # Smoothly increase scale to 1 | |
| if anim[3] <= 0: | |
| animations.remove(anim) # Remove when animation ends | |
| # Rendering | |
| screen.fill(SKY_COLOR) # Sky background | |
| # Calculate visible tile range | |
| start_x = max(0, math.floor(camera_x / TILE_SIZE)) | |
| end_x = min(WORLD_WIDTH, math.ceil((camera_x + SCREEN_WIDTH) / TILE_SIZE)) | |
| start_y = max(0, math.floor(camera_y / TILE_SIZE)) | |
| end_y = min(WORLD_HEIGHT, math.ceil((camera_y + SCREEN_HEIGHT) / TILE_SIZE)) | |
| # Draw blocks | |
| for x in range(start_x, end_x): | |
| for y in range(start_y, end_y): | |
| if world[x][y] != 0: | |
| screen_x = x * TILE_SIZE - camera_x | |
| screen_y = y * TILE_SIZE - camera_y | |
| block_color = BLOCK_COLORS[world[x][y]] | |
| # Check if this block is animating | |
| anim_scale = 1.0 | |
| for anim in animations: | |
| if anim[0] == x and anim[1] == y: | |
| anim_scale = anim[2] | |
| break | |
| # Calculate scaled size and position | |
| size = int(TILE_SIZE * anim_scale) | |
| offset = (TILE_SIZE - size) // 2 | |
| pygame.draw.rect(screen, block_color, (screen_x + offset, screen_y + offset, size, size)) | |
| # Highlight block under mouse | |
| mouse_x, mouse_y = pygame.mouse.get_pos() | |
| world_x = camera_x + mouse_x | |
| world_y = camera_y + mouse_y | |
| tile_x = int(world_x / TILE_SIZE) | |
| tile_y = int(world_y / TILE_SIZE) | |
| if 0 <= tile_x < WORLD_WIDTH and 0 <= tile_y < WORLD_HEIGHT: | |
| screen_x = tile_x * TILE_SIZE - camera_x | |
| screen_y = tile_y * TILE_SIZE - camera_y | |
| pygame.draw.rect(screen, HIGHLIGHT_COLOR, (screen_x, screen_y, TILE_SIZE, TILE_SIZE), 2) | |
| pygame.display.flip() | |
| pygame.quit() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment