XNA 개발 프레임워크
XNA는 XBOX와 Windows용 게임 애플리케이션을 .net 기반으로 통합해서 개발할 수 있도록 제공되는 framework 입니다. 2008년 10월에 Version 3.0이 출시되면서 휴대용 멀티미디어 장치인 Zune 용 애플리케이션도 XNA를 이용해서 개발 할 수 있게 되었습니다.
이를 이용해서 개발된 애플리케이션은 XBOX Live Marketplace에 업로드해서 유료로 일반 사용자에게 판매할 수 있고, 이를 통해 수익을 올릴 수 있습니다. (Apple의 AppStore와 유사한 개념입니다.)
가장 최근에 출시된 3.1 버전의 경우 Avartar, Video Playback 등의 추가 기능을 포함하고 있으며, 3.1 extension for Zune HD를 설치하면 Visual Studio 2008을 이용해서 Zune HD용 애플리케이션도 개발이 가능합니다. 앞으로 계속해서 새로운 기능들이 추가될 예정으로 있다고 합니다.
다음은 GDC(Game Developer Conference) 2009에서 소개된 세션 자료입니다. 참고하시기 바랍니다.
GDC 2009 : XNA Game Studio Program Overview
http://www.microsoft.com/downloads/details.aspx?displaylang=en&FamilyID=ced54340-d2ad-44bd-8a77-22339ed86e08
GDC 2009: XNA Game Studio XDK Extensions, Certification, and You
http://www.microsoft.com/downloads/details.aspx?FamilyID=964F0247-9202-4CC0-893D-5519F30C1CCB&displayLang=en
그리고, 다음은 XNA 개발자 센터 사이트입니다. 관련 커뮤니티나 블로그에서 정보를 얻을 수 있습니다.
XNA Developer Center
http://msdn.microsoft.com/en-us/aa937791.aspx
Got Game?
상상력에 날개를 다는 XNA Game Studio Express
Charles Cox and Michael Klucher
온라인으로 코드 찾아보기
비디오 게임을 즐기는 동안 "나도 이런 게임을 만들고 싶다"는 생각을 해본 적이 있으십니까? XNA™ Game Studio Express는 Microsoft® Windows®와 Xbox 360™ 모두를 위한 새로운 게임 개발 솔루션으로, 주로 학생이나 취미 사용자, 독립 게임 개발자를 대상으로 합니다. 즉, 바로 여러분을 위한 솔루션입니다.
Visual C#® 2005 Express Edition에 기반을 두고 있는 XNA Game Studio Express는 게임 개발을 위해 설계된 관리 코드 클래스 라이브러리인 XNA Framework를 바탕으로 개발되었습니다. 이 프레임워크는 Xbox 360과 Windows XP SP2라는, 서로 전혀 다른 두 가지 플랫폼의 코드 작성 프로세스를 간소화합니다. 사실 작성한 코드의 대부분은 아무런 변경 작업 없이 두 시스템 모두에서 작동합니다.
MSDN®(msdn2.microsoft.com/xna)에서 XNA Game Studio Express를 다운로드하면 곧바로 Windows용 게임 개발을 시작할 수 있습니다. Xbox 360 콘솔 게임을 개발하려면 XNA Creators Club 멤버 자격을 획득해야 합니다. 자세한 내용은 msdn2.microsoft.com/bb219592.aspx를 참조하십시오. 멤버 자격을 획득하면 게임 관련 자료와 XNA Creators Club 전용 버전의 시작 키트를 사용할 수 있게 됩니다.
XNA Game Studio Express를 살펴보려면 먼저 이를 다운로드하여 설치해야 합니다. Xbox 360 콘솔에 설치하는 방법은 msdn.com/xna/videos에 있는 비디오 학습 자료를 참조하십시오. 제목이 "Getting Started with the XNA Creators Club"인 비디오를 찾으면 됩니다.
게임 개발의 기본
게임 개발에는 여러 가지 독특한 과제가 있습니다. 게임은 디자인 측면뿐만 아니라 기술적인 측면에서도 사용자에게 매력적이어야 합니다. 말하자면 화려한 그래픽을 보여 주면서도 적절한 프레임 속도를 유지해야 합니다. 게임과의 상호 작용을 위한 직관적인 입력 방법과 고품질 오디오 출력도 추가적인 고려 사항입니다.
XNA Game Studio Express가 나오기 전, 게임 개발자는 DirectX® 및 OpenGL과 같은 기술을 사용했습니다. 이러한 API는 하드웨어에 대한 기본적인 액세스는 제공하지만 사용하기가 쉽지 않습니다. 따라서 대개 개발자들은 그래픽, 오디오, 입력과 같은 핵심 구성 요소를 엔진이라고 하는 프레임워크로 결합하고, 이 프레임워크 위에 특정 게임 논리를 얹는 방식을 사용했습니다. 이러한 추상화는 대부분 제작 및 사용에 많은 비용과 시간이 소모됩니다.
게다가 게임 개발의 주요 언어인 C++로 메모리와 논리를 관리하기란 기술적으로 매우 까다롭고, 게임에서 사용되는 많은 수의 아트 콘텐츠를 관리하기도 쉽지 않습니다. 이렇다 보니 아마추어 개발자에게 게임 개발이 어렵게 느껴지는 것은 당연한 일입니다. Xbox 360과 같은 차세대 비디오 게임 콘솔용 개발의 복잡한 기술 및 비즈니스 요구 사항도 마찬가지로 높은 장벽입니다.
Visual C# 2005 Express Edition을 기반으로 개발된 XNA Game Studio Express를 사용해 보십시오. XNA Game Studio Express는 취미 사용자, 학생 및 기타 게임 개발에 관심이 많은 사용자가 Windows와 Xbox 360에서 Visual C# 2005 Express Edition 통합 개발 환경을 사용하여 직접 게임을 개발할 수 있도록 설계되었습니다.
XNA Game Studio Express에는 Windows와 Xbox 360 모두를 위한 크로스 플랫폼 게임 개발 API인 XNA Framework가 포함되어 있습니다. XNA Framework를 사용하면 그래픽, 오디오, 입력, 저장뿐만 아니라 모든 게임에 사용되는 기본적인 타이밍 및 드로잉 루프도 대폭 간소화됩니다.
또한 XNA Game Studio Express에는 Visual C# 2005 Express Edition의 빌드 환경에 통합된 XNA Framework Content Pipeline도 포함되어 있습니다. 이제 게임 개발자는 Content Pipeline을 사용하여 IDE에서 3D 모델, 그래픽 텍스처, 셰이더, 오디오와 같은 아트 콘텐츠를 솔루션에 추가할 수 있으며 이렇게 추가된 콘텐츠는 코드에서 액세스 가능한 런타임 개체로 빌드됩니다. 따라서 아트 콘텐츠와 관련된 오버헤드가 줄어듭니다.
이전의 게임 개발 솔루션은 완전히 새로 만드는 경우가 많았습니다. 즉, 각 시간 틱을 관리하고 게임 동작이 올바르게 처리되도록 하는 타이밍 및 렌더링 루프를 직접 작성해야 했습니다. XNA Game Studio Express는 타이밍 및 렌더링 루프를 자동으로 만듭니다. 자체 타이밍 및 렌더링을 처리하는 Game 클래스가 제공되며, 이 클래스에는 각 프레임 업데이트를 위한 개체를 추가할 수 있는 Update 메서드와 화면에 렌더링할 개체를 추가할 수 있는 Draw 메서드가 있습니다.
또한 복잡한 장치 열거 코드를 작성할 필요 없이 자동으로 적절한 그래픽 장치를 설정하는, 응용 프로그램 모델이라고 하는 게임 프레임워크가 제공됩니다. 이 코드를 적소에 사용하면 처음 만들어진 때부터 완전한 기능을 수행하는 타이밍 및 렌더링 루프가 포함된 XNA Game Studio Express 프로젝트를 컴파일하고 실행할 수 있습니다.
Spacewar 시작 키트
XNA Game Studio Express에는 XNA Framework 코드 템플릿 외에 Spacewar 시작 키트가 포함되어 있습니다. 완성된 하나의 게임인 이 키트는 사용자가 수정할 수 있는 소스 코드와 아트 자료를 담고 있습니다. Spacewar 시작 키트는 우주를 배경으로 하는 세로 진행 2인용 슈팅 게임으로, 1962년에 Stephen Russell, Peter Samson 및 Dan Edwards가 DEC PDP-1용으로 개발한 원작 Spacewar에 바탕을 두고 있습니다. 시작 키트에는 원작의 게임 플레이와 그래픽을 그대로 유지한 Retro 버전, 그리고 새로운 3D 그래픽 및 사운드를 추가한 Evolved 버전의 두 가지 버전이 있습니다.
여기에서는 시작 키트를 열어 Evolved 버전을 살펴보면서 게임 구조를 탐색한 다음 일시적으로 적의 공격을 막을 수 있는 방어막 기능을 새로 추가해 보겠습니다.
먼저 XNA Game Studio Express를 실행하고 File(파일) 메뉴와 New Project(새 프로젝트)를 차례로 클릭합니다. New Project(새 프로젝트) 창이 열리면 Spacewar Windows Starter Kit(Spacewar Windows 시작 키트)를 클릭하고 OK(확인)를 클릭합니다(그림 1 참조). Creators Club에 가입했고 XNA Game Studio Express에서 수신하도록 Xbox 360을 설정한 경우에는 Spacewar Xbox 360 Starter Kit(Spacewar Xbox 360 시작 키트)를 클릭하고 OK(확인)를 클릭합니다.
![]()
그림 1 Spacewar 시작 키트 열기 (더 크게 보려면 이미지를 클릭하십시오.)
Spacewar 시작 키트를 로드하는 데 약간의 시간이 걸립니다. 완전히 로드되면 Solution Explorer(솔루션 탐색기) 창에 코드 파일이 표시되며 게임 방법에 대한 설명도 표시됩니다. 최상의 환경을 위해서 Xbox 360 컨트롤러를 연결하십시오. 키보드를 사용할 수도 있습니다. 컨트롤은 Spacewar 시작 키트가 로드될 때 안내 페이지에 표시됩니다.
F5 키를 누르면 Spacewar 응용 프로그램이 컴파일 및 실행됩니다. 게임이 시작되면 Evolved 모드를 선택하고 잠시 게임을 즐기십시오.
게임 루프의 이해
XNA에서 제공하는 핵심 기능 중 하나는 게임 루프입니다. 게임 루프는 사용자 입력, 게임 내 조건 및 기타 적용 가능한 조건에 따라 지속적으로 게임의 상태를 업데이트하고 이를 렌더링합니다. 렌더링에는 화면 드로잉, 적절한 오디오 재생, 컨트롤러 진동을 비롯한 사용자 대상의 출력 일체가 포함됩니다. Spacewar의 게임 루프가 어떻게 작동하는지 이해하면 이 기사에서 수행할 시작 키트 수정 작업을 이해하는 데 도움이 될 것입니다.
다른 .NET 응용 프로그램과 마찬가지로 게임 실행은 Main 메서드에서 시작됩니다. Main 메서드는 다음과 같이 SpacewarGame 클래스의 인스턴스를 만들고 기본 클래스의 Run 메서드를 호출하는 역할만 합니다.
static void Main(string[] args) { using (SpacewarGame game = new SpacewarGame()) { game.Run(); } }
SpacewarGame은 Microsoft.Xna.Framework 네임스페이스에 있는 Game 클래스에서 파생되며 게임 수명 주기에 대한 주요 메서드, 속성 및 이벤트를 제공합니다. 그러면 Game의 메서드를 다시 정의하여 게임에 특정 기능을 제공할 수 있습니다. 예를 들어 SpacewarGame은 Run에서 호출되는 BeginRun 메서드를 다시 정의하여 게임의 타이틀 음악을 재생하고 내부 상태 시스템을 로고 화면 단계로 전환하고 초기 카메라를 생성합니다. 플레이어는 이 카메라를 통해 보게 됩니다.
SpacewarGame의 ChangeState 메서드는 BeginRun 메서드에서 호출되면서 게임에 사용되는 많은 개체를 생성하는 역할을 담당합니다. BeginRun 메서드가 GameState.LogoSplash를 인수로 사용하여 ChangeState를 호출하면 이 메서드는 TitleScreen을 생성합니다. TitleScreen은 Spacewar 프로젝트에 선언된 추상 Screen 클래스에서 파생되는 FullScreenSplash에서 파생됩니다. Screen 클래스는 초기 화면, 선택 화면 또는 실제 게임 레벨과 같은 게임의 렌더링 단위를 나타냅니다. 이 클래스는 여러 가상 메서드를 제공하는데, 클래스에서 파생된 유형이 이러한 가상 메서드를 다시 정의하여 화면별 기능을 제공하게 됩니다. TitleScreen은 Screen.Update 메서드를 다시 정의하여 사용자가 A, B, X 중 어느 키를 눌렀는지 확인합니다. 이 키는 게임 내에서 사용자의 다음 이동 위치(Evolved, Retro, Information)를 지정합니다. TitleScreen은 Spacewar에서 사용되는 여러 Screen 파생 유형 중 하나입니다. Screen에서 파생되는 다른 유형으로는 SelectionScreen(우주선 선택), EvolvedScreen(Evolved 버전의 게임 플레이), VictoryScreen(플레이어가 승리한 경우) 등이 있습니다.
각 Screen은 화면의 기능과 함께 해당 화면의 동작을 업데이트 및 렌더링하는 데 필요한 상태를 캡슐화합니다. 게임의 두 가지 기본 플레이 유형을 나타내는 EvolvedScreen과 RetroScreen은 모두 SpacewarScreen에서 파생됩니다.
public class SpacewarScreen : Screen { protected Projectiles bullets; protected Ship ship1; protected Ship ship2; protected SceneItem sun; protected Particles particles; protected SceneItem backdrop; protected bool paused = true; protected int player1Score; protected int player2Score; ... }
SpacewarScreen에는 두 우주선의 SceneItems(기본 SceneItem 클래스에서 파생되는 SpacewarSceneItem에서 파생되는 Ship으로 구현), 렌더링할 갖가지 입자와 발사체, 게임의 배경 화면, 태양 등 화면에 렌더링되는 항목이 포함됩니다. 또한 플레이어 점수 및 게임의 일시 중지 여부와 같은 게임 상태도 SpacewarScreen에 포함됩니다.
일단 게임이 생성되면(이 경우에는 SpacewarGame) 게임을 수용하고 게임에 응용 프로그램 수준 서비스, 즉 활성화, 비활성화, 종료, 유휴와 같은 이벤트에 대한 알림을 제공할 호스트가 생성되었는지 확인합니다. 여기에서 가장 중요한 것은 유휴 이벤트입니다. Game.Tick 메서드는 이 유휴 처리기에 의해 호출되며 Tick 메서드는 다시 Game.Update와 Game.DrawFrame 메서드를 호출합니다. Game.Update 메서드는 SpacewarGame.Update에 의해 다시 정의됩니다. SpacewarGame.Update는 ChangeState 메서드에서 현재 장면으로 설정된 대상에 대해 Update를 호출합니다. Game.DrawFrame은 Game.Draw를 호출하며, Game.Draw는 현재 장면에 대해 Render를 호출하기 위해 SpacewarGame에 의해 다시 정의됩니다.
방어막 장착!
Spacewar에 새로운 기능을 추가하기는 쉽습니다. 에너지 방어막을 추가해 봅시다. 이 방어막은 게임 화면의 다른 물체로부터 우주선을 보호합니다. 편집해야 할 코드 파일은 Ship.cs와 SpacewarScreen.cs 두 가지입니다. 이 파일은 msdn.microsoft.com/msdnmag/code07.aspx에서 다운로드하거나 살펴볼 수 있습니다.
대부분의 코딩은 Ship.cs 파일에서 이루어집니다. Spacewar에서 Ship.cs 파일은 Ship 개체를 정의합니다. Ship 개체에는 플레이어가 조종하는 우주선 개체를 정의하는 메서드와 데이터가 포함됩니다. Solution Explorer(솔루션 탐색기)에서 Ship.cs 파일을 찾은 다음 두 번 클릭하여 엽니다.
먼저 방어막의 논리를 제어할 몇 가지 변수를 정의해야 합니다. 방어막은 5초 동안 지속되며 라운드당 한 번만 사용할 수 있습니다. Ship.cs에서 40번 줄로 이동하여 invulnerable, inHyperspace 또는 inRecovery와 같은 우주선의 현재 상태를 저장하는 전용 멤버들 사이에 다음 코드를 추가합니다.
private bool inShield; private bool shieldUsed; private double exitShieldTime; private const double shieldTime = 5.0;
우주선 방어막의 활성화 여부를 쉽게 확인할 수 있도록 속성을 사용하겠습니다. 이 속성은 잠시 후 SpacewarScreen.cs를 수정하여 액세스하게 됩니다. Ship.cs에서 188번 줄로 이동하여(앞 코드를 추가한 이후의 188번째 줄) 다음 코드를 추가합니다.
public bool Shield { get { return inShield; } }
지금까지 변수 집합 하나와 접근자 하나를 추가했습니다. 이제 이 변수를 게임 동작과 연결하겠습니다. 이를 위해 Ship.cs에 있는 Update 메서드를 수정할 것입니다. 앞서 설명했듯이 Ship의 Update 메서드는 XNA Framework 응용 프로그램 모델이 프레임당 한 번(또는 게임 속도에 따라 더 자주) 자동으로 호출하는 게임 루프의 Update 호출에 의해 호출됩니다. Update는 게임 개체를 움직이고 개체 간 상호 작용을 구현하고 사용자 입력을 받는 지점입니다. 이 중 Update 메서드에서 사용자 입력을 구현해 보겠습니다.
그런 다음 사용자 입력에 반응하여 새로운 방어막을 활성화하도록 Ship의 Update 메서드를 수정해야 합니다. Ship.cs에서 Update 메서드 내부의 "if (inHyperspace)"를 확인하는 바로 앞 248번 줄로 이동하여 다음 코드를 추가합니다.
if (XInputHelper.GamePads[player].XPressed && !shieldUsed) { inShield = true; shieldUsed = true; exitShieldTime = shieldTime; Sound.PlayCue( Sounds.PhaseActivate ); }
Spacewar 프로젝트에 있는 settings.xml 파일을 수정하면 이러한 키보드 매핑을 손쉽게 변경할 수 있습니다. Settings.xml은 Spacewar 전용이지만(Game.Initialize 메서드의 SpacewarGame 재정의에서 로드됨) 일반적으로 XML 데이터 파일은 게임 데이터를 위한 좋은 선택입니다. XNA Game Studio Express는 .NET Framework를 기반으로 구축되었기 때문에 게임에서 Xml 네임스페이스를 사용할 수 있습니다.
조건문 내의 코드는 방어막을 가동하고 현재 라운드에 방어막이 사용되었음을 표시하고 방어막 타이머를 시작합니다. 또한 이 코드는 XNA Framework 오디오 시스템을 사용하여 큐를 재생하고, 큐는 사용자가 듣는 사운드를 재생합니다. Spacewar는 Sounds.PhaseActivate와 같은 열거형 값을 사용하여 XNA Framework의 오디오 계층을 추상화함으로써 재생할 오디오 큐를 식별합니다. 일반적으로 큐는 문자열 값을 사용하여 호출합니다. Spacewar와 같이 큐의 수가 제한적인 경우, 특히 개발 중에 큐 이름이 변경되는 경우에는 열거형이 좋은 해결책입니다.
게임에 사운드를 추가하는 데는 XNA Game Studio Express에서 제공하는 Microsoft XACT(Cross-Platform Audio Creation)를 사용합니다. 모든 오디오 파일 및 이에 연결된 큐는 XACT 프로젝트에 보관되며, 프로젝트에 사운드를 끌어서 놓을 수 있는 그래픽 인터페이스로 표시됩니다. 게임을 빌드하면 XNA Framework Content Pipeline은 XACT 프로젝트를 로드하고 필요한 오디오 파일을 구축합니다. Spacewar에 사운드를 추가하려면 큐 이름 배열에 큐 이름을 추가하고, 큐 이름 배열에 Sounds 색인에 대한 열거형 값을 제공하는 부가적인 단계를 수행해야 합니다. 이렇게 하면 Sounds 열거형을 사용하여 사운드를 호출할 수 있습니다.
Update 호출에서는 방어막이 활성화된 경우 방어막 타이머를 실행하는 데 필요한 논리를 추가해야 합니다. 348번 줄로 이동하여("if (!Paused)" 블록의 끝부분) 다음 코드를 입력합니다.
if (inShield) { exitShieldTime -= elapsedTime.TotalSeconds; if (exitShieldTime <= 0) { inShield = false; Sound.PlayCue( Sounds.PhaseExpire ); } }
세부 렌더링
입력과 사운드는 매끄럽게 처리했지만 아직 의문이 남아 있습니다. 방어막 모양은 어떻게 만들어야 할까요? Render 메서드에 약간의 코드를 추가해야 합니다. XNA Framework에서 제공되는 몇 가지 연산 및 드로잉 기능을 사용하여 우주선의 3D 위치 위에 스프라이트(투명도가 적용된 2D 텍스처)를 그려 보겠습니다.
Solution Explorer(솔루션 탐색기)에서 솔루션 트리의 Content 폴더를 찾아 연 다음 Textures 폴더를 엽니다. 다양한 .tga 파일을 볼 수 있을 것입니다. 이 파일 중 하나를 방어막 텍스처로 사용하겠습니다. .tga 파일 하나가 2D 그래픽 이미지, 즉 스프라이트를 표현하게 됩니다.
Ship.cs에서 433번 줄로 이동하여 "if (showThrust && evolved)" 블록이 끝난 다음 부분에 새 줄을 삽입합니다. 이 새 줄에 그림 2의 코드를 추가합니다.
![]() if (inShield && evolved) { Texture2D shieldtexture = SpacewarGame.ContentManager.Load<Texture2D>( SpacewarGame.Settings.MediaPath + @”textures\circle” ); batch.Begin( SpriteBlendMode.AlphaBlend ); // Move into screen space. Vector3 location = device.Viewport.Project( position, SpacewarGame.Camera.Projection, SpacewarGame.Camera.View, Matrix.Identity ); batch.Draw( shieldtexture, new Vector2( location.X - shieldtexture.Width / 2.0f, location.Y - shieldtexture.Height / 2.0f ), new Rectangle( 0, 0, shieldtexture.Width, shieldtexture.Height ), new Color( new Vector4( 0.0f, 1.0f, 0.0f, 0.5f ) ), 0.0f, new Vector2( shieldtexture.Width / 2.0f, shieldtexture.Height / 2.0f ), (3.0f * (float)(Math.Abs( Math.Cos( exitShieldTime ) ))) + 2.0f, SpriteEffects.None, 0.0f); batch.End(); }
이 코드가 어떤 기능을 수행하는지 확인해 보겠습니다. 먼저 ContentManager 클래스가 XNA Framework와 XNA Framework Content Pipeline을 사용하여 Content\Textures 폴더에서 circle이라는 텍스처를 로드합니다. ContentManager 클래스는 런타임에 Content Pipeline에서 콘텐츠를 로드하는 XNA Framework 클래스로, 각 새로운 XNA Game Studio Express 프로젝트에서 미리 채워진 응용 프로그램 모델 코드의 일부입니다. "circle"이라는 이름은 Content\Textures 폴더에 있는 circle.tga 파일과 연결되어 있습니다. XNA Framework Content Pipeline은 각 콘텐츠 파일에 친숙한 이름을 할당하며, 이 이름은 런타임에 콘텐츠를 로드하는 데 사용됩니다.
다음 단계로, 텍스처는 XNA Framework에서 제공하는 Texture2D 클래스로 로드됩니다. Texture2D 개체를 화면에 그리는 데는 SpriteBatch(이 코드 블록에서는 batch라는 이름으로 사용됨)가 사용됩니다. SpriteBatch는 한꺼번에 화면에 그릴 텍스처 묶음을 나타냅니다.
batch.Begin을 호출하여 스프라이트 드로잉 시작을 알리고 알파 블렌딩을 사용할 것임을 표시합니다. 알파 블렌딩을 사용하면 circle 텍스처의 가장자리를 투명하게 하고 전체적으로는 반투명하게 처리하여 방어막 아래에 있는 우주선이 보이도록 할 수 있습니다.
드로잉을 시작하기 전에 드로잉을 수행할 화면 위치를 알아야 합니다. Spacewar Evolved는 3D 게임이므로 개체는 3차원 공간을 이동하며 드로잉을 수행할 때만 2D 평면으로 투영됩니다. 따라서 방어막을 그리려면 3D 우주선의 2D 위치를 찾아야 합니다.
XNA Framework에서는 그래픽 장치를 통해 이 정보를 얻을 수 있습니다. device.Viewport.Project를 호출하고 우주선의 3D 좌표와 뷰 및 투영 행렬을 전달합니다. 뷰 행렬은 플레이어의 시점에 따라 개체를 올바르게 배치하기 위해 각 3D 개체에 적용되는 선형 대수 변환을 정의합니다. 투영 행렬은 개체를 화면에 그릴 수 있도록 각 개체의 3D 좌표를 2D 화면 좌표로 변환합니다. 이러한 행렬은 미리 계산하여 저장되는 경우가 많습니다. Spacewar에서 이 두 행렬은 플레이어의 시점을 정의하는 Camera 클래스에 보관됩니다. 이러한 값으로 device.Viewport.Project를 호출하면 좌표에 실제로 우주선을 그리지 않고서도 우주선의 위치를 2D 좌표로 변환하는 작업을 시뮬레이션할 수 있습니다. 이렇게 호출하면 방어막을 그리는 데 사용할 2D 드로잉 좌표를 가진 벡터가 반환됩니다.
다음 단계는 다음 정보를 전달하고 batch.Draw를 호출하는 것입니다.
방어막에 에너지 공급!
이제 방어막을 가동하고 시각적으로 표시하고 지정된 시간이 흐른 뒤 사라지도록 할 수 있지만 아직 이 방어막은 보호 효과는 전혀 제공하지 못합니다. 보호 기능을 구현하려면 SpacewarScreen.cs를 열고 간단한 코드 블록을 두 개(각 플레이어에 대해 하나씩) 추가하면 됩니다. SpacewarScreen.cs에서 94번 줄로 이동하여 HitPlayer2 시작 부분에 다음 코드를 추가합니다.
if (ship2.Shield) { // Make a bouncy sound rather than an explosion. Sound.PlayCue( Sounds.WeaponPickup ); return; } if (ship1.Shield) { // Make a bouncy sound rather than an // explosion. Sound.PlayCue( Sounds.WeaponPickup ); return; }
앞에서 설명했듯이 SpacewarScreen.cs는 Spacewar 게임 루프의 업데이트 논리를 나타냅니다. Spacewar를 비롯한 많은 게임은 주 메뉴, 무기 선택 및 실제 게임 자체와 같은 다양한 게임 상태에 대해 별도의 게임 논리를 활용합니다. 플레이어가 게임을 진행하는 동안 제어는 여러 상태를 오갑니다. Spacewar에서 이러한 상태는 화면이라고 하며 Screen 클래스로 나타냅니다. SpacewarScreen은 Screen에서 파생되며 두 플레이어가 각자의 우주선을 조종하고 전투를 수행하는 실제 게임 플레이 상태를 처리합니다.
SpacewarScreen 클래스에서 Update 루프는 우주선, 무기, 부유하는 소행성과 같은 게임 개체를 관리합니다. 이러한 개체가 우주선과 충돌하면 논리는 HitPlayer1 또는 HitPlayer2를 호출하여 우주선에 가해질 피해를 계산합니다.
이 코드는 HitPlayer1 및 HitPlayer2의 게임 논리를 수정하여 우주선에 대한 피해를 결정하기 전에 방어막을 확인하도록 합니다. 방어막이 가동 중인 경우에는 충돌을 막는 사운드가 재생되면서 피해 함수가 더 이상 진행되지 않고 종료됩니다.
이제 끝났습니다. F5 키를 눌러 컴파일하고 실행해 보십시오. Main Menu(주 메뉴)에서 Evolved 게임 모드를 선택하고 게임이 시작되면 X 단추 또는 해당 키보드(플레이어 1은 F 키, 플레이어 2는 Page Up 키) 키를 눌러 그림 3과 같이 방어막을 가동해 보십시오. 두 플레이어는 모두 라운드당 한 번만 방어막을 사용할 수 있지만 이 방어막은 상당히 강력합니다. 모든 종류의 총알을 흡수할 뿐 아니라 소행성과 충돌해도 피해가 없으며 심지어 태양과 충돌해도 끄떡없습니다!
![]()
그림 3 방어막 가동! (더 크게 보려면 이미지를 클릭하십시오.)
방어막을 작동하고 플레이를 즐겨 보십시오. 하지만 방어막은 5초 동안만 동작하므로 시간이 얼마 없을 때는 태양에 너무 가까이 가지 않는 것이 좋습니다.
여기에서 추가로 구현할 수 있는 몇 가지 아이디어가 있습니다. 약간의 벡터 연산을 사용하면 방어막에서 총알이 흡수되지 않고 반사되도록 할 수 있습니다. 자신이 쏜 총알이 반사되어 돌아온다면 적들은 놀랍고도 괴로울 것입니다! 또는 피해 시스템을 수정하여 방어막을 가동한 우주선으로 적을 들이받으면 두 배의 피해를 주도록 할 수 있습니다. 전속력으로 돌격하십시오!
게임 개발의 재미는 실험에 있습니다. XNA Game Studio Express를 사용하면 손쉽게 재미있는 소재를 구현하여 자신만의 게임을 만들 수 있습니다.
보너스 기능: 우주를 바꾸자!
XNA Game Studio Express는 게임에서 새로운 기능을 최적의 코드로 작성하려는 사용자를 지원하는 데 그치지 않고 앞서 언급한 XNA Framework Content Pipeline이라는 기능 집합도 포함하고 있습니다. XNA Framework Content Pipeline을 사용하면 XNA Framework 기반 게임을 위한 2D, 3D 콘텐츠는 물론 오디오 콘텐츠도 만들 수 있습니다.
XNA Framework Content Pipeline은 콘텐츠 빌드 및 컴파일 프로세스를 Visual C# Express로 통합하는 기능도 제공합니다. 이에 따르는 부가적인 장점은 Visual C# Express에서 특정 유형의 콘텐츠를 직접 실행할 수 있다는 점입니다. 즉, 콘텐츠를 편집하고 다시 컴파일하여 게임에 어떤 변화가 있는지 확인할 수 있습니다. 코드를 컴파일할 때 콘텐츠도 동시에 컴파일함으로써 게임을 실행하기 전에 콘텐츠 오류를 발견할 수 있습니다.
XNA Framework Content Pipeline은 .bmp, .jpg, .png, .tga 및 .dxt를 포함한 다양한 2D 그래픽 파일 형식을 지원하며 .x, .fbx의 두 가지 3D 파일 형식도 지원합니다. 이러한 두 3D 형식 모두 다양한 무료 및 전문 3D 그래픽 창작 도구를 위한 파일 형식 내보내기를 지원합니다. 또한 XNA Framework Content Pipeline은 확장성이 뛰어나도록 설계되었으므로 온라인에서 검색하면 더 많은 파일 형식에 대한 지원을 찾을 수 있습니다.
Spacewar를 사용하여 XNA Framework Content Pipeline을 살펴보겠습니다. XNA Game Studio Express로 돌아가서 Solution Explorer(솔루션 탐색기)로 이동하십시오. Content 폴더와 Textures 폴더를 차례로 엽니다. Spacewar에서 사용하는 여러 텍스처를 볼 수 있습니다. B1_nebula01.tga 파일을 클릭하십시오. 이 파일은 게임을 플레이할 때 사용되는 배경 중 하나입니다. Solution Explorer(솔루션 탐색기) 아래에 있는 속성 표에 관련 속성이 표시됩니다(그림 4 참조). 속성 표가 표시되지 않으면 B1_nebula01.tga 파일을 마우스 오른쪽 단추로 클릭하고 Properties(속성)를 클릭하십시오.
![]()
그림 4 텍스처 속성
속성 표에서 XNA Framework Content Pipeline에만 있는 몇몇 속성을 볼 수 있습니다. 여기에서는 Content Importer 속성이 사용됩니다. 가져오기 도구는 원본 데이터(이 예에서는 .tga 파일)를 가져와 XNA Framework 콘텐츠 DOM으로 변환하는 작업을 수행합니다. 콘텐츠 DOM은 가져오기 도구에 의해 변환 및 정규화된 데이터를 보관하므로 프로세서는 파일 형식과 무관하게 작업할 수 있습니다. 다음으로 살펴볼 속성은 Content Processor 속성입니다. 프로세서는 콘텐츠 DOM의 데이터를 런타임에 사용할 적합한 개체(이 예에서는 스프라이트)로 변환하는 작업을 수행합니다. Asset Name 속성은 런타임에 자료를 로드하는 데 사용됩니다. XNA Framework Content 속성을 False로 설정하면 자료 처리를 비활성화할 수 있습니다.
B1_nebula01.tga 그래픽 파일을 편집하여 Spacewar에 어떤 변화가 있는지 확인해 보겠습니다. 먼저 .tga 파일을 편집할 수 있는 이미지 편집기가 필요합니다. 편집기가 없는 경우에는 getpaint.net에서 Paint.NET을 다운로드하십시오.
파일을 두 번 클릭하여 해당 파일과 연결된 편집기를 연 다음 파일을 약간 편집합니다(그림 5 참조). Paint.NET을 사용하는 경우에는 Adjustments 메뉴를 클릭하고 Hue/Saturation 을 클릭하여 이미지의 색상 및 채도를 간단하게 변경할 수 있습니다. 슬라이더를 이동하여 그래픽의 색상, 채도 및 밝기를 변경한 다음 OK를 클릭하여 변경 내용을 적용합니다. 파일을 수정하고 저장한 다음 XNA Game Studio Express로 돌아옵니다. F5 키를 눌러 Spacewar 프로젝트를 컴파일하고 실행합니다. XNA Game Studio Express는 파일이 변경된 것을 감지하고 새 자료를 다시 빌드하여 배포합니다(Xbox 360 콘솔에도 마찬가지). Evolved 모드로 게임을 시작하면 배경이 달라진 것을 확인할 수 있습니다.
![]()
그림 5 Paint.NET에서 텍스처 편집 (더 크게 보려면 이미지를 클릭하십시오.)
이륙!
이러한 간단한 예제는 XNA Game Studio Express의 강력한 기능 중 극히 일부에 불과합니다. XNA Framework와 XNA Framework Content Pipeline의 크로스 플랫폼 조합을 통해 이제 게임 개발의 재미있는 측면, 즉 훌륭한 콘텐츠와 창조적인 게임 플레이에 집중할 수 있습니다.
또한 XNA Creators Club에 가입하면 게임 개발 기술을 한 단계 더 높일 수 있습니다. 클럽 멤버가 되면 Xbox 360 플랫폼에서 자신만의 게임을 개발할 수 있을 뿐 아니라 멤버 전용 콘텐츠, 샘플, 시작 키트를 비롯한 게임에서 여러분의 상상을 현실화할 수 있는 다양한 리소스에 액세스할 수 있습니다.
Charles Cox는 Microsoft 게임 플랫폼 문서 그룹에서 개발자 교육을 담당하고 있으며 이전에는 DirectX 및 Microsoft Game Studios에서 테크니컬 라이터로 활약했습니다. 현재 Charles는 XNA Game Studio Express 자습서와 교육 워크숍을 개발하여 제공하고 있습니다.
Michael Klucher는 Microsoft XNA Game Studio 팀의 프로그램 관리자로, 현재는 Xbox 360 콘솔용 XNA Framework Content Pipeline 및 XNA Game Launcher를 담당하고 있습니다. 문의 사항이 있으면 Michael의 블로그(klucher.com)를 방문하십시오.
|
XNA 번역서