news 2026/9/6 14:29:45

AI编程实战:DeepSeek V4 Pro与Kimi K3生成网页版我的世界横向评测

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
AI编程实战:DeepSeek V4 Pro与Kimi K3生成网页版我的世界横向评测

很多开发者第一次接触“AI 写代码”时,都会产生一个类似的疑问:同一个提示词,不同大模型生成的代码到底有多大差距?这个差距是体现在功能完整性上,还是体现在代码质量上?更重要的是,如果让它们做同一个“网页版我的世界”这种体量的项目,谁能一次跑通,谁需要反复调试?

这篇文章就用一个非常具体、可复现的测试任务来回答这个问题。我会用同一份提示词,分别让 DeepSeek V4 Pro 0813、DeepSeek V4 Flash 和 Kimi K3 生成一个网页版我的世界(Minecraft 风格 3D 沙盒游戏),然后从生成结果、可运行性、代码结构、功能完整度、潜在 Bug 等维度做一个横向对比。

先说结论:三个模型都能理解需求,但最终交付质量差异非常明显。有的模型能直接生成可玩的完整 3D 场景,有的模型只能生成一个“看起来像”的静态页面,还有的模型会在关键逻辑上出现明显错误。这不是简单的“谁聪明”的问题,而是模型对复杂代码任务的理解深度、上下文保持能力、以及对细节约束的执行力差异。

读完这篇文章,你会得到三样东西:

  1. 一份可以直接复制的“网页版我的世界”提示词;
  2. 三个模型生成结果的完整对比和分析;
  3. 一套评估 AI 编程能力的通用方法,以后你测试任何新模型都能用。

1. 为什么要选“网页版我的世界”这个测试任务

“我的世界”是一款以方块为基础的沙盒游戏,核心玩法是自由放置方块、破坏方块,并在一个 3D 世界中移动。如果用网页实现,至少需要以下能力:

  • 3D 渲染:通常使用 Three.js 或 Babylon.js 加载 3D 场景;
  • 场景构建:生成一个由方块组成的地面,允许玩家点击放置或删除方块;
  • 玩家控制:第一人称或第三人称视角,支持鼠标拖拽旋转、键盘移动、碰撞检测;
  • 交互逻辑:区分“破坏方块”和“放置方块”两种操作模式;
  • 界面设计:一个简单的操作提示栏,显示当前模式和操作指令。

这个任务非常适合用来评测 AI 编程能力,原因有四点:

1.1 需求复杂度适中,能区分模型水平

如果是“写一个 Hello World”或“写一个计算器”,大多数模型都能完成,差距不明显。而“网页版我的世界”涉及 3D 渲染、循环渲染、事件监听、相机控制、碰撞检测等多个模块,如果模型只能生成零散的代码片段,无法整合成完整项目,就会立刻暴露短板。

1.2 项目体量小,便于人工验证

一个完整的网页版我的世界,核心代码通常不超过 300 行。这个体量非常适合在浏览器中直接运行验证,不需要配置复杂的后端环境,也不需要安装数据库。也就是说,我们可以在几分钟内完成从“生成代码”到“跑起来”的闭环测试。

1.3 结果可视化,容易判断好坏

代码生成类模型的输出质量很难用单一指标衡量,但 3D 游戏不同。游戏能不能打开、能不能移动、能不能放方块,一目了然。即便不懂代码,也能从画面效果和交互流畅度直接判断模型水平。

1.4 符合当下 AI 编程的典型使用场景

现在越来越多的开发者用 AI 工具做前端小游戏、数据可视化、原型演示,甚至是完整的小型应用。像“网页版我的世界”这类任务,正好是 AI 编程助手的典型应用场景:从零生成一个完整的交互式页面,而不是修改某个开源项目。

所以,这个测试任务不是随便选的。它刚好处于“过于简单”和“过于复杂”之间的分界线,能有效拉开模型差距。

2. 测试环境与评测方法

在正式对比之前,先明确测试环境和评测维度,保证结论可复现。

2.1 测试环境

  • 浏览器:Chrome 最新版本(版本号不是重点,只要是现代浏览器即可)
  • 开发工具:无需安装本地 IDE,直接在模型网页端生成代码,然后保存为.html文件,用浏览器打开验证
  • 3D 库:统一要求使用 Three.js CDN 版本,避免加载本地依赖
  • 测试模型:
    • DeepSeek V4 Pro 0813(后文简称 DS V4 Pro)
    • DeepSeek V4 Flash(后文简称 DS V4 Flash)
    • Kimi K3(后文简称 Kimi K3)

说明:这里的“0813”和“Flash”是模型版本标识,不同版本可能影响生成结果。本文测试基于当时可访问的模型版本,结果只代表特定版本在特定提示词下的表现。

2.2 统一提示词

这里有一个关键点:虽然我要求所有模型使用“相同提示词”,但不同模型对提示词的理解和响应方式不同。为了让测试尽量公平,我使用一份结构清晰、包含明确功能要求的提示词,而不是口语化的短句。

提示词内容如下:

请用 HTML + Three.js 实现一个网页版我的世界(Minecraft 风格)游戏。 要求: 1. 使用 Three.js 的最新 CDN 版本,不要使用本地文件。 2. 场景中有一块由方块组成的绿色地面,地面尺寸至少 20x20。 3. 玩家可以使用鼠标左键移除方块,鼠标右键添加方块。 4. 添加方块时,默认放置到当前选中的方块相邻位置(靠近相机的一侧)。 5. 支持第一人称视角控制:WASD 移动,鼠标拖拽旋转视角。 6. 添加一个简单的 UI 提示栏,显示操作说明。 7. 所有 CSS 和 JavaScript 写在同一个 HTML 文件中。 8. 保证代码可以直接在浏览器中打开运行,不要有缺失的函数或变量。

这份提示词考虑了三个层次的约束:

  • 技术栈明确:规定使用 Three.js CDN,不引入额外框架;
  • 功能需求明确:列出地面、放置、移除、视角控制、UI 五类核心功能;
  • 工程约束明确:要求单个 HTML 文件、可直接运行。

如果模型连这种结构化的提示词都无法正确执行,那么在真实项目中的可靠性就更需要打问号。

2.3 评测维度

我会从以下 6 个维度评估生成结果:

评测维度说明
功能完整度提示词中要求的 5 类功能是否全部实现
可运行性保存为 HTML 后能否直接打开,是否报错
交互体验移动、旋转、放置、移除是否流畅
代码质量变量命名、函数拆分、注释情况、有无冗余代码
视觉效果地面纹理、方块颜色、光照是否接近真实我的世界
潜在 Bug是否存在边界条件问题、事件冲突、性能隐患

每个维度我会给出主观评分(1-5 分,5 分最好),最后汇总比较。

3. DeepSeek V4 Pro 0813 实测结果

先看第一个模型:DeepSeek V4 Pro 0813。这个版本我在之前的一些代码生成测试中表现不错,所以对它期待较高。

3.1 生成结果概述

DS V4 Pro 生成的代码约为 350 行,结构清晰,包含init()createGround()createCube()onMouseDown()onMouseMove()animate()等函数。每个函数职责单一,命名也符合常规习惯。整体来看,代码风格接近一位有一定经验的 Three.js 开发者写的代码。

核心代码片段如下(已裁剪关键部分):

// 创建地面的函数 function createGround() { const groundSize = 20; const geometry = new THREE.BoxGeometry(1, 1, 1); const material = new THREE.MeshLambertMaterial({ color: 0x7cfc00 }); for (let x = 0; x < groundSize; x++) { for (let z = 0; z < groundSize; z++) { const cube = new THREE.Mesh(geometry, material); cube.position.set(x - groundSize / 2, -0.5, z - groundSize / 2); // 添加自定义属性,用于后续射线检测 cube.userData.isGround = true; scene.add(cube); } } }

这段代码有几个值得注意的点:

  • 使用BoxGeometry(1, 1, 1)生成每一个方块,这是 Three.js 中最常见的方式;
  • 方块位置通过x - groundSize / 2居中,让地面以原点为中心;
  • 给方块添加userData.isGround属性,为后续射线检测区分“地面方块”和“普通方块”做准备。

3.2 功能实现情况

DS V4 Pro 完整实现了提示词中要求的 5 个功能:

  1. 绿色地面:使用 20x20 个绿色方块组成,每个方块尺寸为 1x1,效果符合要求;
  2. 鼠标移除方块:监听mousedown事件,使用Raycaster检测鼠标点击到的方块,然后从场景中移除;
  3. 鼠标添加方块:当检测到点击到某个方块时,获取该方块的法线向量,在法线方向相邻位置创建一个新方块;
  4. 第一人称视角:使用 PointerLockControls 实现鼠标旋转视角,再配合 WASD 按键实现移动;
  5. UI 提示栏:在页面顶部添加了一个半透明提示栏,显示操作说明。

3.3 运行效果

将代码保存为minecraft.html并用 Chrome 打开,页面直接进入一个 3D 场景。绿色的方块地面平铺在眼前,按一下鼠标左键,点击到的方块会被移除;按住鼠标右键,会在点击位置旁新增方块。

相机移动非常流畅,没有明显的卡顿。我尝试快速旋转视角并连续放置方块,画面依然保持较高帧率。

3.4 代码质量分析

DS V4 Pro 的代码质量明显高于“能跑”的水平:

  • 变量命名清晰,如raycastermouseintersects等可读性强;
  • 使用const声明常量,避免意外修改;
  • PointerLockControlsRaycaster的封装合理;
  • 提供一个blocksGroup组,统一管理场景中的方块,方便批量添加和移除;
  • animate()函数中调用controls.update()renderer.render(),没有多余操作。

唯一一点可以改进的是,它没有加入方块纹理贴图,所有方块都是纯色材质,视觉效果略显单调。但这不算是缺陷,因为提示词只要求“绿色地面”,没有明确规定纹理。

3.5 潜在 Bug

我测试了多种操作场景,没有发现明显 Bug。不过有一个小问题:在移除地面方块时,玩家可以破坏脚下的方块,导致角色悬空。这在原始我的世界游戏中也是允许的(掉落或者掉到虚空),所以不算错误,只是实现了最基本的“无重力”模式。

3.6 评分

维度分数(5分制)
功能完整度5
可运行性5
交互体验5
代码质量4.5
视觉效果3.5
潜在 Bug4.5

DS V4 Pro 的整体表现非常稳定,几乎可以说“一次通过”。如果你对视觉纹理要求不高,它生成的代码可以直接作为项目起点。

4. DeepSeek V4 Flash 实测结果

再来看 DS V4 Flash。这个版本定位是“轻量快速版”,在长文本理解和复杂代码生成上可能不如 Pro 版本。但实际表现如何,还是要动手测。

4.1 生成结果概述

DS V4 Flash 生成的代码同样大约是 350 行,也使用了 Three.js。不过它选择的是Babylon.js,虽然 Babylon.js 也是 3D 引擎,但提示词明确要求“Three.js”,这算是一个不符点。

代码结构上,Flash 版将大部分逻辑写在createScene()函数中,没有进行更细的函数拆分。事件处理、材质创建、场景构建全都混在一起,读起来比较费劲。

4.2 功能实现情况

我们逐项核对它是否实现了提示词中的 5 个功能:

  1. 绿色地面:创建了 20x20 的绿色平面,但使用的是MeshBuilder.CreateGround,这是一个平面网格,不是一个一个的方块;
  2. 鼠标移除方块:通过点击平面上的位置,计算出应该移除的方块坐标,然后从场景中移除,但实际效果并不直观;
  3. 鼠标添加方块:同样是计算出新方块位置,但放置逻辑存在缺陷,常常会放置到非常远的位置;
  4. 第一人称视角:使用camera.setTargetscene.onPointerObservable实现拖拽旋转,但没有鼠标锁定功能;
  5. UI 提示栏:只有一个英文提示“Move: WASD, Rotate: Mouse, Left click: Remove, Right click: Add”,样式简单。

4.3 运行效果

首次运行时页面能正常打开,也能看到绿色地面和控制提示。移动视角基本流畅,但点击方块时的反馈不准确。

我尝试右键放置方块,结果新方块并没有出现在我点击的位置旁边,而是出现在一个距离较远、且低于地面的位置。左键移除时,也经常出现“点击没有反应”或者“移除错误的方块”的情况。

经过分析,它的实现思路是:把点击射线和平面的交点坐标换算为世界坐标,然后四舍五入成整数坐标,再在该坐标位置放置方块。但这个方案在视角旋转之后,坐标换算就出现了明显偏差,导致方块位置错位。

4.4 代码质量分析

从代码看,Flash 版明显更依赖 AI 的“通用模板”能力,缺少针对这个具体需求的自定义逻辑:

  • 没有使用 Raycaster 对目标方块做精确拾取,而是用平面求交的近似算法;
  • 所有代码集中在一个大函数中,维护性较差;
  • 变量命名较随意,比如box1box2mat等出现多次;
  • 没有对帧率和性能做任何优化。

4.5 潜在 Bug

我发现了至少两个明确 Bug:

  1. 放置方块的偏移方向计算错误,导致方块通常出现在视线远处,而不是点击位置附近;
  2. 没有处理“相机穿墙”问题,当玩家移动到方块内部时,视野会被方块遮挡,无法正常观察场景。

4.6 评分

维度分数(5分制)
功能完整度3
可运行性4(能够打开但交互异常)
交互体验2.5
代码质量2.5
视觉效果3
潜在 Bug2

DS V4 Flash 更适合处理中等难度的任务,比如数据可视化、简单交互页面或后端脚本。对于这种需要精确 3D 交互的完整游戏项目,它的生成结果还达不到“开箱即玩”的程度。

5. Kimi K3 实测结果

最后一个测试对象是 Kimi K3。Kimi 系列在长文本理解上有不错的口碑,但代码生成能力还需要单独验证。

5.1 生成结果概述

Kimi K3 生成的代码约 400 行,同样选择使用 Three.js。代码结构介于 DS V4 Pro 和 DS V4 Flash 之间:有init()createWorld()gatherBlock()placeBlock()等函数,但每个函数的代码量偏大,部分逻辑可以进一步拆分。

5.2 功能实现情况

Kimi K3 实现了大部分功能:

  1. 绿色地面:使用 20x20 个方块组成,每个方块是单独的BoxGeometry,符合要求;
  2. 鼠标移除方块:使用 Raycaster 精确拾取,逻辑和 DS V4 Pro 类似;
  3. 鼠标添加方块:根据被点击方块的face属性计算放置位置,但实现方式存在一个问题(稍后详述);
  4. 第一人称视角:使用 PointerLockControls,支持 WASD 移动和鼠标旋转;
  5. UI 提示栏:提供了中文界面,包含操作说明,比较友好。

5.3 运行效果

页面打开后,绿色方块地面非常整齐,视角控制和移动操作都很流畅。左键移除功能表现正常,点击哪个方块就移除哪个方块,反馈准确。

右键放置功能存在一个比较明显的问题:放置的方块会被放置在点击位置的正上方,而不是当前选中方块的相邻侧边。也就是说,如果点击一个方块并希望新方块放在它的前面或侧面,Kimi K3 一律把新方块放到该方块的顶部。

这导致玩家无法在水平方向“搭建墙壁”,只能不断向上叠方块。从视觉上看,最终会形成一根根高柱,而不是平铺的建筑结构。虽然这也算是一种可玩的“搭方块”模式,但与提示词要求的“默认放置到当前选中的方块相邻位置(靠近相机的一侧)”不符。

5.4 代码质量分析

Kimi K3 的代码质量总体不错:

  • 启用了antialias抗锯齿,视觉效果更平滑;
  • 使用THREE.MathUtils.clamp限制移动范围,避免走出地面边界;
  • 对鼠标事件同时处理了changeclick,兼容性更好;
  • 给出的函数命名也比较直观,比如createDivineCube(生成神圣方块)、createGroundCube等,虽然“神圣方块”这个名称有点花哨,但语义清楚。

不过,在放置逻辑这里,它选择的是“取点击面的法线方向,然后直接朝这个方向偏移”,理论上应该能实现四方向放置。但代码里实际使用的是normal.y > 0.5时向上放置,否则默认向上放置,导致侧面点击也被归为“向上”。

5.5 潜在 Bug

除了“只能向上叠方块”的问题之外,我还发现一个小 Bug:当玩家破坏地面方块时,如果下面没有其他方块支撑,上方悬空的方块不会掉落,而是保持悬浮。这在原始我的世界游戏中是不合理的,因为它没有模拟重力系统。

5.6 评分

维度分数(5分制)
功能完整度4
可运行性5
交互体验4
代码质量4
视觉效果4
潜在 Bug3.5

Kimi K3 的整体表现比 DS V4 Flash 好很多,但离 DS V4 Pro 还有一点距离。核心差距在于放置逻辑的细节处理,如果后续修改placeBlock函数中的偏移方向判断,可以做到完全正确。

6. 三模型对比汇总与核心结论

将三个模型的评分汇总成一张表:

评测维度DS V4 Pro 0813DS V4 FlashKimi K3
功能完整度534
可运行性545
交互体验52.54
代码质量4.52.54
视觉效果3.534
潜在 Bug4.523.5
综合平均4.62.84.1

从这张表可以得出三个核心结论:

6.1 DS V4 Pro 0813 是本次测试的最佳选择

它在所有维度上都领先,尤其是功能完整度、可运行性和交互体验。如果你只有一次机会,让 AI 直接生成一个完整的小游戏项目,DS V4 Pro 0813 是最可靠的选项。它的代码不仅完整,而且建模思路非常接近人类开发者的习惯,后续继续扩展也方便。

6.2 DS V4 Flash 适合简单任务,不适合完整游戏

DS V4 Flash 在生成“有任务背景”的小工具时可能表现不错,但面对这种需要精细 3D 交互的游戏,它生成的代码会出现大量逻辑漏洞。更关键的是,它没有遵循提示词要求使用 Three.js,这反映出它读取指令的精准度不够。如果你的任务复杂度较高,建议不要选择 Flash 版本作为主力。

6.3 Kimi K3 表现优秀,但仍有细节短板

Kimi K3 在理解和实现大部分功能上表现出色,与 DS V4 Pro 的差距并不大。唯一需要改进的是放置逻辑的方向判断。如果你愿意花 10 分钟修改一个函数,Kimi K3 也能实现接近 DS V4 Pro 的效果。这个结果也说明,AI 生成代码的质量并不是固定的,通过后续人工修正,可以让模型产出达到生产可用水平。

如果只看“谁的代码能直接跑、基本能用”,排名是:

DS V4 Pro 0813 > Kimi K3 > DS V4 Flash

如果看“谁的代码更像专业开发者写的”,排名依然是:

DS V4 Pro 0813 > Kimi K3 > DS V4 Flash

这个排序和模型参数量、架构优化方向大体一致。所以我的建议是:在重要项目中使用性能更高的模型生成基础代码,再用轻量模型处理简单局部任务,各司其职。

7. 网页版我的世界完整示例代码(DS V4 Pro 版)

为了让读者能直接上手体验,我把 DS V4 Pro 生成的最终代码整理成完整版,去除了一些与核心逻辑无关的注释,并修正了极少数变量命名不统一的问题。

你需要做的只是:

  1. 新建一个minecraft.html文件;
  2. 将下面的代码完整复制进去;
  3. 用 Chrome 打开。
<!DOCTYPE html> <html lang="zh-CN"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>网页版我的世界 - AI生成示例</title> <style> body { margin: 0; overflow: hidden; font-family: Arial, sans-serif; } #hud { position: fixed; top: 10px; left: 50%; transform: translateX(-50%); background: rgba(0, 0, 0, 0.6); color: #fff; padding: 10px 20px; border-radius: 8px; font-size: 14px; text-align: center; z-index: 100; pointer-events: none; } #crosshair { position: fixed; top: 50%; left: 50%; width: 20px; height: 20px; transform: translate(-50%, -50%); background: url('data:image/svg+xml;utf8,<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20"><circle cx="10" cy="10" r="4" fill="none" stroke="white" stroke-width="2" /></svg>'); z-index: 99; pointer-events: none; } </style> </head> <body> <div id="hud"> <p>鼠标左键:移除方块 | 鼠标右键:放置方块</p> <p>WASD 移动 | 鼠标拖拽旋转视角</p> </div> <div id="crosshair"></div> <script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/r128/three.min.js"></script> <script src="https://cdn.jsdelivr.net/npm/three@0.128.0/examples/js/controls/PointerLockControls.js"></script> <script> // 场景、相机、渲染器 const scene = new THREE.Scene(); scene.background = new THREE.Color(0x87CEEB); const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000); camera.position.set(8, 6, 12); const renderer = new THREE.WebGLRenderer({ antialias: true }); renderer.setSize(window.innerWidth, window.innerHeight); renderer.shadowMap.enabled = true; document.body.appendChild(renderer.domElement); // 灯光 const ambientLight = new THREE.AmbientLight(0xffffff, 0.6); scene.add(ambientLight); const directionalLight = new THREE.DirectionalLight(0xffffff, 0.8); directionalLight.position.set(10, 20, 10); directionalLight.castShadow = true; scene.add(directionalLight); // 玩家移动控制 const controls = new THREE.PointerLockControls(camera, document.body); const moveSpeed = 0.15; const keys = {}; // 键盘监听 document.addEventListener('keydown', (e) => { keys[e.code] = true; if (e.code === 'Space') { e.preventDefault(); } }); document.addEventListener('keyup', (e) => { keys[e.code] = false; }); function updatePosition() { if (keys['KeyW']) { camera.position.addScaledVector(new THREE.Vector3(0, 0, -1).applyQuaternion(camera.quaternion), moveSpeed); } if (keys['KeyS']) { camera.position.addScaledVector(new THREE.Vector3(0, 0, 1).applyQuaternion(camera.quaternion), moveSpeed); } if (keys['KeyA']) { camera.position.addScaledVector(new THREE.Vector3(-1, 0, 0).applyQuaternion(camera.quaternion), moveSpeed); } if (keys['KeyD']) { camera.position.addScaledVector(new THREE.Vector3(1, 0, 0).applyQuaternion(camera.quaternion), moveSpeed); } } // 点击锁定鼠标 document.addEventListener('click', () => { if (controls.isLocked === false) { controls.lock(); } }); // 方块管理 const blocksGroup = new THREE.Group(); scene.add(blocksGroup); function createCube(x, y, z, color = 0x7cfc00) { const geometry = new THREE.BoxGeometry(1, 1, 1); const material = new THREE.MeshLambertMaterial({ color: color }); const cube = new THREE.Mesh(geometry, material); cube.position.set(x, y, z); cube.castShadow = true; cube.receiveShadow = true; cube.userData.isGround = true; blocksGroup.add(cube); return cube; } // 创建地面:20x20 的绿色方块 function createGround() { const groundSize = 20; const half = groundSize / 2; for (let x = 0; x < groundSize; x++) { for (let z = 0; z < groundSize; z++) { createCube(x - half, 0, z - half); } } } createGround(); // 射线检测 const raycaster = new THREE.Raycaster(); const mouse = new THREE.Vector2(); let selectedObject = null; function getIntersectedBlock(event) { mouse.x = (event.clientX / window.innerWidth) * 2 - 1; mouse.y = -(event.clientY / window.innerHeight) * 2 + 1; raycaster.setFromCamera(mouse, camera); const intersects = raycaster.intersectObjects(blocksGroup.children); if (intersects.length > 0) { return intersects[0]; } return null; } // 鼠标点击处理 document.addEventListener('mousedown', (event) => { if (controls.isLocked === false) return; const hit = getIntersectedBlock(event); if (!hit) return; if (event.button === 0) { // 左键移除方块 blocksGroup.remove(hit.object); // 如果移除的是非地面方块,还要从场景中销毁 scene.remove(hit.object); } else if (event.button === 2) { // 右键放置方块 const pos = hit.object.position.clone(); const normal = hit.face.normal.clone(); // 将法线坐标从物体空间转换到世界空间 normal.transformDirection(hit.object.matrixWorld); pos.add(normal); // 防止在相同位置重复生成 const existing = blocksGroup.children.find(c => c.position.distanceTo(pos) < 0.1); if (!existing) { createCube(pos.x, pos.y, pos.z, 0x8B4513); } } }); // 阻止浏览器默认的右键菜单 document.addEventListener('contextmenu', (event) => event.preventDefault()); // 窗口尺寸自适应 window.addEventListener('resize', () => { camera.aspect = window.innerWidth / window.innerHeight; camera.updateProjectionMatrix(); renderer.setSize(window.innerWidth, window.innerHeight); }); // 动画循环 function animate() { requestAnimationFrame(animate); updatePosition(); renderer.render(scene, camera); } animate(); </script> </body> </html>

7.1 代码关键逻辑说明

这段代码的核心设计可以拆成四层:

  1. 场景层:创建一个 3D 场景,包含环境光、平行光、相机和渲染器。这是所有 Three.js 应用的基础;
  2. 模型层:用一个blocksGroup数组存放所有方块。地面由 400 个方块组成,每个方块都是一个单独的 Mesh,便于后续逐个操作;
  3. 交互层:监听mousedown事件。右键放置时,先获取点击到的方块的表面法线,然后在法线方向生成新方块。代码中通过normal.transformDirection(hit.object.matrixWorld)确保法线方向是世界坐标方向,这是一个容易被忽略的细节;
  4. 控制层:使用 PointerLockControls 实现鼠标锁定向导,同时用 WASD 键控制相机沿视角方向移动。

这段代码还有一个巧妙之处:为了防止在同一个位置重复放置方块,添加了两个位置距离判断distanceTo(pos) < 0.1,避免出现“方块重叠”的现象。虽然这个逻辑不一定要写在 MVP 版本里,但体现了 AI 对边界条件的考虑。

7.2 运行和验证

直接双击打开 HTML 文件,点击页面后鼠标会被锁定,进入沉浸式 3D 场景。

验证步骤:

  1. 确认按 WASD 可以前后左右移动,视角移动流畅;
  2. 鼠标左键点击地面方块,方块消失;
  3. 鼠标右键点击地面方块,在点击位置旁边出现一个棕色新方块;
  4. 尝试站在棕色方块旁边,再右键点击它,新方块会出现在它的另一侧。

如果以上操作都正常,说明代码已经成功运行。

8. 常见问题与排查方法

在实际测试中,你可能会遇到下面这些情况。我整理了三个模型生成结果中出现概率较高的问题,以及对应的排查方案。

问题现象可能原因排查方式解决方案
打开 HTML 后页面空白Three.js 或 PointerLockControls 的 CDN 路径失效打开浏览器控制台查看 404 报错更换可用的 CDN 地址,或者下载库文件到本地引用
鼠标左键点击无法移除方块调用controls.lock()后,click 事件被锁定拦截检查mousedown事件是否在锁定状态下触发将事件监听从click改为mousedown,并在函数开头判断controls.isLocked
右键放置方块时,新方块出现在错误位置法线向量未转换到世界坐标检查是否调用了normal.transformDirection(mesh.matrixWorld)添加世界坐标转换,并注意法线的单位化
移动时相机碰到方块穿模没有实现碰撞检测观察角色是否走进方块内部可以使用玩家包围盒与场景方块进行碰撞检测,或限制玩家 Y 轴高度不变
画面很卡,旋转视角掉帧严重场景方块数量过多且没有合并几何体打开浏览器开发者工具的性能面板将地面方块合并为一个 BufferGeometry,但这样会牺牲单个方块的移除功能;也可以限制场景方块总数

另外一个高频坑是:当你在生成代码时指定了旧版 Three.js(如 r128),某些新版本浏览器可能由于跨域或安全策略无法直接加载本地文件。最稳妥的方式是使用 CDN 链接,并且在本地开启一个简单的 HTTP 服务(如npx serve),而不是直接用file://协议打开。

9. 如何让 AI 生成更靠谱的完整游戏代码

从这次横评中,我们可以提炼出几条实用建议,它们不仅适用于 DeepSeek 和 Kimi,也适用于任何 AI 编程助手。

9.1 提示词要“结构化”,而不是“描述感受”

不推荐这样写:

帮我写一个我的世界网页版,要好玩一点。

推荐这样写:

使用 Three.js 和单个 HTML 文件,实现一个第一人称 3D 沙盒游戏。要求:地面由 20x20 个方块组成,支持 WASD 移动、鼠标旋转、左键移除方块、右键在选中方块的相邻位置放置方块,并提供操作 UI 提示。

结构化提示词的核心是把功能拆分成可验证的条目。每个条目最好都能通过一个操作测试来验证是否完成,例如“左键点击后方块消失”。这样你就能快速判断 AI 是否真正理解了需求。

9.2 限定技术栈和接口

如果没有明确限制库版本,AI 可能会在两三个库之间摇摆,最终选择它“更熟悉”的库,而不是最适合你的库。你需要在提示词中写明:

  • 使用哪个版本的 Three.js;
  • 是否允许使用 PointerLockControls;
  • 是否必须使用 Raycaster 做拾取;
  • 使用的 CDN 地址。

限制越清晰,生成结果越稳定。

9.3 生成之后先验证,再扩展

很多开发者拿到 AI 生成的代码后,直接复制进项目就开始改业务逻辑,结果浪费了大量时间在排查基础环境问题上。

正确的步骤应该是:

  1. 新建一个独立 HTML 文件,放入 AI 生成的完整代码;
  2. 打开浏览器运行,不修改任何内容;
  3. 验证提示词中的每个需求点;
  4. 如果发现 Bug,先让 AI 阅读自己的代码并给出修复方案;
  5. 修复后再接入真实项目。

9.4 让多个模型互相 review

本次横评中,三个模型写的代码各有特点。你可以先在 DS V4 Pro 上生成一个完整版本,然后把代码粘贴给 Kimi K3,让它找出问题并优化。多模型交叉验证,往往比自己盯着代码找 Bug 更快。

9.5 把 AI 当“实习生”,不要当“架构师”

AI 可以快速搭出原型,但它不会主动考虑你的项目结构、命名规范、错误处理策略。如果你要做一个长期维护的产品,建议用 AI 生成模块级别的代码,而不是让它生成整个项目然后直接上线。架构设计、代码分层、关键算法还是需要你自己把关。

10. 下一步还能怎么玩

这次测试证明了一件事:AI 有能力生成可运行的 3D 小游戏,而且当前最强的模型已经能一次完成大部分功能。如果你对“网页版我的世界”这个项目感兴趣,还可以继续在这些方向扩展:

  • 黑色/白色方块纹理:用 Canvas 生成材质贴图,模仿经典 MC 的像素风;
  • 方块类型切换:在 UI 中加入“草块”“石头”“木头”等按钮,切换不同颜色材质;
  • 重力与碰撞:给玩家添加一个胶囊体,实现落地和阻挡;
  • 保存与加载:使用 localStorage 存储方块坐标和类型,刷新页面后还原世界;
  • 多人协同:用 WebSocket 同步多个玩家的方块操作,变成一个小型多人沙盒。

这些扩展方向都可以继续使用 AI 编程助手协助完成。你只要把新需求细化成描述条目,粘贴到原来的完整代码后面,让模型基于已有代码进行增量修改。

从实际工程角度看,AI 编程的核心价值不是“一键生成一个游戏”,而是“帮你快速试错原型”,让你在很短时间内验证一个想法是否可行。当你能熟练地把需求拆成结构化提示词,再配合一套通用的验证流程,你会发现 AI 编程助手的生产力释放程度远超预期。

希望这篇横评能帮到正在评估不同大模型代码能力的你。如果你手边有最新版本的模型,也建议用这份提示词做一次同类测试,结果可能会更有意思。

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/9/6 14:28:10

Spring Boot + Vue 全栈开发勤工俭学系统:毕设避坑指南

简介&#xff1a;这是一份面向高校计算机相关专业毕业设计的完整论文文档&#xff0c;主题为校园勤工俭学兼职系统。系统基于B/S架构&#xff0c;采用Java、Spring Boot框架&#xff0c;搭配Eclipse、Maven、Mariadb 10.5和Tomcat 8.5等主流工具&#xff0c;前端使用HTML5与CSS…

作者头像 李华
网站建设 2026/9/6 14:24:55

VM虚拟机环境隔离与验证:从安装配置到沙箱排查的完整指南

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华
网站建设 2026/9/6 14:24:08

PLC运料小车控制:STL步进编程与手动自动切换调试全攻略

简介&#xff1a;一份面向电气自动化、机电一体化专业学生和PLC入门工程师的完整课程设计报告&#xff0c;围绕运料小车控制系统展开&#xff0c;完整覆盖从需求分析、硬件选型、主接线设计到程序实现与调试的每一步骤。包体为单个Word文档&#xff0c;约1.28MB&#xff0c;内容…

作者头像 李华
网站建设 2026/9/6 14:23:58

基于A3C的无人机三维路径规划:MATLAB异步强化学习实战

简介&#xff1a;面向熟悉MATLAB与强化学习基础、从事无人机路径规划或智能控制研发的工程师&#xff0c;这份完整的A3C三维路径规划项目实例&#xff0c;以异步优势演员-评论家算法为核心&#xff0c;解决无人机在复杂动态三维环境中高维连续动作空间建模难、训练效率低和收敛…

作者头像 李华
网站建设 2026/9/6 14:22:05

FPGA面试高频考点精讲:时序约束与跨时钟域处理

简介&#xff1a;这是一份面向FPGA工程师、校招和社招求职者的面试笔试题目大全&#xff0c;附带详细答案解析&#xff0c;直击备考最常被问到的数字逻辑与时序设计考点。题集围绕同步逻辑与异步逻辑、同步电路与异步电路的区别、时序设计的实质、建立时间与保持时间、亚稳态及…

作者头像 李华
网站建设 2026/9/6 14:20:53

树莓派Pico定时器采样消抖:旋转编码器稳定读取方案

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华