메뉴 바로가기 검색 및 카테고리 바로가기 본문 바로가기

한빛출판네트워크

한빛랩스 - 지식에 가능성을 머지하다 / 강의 콘텐츠 무료로 수강하시고 피드백을 남겨주세요. ▶︎

IT/모바일

루비로 게임 만들기 1-2

한빛미디어

|

2008-02-01

|

by HANBIT

14,485

제공 : 한빛 네트워크
저자 : Andrea O. K. Wright
역자 : 주재경
원문 : Creating Games in Ruby (Part 1)

Rubygame
Creator and Lead Developer: John Croisant

Rubygame은 SDL의 C API 주변의 저수준 랩퍼를 드러내주며 다양한 기능이 들어 있는 고수준의 게임 개발 라이브러리이다. Rubygame의 편리한 메서드와 helper클래스를 사용하여 바로 프로젝트를 시작할 수도 있고 코드를 수정하기 위해 Rubygame을 통해 SDL함수를 바로 접근할 수도 있다.

Rubygame은 초기에 유명한 파이썬 기반의 프레임워크 Pygame을 따라했으며 이름 또한 이를 반영한다. Rubygame을 만든 John Croisant에 따르면 그 당시에 그가 알고 있는 최선의 게일 개발 프레임워크가 Pygame이었다. 시간이 지남에 따라 Pygame에서 바로 가져온 기능은 이들이 구현된 방식에 따라 좀더 Ruby에 적합한 모습으로 바뀌었다.

다음 릴리즈 버전이 될 Rubygame3.0은 Pygame과는 많이 달라질 것이다. John은 현재 몇 개의 수정할 부분이 남아 있긴 하지만 새로운 시스템에서 이전 게임들이 잘 돌아가는지를 확인하는 작업을 하고 있다.

Rubygame3.0에 무엇이 있는지 살펴보기 전에 Rubygame의 현 버전인 Rubygame2.1.0에 패키징된 샘플을 살펴봄으로써 Pygame과 같은 게임 엔진의 의미를 살펴보고자 한다.

이 배너 광고를 닮은 Punch the Chimp게임은 Pygame 튜토리얼에 있는 것을 바로 가져온 것이다. Rubygame과 Pygame API는 아주 비슷하며 단계별로 Pygame 튜토리얼을 따라하다 보면 Rubygame코드를 따라가는 것이 아주 쉽다. 먼저 커서를 옮기고 마우스를 클릭하여 주먹을 날린다. 주먹을 맞는 경우 침팬지는 돈다.


[그림 3] Rubygame으로 패키징된 Punch the Chimp

Rect는 Rubygame2.x에서 주요한 클래스 가운데 하나인 것 처럼 Pygame의 가장 중요한 클래스 가운데 하나이다. Rect는 전형적으로 sprite와 짝을 이루며 sprite를 표현하는 이미지의 차원에 기반한다. 아래의 비트맵은 게임에 사용되는 침팬지를 나타낸다. 빨간 배경색은 게임이 진행되는 동안 나타나지 않는다. 다른 대부분의 게임 프레임워크처럼 Rubygame은 특정이미지가 화면에 나타날 때 사용자가 랜더링되지 않아야 하는 색깔을 정할 수 있도록 한다. 배경이 없이 침팬지만 화면상에서 잘라낸다.


[그림 4] Punch the Chimp에 사용되는 침팬지 비트맵

Rect는 sprite를 움직이는 데에 사용될 수도 있다. Sprtie의 Rect에서 midleft나 bottom(아래 그림에서 원이나 점선으로 표시된)값을 설정하여 sprite의 위치를 변경할 수 있다. 게임을 시작하면 침팬지의 위치를 위해 @rect.topleft = 10,10이 사용된다. 주먹이 마우스를 바로 따라오게 하기 위해서는 Rect의 midtop값이 모든 프레임에서 마우스 좌표와 일치하도록 설정한다.


[그림 5] Rect속성

Rect클래스는 충돌검출 서비스와 다른 Rect내부에서 Rect에게 권한을 주는 clamp 그리고 양수와 음수에 따라 Rect가 커지거나 작아지도록 하는 inflate와 같은 많은 유용한 기능을 제공한다. 아래에 주먹이 맞았는지를 결정하는 코드가 있다. 주먹이 목표물을 사각형 모양으로 때린 경우에만 인정하도록 하기 위해 Rect를 확대하거나 축소시킨 버전으로 검사한다.
# 목표물 때리기. 
# 때리기 성공이면 true리턴 그렇지 않으면 false 리턴.
def punch(target)
  @punching = true
  return @rect.inflate(-5,-5).collide_rect?(target.rect)
end
Pygame프로그래밍에서 또 다른 핵심 개념은 sprite그룹에 관한 아이디어 이다. Rubygame에서 Sprites::Group클래스는 Pygame의 sprite그룹에 기반하고 있다.

sprite그룹은 드로잉, 화면갱신, 충돌 검출을 포함하는 sprite의 모든 동작을 제어한다. Punch the Chimp에서 주먹과 침팬지는 같은 spite그룹에 속하지만 실제 게임에서는 한 장면에 있는 sprite는 일반적으로 같은 sprite그룹에 속하지 않는다. 게임은 sprite그룹으로 구성될 수 있다. 예를 들어 서로 다른 팀에 대해 서로 다른 sprite그룹이 있을 수 있다.Sprite그룹은 쉽게 확장 가능하다.

Ruby/SDL샘플코드를 보면 배열에 모든 sprite를 집어 넣고 모든 프레임에 대해 각 sprite를 다시 그리도록 루프에 배열을 대입시켜 sprite그룹이 갱신되는 것을 알 수 있다. sprite그룹에는 어떤 특징들이 있는가? Rubygame의 UpdateGroup모듈이나 Pygame의 RenderUpdate모듈을 사용하고자 할 때 유용한 기능 중 하나는 마지막 화면 업데이트 이후 위치가 바뀐 Rect의 위치를 가지고 있으며 이를 다시 화면에 표시할 수 있다는 것이다.

Edge Rubygame과 같이 Rubygame영역에서 현재 무엇이 진행되고 있는지 살펴보자. 커다란 변화중의 하나는 새로운 이벤트 핸들링 메커니즘을 사용하고 Rect기반의 Pygame과는 확연히 구분되는 위치 시스템을 가진 좀 더 밀접한 OpenGL과의 상호 작용으로 만들어진 새로운 화면 관리 시스템이다.

Rubygame3.0의 데모 스크린샷이 아래에 있다. 커다란 팬더가 마우스를 따라 움직인다. 화면을 클릭하면 팬더와 루비 보석은 커서로 점프한다. 팬더와 루비보석이 충돌하면 이들은 붉은색으로 변한다. 이 장면을 축소한 화면이 화면의 오른쪽 위쪽 구석에 나타나 있다.


[그림 6] Rubygame3.0에 패키징된 데모:충돌 검출 없음


[그림 7] Rubygame3.0에 패키징된 데모: 충돌 검출 있음

아래 코드는 새로운 시스템에 있는 sprite를 나타내는 방법을 보여준다. 데모에 있는 루비보석을 보여주는 코드이다. RUDL예제에서 살펴본 것과 같은 OpenGL API가 사용되고 있긴 하지만 이 예제에서는 setup_texture 단독 호출로 감싸져 있다. 위치는 2개의 좌표를 이용해 설정하지만 프레임워크는 z좌표값을 0으로 설정하는 OpenGL의 3D 위치 시스템을 이용하고 있다.

Rubygame3.0과 OpenGL은 서로 밀접하게 연동하고 있지만 John은 3D그래픽 카드 없이도 새로운 시스템을 구동하도록 하고 있다. OpenGL이 필요 없는 새로운 화면 관리 프레임워크가 있을 수도 있을 것이다.
ruby = GLImageSprite.new {
  @surface = Surface.load_image("ruby.png")
  setup_texture()
  @pos = Vector2[100,300]
  @depth = -0.1
  @angle = -0.2
}
Rubygame의 picture-in-a-picture기능은 Nebular Gauntlet의 예제에서 보았던 작은 레이더 영역을 생각나게 하지만 구현은 확연히 다르다.

[그림 8] Nebular Gauntlet의 레이더 화면

Nebular Gauntlet에서 화면 축소는 우주선 각각을 표현하기 위해 작은 모양을 그려 이루어진다. 레이더 영역에 대한 코드는 모든 비행체와 봇 그리고 방어벽에 대해 루프를 돈다. 그리고 응용프로그램의 초기화 루틴에서 15로 설정된 크기 조절자로 각 물체를 x, y축으로 나누어 물체의 크기를 결정한다. 그 다음 물체 각각을 표현하기 위해 흰색 원을 그린다.

Rubygame3.0 데모에서 오른쪽 위에 있는 창은 화면 관리자의 관점과는 구별되는 가상 카메라의 관점으로 또 다른 장면을 보여준다.

임의의 한 영역에 초점을 두고 이 영역을 2차원 화면으로 나타낸다는 점에서 휴대폰 카메라와 비슷한 가상 소프트웨어 카메라를 생각해 볼 수 있다. 카메라에 잡히는 영역이 카메라의 영역과 일치하도록 정의 된다면 화면 영역은 더 작아질 것이고 이 경우에 물체는 작게 보이게 된다.

Nebular Gauntlet의 레이더 화면에 그려진 흰색 원과 같이 2번째 팬더나 루비 보석을 그리는 코드는 없다. 2번째 카메라는 add_camera를 사용하여 추가된다.

Rubygame3.0의 릴리즈 일정은 아직 결정되지 않았다. John이 이 버전에 포함 시키고자 하는 많은 아이디어들이 여전히 남아 있다.

Rubygame코드와 그의 블로그에서 그의 아이디어를 볼 수 있을 것이다. 그는 최근에 노란색으로 터널의 가운데 부분을 랜더링 하는데 RGB 컬러 모델이 왜 불충분한지에 대해 글을 썼다. 노란색으로 모든 것을 칠하고 나서 좀더 실제와 가까운 장면을 만들기 위해서는 무엇이 필요한지를 생각해 보자. 실제에서는 터널의 빛이 방출하는 제한된 스펙트럼이 붉은색의 차를 어두운 노란 오렌지색으로 보이도록 하고 푸른색의 차는 거의 검정색으로 나타나게 한다.

자료

GGZ Gaming Zone
Gosu
Nebular Gauntlet
Neon Helium OpenGL Tutorials
Rubygame
Ruby/SDL RUDL Shattered Ruby


저자 Andrea O.K. Wright는 Fort Washington에 있는 컨설팅회사 Chariot Solution에서 그녀의 동녀들과 함께 매주 화요일 점심시간을 이용해 Ruby관련 모임을 이끌고 있다. 그녀는 RubyConf 2007이외의 여러 컨퍼런스에서 루비용 게임 개발에 관해 발표했다.
TAG :
댓글 입력
자료실

최근 본 상품0