R3F
1. 3D 웹 개발
High Level: R3F
Three.js / Babylon.js
Low Level : WebGL / WebGPU
웹에서 3D를 다루기 위해서는 웹 표준 기술인 WebGL 혹은 WebGPU를 사용해야 한다.
하지만 이 기술은 파이프라인, 쉐이더, 수학에 대한 이해가 필요하며, 이를 통해 코드를 작성하는 것은 매우 어렵다.
이 복잡한 기술을 쉽게 사용할 수 있게 해주는 라이브러리가 Three.js이다.
또 Three.js를 리액트에서 사용할 수 있게 하는 라이브러리가 R3F이다.
1.1 Three.js 기본 구조
- Renderer: Three.js로 구현된 요소가 렌더링된 결과물 객체
- Scene: 물체들이 존재하는 장소
- Mesh: Geometry와 Material로 이루어진 물체
- Light: 조명
- Camera: Scene을 어디서 어떻게 바라볼지 결정하는 요소
1.2 개발 환경 세팅
npm i three @react-three/fiber @react-three/drei
npm i -D @types/three
2. Canvas
R3F에서 Canvas
컴포넌트를 렌더하는 것으로 기본적인 Renderer, Scene, Camera를 초기화해준다.
import * as THREE from "three";
// init
const camera = new THREE.PerspectiveCamera(70, width / height, 0.01, 10);
const scene = new THREE.Scene();
const renderer = new THREE.WebGLRenderer({ antialias: true });
// ...
JS에서는 직접 초기화해주었다면, R3F에서는 자동으로 초기화한다.
import { Canvas } from "@react-three/fiber";
import MyElement3D from "./MyElement3D";
export default function App() {
return (
<Canvas>
<MyElement3D />
</Canvas>
);
}
Canvas
의 자식으로 모델이나 조명, 카메라 설정 등을 추가한다.
3. Scene
3.1 좌표계
// axesHelper를 통해 좌표계를 확인할 수 있다.
<axesHelper scale={10} />
3.2 회전 방향
- (+) 회전 방향은 반시계 방향이다.
- 라디안 단위를 사용한다.: (도 단위) * (PI / 180)
<mesh rotation-x={45 * (Math.PI / 180)} /> <mesh rotation-x={THREE.MathUtils.degToRad(45)}>
4. mesh
mesh: 렌더링되는 3차원 모델
mesh = Geometry + Material 뼈다귀(geometry)와 material(껍데기)를 합한 것이 mesh(Object)이다.
<mesh>
<boxGeometry />
<meshStandardMaterial color="#eeff00" />
</mesh>
4.1 Geometry
Geometry: mesh의 모양을 정의
Three.js에서 제공하는 기본 Geometry 클래스
Geometry에 따른 mesh 생성 방법 3가지
-
Three.js Element 사용
<mesh> <boxGeometry /> <meshStandardMaterial /> </mesh>
-
react-three@drei
사용import { Box } from "@react-three/drei"; <Box> <meshStandardMaterial /> </Box>;
-
mesh의
geometry
attribute 이용const geometry = new THREE.BoxGeometry() <mesh geometry={geometry}> <boxGeometry /> </mesh>
기본 Geometry를 생성할 때 옵션 지정하기
R3F에서는 args
어트리뷰트로 생성되는 Geometry를 제어할 수 있다.
이 args는 Three.js에서 Geometry 클래스의 생성자 인자값에 해당한다.
각 args에 대한 정보는 Three.js 문서에서 확인할 수 있다.
boxGeometry의 예시
new THREE.BoxGeometry(1, 1, 1, 2, 2, 2);
<boxGeometry args={[1, 1, 1, 2, 2, 2]} />
- width: x축 기준 length
- height: y축 기준 length
- depth: z축 기준 length
- widthSegments: 가로 방향으로 분할할 사각형 면의 수
- heightSegments: 세로 방향으로 분할할 사각형 면의 수
- depthSegments: 깊이 방향으로 분할할 사각형 면의 수
4.2 Material
Material: mesh의 재질
<mesh>
<boxGeometry />
<meshStandardMaterial color="#ffffff" />
</mesh>
5. Light
5.1 광원의 종류
- AmbientLight: 자연광
- HemisphereLight: 반구광
- DirectionalLight: 직사광(태양)
- PointLight: 한 점에서 뻗어나가는 광원
- SpotLight: 조명광(원뿔)
- RectAreaLight: 사각형태의 조명(형광등)
- Environment: Drei에서 제공하는 Light
5.2 그림자
그림자를 지원하는 광원: DirectionalLight, PointLight, SpotLight
Drei에서 제공하는 그림자 컴포넌트: AccmulativeShadows, ContactShadows, SoftShadows
광원을 통한 그림자 만들기
export default function App() {
return (
<Canvas shadows>
<directionalLight castShadow />
<mesh receiveShadow>
<boxGeometry />
<meshStandardMaterial color="#ffffff" />
</mesh>
</Canvas>
);
}
- Canvas의
shadows
: 그림자 시스템이 전체 Canvas에서 작동하도록 설정 - 조명의
castShadow
: 조명이 물체에 대해 그림자를 생성하도록 설정 - mesh의
castShadow
: 해당 mesh가 다른 객체 위에 드림자를 드리우도록 설정 - mesh의
receiveShadow
: 해당 mesh가 다른 객체의 그림자를 받을 수 있도록 설정
6. Camera
Three.js에서 두 가지 카메라의 종류
카메라의 종류에 따라 시야 범위를 정의하는 6개의 평면으로 이루어진 절두체가 다르다.
절두체에 들어간 물체만이 화면에 렌더링된다.
<Canvas />
를 선언했을 때 기본적으로 Perspective Camera를 생성한다.
또 파라미터 중 Aspect는 웹에서 canvas에 해당하는 영역의 비율로 자동 설정된다.
따라서 카메라를 조정할 때는 나머지 3가지 파라미터만 신경 쓰면 된다.
export default function App() {
return (
<Canvas camera=>
<MyElement3D />
</Canvas>
);
}
댓글남기기