Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- <!DOCTYPE html>
- <html lang="en">
- <head>
- <meta charset="UTF-8">
- <meta name="viewport" content="width=device-width, initial-scale=1.0">
- <title>Watermelon Physics Simulation</title>
- <style>
- body {
- margin: 0;
- padding: 0;
- display: flex;
- flex-direction: column;
- align-items: center;
- justify-content: center;
- min-height: 100vh;
- background-color: #f0f0f0;
- font-family: Arial, sans-serif;
- }
- #canvas-container {
- position: relative;
- width: 800px;
- height: 600px;
- margin: 20px auto;
- box-shadow: 0 0 10px rgba(0, 0, 0, 0.2);
- border-radius: 8px;
- overflow: hidden;
- }
- canvas {
- background-color: #87CEEB;
- display: block;
- }
- .controls {
- margin: 20px 0;
- display: flex;
- gap: 10px;
- }
- button {
- padding: 10px 20px;
- background-color: #4CAF50;
- color: white;
- border: none;
- border-radius: 4px;
- cursor: pointer;
- font-size: 16px;
- transition: background-color 0.3s;
- }
- button:hover {
- background-color: #45a049;
- }
- .info {
- margin-top: 10px;
- text-align: center;
- color: #333;
- }
- </style>
- </head>
- <body>
- <h1>Watermelon Physics Simulation</h1>
- <div id="canvas-container">
- <canvas id="simulationCanvas" width="800" height="600"></canvas>
- </div>
- <div class="controls">
- <button id="restartBtn">Restart Simulation</button>
- </div>
- <div class="info">
- Watch as the watermelon falls, hits the ground, and bursts into fragments!
- </div>
- <script>
- // Canvas setup
- const canvas = document.getElementById('simulationCanvas');
- const ctx = canvas.getContext('2d');
- const width = canvas.width;
- const height = canvas.height;
- // Physics constants
- const gravity = 0.2;
- const friction = 0.98;
- const restitution = 0.7; // Bounciness
- // Watermelon properties
- let watermelon = {
- x: width / 2,
- y: 100,
- radiusX: 40,
- radiusY: 50,
- velocityX: 0,
- velocityY: 0,
- rotation: 0,
- rotationSpeed: 0,
- isBurst: false,
- burstHeight: 0
- };
- // Fragment class
- class Fragment {
- constructor(x, y, radius, color, velocityX, velocityY, rotationSpeed) {
- this.x = x;
- this.y = y;
- this.radius = radius;
- this.color = color;
- this.velocityX = velocityX;
- this.velocityY = velocityY;
- this.rotation = Math.random() * Math.PI * 2;
- this.rotationSpeed = rotationSpeed;
- this.opacity = 1;
- }
- update() {
- this.velocityY += gravity;
- this.x += this.velocityX;
- this.y += this.velocityY;
- this.velocityX *= friction;
- this.velocityY *= friction;
- this.rotation += this.rotationSpeed;
- // Ground collision
- if (this.y + this.radius > height - 20) {
- this.y = height - 20 - this.radius;
- this.velocityY *= -restitution;
- this.velocityX *= friction;
- }
- // Side walls collision
- if (this.x - this.radius < 0) {
- this.x = this.radius;
- this.velocityX *= -restitution;
- }
- if (this.x + this.radius > width) {
- this.x = width - this.radius;
- this.velocityX *= -restitution;
- }
- }
- draw() {
- ctx.save();
- ctx.translate(this.x, this.y);
- ctx.rotate(this.rotation);
- ctx.globalAlpha = this.opacity;
- // Draw fragment
- ctx.beginPath();
- ctx.arc(0, 0, this.radius, 0, Math.PI * 2);
- ctx.fillStyle = this.color;
- ctx.fill();
- // Add seed details
- ctx.beginPath();
- ctx.arc(0, 0, this.radius * 0.7, 0, Math.PI * 2);
- ctx.fillStyle = '#ff6347';
- ctx.fill();
- // Draw seed
- ctx.beginPath();
- ctx.ellipse(0, 0, this.radius * 0.3, this.radius * 0.15, 0, 0, Math.PI * 2);
- ctx.fillStyle = '#333';
- ctx.fill();
- ctx.restore();
- }
- }
- // Particle class for splash effect
- class Particle {
- constructor(x, y) {
- this.x = x;
- this.y = y;
- this.size = Math.random() * 5 + 2;
- this.velocityX = (Math.random() - 0.5) * 10;
- this.velocityY = (Math.random() - 0.5) * 10 - 5;
- this.gravity = 0.2;
- this.opacity = 1;
- this.color = `hsl(${Math.random() * 30 + 10}, 100%, 50%)`;
- }
- update() {
- this.velocityY += this.gravity;
- this.x += this.velocityX;
- this.y += this.velocityY;
- this.opacity -= 0.02;
- if (this.y + this.size > height - 20) {
- this.y = height - 20 - this.size;
- this.velocityY *= -0.6;
- }
- }
- draw() {
- ctx.globalAlpha = this.opacity;
- ctx.fillStyle = this.color;
- ctx.beginPath();
- ctx.arc(this.x, this.y, this.size, 0, Math.PI * 2);
- ctx.fill();
- ctx.globalAlpha = 1;
- }
- }
- // Arrays to store fragments and particles
- let fragments = [];
- let particles = [];
- // Draw ground
- function drawGround() {
- ctx.fillStyle = '#8B4513';
- ctx.fillRect(0, height - 20, width, 20);
- // Add some texture to the ground
- ctx.fillStyle = '#6B3300';
- for (let i = 0; i < width; i += 20) {
- ctx.fillRect(i, height - 20, 10, 5);
- }
- }
- // Draw watermelon
- function drawWatermelon() {
- ctx.save();
- ctx.translate(watermelon.x, watermelon.y);
- ctx.rotate(watermelon.rotation);
- // Outer green rind
- ctx.beginPath();
- ctx.ellipse(0, 0, watermelon.radiusX, watermelon.radiusY, 0, 0, Math.PI * 2);
- ctx.fillStyle = '#2E8B57';
- ctx.fill();
- // Inner red flesh
- ctx.beginPath();
- ctx.ellipse(0, 0, watermelon.radiusX * 0.8, watermelon.radiusY * 0.85, 0, 0, Math.PI * 2);
- ctx.fillStyle = '#FF6347';
- ctx.fill();
- // Seeds
- for (let i = 0; i < 15; i++) {
- const angle = Math.random() * Math.PI * 2;
- const distance = Math.random() * watermelon.radiusX * 0.6;
- const x = Math.cos(angle) * distance;
- const y = Math.sin(angle) * distance;
- ctx.beginPath();
- ctx.ellipse(x, y, 3, 6, angle, 0, Math.PI * 2);
- ctx.fillStyle = '#333';
- ctx.fill();
- }
- ctx.restore();
- }
- // Burst watermelon into fragments
- function burstWatermelon() {
- watermelon.isBurst = true;
- // Create fragments
- const fragmentCount = 30;
- for (let i = 0; i < fragmentCount; i++) {
- const angle = Math.random() * Math.PI * 2;
- const distance = Math.random() * watermelon.radiusX * 0.8;
- const x = watermelon.x + Math.cos(angle) * distance;
- const y = watermelon.y + Math.sin(angle) * distance;
- const radius = Math.random() * 15 + 10;
- // Random color between green and red
- const colorChoice = Math.random() > 0.5 ? '#2E8B57' : '#FF6347';
- // Velocity based on explosion force
- const power = 5 + Math.random() * 10;
- const velocityX = Math.cos(angle) * power;
- const velocityY = Math.sin(angle) * power - 5; // Upward bias
- fragments.push(new Fragment(
- x, y, radius, colorChoice, velocityX, velocityY,
- (Math.random() - 0.5) * 0.2
- ));
- }
- // Create splash particles
- for (let i = 0; i < 50; i++) {
- particles.push(new Particle(watermelon.x, watermelon.y));
- }
- }
- // Update simulation
- function update() {
- // Clear canvas
- ctx.clearRect(0, 0, width, height);
- // Draw sky background with gradient
- const gradient = ctx.createLinearGradient(0, 0, 0, height);
- gradient.addColorStop(0, '#87CEEB');
- gradient.addColorStop(1, '#E0F7FF');
- ctx.fillStyle = gradient;
- ctx.fillRect(0, 0, width, height);
- // Draw ground
- drawGround();
- // Update watermelon if not burst
- if (!watermelon.isBurst) {
- watermelon.velocityY += gravity;
- watermelon.y += watermelon.velocityY;
- watermelon.x += watermelon.velocityX;
- watermelon.rotation += watermelon.rotationSpeed;
- // Check if watermelon hits the ground
- if (watermelon.y + watermelon.radiusY > height - 20) {
- watermelon.y = height - 20 - watermelon.radiusY;
- watermelon.velocityY *= -restitution;
- watermelon.velocityX *= friction;
- watermelon.rotationSpeed += (Math.random() - 0.5) * 0.1;
- // Burst if velocity is high enough
- if (Math.abs(watermelon.velocityY) > 5) {
- burstWatermelon();
- }
- }
- // Draw watermelon
- drawWatermelon();
- } else {
- // Update and draw fragments
- for (let i = fragments.length - 1; i >= 0; i--) {
- fragments[i].update();
- fragments[i].draw();
- // Remove fragments that have stopped moving
- if (Math.abs(fragments[i].velocityX) < 0.1 &&
- Math.abs(fragments[i].velocityY) < 0.1 &&
- fragments[i].y + fragments[i].radius >= height - 20) {
- fragments.splice(i, 1);
- }
- }
- // Update and draw particles
- for (let i = particles.length - 1; i >= 0; i--) {
- particles[i].update();
- particles[i].draw();
- // Remove faded particles
- if (particles[i].opacity <= 0) {
- particles.splice(i, 1);
- }
- }
- }
- requestAnimationFrame(update);
- }
- // Initialize simulation
- function init() {
- // Reset watermelon
- watermelon = {
- x: width / 2,
- y: 100,
- radiusX: 40,
- radiusY: 50,
- velocityX: 0,
- velocityY: 0,
- rotation: 0,
- rotationSpeed: 0,
- isBurst: false,
- burstHeight: 0
- };
- // Clear fragments and particles
- fragments = [];
- particles = [];
- // Start animation
- update();
- }
- // Event listeners
- document.getElementById('restartBtn').addEventListener('click', init);
- // Add some initial velocity to make it more interesting
- watermelon.velocityX = (Math.random() - 0.5) * 2;
- watermelon.rotationSpeed = (Math.random() - 0.5) * 0.05;
- // Start simulation
- init();
- </script>
- </body>
- </html>
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement