Creating a Platform Game with TCJSGame v3: Step-by-Step Tutorial
In this tutorial, we'll create a simple platform game using TCJSGame v3, a lightweight JavaScript game engine. We'll cover everything from setting up the environment to adding player movement, platforms, and collision detection.
Prerequisites
- Basic knowledge of HTML and JavaScript
- A text editor (VS Code, Sublime Text, etc.)
- A modern web browser
Step 1: Setting Up the HTML File
Create a new HTML file and include the TCJSGame v3 library:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Platform Game with TCJSGame v3</title> <style> body { margin: 0; padding: 20px; display: flex; justify-content: center; align-items: center; min-height: 100vh; background: #2c3e50; font-family: Arial, sans-serif; } canvas { border: 3px solid #ecf0f1; border-radius: 5px; background: #34495e; } </style> </head> <body> <script src="http://tcjsgame.vercel.app/mat/tcjsgame-v3.js"></script> <script> // Our game code will go here </script> </body> </html>
Step 2: Initialize the Game Display
Inside the <script>
tag, let's set up our game display:
// Create display instance const display = new Display(); // Start the game with a 800x450 canvas display.start(800, 450); // Set background gradient display.lgradient("bottom", "#3498db", "#2c3e50");
Step 3: Create the Player Character
Now let's create our player character:
// Create player const player = new Component(30, 50, "#e74c3c", 100, 100, "rect"); // Enable physics for the player player.physics = true; player.gravity = 0.5; player.bounce = 0.2; // Add player to the display display.add(player); // Set camera to follow player with smooth movement display.camera.follow(player, true);
Step 4: Create Platforms
Let's create some platforms for our player to jump on:
// Create platforms const ground = new Component(800, 30, "#27ae60", 0, 420, "rect"); ground.physics = true; const platform1 = new Component(200, 20, "#2980b9", 150, 350, "rect"); platform1.physics = true; const platform2 = new Component(200, 20, "#2980b9", 450, 280, "rect"); platform2.physics = true; const platform3 = new Component(200, 20, "#2980b9", 200, 200, "rect"); platform3.physics = true; // Add platforms to display display.add(ground); display.add(platform1); display.add(platform2); display.add(platform3);
Step 5: Implement Player Controls
Now let's add keyboard controls for our player:
// Player movement variables const playerSpeed = 5; const jumpStrength = 12; let canJump = false; // Update function for game logic function update() { // Left and right movement if (display.keys[65] || display.keys[37]) { // A key or Left arrow player.speedX = -playerSpeed; } else if (display.keys[68] || display.keys[39]) { // D key or Right arrow player.speedX = playerSpeed; } else { player.speedX = 0; } // Jumping if ((display.keys[87] || display.keys[32] || display.keys[38]) && canJump) { // W, Space, or Up arrow player.gravitySpeed = -jumpStrength; canJump = false; } // Check if player is on a platform canJump = player.y >= display.canvas.height - player.height - 1 || player.crashWith(ground) || player.crashWith(platform1) || player.crashWith(platform2) || player.crashWith(platform3); // Keep player within screen bounds if (player.x < 0) player.x = 0; if (player.x > display.canvas.width - player.width) { player.x = display.canvas.width - player.width; } // Reset if player falls off the screen if (player.y > display.canvas.height) { player.x = 100; player.y = 100; player.speedX = 0; player.speedY = 0; } }
Step 6: Add Collectible Items
Let's add some collectible coins to our game:
// Create coins const coins = []; const coinPositions = [ [200, 320], [300, 320], [500, 250], [550, 250], [250, 170], [300, 170], [600, 370] ]; coinPositions.forEach((pos, index) => { const coin = new Component(15, 15, "#f1c40f", pos[0], pos[1], "rect"); coin.index = index; display.add(coin); coins.push(coin); }); let score = 0;
Step 7: Add Score Display
Let's create a text component to display the score:
// Create score display const scoreText = new Component("16px", "Arial", "#ecf0f1", 20, 30, "text"); scoreText.text = "Score: 0"; display.add(scoreText);
Step 8: Enhance the Update Function
Now let's update our update function to handle coin collection and score:
// Enhanced update function function update() { // ... (previous movement code) // Check for coin collection coins.forEach((coin, index) => { if (coin && player.crashWith(coin)) { // Remove the coin coin.hide(); coins[index] = null; // Increase score score += 10; scoreText.text = `Score: ${score}`; } }); // ... (previous bounds checking code) }
Step 9: Add Enemies
Let's add some moving enemies to make the game more challenging:
// Create enemies const enemy1 = new Component(30, 30, "#e74c3c", 300, 390, "rect"); enemy1.physics = true; enemy1.speedX = 2; const enemy2 = new Component(30, 30, "#e74c3c", 600, 240, "rect"); enemy2.physics = true; enemy2.speedX = -2; display.add(enemy1); display.add(enemy2);
Step 10: Final Game Logic
Let's complete our game logic with enemy movement and game over conditions:
// Enhanced update function with enemy logic function update() { // ... (previous movement and coin collection code) // Enemy movement and behavior if (enemy1.x <= 250 || enemy1.x >= 500) { enemy1.speedX *= -1; } if (enemy2.x <= 450 || enemy2.x >= 650) { enemy2.speedX *= -1; } // Check for collision with enemies if (player.crashWith(enemy1) || player.crashWith(enemy2)) { // Reset game player.x = 100; player.y = 100; player.speedX = 0; player.speedY = 0; // Reset enemies enemy1.x = 300; enemy2.x = 600; // Reset coins coins.forEach((coin, index) => { if (coin) { coin.show(); coin.x = coinPositions[index][0]; coin.y = coinPositions[index][1]; } else { const newCoin = new Component(15, 15, "#f1c40f", coinPositions[index][0], coinPositions[index][1], "rect"); display.add(newCoin); coins[index] = newCoin; } }); // Reset score score = 0; scoreText.text = `Score: ${score}`; } }
Step 11: Add Visual Enhancements
Let's add some visual improvements to make our game more appealing:
// Add decorative elements const decoration = new Component(40, 40, "#8e44ad", 700, 100, "rect"); decoration.changeAngle = true; display.add(decoration); // Animate the decoration setInterval(() => { decoration.angle += 0.1; }, 100);
Complete Game Code
Here's the complete code for our platform game:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Platform Game with TCJSGame v3</title> <style> body { margin: 0; padding: 20px; display: flex; justify-content: center; align-items: center; min-height: 100vh; background: #2c3e50; font-family: Arial, sans-serif; } canvas { border: 3px solid #ecf0f1; border-radius: 5px; background: #34495e; } </style> </head> <body> <script src="http://tcjsgame.vercel.app/mat/tcjsgame-v3.js"></script> <script> // Create display instance const display = new Display(); // Start the game with a 800x450 canvas display.start(800, 450); // Set background gradient display.lgradient("bottom", "#3498db", "#2c3e50"); // Create player const player = new Component(30, 50, "#e74c3c", 100, 100, "rect"); player.physics = true; player.gravity = 0.5; player.bounce = 0.2; display.add(player); // Set camera to follow player display.camera.follow(player, true); // Create platforms const ground = new Component(800, 30, "#27ae60", 0, 420, "rect"); ground.physics = true; const platform1 = new Component(200, 20, "#2980b9", 150, 350, "rect"); platform1.physics = true; const platform2 = new Component(200, 20, "#2980b9", 450, 280, "rect"); platform2.physics = true; const platform3 = new Component(200, 20, "#2980b9", 200, 200, "rect"); platform3.physics = true; display.add(ground); display.add(platform1); display.add(platform2); display.add(platform3); // Create coins const coins = []; const coinPositions = [ [200, 320], [300, 320], [500, 250], [550, 250], [250, 170], [300, 170], [600, 370] ]; coinPositions.forEach((pos, index) => { const coin = new Component(15, 15, "#f1c40f", pos[0], pos[1], "rect"); coin.index = index; display.add(coin); coins.push(coin); }); let score = 0; // Create score display const scoreText = new Component("16px", "Arial", "#ecf0f1", 20, 30, "text"); scoreText.text = "Score: 0"; display.add(scoreText); // Create enemies const enemy1 = new Component(30, 30, "#e74c3c", 300, 390, "rect"); enemy1.physics = true; enemy1.speedX = 2; const enemy2 = new Component(30, 30, "#e74c3c", 600, 240, "rect"); enemy2.physics = true; enemy2.speedX = -2; display.add(enemy1); display.add(enemy2); // Add decorative elements const decoration = new Component(40, 40, "#8e44ad", 700, 100, "rect"); decoration.changeAngle = true; display.add(decoration); // Animate the decoration setInterval(() => { decoration.angle += 0.1; }, 100); // Player movement variables const playerSpeed = 5; const jumpStrength = 12; let canJump = false; // Update function for game logic function update() { // Left and right movement if (display.keys[65] || display.keys[37]) { // A key or Left arrow player.speedX = -playerSpeed; } else if (display.keys[68] || display.keys[39]) { // D key or Right arrow player.speedX = playerSpeed; } else { player.speedX = 0; } // Jumping if ((display.keys[87] || display.keys[32] || display.keys[38]) && canJump) { player.gravitySpeed = -jumpStrength; canJump = false; } // Check if player is on a platform canJump = player.y >= display.canvas.height - player.height - 1 || player.crashWith(ground) || player.crashWith(platform1) || player.crashWith(platform2) || player.crashWith(platform3); // Check for coin collection coins.forEach((coin, index) => { if (coin && player.crashWith(coin)) { coin.hide(); coins[index] = null; score += 10; scoreText.text = `Score: ${score}`; } }); // Enemy movement and behavior if (enemy1.x <= 250 || enemy1.x >= 500) { enemy1.speedX *= -1; } if (enemy2.x <= 450 || enemy2.x >= 650) { enemy2.speedX *= -1; } // Keep player within screen bounds if (player.x < 0) player.x = 0; if (player.x > display.canvas.width - player.width) { player.x = display.canvas.width - player.width; } // Check for collision with enemies if (player.crashWith(enemy1) || player.crashWith(enemy2)) { // Reset game player.x = 100; player.y = 100; player.speedX = 0; player.speedY = 0; enemy1.x = 300; enemy2.x = 600; coins.forEach((coin, index) => { if (coin) { coin.show(); coin.x = coinPositions[index][0]; coin.y = coinPositions[index][1]; } else { const newCoin = new Component(15, 15, "#f1c40f", coinPositions[index][0], coinPositions[index][1], "rect"); display.add(newCoin); coins[index] = newCoin; } }); score = 0; scoreText.text = `Score: ${score}`; } // Reset if player falls off the screen if (player.y > display.canvas.height) { player.x = 100; player.y = 100; player.speedX = 0; player.speedY = 0; } } </script> </body> </html>
Game Features
Our platform game includes:
- Player character with physics-based movement
- Multiple platforms to jump on
- Collectible coins that increase score
- Moving enemies that reset the game on contact
- Score display
- Camera that follows the player
- Visual decorations
Next Steps
To expand this game, you could:
- Add multiple levels with increasing difficulty
- Implement different enemy types with unique behaviors
- Add power-ups (e.g., double jump, speed boost)
- Create a tilemap for more complex level design
- Add sound effects and background music
- Implement a game menu and pause functionality
TCJSGame v3 provides a simple yet powerful framework for creating 2D games in JavaScript. With its component-based architecture and built-in physics, you can quickly prototype and build engaging browser-based games.
Top comments (0)