飞刀游戏的魅力就在于简单到极致的规则 :玩家控制飞刀,一把一把投向旋转的靶子 ,只要投中木靶就能得分,但如果飞刀碰到了之前插上的刀,立刻失败。
如果自己开发,一堆事等着你:飞刀投掷轨迹、靶子的旋转逻辑、碰撞检测、速度递增机制......这些全都要手写,调起来还挺累。
现在,用 Trae IDE,只需要一句话,就能看到一个完整的飞刀游戏出现在眼前。
💡 我想要的玩法
我的构想特别直白:
- 一个会旋转的木靶:从一开始就转个不停,越到后面越快;
- 玩家投飞刀:点击或按键就能投出飞刀,插在木靶上;
- 碰到别的刀就失败:飞刀只要撞上了已经插着的飞刀,游戏立刻结束;
- 难度逐渐增加:每过一关,旋转速度更快,刀的数量也更多。
于是我给 Trae 下了一句指令:
"生成一个飞刀游戏,玩家投掷飞刀击中旋转的靶子,避免击中其他飞刀。"

✨ Trae 怎么"几秒搞定"
不到十秒钟,Trae 就给我生成了一个完整能玩的飞刀游戏:
✅ 飞刀投掷逻辑 :轻点一下,飞刀精准射出并插在靶子上; ✅ 靶子旋转动画 :从一开始缓慢旋转,后面越转越快; ✅ 碰撞检测 :如果飞刀碰到靶子上已有的刀,直接 Game Over; ✅ 渐进难度系统:一关比一关更紧张,后面基本全靠反应力。

🧩 试玩体验
第一次玩的时候我就感受到那种"看似简单,实则虐心"的快乐:
🎯 第一关轻松投 ,飞刀一把一把插上去,满满的成就感; ⚠ 后面靶子加速 ,刀的间隙越来越窄,我开始犹豫按键的时机; 💥 一不小心撞刀,Game Over 的那一瞬间让我直接按了"再来一局"。
Trae 生成的这个版本,不只是能玩,还能让人上瘾到停不下来。
🛠 想增加花样?一句话就能实现
Trae 的可扩展性真的逆天,想加什么,直接说,比如:

- "让木靶换成水果或怪物" → 每关都有新视觉,趣味性更强;
- "加一个奖励刀模式" → 投中特定位置能获得额外飞刀;
- "让靶子偶尔反向旋转" → 瞬间打乱节奏,挑战感翻倍;
- "加上积分排行榜" → 让玩家拼命刷新分数。
所有这些变化,不用手动改代码,Trae 自动补逻辑、调动画。
🎮 过去 vs 现在
过去写飞刀游戏:
- 手写 飞刀投掷轨迹;
- 调 旋转动画和速度递增;
- 写 碰撞检测;
- 再慢慢加关卡和 UI。
麻烦、费时间,还容易出 bug。
现在有了 Trae: 👉 一句话 → 基础玩法全搞定; 👉 想扩展 → 再说几句,逻辑就自动完善。
开发变成了创意输出,做游戏像聊天一样简单。
✅ 结语
如果你也想做一款"上手秒懂、玩到停不下"的飞刀游戏,打开 Trae,只要输入:
"生成一个飞刀游戏,玩家投掷飞刀击中旋转的靶子,避免击中其他飞刀。"
几秒后,你就能玩到一款完整的飞刀挑战游戏:投掷流畅、旋转自然、难度渐进,还能无限扩展新花样。
这就是 Trae 的魔力 ------ 让创意直接变成可玩的游戏。
html
<!DOCTYPE html>
<html lang="zh-CN">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>飞刀游戏</title>
<style>
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
body {
font-family: 'Arial', sans-serif;
background-color: #1a1a2e;
display: flex;
justify-content: center;
align-items: center;
height: 100vh;
overflow: hidden;
color: #fff;
}
.game-container {
position: relative;
width: 400px;
height: 600px;
background: linear-gradient(to bottom, #16213e, #0f3460);
border-radius: 20px;
box-shadow: 0 0 30px rgba(0, 0, 0, 0.5);
overflow: hidden;
}
.score-container {
position: absolute;
top: 20px;
left: 0;
width: 100%;
text-align: center;
font-size: 24px;
font-weight: bold;
color: #fff;
text-shadow: 0 0 10px rgba(255, 255, 255, 0.5);
z-index: 10;
}
.stage-container {
position: absolute;
top: 60px;
left: 0;
width: 100%;
text-align: center;
font-size: 18px;
color: #e94560;
z-index: 10;
}
.target-container {
position: absolute;
top: 150px;
left: 50%;
transform: translateX(-50%);
width: 200px;
height: 200px;
display: flex;
justify-content: center;
align-items: center;
}
.target {
position: relative;
width: 150px;
height: 150px;
border-radius: 50%;
background: url('data:image/svg+xml;utf8,<svg xmlns="http://www.w3.org/2000/svg" width="150" height="150" viewBox="0 0 150 150"><circle cx="75" cy="75" r="75" fill="%23533483"/><circle cx="75" cy="75" r="60" fill="%23e94560"/><circle cx="75" cy="75" r="45" fill="%23533483"/><circle cx="75" cy="75" r="30" fill="%23e94560"/><circle cx="75" cy="75" r="15" fill="%23533483"/></svg>');
background-size: cover;
box-shadow: 0 0 20px rgba(233, 69, 96, 0.5);
transition: transform 0.2s;
}
.knife-container {
position: absolute;
bottom: 100px;
left: 50%;
transform: translateX(-50%);
width: 50px;
height: 100px;
display: flex;
justify-content: center;
}
.knife {
position: absolute;
width: 10px;
height: 50px;
background: linear-gradient(to bottom, #e0e0e0, #a0a0a0);
border-radius: 2px 2px 0 0;
transform-origin: center bottom;
z-index: 5;
}
.knife:before {
content: '';
position: absolute;
top: -10px;
left: 0;
width: 0;
height: 0;
border-left: 5px solid transparent;
border-right: 5px solid transparent;
border-bottom: 10px solid #e0e0e0;
}
.knife-handle {
position: absolute;
bottom: 0;
left: 2.5px;
width: 5px;
height: 15px;
background-color: #533483;
border-radius: 0 0 2px 2px;
}
.knife-in-target {
position: absolute;
width: 10px;
height: 50px;
background: linear-gradient(to bottom, #e0e0e0, #a0a0a0);
border-radius: 2px 2px 0 0;
transform-origin: center bottom;
z-index: 5;
}
.knife-in-target:before {
content: '';
position: absolute;
top: -10px;
left: 0;
width: 0;
height: 0;
border-left: 5px solid transparent;
border-right: 5px solid transparent;
border-bottom: 10px solid #e0e0e0;
}
.knife-in-target .knife-handle {
position: absolute;
bottom: 0;
left: 2.5px;
width: 5px;
height: 15px;
background-color: #533483;
border-radius: 0 0 2px 2px;
}
.game-over {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-color: rgba(26, 26, 46, 0.9);
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
z-index: 20;
display: none;
}
.game-over-title {
font-size: 36px;
font-weight: bold;
color: #e94560;
margin-bottom: 20px;
text-shadow: 0 0 10px rgba(233, 69, 96, 0.5);
}
.final-score {
font-size: 24px;
color: #fff;
margin-bottom: 10px;
}
.highest-stage {
font-size: 20px;
color: #fff;
margin-bottom: 30px;
}
.restart-button {
padding: 15px 30px;
font-size: 18px;
font-weight: bold;
background-color: #e94560;
color: #fff;
border: none;
border-radius: 30px;
cursor: pointer;
transition: all 0.3s;
box-shadow: 0 0 15px rgba(233, 69, 96, 0.5);
}
.restart-button:hover {
background-color: #d63d57;
transform: scale(1.05);
box-shadow: 0 0 20px rgba(233, 69, 96, 0.7);
}
.start-screen {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-color: rgba(26, 26, 46, 0.9);
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
z-index: 20;
}
.game-title {
font-size: 40px;
font-weight: bold;
color: #e94560;
margin-bottom: 20px;
text-shadow: 0 0 15px rgba(233, 69, 96, 0.7);
}
.game-description {
font-size: 16px;
color: #fff;
text-align: center;
margin-bottom: 40px;
max-width: 80%;
line-height: 1.5;
}
.start-button {
padding: 15px 30px;
font-size: 18px;
font-weight: bold;
background-color: #e94560;
color: #fff;
border: none;
border-radius: 30px;
cursor: pointer;
transition: all 0.3s;
box-shadow: 0 0 15px rgba(233, 69, 96, 0.5);
}
.start-button:hover {
background-color: #d63d57;
transform: scale(1.05);
box-shadow: 0 0 20px rgba(233, 69, 96, 0.7);
}
.stage-complete {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-color: rgba(26, 26, 46, 0.8);
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
z-index: 20;
display: none;
}
.stage-complete-title {
font-size: 32px;
font-weight: bold;
color: #e94560;
margin-bottom: 20px;
text-shadow: 0 0 10px rgba(233, 69, 96, 0.5);
}
.stage-score {
font-size: 20px;
color: #fff;
margin-bottom: 30px;
}
.next-stage-button {
padding: 15px 30px;
font-size: 18px;
font-weight: bold;
background-color: #e94560;
color: #fff;
border: none;
border-radius: 30px;
cursor: pointer;
transition: all 0.3s;
box-shadow: 0 0 15px rgba(233, 69, 96, 0.5);
}
.next-stage-button:hover {
background-color: #d63d57;
transform: scale(1.05);
box-shadow: 0 0 20px rgba(233, 69, 96, 0.7);
}
.knife-count {
position: absolute;
bottom: 20px;
left: 0;
width: 100%;
text-align: center;
font-size: 18px;
color: #fff;
z-index: 10;
}
.knife-icon {
display: inline-block;
width: 6px;
height: 20px;
background: linear-gradient(to bottom, #e0e0e0, #a0a0a0);
border-radius: 1px 1px 0 0;
margin: 0 5px;
position: relative;
}
.knife-icon:before {
content: '';
position: absolute;
top: -5px;
left: 0;
width: 0;
height: 0;
border-left: 3px solid transparent;
border-right: 3px solid transparent;
border-bottom: 5px solid #e0e0e0;
}
.knife-icon:after {
content: '';
position: absolute;
bottom: 0;
left: 1.5px;
width: 3px;
height: 6px;
background-color: #533483;
border-radius: 0 0 1px 1px;
}
@keyframes targetHit {
0% { transform: scale(1); }
50% { transform: scale(0.9); }
100% { transform: scale(1); }
}
@keyframes knifeThrow {
0% { transform: translateY(0); }
100% { transform: translateY(-300px); }
}
.apple {
position: absolute;
width: 30px;
height: 30px;
background: url('data:image/svg+xml;utf8,<svg xmlns="http://www.w3.org/2000/svg" width="30" height="30" viewBox="0 0 30 30"><circle cx="15" cy="17" r="12" fill="%23e94560"/><path d="M15,5 L15,10" stroke="%23228B22" stroke-width="2"/><path d="M15,5 C12,7 18,7 15,5" fill="%23228B22"/></svg>');
background-size: cover;
z-index: 6;
}
</style>
</head>
<body>
<div class="game-container" id="game-container">
<div class="score-container">
分数: <span id="score">0</span>
</div>
<div class="stage-container">
关卡: <span id="stage">1</span>
</div>
<div class="target-container">
<div class="target" id="target"></div>
</div>
<div class="knife-container">
<div class="knife" id="knife">
<div class="knife-handle"></div>
</div>
</div>
<div class="knife-count" id="knife-count"></div>
<div class="game-over" id="game-over">
<div class="game-over-title">游戏结束</div>
<div class="final-score">最终分数: <span id="final-score">0</span></div>
<div class="highest-stage">最高关卡: <span id="highest-stage">1</span></div>
<button class="restart-button" id="restart-button">再玩一次</button>
</div>
<div class="stage-complete" id="stage-complete">
<div class="stage-complete-title">关卡完成!</div>
<div class="stage-score">关卡分数: <span id="stage-score">0</span></div>
<button class="next-stage-button" id="next-stage-button">下一关</button>
</div>
<div class="start-screen" id="start-screen">
<div class="game-title">飞刀大师</div>
<div class="game-description">
点击屏幕或按空格键投掷飞刀,击中旋转的靶子。<br>
避免击中已经插在靶子上的其他飞刀。<br>
每关需要投掷特定数量的飞刀,关卡越高难度越大。<br>
收集红色苹果获得额外分数和飞刀。
</div>
<button class="start-button" id="start-button">开始游戏</button>
</div>
</div>
<script>
// 游戏元素
const gameContainer = document.getElementById('game-container');
const target = document.getElementById('target');
const knife = document.getElementById('knife');
const scoreElement = document.getElementById('score');
const stageElement = document.getElementById('stage');
const knifeCountElement = document.getElementById('knife-count');
const gameOverElement = document.getElementById('game-over');
const finalScoreElement = document.getElementById('final-score');
const highestStageElement = document.getElementById('highest-stage');
const restartButton = document.getElementById('restart-button');
const stageCompleteElement = document.getElementById('stage-complete');
const stageScoreElement = document.getElementById('stage-score');
const nextStageButton = document.getElementById('next-stage-button');
const startScreen = document.getElementById('start-screen');
const startButton = document.getElementById('start-button');
// 游戏配置
const targetRadius = 75; // 靶子半径
const knifeWidth = 10;
const knifeHeight = 50;
const knifeThrowDuration = 200; // 毫秒
// 游戏状态
let score = 0;
let stage = 1;
let knivesLeft = 5; // 每关的飞刀数量
let knivesInTarget = []; // 已经插在靶子上的飞刀
let targetRotationSpeed = 1; // 靶子旋转速度
let targetRotationAngle = 0; // 靶子当前旋转角度
let isKnifeThrowing = false; // 飞刀是否正在投掷中
let gameRunning = false; // 游戏是否正在运行
let rotationInterval; // 靶子旋转的定时器
let apples = []; // 苹果数组
let appleGenerationChance = 0.3; // 苹果生成概率
// 初始化游戏
function initGame() {
// 隐藏开始屏幕
startScreen.style.display = 'none';
// 重置游戏状态
score = 0;
stage = 1;
knivesLeft = 5 + stage;
knivesInTarget = [];
targetRotationSpeed = 1;
targetRotationAngle = 0;
isKnifeThrowing = false;
apples = [];
// 清除所有已有的飞刀和苹果
const existingKnives = document.querySelectorAll('.knife-in-target');
existingKnives.forEach(k => k.remove());
const existingApples = document.querySelectorAll('.apple');
existingApples.forEach(a => a.remove());
// 更新显示
updateDisplay();
// 显示飞刀
knife.style.display = 'block';
// 开始靶子旋转
gameRunning = true;
rotationInterval = setInterval(rotateTarget, 16); // 约60帧每秒
}
// 更新显示
function updateDisplay() {
scoreElement.textContent = score;
stageElement.textContent = stage;
// 更新剩余飞刀显示
knifeCountElement.innerHTML = '';
for (let i = 0; i < knivesLeft; i++) {
const knifeIcon = document.createElement('div');
knifeIcon.className = 'knife-icon';
knifeCountElement.appendChild(knifeIcon);
}
}
// 旋转靶子
function rotateTarget() {
if (!gameRunning) return;
// 更新靶子旋转角度
targetRotationAngle += targetRotationSpeed;
if (targetRotationAngle >= 360) {
targetRotationAngle -= 360;
}
// 应用旋转
target.style.transform = `rotate(${targetRotationAngle}deg)`;
// 同时旋转已插入的飞刀
knivesInTarget.forEach(knifeObj => {
const knifeElement = knifeObj.element;
knifeElement.style.transform = `rotate(${targetRotationAngle + knifeObj.angle}deg) translateY(-${targetRadius}px)`;
});
// 同时旋转苹果
apples.forEach(appleObj => {
const appleElement = appleObj.element;
appleElement.style.transform = `rotate(${targetRotationAngle + appleObj.angle}deg) translateY(-${targetRadius}px)`;
});
}
// 投掷飞刀
function throwKnife() {
if (!gameRunning || isKnifeThrowing || knivesLeft <= 0) return;
isKnifeThrowing = true;
// 创建飞刀动画
knife.style.animation = `knifeThrow ${knifeThrowDuration}ms forwards`;
// 飞刀动画结束后
setTimeout(() => {
// 检查是否击中其他飞刀
const hitAnotherKnife = checkKnifeCollision();
if (hitAnotherKnife) {
// 游戏结束
endGame();
} else {
// 检查是否击中苹果
const hitApple = checkAppleCollision();
if (hitApple) {
// 增加分数和飞刀
score += 50;
knivesLeft += 1;
updateDisplay();
}
// 将飞刀添加到靶子上
addKnifeToTarget();
// 减少剩余飞刀数量
knivesLeft--;
updateDisplay();
// 重置飞刀位置和动画
knife.style.animation = '';
// 检查是否完成关卡
if (knivesLeft <= 0) {
completeStage();
} else {
// 随机生成苹果
if (Math.random() < appleGenerationChance) {
generateApple();
}
isKnifeThrowing = false;
}
}
}, knifeThrowDuration);
}
// 检查飞刀碰撞
function checkKnifeCollision() {
// 计算当前飞刀的角度
const knifeAngle = (360 - targetRotationAngle) % 360;
// 检查是否与已有飞刀碰撞
for (const knifeObj of knivesInTarget) {
const existingKnifeAngle = knifeObj.angle;
const angleDiff = Math.abs(knifeAngle - existingKnifeAngle);
// 如果角度差小于一定阈值,则认为碰撞
if (angleDiff < 25 || angleDiff > 335) {
return true;
}
}
return false;
}
// 检查苹果碰撞
function checkAppleCollision() {
if (apples.length === 0) return false;
// 计算当前飞刀的角度
const knifeAngle = (360 - targetRotationAngle) % 360;
// 检查是否击中苹果
for (let i = 0; i < apples.length; i++) {
const appleObj = apples[i];
const appleAngle = appleObj.angle;
const angleDiff = Math.abs(knifeAngle - appleAngle);
// 如果角度差小于一定阈值,则认为击中
if (angleDiff < 15 || angleDiff > 345) {
// 移除苹果
appleObj.element.remove();
apples.splice(i, 1);
return true;
}
}
return false;
}
// 将飞刀添加到靶子上
function addKnifeToTarget() {
// 创建新的飞刀元素
const newKnife = document.createElement('div');
newKnife.className = 'knife-in-target';
// 添加飞刀手柄
const knifeHandle = document.createElement('div');
knifeHandle.className = 'knife-handle';
newKnife.appendChild(knifeHandle);
// 计算飞刀角度 (相对于靶子)
const knifeAngle = (360 - targetRotationAngle) % 360;
// 设置飞刀位置和旋转
newKnife.style.transform = `rotate(${targetRotationAngle + knifeAngle}deg) translateY(-${targetRadius}px)`;
newKnife.style.transformOrigin = 'center bottom';
newKnife.style.position = 'absolute';
newKnife.style.bottom = '50%';
newKnife.style.left = `calc(50% - ${knifeWidth / 2}px)`;
// 将飞刀添加到靶子中
target.appendChild(newKnife);
// 添加到飞刀数组
knivesInTarget.push({
element: newKnife,
angle: knifeAngle
});
// 播放靶子被击中的动画
target.style.animation = 'targetHit 0.2s';
setTimeout(() => {
target.style.animation = '';
}, 200);
// 增加分数
score += 10;
scoreElement.textContent = score;
}
// 生成苹果
function generateApple() {
// 如果已经有两个苹果,不再生成
if (apples.length >= 2) return;
// 创建苹果元素
const apple = document.createElement('div');
apple.className = 'apple';
// 随机角度 (避开已有的飞刀)
let appleAngle;
let validAngle = false;
while (!validAngle) {
appleAngle = Math.floor(Math.random() * 360);
validAngle = true;
// 检查是否与已有飞刀角度冲突
for (const knifeObj of knivesInTarget) {
const existingKnifeAngle = knifeObj.angle;
const angleDiff = Math.abs(appleAngle - existingKnifeAngle);
if (angleDiff < 30 || angleDiff > 330) {
validAngle = false;
break;
}
}
// 检查是否与已有苹果角度冲突
for (const appleObj of apples) {
const existingAppleAngle = appleObj.angle;
const angleDiff = Math.abs(appleAngle - existingAppleAngle);
if (angleDiff < 60 || angleDiff > 300) {
validAngle = false;
break;
}
}
}
// 设置苹果位置和旋转
apple.style.transform = `rotate(${targetRotationAngle + appleAngle}deg) translateY(-${targetRadius}px)`;
apple.style.transformOrigin = 'center bottom';
apple.style.position = 'absolute';
apple.style.bottom = '50%';
apple.style.left = `calc(50% - 15px)`; // 苹果宽度的一半
// 将苹果添加到靶子中
target.appendChild(apple);
// 添加到苹果数组
apples.push({
element: apple,
angle: appleAngle
});
}
// 完成关卡
function completeStage() {
gameRunning = false;
clearInterval(rotationInterval);
// 计算关卡分数
const stageScore = 100 + knivesInTarget.length * 10;
score += stageScore;
// 更新显示
stageScoreElement.textContent = stageScore;
scoreElement.textContent = score;
// 显示关卡完成界面
stageCompleteElement.style.display = 'flex';
}
// 下一关
function nextStage() {
stage++;
stageCompleteElement.style.display = 'none';
// 增加难度
targetRotationSpeed = 1 + stage * 0.5;
knivesLeft = 5 + stage;
appleGenerationChance = Math.min(0.5, 0.3 + stage * 0.05);
// 清除所有已有的飞刀和苹果
knivesInTarget = [];
apples = [];
const existingKnives = document.querySelectorAll('.knife-in-target');
existingKnives.forEach(k => k.remove());
const existingApples = document.querySelectorAll('.apple');
existingApples.forEach(a => a.remove());
// 更新显示
updateDisplay();
stageElement.textContent = stage;
// 显示飞刀
knife.style.display = 'block';
isKnifeThrowing = false;
// 开始靶子旋转
gameRunning = true;
rotationInterval = setInterval(rotateTarget, 16);
}
// 游戏结束
function endGame() {
gameRunning = false;
clearInterval(rotationInterval);
// 更新显示
finalScoreElement.textContent = score;
highestStageElement.textContent = stage;
// 显示游戏结束界面
gameOverElement.style.display = 'flex';
}
// 重新开始游戏
function restartGame() {
gameOverElement.style.display = 'none';
initGame();
}
// 事件监听
gameContainer.addEventListener('click', throwKnife);
document.addEventListener('keydown', (e) => {
if (e.code === 'Space') {
throwKnife();
}
});
startButton.addEventListener('click', initGame);
restartButton.addEventListener('click', restartGame);
nextStageButton.addEventListener('click', nextStage);
</script>
</body>
</html>