이것은 정말 많은 차이가 있으면서도 비슷하다.
게임 루프와 관계가 정말 많이 되어있다.
[Game Developer, 게임개발자] - 게임의 근간인 게임 루프, Game Loop에 대해서
게임의 시간은 어떻게 판단될까?
가 문제다.
우리는 FPS라는 것을 가지고 있고 30FPS의 게임이라면 우
리는 프레임 당 약 0.0333333s을 가지고 있는 것을 안다.
하지만 60 FPS에서는 프레임 당 0.0166666666s을 가지고 있다는 것도 안다.
즉, 프레임과 현실 시간과 무엇인가 관계가 되어있을 것 같다는 생각도 든다.
그리고 게임을 일시정지 시키면 real time으로 1분이 흘러도 게임 시간은 흐르지 않는다.
무엇인가 비슷하면서도 다른 느낌이 확연히 든다.
가장 게임 시간과 현실 시간의 차이를 잘 느낄 수 있는 게임이
Super Hot이라고 생각한다.
++나는 스팀에서 사서 재미있게 플레이 했다.
플레이어가 움직일 때 가장 시간이 빨리 흘러가고
움직이지 않는다면 시간이 느리게 흘러간다.
???? 어떻게 한거지???
우선 게임 시간에 대해서 더 알아보자
게임은 사실 하드웨어에 맞추어서 만들어졌기 때문에 처음에는 문제가 없었다.
어차피 position.x += 5.0f; 라는 문장을 게임 루프에 넣어서 실행을 해도
우리 계산 범주 안에 들어와서 정상적으로 작동했으니까..
하지만 무어의 법칙을 따라 프로세서의 성능이 비약적으로 상승했고
그에 따라 하드웨어의 처리속도가 빨라졌다.
즉, 게임 루프의 처리속도가 빨라진 것이다.
즉, 우리는 1초에 30번 프레임이 갱신될 것이라 생각했는데 좋은 하드웨어에서는 60 FPS를 가지고 있어서
우리가 5만큼 움직일 것을 쟤네쪽에서는 10만큼 움직여버리는 결과를 초래했다.
쉽게 말해서 게임이 2배속으로 진행되는 것이다.
??? 하지만 프로그래머들은 언제나 그랬듯이 답을 찾았다.
바로 delta time이라는 개념을 도입했다.
델타 타임이란 전 프레임을 수행하는데 걸린 게임 시간을 말한다.
음... 그걸 어떻게 쓰는데???
쉽게 설명해보겠다.
앞에서 써놓았듯이
30FPS에서는 1프레임이 0.03333333
60FPS에서는 1프레임이 0.01666666
정도를 가진다고 했다.
deltaTime은 결국 저 1프레임의 시간을 말한다.
position.x += 5.0f * deltaTime;
이 된다면
30FPS의 게임 안에서는
position.x += 5.0f * 0.0333333
60FPS의 게임 안에서는
position.x += 5.0f * 0.016666
임의의 k FPS에서는
position.x += 5.0f * 1/k; 가 될 것이다.
하지만 deltaTime은 정확하게는 전 프레임을 수행하는데 걸린 시간으로
저렇게 정확하게 떨어지지는 않는다.
다만 프레임을 수행하는데 걸린 시간을 이용하기에
FPS가 바뀌어도 1초 동안의 수행한 정도는 같아지는 것이다.
즉, 1/30 * 30 == 1 1/60 * 60 == 1 과 같이
게임루프가 얼마나 빠르게 돌아가느냐와 상관 없이
실제 시간에서 수행한 정도가 같아지는 것이다.
다만 게임루프가 많다는 것은 업데이트가 더 많다는 것이고
이는 조금 더 섬세하게 보여줄 수 있다는 것을 의미한다.
**물론 렌더링과 모니터 주사율과 관계가 있다.
**사람들의 144Hz, 240Hz를 찾는 것은 모니터 주사율이다.
게임 루프의 속도와 관계 없다.
게임 루프가 해당 속도를 뛰어넘을 때에나 의미가 있는 수치다.
즉, 프로세서가 좋아서 게임이 240Hz으로 돌아갈 때나 의미있는 수치다.
**그렇다고 240Hz가 60Hz에서 안좋은 것은 아니지만 모니터의 모든 성능을 이끌어내지 못한다는 말이다.
아무튼 그렇다면 SuperHot은 어떻게 구현한 것일까?
물론 내가 SuperHot을 코드를 열어보진 않았지만 생각해보자면
사용자 입력이 없을 때는.. 기준이 1초가 아니라 10초가 되는 것이 아닐까?
임의의 변수 TimeScale을 정해놓고
사용자 입력이 없을 때는 TimeScale이 0.1이 되고
있을 때는 TimeScale이 1이 되지 않을까?
솔직히 게임루프 자체를 늦출 것 같지는 않다.
if(userInput){
timeScale = 1.0f;
}else{
timeScale = 0.1f;
}
...
position.x += speed * deltaTime * timeScale;
이 아닐까싶다.
timeScale이 작아지면 1초에 원래 10을 가던 것이 1밖에 못갈 것이니까..?
아무튼 뭐 이런 식이 아닐까싶다.
'Game Development, 게임개발 > 배경지식' 카테고리의 다른 글
이벤트 큐의 활용 - 서버 요청 응답의 순서 보장 (0) | 2022.04.03 |
---|---|
튜토리얼에 대한 고찰 (0) | 2022.03.12 |
Reactive Programming이란, Rx란? (0) | 2022.01.17 |
Scroll, 스크롤에 대한 것 (0) | 2021.11.11 |
게임의 근간인 게임 루프, Game Loop에 대해서 (0) | 2021.11.09 |