Surprise! We've been running on hardware provided by BuyVM for a few months and wanted to show them a little appreciation.
Running a paste site comes with unique challenges, ones that aren't always obvious and hard to control. As such, BuyVM offered us a home where we could worry less about the hosting side of things and focus on maintaining a clean and useful service! Go check them out and show them some love!
Submitted on April 19, 2025 at 08:27 PM
Expires on May 19, 2025 at 08:27 PM (3 weeks from now)

New Paste 1 (Python)

import tkinter as tk
import math
import numpy as np
from dataclasses import dataclass
from typing import List, Tuple
import random
import sys

# Constants
WINDOW_WIDTH = 800
WINDOW_HEIGHT = 800
GRAVITY = 9.8 * 30  # Scaled for better visual effect
GROUND_Y = WINDOW_HEIGHT - 50
WATERMELON_RADIUS = 40
TIME_STEP = 1/60  # 60 FPS
FRICTION = 0.95  # Friction coefficient for fragments
BOUNCE = 0.6  # Bounce coefficient
FRAGMENT_COUNT = 20  # Number of fragments when watermelon bursts
SEED_COUNT = 30  # Number of seeds to spawn on impact
SEED_LIFETIME = 1.5  # Seconds seeds remain visible
WATERMELON_MASS = 10.0  # Mass of watermelon

@dataclass
class Vector2D:
    x: float
    y: float
    
    def __add__(self, other):
        return Vector2D(self.x + other.x, self.y + other.y)
    
    def __sub__(self, other):
        return Vector2D(self.x - other.x, self.y - other.y)
    
    def __mul__(self, scalar):
        return Vector2D(self.x * scalar, self.y * scalar)
    
    def length(self):
        return math.sqrt(self.x**2 + self.y**2)
    
    def normalize(self):
        length = self.length()
        if length > 0:
            return Vector2D(self.x / length, self.y / length)
        return Vector2D(0, 0)

class Fragment:
    def __init__(self, position, velocity, size, color, rotation=0, rotation_speed=0):
        self.position = position
        self.velocity = velocity
        self.size = size
        self.color = color
        self.rotation = rotation
        self.rotation_speed = rotation_speed
        self.id = None
        self.active = True
        
    def update(self):
        # Apply gravity
        self.velocity.y += GRAVITY * TIME_STEP
        
        # Update position
        self.position.x += self.velocity.x * TIME_STEP
        self.position.y += self.velocity.y * TIME_STEP
        
        # Update rotation
        self.rotation += self.rotation_speed * TIME_STEP
        
        # Check ground collision
        if self.position.y + self.size > GROUND_Y:
            self.position.y = GROUND_Y - self.size
            self.velocity.y = -self.velocity.y * BOUNCE
            self.velocity.x *= FRICTION
            
            # Apply friction to rotation
            self.rotation_speed *= FRICTION
            
        # Check wall collisions
        if self.position.x - self.size < 0:
            self.position.x = self.size
            self.velocity.x = -self.velocity.x * BOUNCE
        elif self.position.x + self.size > WINDOW_WIDTH:
            self.position.x = WINDOW_WIDTH - self.size
            self.velocity.x = -self.velocity.x * BOUNCE
            
        # Deactivate if almost stopped
        if (abs(self.velocity.x) < 5 and abs(self.velocity.y) < 5 and 
            abs(self.rotation_speed) < 0.1 and self.position.y + self.size >= GROUND_Y - 1):
            self.velocity.x = 0
            self.velocity.y = 0
            self.rotation_speed = 0

class Seed:
    def __init__(self, position, velocity, size):
        self.position = position
        self.velocity = velocity
        self.size = size
        self.id = None
        self.lifetime = SEED_LIFETIME
        self.active = True
        
    def update(self):
        # Apply gravity (lighter than fragments)
        self.velocity.y += GRAVITY * TIME_STEP * 0.5
        
        # Update position
        self.position.x += self.velocity.x * TIME_STEP
        self.position.y += self.velocity.y * TIME_STEP
        
        # Check ground collision
        if self.position.y + self.size > GROUND_Y:
            self.position.y = GROUND_Y - self.size
            self.velocity.y = -self.velocity.y * 0.3  # Less bounce
            self.velocity.x *= 0.8  # More friction
            
        # Check wall collisions
        if self.position.x - self.size < 0:
            self.position.x = self.size
            self.velocity.x = -self.velocity.x * 0.3
        elif self.position.x + self.size > WINDOW_WIDTH:
            self.position.x = WINDOW_WIDTH - self.size
            self.velocity.x = -self.velocity.x * 0.3
            
        # Reduce lifetime
        self.lifetime -= TIME_STEP
        if self.lifetime <= 0:
            self.active = False

class Watermelon:
    def __init__(self, x, y):
        self.position = Vector2D(x, y)
        self.velocity = Vector2D(0, 0)
        self.radius = WATERMELON_RADIUS
        self.mass = WATERMELON_MASS
        self.burst = False
        self.id_outer = None
        self.id_inner = None
        self.id_seeds = []
        
    def update(self):
        if not self.burst:
            # Apply gravity
            self.velocity.y += GRAVITY * TIME_STEP
            
            # Update position
            self.position.x += self.velocity.x * TIME_STEP
            self.position.y += self.velocity.y * TIME_STEP
            
            # Check ground collision
            if self.position.y + self.radius > GROUND_Y:
                self.burst = True
                
            # Check wall collisions
            if self.position.x - self.radius < 0:
                self.position.x = self.radius
                self.velocity.x = -self.velocity.x * BOUNCE
            elif self.position.x + self.radius > WINDOW_WIDTH:
                self.position.x = WINDOW_WIDTH - self.radius
                self.velocity.x = -self.velocity.x * BOUNCE

class WatermelonSimulation:
    def __init__(self, root):
        self.root = root
        self.root.title("Watermelon Splash Simulation")
        self.root.geometry(f"{WINDOW_WIDTH}x{WINDOW_HEIGHT}")
        
        self.canvas = tk.Canvas(root, width=WINDOW_WIDTH, height=WINDOW_HEIGHT, bg="skyblue")
        self.canvas.pack()
        
        # Create ground
        self.ground = self.canvas.create_rectangle(0, GROUND_Y, WINDOW_WIDTH, WINDOW_HEIGHT, fill="sienna")
        
        # Create watermelon
        self.watermelon = Watermelon(WINDOW_WIDTH // 2, 100)
        self.draw_watermelon()
        
        # Lists for fragments and seeds
        self.fragments = []
        self.seeds = []
        
        # Start simulation
        self.is_running = True
        self.update()
        
        # Bind restart on click
        self.canvas.bind("<Button-1>", self.restart)
        
    def draw_watermelon(self):
        x, y = self.watermelon.position.x, self.watermelon.position.y
        r = self.watermelon.radius
        
        # Draw outer green part
        self.watermelon.id_outer = self.canvas.create_oval(
            x - r, y - r, x + r, y + r, 
            fill="green", outline="darkgreen", width=2
        )
        
        # Draw inner red part (slightly smaller)
        inner_r = r * 0.85
        self.watermelon.id_inner = self.canvas.create_oval(
            x - inner_r, y - inner_r, x + inner_r, y + inner_r, 
            fill="red", outline=""
        )
        
        # Draw some seed-like details
        self.watermelon.id_seeds = []
        for _ in range(8):
            angle = random.uniform(0, 2 * math.pi)
            distance = random.uniform(0.3, 0.7) * inner_r
            seed_x = x + math.cos(angle) * distance
            seed_y = y + math.sin(angle) * distance
            seed_size = random.uniform(2, 4)
            
            seed = self.canvas.create_oval(
                seed_x - seed_size, seed_y - seed_size,
                seed_x + seed_size, seed_y + seed_size,
                fill="black", outline=""
            )
            self.watermelon.id_seeds.append(seed)
    
    def burst_watermelon(self):
        x, y = self.watermelon.position.x, self.watermelon.position.y
        
        # Create fragments
        for _ in range(FRAGMENT_COUNT):
            # Random direction
            angle = random.uniform(0, 2 * math.pi)
            speed = random.uniform(100, 300)
            
            # Calculate velocity based on watermelon's velocity and explosion
            vel_x = self.watermelon.velocity.x + math.cos(angle) * speed
            vel_y = self.watermelon.velocity.y + math.sin(angle) * speed
            
            # Random size for fragment
            size = random.uniform(self.watermelon.radius * 0.2, self.watermelon.radius * 0.4)
            
            # Random color (green or red)
            color = random.choice(["green", "red"])
            
            # Random rotation
            rotation = random.uniform(0, 360)
            rotation_speed = random.uniform(-180, 180)
            
            # Create fragment at watermelon's position
            fragment = Fragment(
                Vector2D(x, y),
                Vector2D(vel_x, vel_y),
                size,
                color,
                rotation,
                rotation_speed
            )
            
            # Draw the fragment
            fragment.id = self.canvas.create_oval(
                x - size, y - size, x + size, y + size,
                fill=color, outline="darkgreen" if color == "green" else "darkred"
            )
            
            self.fragments.append(fragment)
        
        # Create seeds
        for _ in range(SEED_COUNT):
            # Random direction
            angle = random.uniform(0, 2 * math.pi)
            speed = random.uniform(50, 200)
            
            # Calculate velocity
            vel_x = math.cos(angle) * speed
            vel_y = math.sin(angle) * speed
            
            # Create seed
            seed = Seed(
                Vector2D(x, y),
                Vector2D(vel_x, vel_y),
                random.uniform(1.5, 3)
            )
            
            # Draw the seed
            seed.id = self.canvas.create_oval(
                x - seed.size, y - seed.size, x + seed.size, y + seed.size,
                fill="black", outline=""
            )
            
            self.seeds.append(seed)
    
    def update(self):
        if not self.is_running:
            return
            
        # Update watermelon
        self.watermelon.update()
        
        if self.watermelon.burst:
            # If just burst, create fragments
            if not self.fragments:
                self.burst_watermelon()
                
                # Remove original watermelon
                self.canvas.delete(self.watermelon.id_outer)
                self.canvas.delete(self.watermelon.id_inner)
                for seed in self.watermelon.id_seeds:
                    self.canvas.delete(seed)
        else:
            # Update watermelon position on canvas
            x, y = self.watermelon.position.x, self.watermelon.position.y
            r = self.watermelon.radius
            
            self.canvas.coords(
                self.watermelon.id_outer,
                x - r, y - r, x + r, y + r
            )
            self.canvas.coords(
                self.watermelon.id_inner,
                x - r * 0.85, y - r * 0.85, x + r * 0.85, y + r * 0.85
            )
            
            # Update seed positions
            for i, seed_id in enumerate(self.watermelon.id_seeds):
                angle = (i / len(self.watermelon.id_seeds)) * 2 * math.pi
                distance = self.watermelon.radius * 0.6
                seed_x = x + math.cos(angle) * distance
                seed_y = y + math.sin(angle) * distance
                seed_size = 3
                
                self.canvas.coords(
                    seed_id,
                    seed_x - seed_size, seed_y - seed_size,
                    seed_x + seed_size, seed_y + seed_size
                )
        
        # Update fragments
        for fragment in self.fragments[:]:
            fragment.update()
            
            if fragment.active:
                # Update fragment position on canvas
                x, y = fragment.position.x, fragment.position.y
                
                # For simplicity, we're using ovals for fragments
                # In a more complex simulation, we could use polygons with rotation
                self.canvas.coords(
                    fragment.id,
                    x - fragment.size, y - fragment.size,
                    x + fragment.size, y + fragment.size
                )
            else:
                # Remove inactive fragment
                self.canvas.delete(fragment.id)
                self.fragments.remove(fragment)
        
        # Update seeds
        for seed in self.seeds[:]:
            seed.update()
            
            if seed.active:
                # Update seed position on canvas
                x, y = seed.position.x, seed.position.y
                
                self.canvas.coords(
                    seed.id,
                    x - seed.size, y - seed.size,
                    x + seed.size, y + seed.size
                )
                
                # Fade out based on lifetime
                alpha = min(1.0, seed.lifetime / SEED_LIFETIME)
                # We can't do true alpha with tkinter, but we can adjust color intensity
                intensity = int(255 * alpha)
                color = f"#{intensity:02x}{intensity:02x}{intensity:02x}"
                self.canvas.itemconfig(seed.id, fill=color)
            else:
                # Remove inactive seed
                self.canvas.delete(seed.id)
                self.seeds.remove(seed)
        
        # Continue simulation
        self.root.after(int(TIME_STEP * 1000), self.update)
    
    def restart(self, event=None):
        # Clear all objects
        for fragment in self.fragments:
            self.canvas.delete(fragment.id)
        for seed in self.seeds:
            self.canvas.delete(seed.id)
        
        self.fragments = []
        self.seeds = []
        
        # Reset watermelon
        self.watermelon = Watermelon(WINDOW_WIDTH // 2, 100)
        self.draw_watermelon()

def main():
    root = tk.Tk()
    app = WatermelonSimulation(root)
    root.mainloop()

if __name__ == "__main__":
    main()