Math.sin, cos, tan
이전에 작성했던 Three.js 코드 중에 이해가 안되고 넘어간 부분이 있어 정리합니다.
문제의 코드는 다음과 같습니다.
// 오브젝트02 서서히 올라갔다 내려갔다
octaAnimation() {
if (this.objGroup && this.objGroup.getObjectByName('object02')) {
const to = this.objGroup.getObjectByName('object02');
if (to) {
to.rotation.y += 0.001;
to.position.y = -9 + Math.sin(Date.now() / 1000) * 1;
}
}
}
그냥 매우 간단한 수학(Math.sin)을 이용한 것이지만
바로 이해가 되지 않았습니다.
그래서 라디안과 원주율 부터 하나씩 정리해봅니다.
라디안 (Radian) 과 Math.PI (원주율)
우리가 흔히 사용하는 각의 단위는 도수(30도, 60, 90도) 입니다.
하지만 자바스크립트 Math 에서는 라디안을 사용합니다.
라디안은 반지름과 호의 길이가 같을 때의 중심각의 크기 입니다.
도수를 라디안으로 변환하거나, 반대로 변환하는 경우에 원주율이 필요합니다.
수학에서 원주율은 π(파이)로 표시 합니다.
자바스크립트에서는 Math.PI를 사용합니다.
// 원주율
const pi = Math.PI;
console.log(pi) // 3.141592653589793
// 도 정보만 알고 있는 경우
var degree = 30;
var radian = (degree * Math.PI) / 180;
// 역으로 반환하고 싶은 경우
var radian = 0.5235987755982988;
var degree = (radian * 180) / Math.PI;
- 변환 공식 없이도 라디안 값을 알 수도 있습니다.
- Math.PI : 180º의 라디안 값
- Math.PI / 2 : 90º 의 라디안 값
- Math.PI / 3 : 60º 의 라디안 값
- Math.PI / 4 : 45º 의 라디안 값
- Math.PI / 6 : 30º 의 라디안 값
기본 삼각함수의 정의
삼각함수의 값들은 보통 단위원(circle)을 기준으로 설명됩니다.
단위원은 반지름이 1인 원으로, 이 원을 기준으로 삼각함수를 정의할 수 있습니다.
- 단위원에서의 각도: 단위원의 중심에서 원의 둘레로 선을 그린 후, 이 선이 x축과 이루는 각도를 기준으로 삼각함수를 계산합니다.
- 사인(Sine): 주어진 각도에서 y축 방향의 값.
- 코사인(Cosine): 주어진 각도에서 x축 방향의 값.
- 탄젠트(Tangent): 사인 값을 코사인 값으로 나눈 값, 즉 ( \tan(\theta) = \frac{\sin(\theta)}{\cos(\theta)} )로 정의됩니다.
삼각함수는 삼각형의 각도와 변의 길이 간의 관계를 나타내며, 특히 회전이나 주기적인 동작을 표현할 때 유용하게 사용됩니다. Math.sin()
, Math.cos()
, Math.tan()
은 JavaScript에서 삼각함수를 계산하는 메서드로, 주로 각도에 따른 x와 y 좌표 변화를 표현하거나 애니메이션에서 주기적인 동작을 구현할 때 많이 쓰입니다.
Math.sin()
, Math.cos()
, Math.tan()
의 특징과 활용
Math.sin(라디안)
- 의미: 사인 함수는 y축 방향의 높이 값을 나타내며, 특정 각도에서 위아래로 이동하는 값을 표현합니다.
- 범위: -1에서 1 사이를 반복합니다.
- 주기:
2π
(360도)를 기준으로 한 번의 주기가 반복됩니다. - 활용 예: 오브젝트를 위아래로 반복적으로 움직일 때, 사인 함수를 사용하여 자연스러운 애니메이션을 만들 수 있습니다.
예시:
const y = Math.sin(Date.now() / 1000);
Math.cos(라디안)
- 의미: 코사인 함수는 x축 방향의 위치를 나타내며, 특정 각도에서 좌우 이동을 표현하는 데 사용됩니다.
- 범위: -1에서 1 사이를 반복합니다.
- 주기: 사인 함수와 동일하게
2π
(360도)를 기준으로 반복됩니다. - 활용 예: 원형으로 오브젝트를 회전시키거나, 좌우로 자연스럽게 이동하는 애니메이션에 유용합니다.
예시:
const x = Math.cos(Date.now() / 1000);
Math.tan(라디안)
- 의미: 탄젠트 함수는 각도에 따른 기울기를 나타내며, 특정 각도에서 가파르게 상승하거나 하강하는 효과를 표현할 때 쓰입니다.
- 범위: 무한대로 증가하거나 감소할 수 있습니다. 따라서
π/2
(90도)나3π/2
(270도)에서 값이 발산합니다. - 활용 예: 기울기나 각도 기반의 계산이 필요한 경우에 유용하지만, 값이 급격하게 변할 수 있으므로 그래픽 애니메이션에는 잘 사용되지 않습니다.
예시:
const slope = Math.tan(angle); // 기울기 계산
사인과 코사인 함수의 관계
- 위상 차이: 사인과 코사인은 동일한 주기를 갖지만, 90도(π/2)의 위상 차이가 있습니다.
- 예를 들어,
sin(0)
은 0이지만cos(0)
은 1입니다.
- 예를 들어,
- 원형 회전: 사인과 코사인을 함께 사용하면 원형 궤도로 오브젝트를 이동시킬 수 있습니다.
- 예를 들어,
x = Math.cos(t)
,y = Math.sin(t)
형태로 사용하면,t
가 증가함에 따라 (x, y) 좌표가 원형을 그리며 움직입니다.
const radius = 5;
const x = radius * Math.cos(Date.now() / 1000);
const y = radius * Math.sin(Date.now() / 1000);
시각적 예시: 위아래와 좌우 움직임
- 위아래로 이동:
Math.sin()
을 사용하여 오브젝트가 주기적으로 위아래로 움직이게 할 수 있습니다. - 좌우로 이동:
Math.cos()
을 사용하여 좌우로 이동하게 할 수 있습니다. - 원형 궤도 이동:
Math.sin()
과Math.cos()
을 함께 사용하면 오브젝트가 원형을 그리며 이동하게 됩니다.
각 메서드 사용법 요약
Math.sin()
과Math.cos()
는 주기적인 이동을 쉽게 구현할 수 있는 함수이며,Math.tan()
은 기울기나 급격한 값 변화가 필요한 경우에 사용됩니다.- 이 삼각함수들은 각도와 시간을 입력받아 반복적인 움직임을 만드는 데 적합하며, 애니메이션이나 주기적인 동작을 구현할 때 매우 유용합니다.
참고) 특정 값을 알고 싶을 때 예시
- 각도 A와 밑변의 길이 a를 알고 있는 경우
높이 b와 빗변 c를 구하는 식은 다음과 같습니다.
- 빗변 c를 구하는 공식 : a / Math.cos((A / 180) * Math.PI)
- 높이 b를 구하는 공식 : a * Math.tan((A / 180) * Math.PI)
- 각도 A와 높이 b를 알고 있는 경우
밑변 a 와 빗변 c의 길이를 구하는 식은 다음과 같습니다.
- 밑변 a를 구하는 공식 : b / Math.tan((A / 180) * Math.PI)
- 빗변 c를 구하는 공식 : b / Math.sin((A / 180) * Math.PI)
- 각도 A와 빗변 c를 알고 있는 경우
밑변 a 와 높이 b의 길이를 구하는 식은 다음과 같습니다.
- 밑변 a를 구하는 공식 : c * Math.cos((A / 180) * Math.PI)
- 높이 b를 구하는 공식 : c * Math.sin((A / 180) * Math.PI)
- 빗변 c와 높이 b를 알고 있는 경우 밑변 a를 구하려면
각도 A를 먼저 알아낸 이후 2, 3번의 공식을 사용하면 됩니다.
- 각도 A를 구하는 공식 : (Math.asin(b / c) * 180) / Math.PI
- 빗변 c와 밑변 a를 알고 있는 경우 높이 b를 구하려면
각도 A를 먼저 알아낸 이후 1, 3번의 공식을 사용하면 됩니다.
- 각도 A를 구하는 공식 : (Math.acos(a / c) * 180) / Math.PI
- 밑변 a와 높이 b를 알고 있는 경우 빗변 c를 구하려면
각도 A를 먼저 알아낸 이후 1, 2번의 공식을 사용하면 됩니다.
- 각도 A를 구하는 공식 : (Math.atan(b / a) * 180) / Math.PI
결론
Math.sin(Date.now() / 1000) * 1 부분을 하나씩 살펴보면:
- Date.now() / 1000:
- Date.now()는 밀리초(ms) 단위의 현재 시간을 반환하며, 1000으로 나누어 초 단위로 바꿉니다.
- requestAnimationFrame에 의해 이 함수가 매 프레임 호출되므로, 시간이 흐를수록 Date.now() / 1000의 값은 점차 증가하게 됩니다. - Math.sin(Date.now() / 1000):
- 사인 함수는 주기적이기 때문에, 이 값은 `-1`에서 `1` 사이를 계속 반복하며 변화합니다.
- 시간이 지남에 따라 사인 값이 `0 → 1 → 0 → -1 → 0`의 순서로 변하는 것을 매 프레임마다 계산합니다. - * 1:
- 1은 사인 함수의 출력을 그대로 유지해 -1과 1 사이에서 변동하게 만듭니다.
- 만약 * 2를 했다면 -2와 2 사이를 오가게 되었을 것입니다.
결과적으로, Math.sin(Date.now() / 1000) * 1은 시간이 지남에 따라 -1과 1 사이의 값을
반복적으로 반환하게 되고, 이를 to.position.y = -9 + ...에 더해 주기적으로 위아래로 움직이게 합니다.
'TIL' 카테고리의 다른 글
[241031 TIL] pnpm lock 자꾸 변경될 때 (0) | 2024.10.31 |
---|---|
[241030 TIL] 가장짧은문자거리(시간복잡도) (0) | 2024.10.30 |
[241024 TIL] Docker 개념정리 (1) | 2024.10.24 |
[241024 TIL] CI/CD 정리 (0) | 2024.10.24 |
[241017 TIL] CORS 정리 (0) | 2024.10.17 |