Three.js의 Mesh Material에 그라데이션 적용하기

limteract·2024년 7월 3일

WebGL

목록 보기
2/2
post-thumbnail

Three.js에서 쉐이더를 사용하지 않고 메쉬에 그라데이션 색상을 적용할 수 있습니다. 그라데이션 캔버스를 생성하여 메쉬의 Material 텍스쳐로 입히는 방법입니다.

1. 메쉬 생성

기본 메쉬를 생성합니다. 그라데이션이 없는 단색상의 메쉬입니다.

const geometry = new THREE.SphereGeometry(1, 32, 32); 
const material = new THREE.MeshBasicMaterial({color: '#bb55ff' });
const mesh = new THREE.Mesh(geometry, material);

2. 그라데이션 캔버스 생성

원하는 색상을 인자로 받아 그라데이션 캔버스를 생성하는 메소드입니다.

구의 상부에서 하부로 그라데이션이 이어질 수 있도록, 세로 그라데이션을 설정하였습니다.

function getGraientCanvas(startColor, endColor) {

  // 캔버스 생성
  const canvas = document.createElement('canvas');
  const context = canvas.getContext('2d');
  canvas.width = 1;
  canvas.height = 256;

  // 0,0 좌표부터 0,256 좌표까지 그라데이션
  const gradient = context.createLinearGradient(0, 0, 0, 256);
  
  // 시작점 0과 끝점 1 사이 소수점을 넣어 색상 단계 추가 가능
  gradient.addColorStop(0, startColor);
  gradient.addColorStop(1, endColor);

  context.fillStyle = gradient; 
  context.fillRect(0, 0, 1, 256); // 그라디언트가 캔버스에 꽉 차도록

  return canvas;
}

🛠️ createLinearGradient() ?

두 개의 주어진 좌표를 연결하는 선을 따라 그라데이션을 생성합니다.

createLinearGradient(x0, y0, x1, y1)
// createLinearGradient(시작점x, 시작점y, 끝점x, 끝점y)

🛠️ addColorStop() ?

색상 지점을 추가합니다. offset은 시작점 0과 끝점 1 사이에서 지정할 수 있습니다. 색상은 CSS와 동일하게 작성합니다.

addColorStop(offset, color)
// addColorStop(색상 지점 (0~1), 색상)

예시

gradient.addColorStop(0, "green");
gradient.addColorStop(0.7, "white");
gradient.addColorStop(1, "pink");

3. 캔버스를 텍스쳐로 변환

getGraientCanvas 함수의 인자로 원하는 시작 색상과 끝 색상을 지정합니다. 리턴받은 그라데이션 캔버스를 메쉬의 Material에 텍스쳐로 적용합니다.

const geometry = new THREE.SphereGeometry(1, 32, 32); 

// 원하는 그라데이션의 캔버스 리턴 받기
const gradientCanvas = getGraientCanvas('#bb55ff','#2c5af2');

// 캔버스 요소를 텍스쳐로 변환
const texture = new THREE.CanvasTexture(gradientCanvas);

// material에 텍스쳐 적용
const material = new THREE.MeshBasicMaterial({ map: texture })

const mesh = new THREE.Mesh(geometry, material);

구에 보라색 파란색의 상하 그라데이션이 입혀진 것을 확인할 수 있습니다.

Three.js만으로 3D 메쉬에 그라데이션 색상을 적용하는 방법을 알아보았습니다.

쉐이더 혹은 벡터를 직접 다룰 수 있다면 더욱 근본적인 3D에 접근할 수 있으나, WebGL에 대한 심화된 이해가 필요합니다. 해당 부분은 추후 WebGL 공부를 통하여 다시 다루어 보고 싶습니다.

참고 자료

0개의 댓글