티스토리 뷰

활동/42Seoul

[cub3d] Ray-Casting

geonwoopaeng@gmail.com 2021. 2. 15. 16:37

* 레이 캐스팅

 

2차원 맥에서 3차원의 원근감을 만드는 렌더링 기술

 

* 기본 아이디어

 

ray_casting

  • 녹색점: 플레이어, 파란색: 벽, 빨간색: 광선
  • 맥의 한칸은 0 or 1 or 2 를 가진다.
    • 0: 벽 없음
    • 1: 벽
    • 2: 아이템
  • 화면의 모든 x에 대해(화면의 모든 수직 줄무늬에 대해) 플레이어 위치에서 시작하는 광선을 플레이어의 보는 방향과 화면의 x좌표의 방향에 따라 보냅니다.
    • 벽에 부딪힌 경우 거리(hit point와 플레이어 거리를 계산)를 이용해서 벽이 화면에 그려야 하는 높이를 계산합니다.
  • 광선이 어느 위치에 있는지 벽에 부딪 힐 때까지 계속 확인한다.
    • 컴퓨터는 광선의 한정된 수의 위치만 확인 가능하므로 단일 공식으로만 광선이 벽에 닿는 것을 확인 할 수 없다.

 

* DDA 알고리즘

 

  • 2차원 그리드를 지나가는 선(line)이 어떤 네모칸을 부딪치는지 찾는 알고리즘

 

* 원리 & 조건

 

  • 기울기의 절대값을 확인
  • 기울기 기준 축 잡기
    • 기울기 < 1: x축 기준
    • 기울기 > 1: y축 기준
  • 기준 기준 축 잡고 이동
    • x축 기준: x축 1씩 이동, y값에 기울기 더하기
    • y축 기준: y축 1씩 이동, x값에 기울기 역수 더하기
  • 좌표에 점 찍기(반올림)

 

ray_casting2

 

raycastmiss3

 

raycastmiss4

 

dda_알고리즘

  • 카메라 평면: blue line

    • 항상 방향벡터에서 수직
    • plane vector: 전체 카메라 평면 중 방향 벡터의 끝점(검정색 점)부터 오른쪽 카메라 평면의 끝점(파란색 점)까지
  • 컴퓨터 화면의 표면을 나타내는 방향 벡터: black line(direction vector)

    • 화면 내부 가리킨다.
  • 플레이어 위치: 초록색 점(position vector)

    • 카메라 평면보다 앞에 있다.

 

* 표현

 

  • 방향벡터 끝점: black spot
    • position vector + direction vector
  • 오른쪽 카메라 평면 끝점: right blue spot
    • (position vector + direction vector) + plane vector
  • 왼쪽 카메라 평면 끝점: left blue spot
    • (position vector + direction vector) - plane vector

 

* 광전 방향(rayDir vector) 구하기

 

  • 방향 벡터 + (카메라 평면 X 배수)
    • ex) 카메라 평면의 오른쪽에서 길이의 약 1/3 지점을 통과하는 세번째 광선(red line)
    • => 광선 방향: direction vector + plane vector * 1/3

 

* FOV(Field of View) 구하기

 

  • 광선(red line)의 사이 각
Fov = 방향벡터 길이 : 평면 길이

 

dda_알고리즘2

  • dierction vector == plane vector의 경우 => FOV는 90 °
방향벡터 길이 : 평면 길이 = 1 : 1

 

dda_알고리즘3

  • dierction vector > plane vector의 경우 => FOV < 90 °
  방향벡터 길이 : 평면 길이 = LONG : 1
  • 시야가 좁아져서 더 자세한 내용을 볼 수 있고 깊이가 줄어들므로 확대와 동일

 

dda_알고리즘4

  • dierction vector < plane vector의 경우 => FOV > 90 °
방향벡터 길이 : 평면 길이 = 1 : LONG
  • 방향 벡터가 0에 가까울 경우 180 °가 최대
  • 축소와 같이 훨씬 넓은 시야를 가진다.

 

* 벡터 회전

 

vector rotation

http://blog.naver.com/PostView.nhn?blogId=dalsapcho&logNo=20144939371&parentCategoryNo=&categoryNo=29&viewDate=&isShowPopularPosts=true&from=search

 

출처자료

 

Raycasting

#define screenWidth 640 #define screenHeight 480 #define texWidth 64 #define texHeight 64 #define mapWidth 24 #define mapHeight 24 int worldMap[mapWidth][mapHeight]= { {4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,7,7,7,7,7,7,7,7}, {4,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,7,0,

lodev.org

<엄청 좋은 자료>

www.notion.so/1-133e9a36f2a3437a8becf6f90a2f2da3

반응형

'활동 > 42Seoul' 카테고리의 다른 글

[용량 부족] 일 경우(linux + wsl2)  (0) 2021.06.19
[push_swap] 풀이과정  (0) 2021.06.19
[miniRT] Ray_Tracing  (0) 2021.02.04
[miniRT, cub3d] wsl2에서 miniRT, cub3d setting  (2) 2021.01.25
[miniRT, cub3D] Man 설명  (0) 2021.01.25
공지사항
최근에 올라온 글