서론
so long 과제의 그래픽을 구현한 부분에 대한 글을 써보려 한다. 프로그램이 시작하면 map을 입력받고 유효성을 검사한다. 이후 map에 대한 그래픽을 화면에 띄우게 된다. 화면에 띄우기 위해 MiniLibx(mlx 라이브러리)를 사용한다.
mlx 라이브러리
- 기본적인 렌더링을 위한 작은 그래픽 라이브러리
- 윈도우 생성, 그리기, 이벤트관리 등 작업 가능
이전 포스팅에서는 check_map에 내한 내용까지를 다루었다.
2024.07.22 - [대외활동/42서울] - [42서울] so_long (맵 유효성 검사(BFS))
구현
start_grapic
이전 코드에서는 맵을 초기화 하고 유효성을 검사했으니 이제 맵을 화면에 출력하면 된다. 다음은 start grapic 함수의 로직이다.
- init_data: data 구조체 초기화 (mlx_init, 이미지 주소값 초기화(mlx_xpm_file_to_image), map 주소 복사 등)
- mlx_new_window: mlx 객체에 윈도우 할당
- mlx_new_image: mlx 윈도우 객체에 이미지 할당
- mlx_get_data_addr: img의 주소값 가져오기
- draw: 이미지 출력
- mlx_hook: 특정 이벤트를 기반으로 행동(함수) 지정
- mlx_loop: 프로그램이 종료되지 않고 후크를 받을 수 있는 상태가 됨
파란색은 mlx 라이브러리의 함수들
data 구조체 초기화
mlx_hook: key_press
mlx_hook(data.win, KEY_PRESS, 0, key_press, &data);
mlx_hook를 이용하여 키보드가 눌리면 key_press 함수로 로직이 넘어가도록 훅을 걸어주었다. key_press 함수에서는 입력한 키가 ESC라면 프로그램을 종료하고, 방향키(WASD, 화살표)라면 플레이어를 움직인다. 이후 draw 함수를 통해 map을 화면에 그리고 이동 횟수를 출력한다.
move_player 함수에서는 플레이어가 이동한 위치를 반영해 map을 업데이트한다. 이동하려는 위치가 벽이거나 코인을 다 수집하지 못한 상태에서 목적지로 이동하려는 경우에는 map을 업데이트하지 않는다.
결과
정리하자면, mlx 객체, 윈도우, 이미지를 초기화하고 map에 따라 초기화된 이미지의 적절한 위치에 그래픽에 띄울 이미지를 복사한다. 이후 사용자가 키를 누를 때마다 ESC 키인지, 방향키인지를 구분하여 적절한 동작을 수행하도록 한다. 방향키를 누른 경우에는 적절한 이동인지 체크하고 map을 수정한다. 수정된 map에 따라 윈도우의 이미지를 아까와 같은 방법으로 초기화한다.
후기
실제로 실행되는 간단한 C 게임을 만들었다. 간단한 과제이지만 결과물을 만들었다는 게 보람있었다. mlx 라이브러리에 대해서 알게 되었고 기본적인 애플리케이션의 동작 방식을 알고 코드를 짤 수 있어서 좋았던 것 같다. 이 과제에서 사용한 mlx 라이브러리는 학교 프로젝트에서 다시 사용하기도 했었다. 굿
비록 리트라이를 5번이나 하고 통과했지만 그만큼 평가도 많이 다니고 받으며 좋은 경험을 할 수 있었다. 기억 남는 점은 main 함수에 큰 로직만 담겨있으며 함수와 파일 분할을 잘했다는 평가를 많이 받았던 것인데 42 서울에서 코드를 열심히 짜면서 이런 부분도 실력이 늘은 것 같아 뿌듯했다. 과제 이후에도 내 코드 리뷰를 하며 개선할만한 부분을 몇 개 찾았는데, 이 부분도 시간이 나면 수정해 봐야겠다.
코드 리뷰
맵을 검사하는 로직과 맵의 높이 너비를 구하는 과정에서 같은 내용을 반복하는 반복문이 여러 번 사용되어서 나중에 최적화를 한다면 이 부분을 수정하면 좋지 않을까 생각했다. 또한 나중에 평가를 받을 때 맵의 크기가 화면을 많이 벗어나는 수준으로 커지면 흰색 윈도우만 생기는 문제점을 발견하였다. 이 부분은 맵의 크기만큼 32 * 32 픽셀을 배치하여 생긴 문제 같다. 윈도우의 크기를 지정하고 그 크기에 맞춰 랜더링 하는 이미지 크기를 조정하면 좋았을 것 같다.
'대외활동 > 42서울' 카테고리의 다른 글
[42서울] minitalk 구현(Makefile 포함) (0) | 2024.08.22 |
---|---|
[42서울] minishell 테스트 케이스 (0) | 2024.08.11 |
[42서울] so_long 맵 유효성 검사(BFS) (0) | 2024.07.22 |
[42서울] get_next_line 구현 (메모리 누수 잡기, 구현 tip) (1) | 2024.07.21 |
[42서울] ft_printf 구현 (한 문장으로 구현하는 이진수 보수 연산) (0) | 2024.06.21 |