Three.js + React 实战系列-3D 个人主页:构建 Hero 场景组件(项目核心)✨
在本节中,我们将完成整个 3D 主业项目中最核心的组件 —— Hero.jsx
。
这个组件作为首页的主视觉部分,整合了 3D 模型、动画相机、交互按钮与自适应布局,构建出一个立体、酷炫、可交互的主场景。
前置准备:
- ✅安装依赖:
npm install three @react-three/fiber @react-three@drei react-responsive leva @gsap/react gsap
包名 | 作用简述 |
---|---|
three | Three.js 本体,WebGL 3D 渲染引擎 |
@react-three/fiber | React 版本的 Three.js 渲染器 |
@react-three/drei | 提供 Three.js 常用封装组件和辅助工具 |
react-responsive | 响应式 Hook(监听设备宽度) |
leva | 一个调试控制面板工具,支持实时调整 3D 属性 |
gsap | 一个高性能、功能丰富的 JavaScript 动画库 |
@gsap/react | GSAP 团队推出的 React 专用集成库 |
🎥 03 · 完成项目核心组件Hero组件
🔍 Hero 组件的作用
Hero.jsx
是网站打开后第一个看到的 3D 场景区域。它承担着两个核心功能:
- 向访客展示个人身份与品牌理念(文本 + 视觉)
- 构建完整的 Three.js 场景:包括模型加载、光源、相机、动画控制等
🧩 涉及的关键技术点
react-three-fiber
:Canvas 渲染、相机控制、模型嵌入@react-three/drei
:相机组件、异步加载react-responsive
:根据屏幕尺寸自适应模型大小与位置- 3D 子组件组合使用:
HackerRoom
、Target
、ReactLogo
、Cube
、Rings
- 相机动画控制:
HeroCamera
- 按钮组件与锚点跳转:
Button
📦 项目结构拆解
在 Hero.jsx
中,组价的层级对应:
Hero.jsx
├── 文本介绍
├── Three.js 场景
│ ├── Canvas
│ │ ├── HeroCamera(自定义动画相机)
│ │ ├── HackerRoom(主模型)
│ │ ├── Target / Cube / Rings / ReactLogo(小精灵)
│ │ ├── ambientLight / directionalLight (环境光 定向光源)
│ │ └── CanvasLoader(加载动画)
└── CTA 按钮(Let's work together)
📐 响应式尺寸控制
const isSmall = useMediaQuery({ maxWidth: 440 });
const isMobile = useMediaQuery({ maxWidth: 768 });
const isTablet = useMediaQuery({ maxWidth: 1024, minWidth: 768 });const sizes = calculateSizes(isSmall, isMobile, isTablet);
这里使用 react-responsive
监听用户设备宽度,并通过 calculateSizes
函数返回对应模型的 scale / position / offset
等数据,确保在手机 / 平板 / PC
上展示效果始终协调。
🎨 Canvas 渲染部分
<Canvas className='w-full h-full'><Suspense fallback={<CanvasLoader />}><PerspectiveCamera makeDefault position={[0, 0, 20]} /><HeroCamera isMobile={isMobile}><HackerRoomscale={sizes.deskScale}position={sizes.deskPosition} rotation={[0, -Math.PI, 0]}/></HeroCamera><group><Target position={sizes.targetPosition} ></Target><ReactLogo position={sizes.reactLogoPosition}></ReactLogo><Cube position={sizes.cubePosition}></Cube><Rings position={sizes.ringPosition}></Rings></group><ambientLight intensity={1} /><directionalLight intensity={0.5} position={[10, 10, 10]} /></Suspense>
</Canvas>
这里是整片场景的构建核心:
-
PerspectiveCamera 设置视角
-
Suspense 管理加载状态
-
HeroCamera 封装了相机动画逻辑(如旋转、缩放)
-
多个 3D 子组件以 group 形式集中管理
-
光源使用了环境光 + 平行光混合
🧮 互动按钮区域
<a href='#about' className='w-fit'><Buttonname="Let's work together"isBeamcontainerClass='sm:w-fit w-full sm:min-w-96'/>
</a>
底部按钮使用自定义 Button 组件,点击后可跳转至页面下方 #about 区域,作为页面导航的核心 CTA(Call To Action)。
✅ 技术亮点总结
技术点 | 描述 |
---|---|
🎛️ useMediaQuery + calculateSizes | 构建响应式模型配置 |
📦 Suspense + CanvasLoader | 优雅管理异步加载 |
🧠 模块化组件划分 | 每个 3D 对象独立封装,易于维护 |
🎥 HeroCamera | 控制相机视角变化,提升动态感 |
🧭 PerspectiveCamera + 光照系统 | 构建真实感场景 |
💬 UI 与 Canvas 叠加展示 | 实现文字/按钮与 3D 并存效果 |
⏭ 下一节预告:组件逐个拆解与优化
我们将在下一篇中开始我们的Work组件
部分,包括:
如果你喜欢这篇文章,欢迎点赞、收藏、留言 💬
我们下一节见!👋