当前位置: 首页 > news >正文

3D地球可视化教程 - 第1篇:基础地球渲染系统

最终效果:
动图只能限制5m以内,所以画质相当低

在这里动图只能限制5m以内,所以画质相当低插入图片描述
本节完成后的效果:
在这里插入图片描述

难度: ⭐⭐☆☆☆ 初级
预计时间: 30分钟
技术栈: Vue3 + Vite + Three.js

📖 教程简介

欢迎来到3D地球可视化的完整教程系列!在这个系列中,我们将从零开始,一步步构建一个专业级的3D地球项目。本篇是系列的第一篇,我们将学习如何创建一个基础但完整的3D地球渲染系统。

🎯 本篇学习目标

  • 理解Three.js的核心概念和渲染管道
  • 掌握3D场景的基础搭建方法
  • 学会创建真实感地球渲染效果
  • 实现基础的相机控制和交互

🏆 最终效果预览

完成本篇教程后,你将获得:

  • ✅ 一个可交互的3D地球
  • ✅ 真实的地球纹理效果
  • ✅ 专业的光照系统
  • ✅ 流畅的鼠标控制

🧠 理论基础

Three.js核心概念

在开始编码之前,我们需要理解Three.js的几个核心概念:

1. 渲染三要素
// Three.js的渲染三要素
const scene = new THREE.Scene();        // 场景 - 3D世界的容器
const camera = new THREE.Camera();      // 相机 - 观察3D世界的视角  
const renderer = new THREE.Renderer();  // 渲染器 - 将3D场景绘制到屏幕
2. 物体构成
// 3D物体 = 几何体 + 材质
const geometry = new THREE.SphereGeometry(); // 几何体 - 物体的形状
const material = new THREE.Material();       // 材质 - 物体的外观
const mesh = new THREE.Mesh(geometry, material); // 网格 - 最终的3D物体
3. 地球渲染原理
  • 使用 SphereGeometry 创建球体几何
  • 通过 MeshPhongMaterial 实现光照效果
  • 加载真实的地球纹理贴图
  • 配置光源系统营造真实感

🛠️ 项目架构设计

目录结构规划

src/
├── components/
│   └── three/
│       ├── models/
│       │   ├── EarthDay/        # 地球白天渲染
│       │   ├── Lights/          # 光照系统
│       │   └── Scene/           # 场景管理
│       └── utils/
│           └── EarthController/ # 地球控制器
├── constants/
│   └── index.js                 # 常量配置
└── assets/└── textures/               # 纹理资源

核心类设计

  1. Scene - 场景管理器(单例模式)
  2. EarthDay - 地球渲染器
  3. Lights - 光照系统
  4. EarthController - 交互控制器

🎨 Step 1: 地球几何体创建

1.1 球体几何体

地球的形状使用Three.js的球体几何体:

// src/components/three/models/EarthDay/EarthDay.js
createGeometry() {// 创建球体几何体this.geometry = new THREE.SphereGeometry(EARTH_RADIUS,      // 半径: 10EARTH_FRAGMENTS,   // 宽度分段: 64 EARTH_FRAGMENTS    // 高度分段: 64);
}

参数解释:

  • radius: 球体半径,决定地球大小
  • widthSegments: 水平方向分段数,影响球体圆滑度
  • heightSegments: 垂直方向分段数,影响球体圆滑度

💡 技巧: 分段数越高球体越圆滑,但性能消耗也越大。64是一个平衡点。

1.2 材质系统

使用Phong材质实现真实的光照效果:

createMaterial() {this.material = new THREE.MeshPhongMaterial({// 🎨 纹理贴图map: this.textures.day,           // 地球表面颜色贴图bumpMap: this.textures.bump,      // 凹凸贴图(山脉、海沟)specularMap: this.textures.specular, // 镜面反射贴图(海洋反光)// 🎭 基础属性  color: new THREE.Color("#ffffff"),opacity: 1.0,transparent: true,// ✨ Phong光照属性emissive: new THREE.Color("#000000"),    // 自发光颜色emissiveIntensity: 0.0,                  // 自发光强度specular: new THREE.Color("#111111"),    // 镜面反射颜色shininess: 30,                           // 光泽度bumpScale: 12.4,                         // 凹凸强度});
}

材质属性详解:

  • map: 主纹理,决定地球表面的颜色
  • bumpMap: 凹凸贴图,模拟地形高低起伏
  • specularMap: 镜面贴图,控制海洋的反光效果
  • shininess: 光泽度,数值越高反光越强

💡 Step 2: 光照系统设计

2.1 光源类型分析

我们的地球使用了多种光源组合:

// src/components/three/models/Lights/Lights.js
class Lights {constructor(parentContainer, camera, controls, options) {// 🌞 方向光 - 模拟太阳光this.directionalLight = new THREE.DirectionalLight("#ffffff",  // 白色光5.1         // 强度);// 🌙 环境光 - 模拟天空散射光this.ambientLight = new THREE.AmbientLight("#ffffff",  // 白色光2.45        // 强度);// 🔆 点光源 - 模拟城市灯光this.pointLight = new THREE.PointLight("#ff6600",  // 橙色光2.0,        // 强度500,        // 照射距离0           // 衰减系数);}
}

2.2 光照效果原理

方向光 (DirectionalLight):

  • 模拟太阳光,平行光线
  • 产生明确的明暗对比
  • 支持阴影投射

环境光 (AmbientLight):

  • 模拟天空散射光
  • 均匀照亮所有物体
  • 避免过暗的阴影区域

点光源 (PointLight):

  • 模拟城市灯光效果
  • 从一个点向四周发散
  • 可设置衰减距离

🎬 Step 3: 场景管理系统

3.1 单例模式设计

场景管理器使用单例模式,确保全局唯一:

// src/components/three/models/Scene/Scene.js
class Scene {static instance = null;constructor(container, options) {// 防止多实例if (Scene.instance) {return Scene.instance;}Scene.instance = this;this.init();}static getInstance() {return Scene.instance;}
}

3.2 组件组织结构

使用分组管理不同类型的组件:

init() {// 🌍 地球主组this.earthGroup = new THREE.Group();// 💡 灯光子组 (固定位置,不随地球旋转)this.lightsGroup = new THREE.Group();this.earthGroup.add(this.lightsGroup);// 🌐 元素子组 (跟随地球旋转)this.elementsGroup = new THREE.Group();this.earthGroup.add(this.elementsGroup);this.scene.add(this.earthGroup);
}

🎮 Step 4: 交互控制系统

4.1 自定义控制器

项目使用自定义的地球控制器替代标准的OrbitControls:

// src/components/three/utils/EarthMouseController.js
class EarthMouseController {constructor(camera, renderer, earthGroup, elementsGroup, scene) {this.camera = camera;this.renderer = renderer;this.earthGroup = earthGroup;        // 整个地球组this.elementsGroup = elementsGroup;  // 只旋转元素组this.setupEventListeners();}setupEventListeners() {// 鼠标事件监听this.renderer.domElement.addEventListener('mousedown', this.onMouseDown);this.renderer.domElement.addEventListener('mousemove', this.onMouseMove);this.renderer.domElement.addEventListener('mouseup', this.onMouseUp);this.renderer.domElement.addEventListener('wheel', this.onWheel);}
}

4.2 旋转逻辑分离

设计亮点: 灯光固定,只旋转地球元素

onMouseMove(event) {if (this.isMouseDown) {const deltaX = event.clientX - this.mouse.x;const deltaY = event.clientY - this.mouse.y;// 🌍 只旋转元素组,灯光保持固定this.elementsGroup.rotation.y += deltaX * 0.005;this.elementsGroup.rotation.x += deltaY * 0.005;// 💡 灯光组不旋转,保持照射方向}
}

🖼️ Step 5: 纹理系统实现

5.1 纹理加载策略

async loadTextures() {const textureLoader = new THREE.TextureLoader();// 并行加载多张纹理const [dayTexture, bumpTexture, specularTexture] = await Promise.all([this.loadTexture(textureLoader, './textures/earth-day.jpg'),this.loadTexture(textureLoader, './textures/earth-bump.jpg'),this.loadTexture(textureLoader, './textures/earth-specular.jpg'),]);// 设置纹理属性dayTexture.colorSpace = THREE.SRGBColorSpace;     // 颜色空间dayTexture.anisotropy = renderer.capabilities.getMaxAnisotropy(); // 各向异性过滤
}

5.2 纹理类型说明

  • Day Texture: 地球表面的彩色贴图
  • Bump Map: 黑白高度图,模拟地形起伏
  • Specular Map: 控制反光强度,海洋更亮,陆地更暗

🎯 Step 6: 完整实现代码

6.1 主要的实现要点

让我们看看当前的核心实现:

  1. 地球几何体创建
  2. Phong材质配置
  3. 多光源照明
  4. 纹理系统
  5. 交互控制

🎯 关键参数配置

// src/constants/index.js
export const EARTH_RADIUS = 20;        // 地球半径
export const EARTH_FRAGMENTS = 64;     // 球体分段数
export const AUTO_ROTATE_SPEED = 0.03; // 自动旋转速度// 纹理路径配置
export const PATHS = {earthMap: "./img/earth-day.jpg",      // 地球白天贴图bumpMap: "./img/bump-map.webp",       // 凹凸贴图specularMap: "./img/specular-map.webp", // 镜面贴图
};

🚀 运行和测试

启动项目

npm run dev

测试功能

在浏览器中你应该看到:

  • ✅ 一个完整的3D地球
  • ✅ 真实的地球纹理
  • ✅ 鼠标拖拽旋转功能
  • ✅ 滚轮缩放功能

📊 性能优化要点

1. 纹理优化

  • 使用WebP格式减少文件大小
  • 设置合适的anisotropy值
  • 启用纹理预加载

2. 几何体优化

  • 64分段是性能和质量的平衡点
  • 避免过高的分段数
  • 复用几何体实例

✅ 已掌握的技能:

  1. Three.js基础概念
  2. 地球几何体创建
  3. Phong材质系统
  4. 多光源照明
  5. 纹理贴图系统
  6. 交互控制系统

🎯 下一篇预告

第2篇:夜晚纹理与昼夜过渡效果



文章转载自:

http://raIi4wDC.fjmfq.cn
http://yC9gjMtQ.fjmfq.cn
http://storzuKx.fjmfq.cn
http://qj12ubne.fjmfq.cn
http://gKUXLBhE.fjmfq.cn
http://cofYrRtR.fjmfq.cn
http://FXUe7ZGp.fjmfq.cn
http://QeMLWptP.fjmfq.cn
http://NOUBgH5C.fjmfq.cn
http://ELr1SwVa.fjmfq.cn
http://DnUQ3ESI.fjmfq.cn
http://QY7z30Fa.fjmfq.cn
http://K50n0g99.fjmfq.cn
http://GzotIziN.fjmfq.cn
http://PLWX7VYu.fjmfq.cn
http://whUNVKTU.fjmfq.cn
http://ds28ct2v.fjmfq.cn
http://mUMKf1NE.fjmfq.cn
http://p31zESkC.fjmfq.cn
http://9eUxxHgm.fjmfq.cn
http://R6eAWygT.fjmfq.cn
http://k1UuGzki.fjmfq.cn
http://CwJ3oawK.fjmfq.cn
http://jY02Ov3c.fjmfq.cn
http://za4SmUEK.fjmfq.cn
http://rlqwSb1Q.fjmfq.cn
http://2cyLpPGO.fjmfq.cn
http://92a1kVRY.fjmfq.cn
http://dENTHvGb.fjmfq.cn
http://AHs2OyHh.fjmfq.cn
http://www.dtcms.com/a/373081.html

相关文章:

  • 单片机开发
  • LLMs之REFRAG:《REFRAG: Rethinking RAG based Decoding》的翻译与解读
  • MATLAB的数值计算(二)线性方程求解
  • Java基础(十一):关键字final详解
  • Java全栈开发面试实录:从基础到微服务的实战经验分享
  • Matlab机器人工具箱使用1 简单的描述类函数
  • 自动捕鱼器设计cad+设计说明书+三维图
  • 深入理解 MyBatis-Plus 的 `ServiceImpl`
  • 软件可靠性定量核心指标与关系深入解析
  • Android音频学习(十七)——音频数据流转
  • 如何一次性将多个PPT幻灯片批量转换成PDF文档
  • Vue响应式底层原理:深入解析依赖追踪机制
  • 抖音批量上传视频怎么弄?抖音矩阵账号管理的专业指南
  • 数学知识--行向量与矩阵相乘,和矩阵与行向量相乘的区别
  • 【硬件-笔试面试题-70】硬件/电子工程师,笔试面试题(知识点:过压保护电路)
  • PostgreSQL打印实时查询语句(监控PostgreSQL监控)(未成功)
  • “代练护航”小程序API源码搭建:高并发接单系统的技术突破与实战,多端适配与跨平台开发 如何覆盖微信、H5、APP全场景?
  • 从航空FACE的一个落地方案漫谈汽车HPC软件架构的思维转变(1/3)FACE基础概念与落地案例
  • Docker多共享网络配置策略(Docker多网络、Docker networks、Docker Compose网络、Docker网络、Docker共享网络)
  • Terraform 从入门到实战:历史、原理、功能与阿里云/Azure 上手指南
  • 阿里云国际代理:稳定、高效、便捷的数据库服务-云数据库RDS
  • Django中的软删除
  • PyCharm旧版本下载地址
  • 华为USG6000v2 NAT模式下IPSEC IKE V1 实验
  • 深入实践G1垃圾收集器调优:Java应用性能优化实战指南
  • sqlite3的使用
  • LeetCode Hot 100 Python (81~90)
  • LeetCode 面试经典 150 题:删除有序数组中的重复项(双指针思想解法详解)
  • apifox的post的表单提交的gbk的解决方案
  • leetcode算法刷题的第二十九天