第 1 篇:Three.js 是什么,以及它在数字孪生中负责什么 第 1 篇Three.js 是什么以及它在数字孪生中负责什么本文是“使用 Three.js 构建转炉数字孪生系统”系列的导读篇。本文不急于讲具体 API而是先解决一个更重要的问题Three.js 在数字孪生系统中究竟处于什么位置它负责什么又不负责什么。一、为什么要先理解 Three.js 的职责边界很多初学者第一次接触数字孪生时容易产生一个误解只要学习 Three.js就可以完成整个数字孪生系统。实际上Three.js 只是数字孪生系统中的一个重要组成部分主要负责浏览器中的三维场景构建、渲染、动画和交互。一个完整的转炉数字孪生系统通常还需要处理以下问题转炉、氧枪、烟罩、钢包等设备的三维模型从哪里来PLC、传感器和生产系统中的数据如何获取实时数据如何传输到浏览器温度、重量、角度、流量等数据如何保存设备状态和生产阶段如何判断报警、权限、报表和历史回放如何实现三维模型如何根据实时数据发生变化。Three.js 能够解决其中的“三维可视化”问题但不能单独解决整个数字孪生系统的全部问题。因此在开始学习具体代码之前需要先建立一个清晰认识Three.js 是数字孪生三维前端的核心渲染工具但不是完整的数字孪生平台。二、Three.js、WebGL 和 WebGPU 是什么关系理解 Three.js首先要分清 GPU、WebGL、WebGPU 和 Three.js 所处的技术层级。可以将它们理解为下面的关系数字孪生业务功能 ↓ Three.js 三维开发框架 ↓ WebGL / WebGPU 图形接口 ↓ 浏览器 ↓ 显卡 GPU它们并不是相互替代的三个同类框架而是位于不同层级。三、WebGL 是什么WebGL 是浏览器提供的一套图形编程接口。它允许 JavaScript 程序使用计算机或移动设备的 GPU在网页的canvas元素中绘制二维和三维图形。如果直接使用 WebGL 开发三维场景开发者通常需要自己处理很多底层内容例如创建和编译着色器创建顶点缓冲区将顶点数据上传到 GPU配置纹理创建投影矩阵和视图矩阵管理渲染状态编写逐帧渲染逻辑处理光照、材质和阴影算法。这些内容非常接近底层图形学代码量大学习成本也比较高。对于数字孪生项目而言我们通常不希望从最底层重新实现一套三维引擎因此需要一个更高层的开发工具这就是 Three.js 的价值。四、WebGPU 是什么WebGPU 是面向现代 GPU 设计的新一代 Web 图形与计算接口。与 WebGL 相比WebGPU 更接近现代原生图形 API 的设计方式并且除了图形渲染以外还能够更好地支持通用 GPU 计算。从发展方向上看可以简单理解为WebGL当前广泛使用的浏览器图形接口 WebGPU面向现代 GPU 的新一代图形与计算接口但是这并不意味着学习 Three.js 时必须先精通 WebGL 或 WebGPU。对于初学者更合理的学习顺序是先掌握 Three.js 的场景、相机、模型、材质、灯光和动画理解渲染器负责将场景提交给底层图形接口在项目需要更高级渲染或 GPU 计算时再深入学习 WebGL、WebGPU 和着色器。当前 Three.js 提供了不同的渲染器。WebGLRenderer使用 WebGL 2 渲染场景WebGPURenderer则会优先尝试 WebGPU 后端并可在不支持时回退到 WebGL 2 后端。需要注意的是渲染后端的选择还会受到浏览器环境、Three.js 版本、项目所使用的材质、后处理功能和兼容性要求影响。因此在实际工业项目中应当以目标设备测试结果为准而不是单纯追求更新的技术名称。五、Three.js 是什么Three.js 是一个用于在浏览器中创建三维内容的 JavaScript 库。它对 WebGL 和 WebGPU 等底层图形接口进行了更高层的封装使开发者可以使用更容易理解的对象组织三维程序。例如在 Three.js 中我们可以直接使用以下概念Scene场景Camera相机Mesh三维网格对象Geometry几何结构Material材质Light灯光Texture纹理AnimationMixer模型动画控制器WebGLRenderer或WebGPURenderer渲染器。如果不使用 Three.js开发者可能需要编写大量矩阵计算、缓冲区管理和着色器代码。使用 Three.js 后我们可以通过更接近三维软件思维的方式描述场景constscenenewTHREE.Scene();constcameranewTHREE.PerspectiveCamera(60,window.innerWidth/window.innerHeight,0.1,2000);constrenderernewTHREE.WebGLRenderer({antialias:true});renderer.setSize(window.innerWidth,window.innerHeight);document.body.appendChild(renderer.domElement);这段代码创建了一个场景、一台透视相机和一个渲染器。Three.js 会在内部帮助我们处理大量底层图形工作。因此可以将 Three.js 理解为位于业务代码和底层 GPU 图形接口之间的三维开发层。六、Three.js 在数字孪生系统中的位置一个较完整的数字孪生系统可以分为多个层级。┌──────────────────────────────────────────┐ │ 用户界面层 │ │ 菜单、面板、报警、趋势图、生产信息、按钮 │ ├──────────────────────────────────────────┤ │ 三维可视化应用层 │ │ 场景管理、模型交互、状态映射、动画控制 │ ├──────────────────────────────────────────┤ │ Three.js │ │ 模型、相机、灯光、材质、动画、渲染 │ ├──────────────────────────────────────────┤ │ WebGL / WebGPU │ ├──────────────────────────────────────────┤ │ 浏览器与 GPU │ └──────────────────────────────────────────┘ ↑ HTTP / WebSocket / MQTT 等 ↑ ┌──────────────────────────────────────────┐ │ 后端与数字孪生服务层 │ │ 数据接口、设备状态、业务规则、历史回放 │ ├──────────────────────────────────────────┤ │ 数据存储层 │ │ 关系数据库、时序数据库、缓存、文件存储 │ ├──────────────────────────────────────────┤ │ 设备与数据源层 │ │ PLC、传感器、控制系统、MES、模型计算结果 │ └──────────────────────────────────────────┘在这套架构中Three.js 主要位于浏览器前端的三维可视化部分。它接收已经整理好的模型和状态数据并将这些内容以三维形式展示给用户。例如后端向前端传递以下数据{converterAngle:-86.5,oxygenLanceHeight:1.8,steelTemperature:1652,oxygenFlow:23800,smeltingStage:blowing,alarmLevel:1}Three.js 不负责判断这些数据是怎样从 PLC 中读取出来的也不负责将数据写入数据库。Three.js 前端通常只需要将数据转换成可视化状态例如将converterAngle转换为转炉模型的旋转角度将oxygenLanceHeight转换为氧枪模型的位置将steelTemperature转换为炉内颜色或发光强度将oxygenFlow转换为氧气流粒子数量或速度将smeltingStage转换为当前工艺阶段动画将alarmLevel转换为设备高亮、闪烁或报警标记。因此Three.js 在数字孪生系统中的核心工作是将设备、空间、状态和过程数据转化为可观察、可交互的三维画面。七、Three.js 能做什么1. 构建三维场景Three.js 可以创建完整的三维空间包括场景相机灯光地面厂房转炉本体氧枪烟罩钢包管道操作平台其他辅助设备。这些对象可以按照真实设备的空间关系组织起来。2. 加载三维模型数字孪生项目通常不会完全依靠代码创建复杂设备而是先使用 Blender、3ds Max、Maya、SolidWorks 或其他建模工具制作模型再导出为浏览器适合使用的格式。Three.js 常用的模型格式是 glTF其文件扩展名通常为.gltf .glb通过GLTFLoaderThree.js 可以将设备模型加载到场景中。import{GLTFLoader}fromthree/addons/loaders/GLTFLoader.js;constloadernewGLTFLoader();loader.load(/models/converter.glb,(gltf){scene.add(gltf.scene);});3. 控制设备的位置和姿态Three.js 可以控制模型的位置旋转缩放显示与隐藏父子层级关系。在转炉数字孪生中可以使用旋转表示转炉倾动converter.rotation.zTHREE.MathUtils.degToRad(converterAngle);也可以根据实时数据控制氧枪升降oxygenLance.position.ycalculateLancePosition(lanceHeight);4. 设置材质、颜色、透明度和发光效果Three.js 可以控制设备表面的视觉效果例如正常状态显示为灰色运行状态显示为绿色高温区域显示为红色或橙色报警设备显示为红色并闪烁被选中的设备显示轮廓高亮烟气、火焰和液体使用透明或发光材质。这些效果可以帮助用户快速理解设备当前状态。5. 创建动画Three.js 可以实现多种动画转炉倾动氧枪升降钢包运输炉门开关机械臂运动模型自带关键帧动画生产流程演示历史数据回放相机巡检动画。动画既可以由时间驱动也可以由实时生产数据驱动。6. 实现鼠标交互Three.js 可以配合射线检测实现模型选择。用户点击设备后可以高亮设备弹出设备信息显示实时参数切换观察视角进入设备内部查看报警记录打开设备控制面板。需要注意的是Three.js 可以判断用户点击了哪个三维对象但具体弹出什么内容、能否执行操作仍然属于前端业务逻辑。7. 实现粒子和特殊效果在转炉数字孪生系统中可能需要展示火焰烟气粉尘氧气流钢水火花热辐射流场结果温度云图。Three.js 可以通过粒子系统、透明材质、自定义着色器、后处理和动态纹理实现这些效果。但需要区分Three.js 可以负责“显示仿真结果”不一定负责“计算仿真结果”。例如计算流体力学软件可以计算烟气速度场Three.js 再将计算结果以粒子或云图形式展示出来。8. 实现多视角和空间导航Three.js 可以实现鼠标旋转、缩放和平移第一人称漫游固定监控视角设备聚焦鸟瞰视角局部剖切视角不同工位之间快速跳转相机自动巡航。这对于大型厂区和复杂设备观察非常重要。八、Three.js 不能负责什么明确 Three.js 不能负责什么比知道它能做什么更加重要。1. Three.js 不负责三维模型生产Three.js 可以加载和显示模型但它不是专业的工业建模软件。复杂的转炉、氧枪、烟道和厂房模型通常需要在其他工具中完成Blender3ds MaxMayaSolidWorksCreoCATIARevit其他 CAD 或 BIM 工具。Three.js 可以使用代码创建简单几何体但不适合直接完成复杂工业设备的精细建模。2. Three.js 不负责采集 PLC 和传感器数据Three.js 本身不会直接读取PLC温度传感器压力传感器编码器流量计工业相机MESSCADADCS。这些数据通常需要由边缘网关、数据采集程序或后端服务读取和转换。3. Three.js 不负责工业通信协议Three.js 不是工业协议解析工具。它不会自动处理OPC UAModbus TCPPROFINETEtherNet/IPMQTT各类厂商私有协议。浏览器前端通常通过 HTTP、WebSocket 或其他 Web 接口获取后端已经处理过的数据。4. Three.js 不负责数据库Three.js 不负责长期保存设备实时数据历史温度冶炼批次报警记录操作日志模型版本用户信息。这些内容需要保存在关系数据库、时序数据库、缓存系统或对象存储中。5. Three.js 不负责业务规则例如下面这些判断通常不应直接交给 Three.js当前是否已经进入吹炼阶段氧枪位置是否超过安全范围转炉是否允许倾动当前炉次是否结束温度是否满足出钢条件报警是否需要升级某个用户是否具有控制权限。这些逻辑通常属于后端服务、控制系统或独立的业务规则模块。Three.js 主要负责根据判断结果改变画面。6. Three.js 不负责科学计算和机理仿真Three.js 可以运行一些数学计算也可以通过 WebGPU 或着色器使用 GPU但它本身不是专业的CFD 求解器有限元求解器热力学计算平台冶金反应模型过程控制模型人工智能训练框架。如果项目需要预测钢水温度、碳含量、炉气成分或流场变化通常需要由后端算法、专业仿真软件或机器学习模型完成计算。Three.js 可以负责将计算结果可视化。7. Three.js 不负责完整的二维界面系统数字孪生系统除了三维场景还需要大量二维界面登录页菜单参数面板趋势图报警列表表格弹窗权限管理页面路由。这些内容通常需要结合 Vue、React 或其他前端框架实现。Three.js 和 Vue、React 并不是竞争关系。一种常见组合是Vue / React负责页面、组件、状态和业务界面 Three.js负责三维场景、模型、动画和空间交互 ECharts负责二维图表和趋势曲线九、转炉数字孪生三维前端的基本结构一个适合逐步扩展的转炉数字孪生前端可以拆分为以下模块。src/ ├─ three/ │ ├─ core/ │ │ ├─ SceneManager.js │ │ ├─ CameraManager.js │ │ ├─ RendererManager.js │ │ └─ RenderLoop.js │ │ │ ├─ loaders/ │ │ ├─ ModelLoader.js │ │ └─ TextureLoader.js │ │ │ ├─ equipment/ │ │ ├─ ConverterController.js │ │ ├─ OxygenLanceController.js │ │ ├─ HoodController.js │ │ └─ LadleController.js │ │ │ ├─ interaction/ │ │ ├─ RaycastManager.js │ │ ├─ SelectionManager.js │ │ └─ CameraNavigation.js │ │ │ ├─ effects/ │ │ ├─ FlameEffect.js │ │ ├─ SmokeEffect.js │ │ ├─ SparkEffect.js │ │ └─ AlarmHighlight.js │ │ │ ├─ data/ │ │ ├─ TwinDataAdapter.js │ │ ├─ EquipmentStateMapper.js │ │ └─ PlaybackController.js │ │ │ └─ performance/ │ ├─ ResourceManager.js │ ├─ LODManager.js │ └─ PerformanceMonitor.js │ ├─ api/ │ ├─ equipmentApi.js │ └─ historyApi.js │ ├─ stores/ │ └─ twinStore.js │ ├─ components/ │ ├─ TwinCanvas.vue │ ├─ EquipmentPanel.vue │ ├─ AlarmPanel.vue │ └─ TrendChart.vue │ └─ views/ └─ ConverterTwinView.vue这个目录不是唯一标准但它体现了一个重要原则不要将模型加载、数据通信、动画、交互和所有设备逻辑全部写在同一个文件中。十、三维前端中各模块分别负责什么1. 场景核心模块负责创建和维护场景相机渲染器灯光渲染循环浏览器窗口尺寸变化页面销毁时的资源释放。这是 Three.js 应用的基础设施。2. 模型资源模块负责加载.glb或.gltf模型加载纹理显示加载进度缓存已加载资源处理加载失败查找模型中的关键节点统一材质和阴影设置。例如加载转炉模型后需要找到其中的可运动节点constconverterBodymodel.getObjectByName(ConverterBody);constoxygenLancemodel.getObjectByName(OxygenLance);consthoodmodel.getObjectByName(Hood);因此建模阶段的节点命名会直接影响 Three.js 程序的可维护性。3. 设备控制模块每一种关键设备都可以拥有自己的控制器。例如ConverterController可以负责设置转炉角度播放倾动动画切换转炉运行状态设置报警高亮恢复默认状态。classConverterController{constructor(model){this.modelmodel;}setAngle(angle){this.model.rotation.zTHREE.MathUtils.degToRad(angle);}setVisible(visible){this.model.visiblevisible;}}这样可以避免在页面组件中到处直接修改模型属性。4. 数据适配模块后端数据结构和 Three.js 对象结构通常并不相同因此需要一个数据适配层。functionapplyTwinData(data,controllers){controllers.converter.setAngle(data.converterAngle);controllers.oxygenLance.setHeight(data.oxygenLanceHeight);controllers.flame.setFlow(data.oxygenFlow);controllers.converter.setAlarmLevel(data.alarmLevel);}这个模块负责将“生产数据”翻译成“三维状态”。它是数字孪生前端中非常关键的一层。5. 交互模块负责鼠标点击鼠标悬停设备选择轮廓高亮相机聚焦标签显示设备信息面板联动。交互模块不应直接承担设备业务逻辑而是将用户操作转换成事件。6. 特效模块负责火焰、烟气、火花、钢水、报警和后处理效果。特效模块需要特别注意性能因为透明粒子、大量动态对象、阴影和后处理都可能增加 GPU 负担。7. 性能和资源管理模块工业数字孪生场景往往包含大量模型因此需要处理模型面数纹理尺寸材质数量Draw CallLOD实例化渲染不可见对象剔除资源缓存几何体和材质释放帧率监控。性能优化不是项目完成后的附加工作而应从模型制作和系统架构阶段开始考虑。十一、转炉数字孪生前端的数据流一个典型的实时数据流可以表示为PLC / 传感器 / MES ↓ 数据采集与协议转换 ↓ 后端数字孪生服务 ↓ HTTP / WebSocket ↓ 前端状态管理 ↓ TwinDataAdapter ↓ 设备控制器 ↓ Three.js 场景对象 ↓ 渲染器 ↓ 浏览器画面在前端程序中不建议让 WebSocket 回调直接修改模型。更合理的方式是socket.onmessage(event){constdataJSON.parse(event.data);twinStore.updateRealtimeData(data);};然后由统一的数据同步模块更新三维对象functionsyncTwinScene(){constdatatwinStore.realtimeData;converterController.setAngle(data.converterAngle);lanceController.setHeight(data.oxygenLanceHeight);flameEffect.setFlow(data.oxygenFlow);}这样做的优点包括数据通信和三维渲染相互解耦后续可以方便地切换实时模式和历史回放模式设备控制逻辑更容易测试页面组件不需要了解模型内部结构项目规模扩大后更容易维护。十二、一个最小的转炉三维前端应该包含什么对于刚开始学习 Three.js 的开发者第一个版本不需要直接实现完整的转炉数字孪生系统。可以先完成一个最小可运行版本。第一阶段显示场景实现场景相机渲染器灯光地面轨道控制器浏览器窗口自适应。第二阶段加载转炉模型实现加载.glb模型显示加载进度调整模型位置和比例查找转炉和氧枪节点。第三阶段控制设备运动实现输入角度控制转炉旋转输入高度控制氧枪升降按钮切换不同生产阶段使用补间动画让运动更加平滑。第四阶段接入模拟数据先不连接真实 PLC而是使用模拟数据constmockData{converterAngle:-45,oxygenLanceHeight:2.4,oxygenFlow:21000,steelTemperature:1620,smeltingStage:blowing};通过模拟数据验证三维状态映射逻辑。第五阶段接入后端实时数据当三维逻辑稳定后再接入HTTP 接口WebSocket实时设备数据历史数据报警数据。这种开发顺序可以降低初学者同时面对三维、后端和工业数据的难度。十三、学习 Three.js 时最容易出现的三个误区误区一认为 Three.js 就是数字孪生Three.js 是数字孪生的三维呈现工具之一。没有实时数据、状态映射和业务逻辑的三维模型只能称为三维展示不能自动成为完整的数字孪生系统。误区二一开始就追求真实工业画质工业数字孪生最重要的是数据是否正确设备状态是否对应动画是否符合真实机械关系信息是否清晰系统是否稳定操作是否流畅。画面真实感很重要但不应优先于数据正确性和系统可用性。误区三将全部代码写进一个页面初学阶段把所有代码写在一个文件中看起来比较简单。但是随着设备数量增加代码很快会混合以下内容场景初始化模型加载动画WebSocket数据解析鼠标交互报警效果页面按钮资源释放。因此即使是第一个项目也应该逐步建立模块化意识。十四、本文总结通过本文需要建立以下几个核心认识。1. WebGL 和 WebGPU 是底层图形接口它们负责让浏览器程序使用 GPU 完成图形渲染或计算。2. Three.js 是更高层的三维开发库它对底层图形接口进行了封装让开发者可以通过场景、相机、模型、材质和灯光等对象构建三维应用。3. Three.js 位于数字孪生系统的前端可视化层它主要负责显示三维设备组织三维场景控制设备动画映射实时状态实现空间交互展示特效和仿真结果。4. Three.js 不能代替完整的数字孪生系统它不能独立负责PLC 数据采集工业协议解析数据库存储后端服务业务规则权限系统专业机理仿真复杂工业模型制作。5. 转炉数字孪生前端应该采用模块化结构至少应逐步拆分场景核心模型加载设备控制数据适配用户交互三维特效性能和资源管理。最终可以用一句话概括 Three.js 在转炉数字孪生中的职责Three.js 不负责产生工业数据而是负责将工业设备、实时数据和运行过程组织成可观察、可交互的三维世界。十五、下一篇学习内容完成本文后下一篇可以开始进入 Three.js 的基础结构第 2 篇Three.js 场景、相机、渲染器与动画循环下一篇将重点介绍Scene的作用透视相机和正交相机WebGLRenderer的基本配置requestAnimationFrame动画循环浏览器窗口尺寸自适应Three.js 程序的基本执行流程如何搭建第一个可运行的转炉三维场景骨架。参考资料Three.js 官方网站Three.js 官方文档Three.js 官方手册Three.js WebGLRenderer 文档Three.js WebGPURenderer 文档MDNWebGL APIMDNWebGPU APIW3CWebGPU 规范