HGE tutorial6 - GUI _Project_SH
2010.06.14 23:34
Kaiserin李 Edit
6월 13일 스터디 주제
1. GUI
1.1 HGE tutorial 06 - Creating Menus
- 기본 튜토리얼 코드 작성
- hgeGUI 및 hgeGUIObject class 의 사용
1.2 외부 UI 라이브러리
- guichan 라이브러리와 CEGUI 라이브러리
- 외부 라이브러리 환경 셋팅
=========================================================================================================
- hgeGUI
- 유저인터페이스를 만들 수 있게 도와주는 헬퍼클래스
- hgeGUIObject
- custom GUI 컨트롤들을 사용할 수 있게 도와주는 추상클래스
- Default classes : hgeGUIText, hgeGUIButton, hgeGUISlider
# main.cpp
// Copy the files "menu.wav", "font1.fnt", "font1.png",
// "bg.png" and "cursor.png" from the folder "precompiled"
// to the folder with executable file. Also copy hge.dll
// and bass.dll to the same folder.
#include <hge.h>
#include <hgefont.h>
#include <hgegui.h>
#include "menuitem.h"
#include <math.h>
// Pointer to the HGE interface.
// Helper classes require this to work.
HGE *hge=0;
// Some resource handles
HEFFECT snd;
HTEXTURE tex;
hgeQuad quad;
// Pointers to the HGE objects we will use
hgeGUI *gui;
hgeFont *fnt;
hgeSprite *spr;
bool FrameFunc()
{
float dt=hge->Timer_GetDelta();
static float t=0.0f;
float tx,ty;
int id;
static int lastid=0;
// If ESCAPE was pressed, tell the GUI to finish
if(hge->Input_GetKeyState(HGEK_ESCAPE)) { lastid=5; gui->Leave(); }
// We update the GUI and take an action if
// one of the menu items was selected
id=gui->Update(dt);
if(id == -1)
{
switch(lastid)
{
case 1:
case 2:
case 3:
case 4:
gui->SetFocus(1);
gui->Enter();
break;
case 5: return true;
}
}
else if(id) { lastid=id; gui->Leave(); }
// Here we update our background animation
t+=dt;
tx=50*cosf(t/60);
ty=50*sinf(t/60);
quad.v[0].tx=tx; quad.v[0].ty=ty;
quad.v[1].tx=tx+800/64; quad.v[1].ty=ty;
quad.v[2].tx=tx+800/64; quad.v[2].ty=ty+600/64;
quad.v[3].tx=tx; quad.v[3].ty=ty+600/64;
return false;
}
bool RenderFunc()
{
// Render graphics
hge->Gfx_BeginScene();
hge->Gfx_RenderQuad(&quad);
gui->Render();
fnt->SetColor(0xFFFFFFFF);
fnt->printf(5, 5, HGETEXT_LEFT, "dt:%.3f\nFPS:%d", hge->Timer_GetDelta(), hge->Timer_GetFPS());
hge->Gfx_EndScene();
return false;
}
int WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, int)
{
hge = hgeCreate(HGE_VERSION);
hge->System_SetState(HGE_LOGFILE, "hge_tut06.log");
hge->System_SetState(HGE_FRAMEFUNC, FrameFunc);
hge->System_SetState(HGE_RENDERFUNC, RenderFunc);
hge->System_SetState(HGE_TITLE, "HGE Tutorial 06 - Creating menus");
hge->System_SetState(HGE_WINDOWED, true);
hge->System_SetState(HGE_SCREENWIDTH, 800);
hge->System_SetState(HGE_SCREENHEIGHT, 600);
hge->System_SetState(HGE_SCREENBPP, 32);
if(hge->System_Initiate())
{
// Load sound and textures
quad.tex=hge->Texture_Load("bg.png");
tex=hge->Texture_Load("cursor.png");
snd=hge->Effect_Load("menu.wav");
if(!quad.tex || !tex || !snd)
{
// If one of the data files is not found, display
// an error message and shutdown.
MessageBox(NULL, "Can't load BG.PNG, CURSOR.PNG or MENU.WAV", "Error", MB_OK | MB_ICONERROR | MB_APPLMODAL);
hge->System_Shutdown();
hge->Release();
return 0;
}
// Set up the quad we will use for background animation
quad.blend=BLEND_ALPHABLEND | BLEND_COLORMUL | BLEND_NOZWRITE;
for(int i=0;i<4;i++)
{
// Set up z-coordinate of vertices
quad.v[i].z=0.5f;
// Set up color. The format of DWORD col is 0xAARRGGBB
quad.v[i].col=0xFFFFFFFF;
}
quad.v[0].x=0; quad.v[0].y=0;
quad.v[1].x=800; quad.v[1].y=0;
quad.v[2].x=800; quad.v[2].y=600;
quad.v[3].x=0; quad.v[3].y=600;
// Load the font, create the cursor sprite
fnt=new hgeFont("font1.fnt");
spr=new hgeSprite(tex,0,0,32,32);
// Create and initialize the GUI
gui=new hgeGUI();
gui->AddCtrl(new hgeGUIMenuItem(1,fnt,snd,400,200,0.0f,"Play"));
gui->AddCtrl(new hgeGUIMenuItem(2,fnt,snd,400,240,0.1f,"Options"));
gui->AddCtrl(new hgeGUIMenuItem(3,fnt,snd,400,280,0.2f,"Instructions"));
gui->AddCtrl(new hgeGUIMenuItem(4,fnt,snd,400,320,0.3f,"Credits"));
gui->AddCtrl(new hgeGUIMenuItem(5,fnt,snd,400,360,0.4f,"Exit"));
gui->SetNavMode(HGEGUI_UPDOWN | HGEGUI_CYCLED);
gui->SetCursor(spr);
gui->SetFocus(1);
gui->Enter();
// Let's rock now!
hge->System_Start();
// Delete created objects and free loaded resources
delete gui;
delete fnt;
delete spr;
hge->Effect_Free(snd);
hge->Texture_Free(tex);
hge->Texture_Free(quad.tex);
}
// Clean up and shutdown
hge->System_Shutdown();
hge->Release();
return 0;
}
# menuitem.cpp
// In menuitem.cpp/h we define the
// behaviour of our custom GUI control
#include "menuitem.h"
// This is a GUI control constructor,
// we should initialize all the variables here
hgeGUIMenuItem::hgeGUIMenuItem(int _id, hgeFont *_fnt, HEFFECT _snd, float _x, float _y, float _delay, char *_title)
{
float w;
id=_id;
fnt=_fnt;
snd=_snd;
delay=_delay;
title=_title;
color.SetHWColor(0xFFFFE060);
shadow.SetHWColor(0x30000000);
offset=0.0f;
timer=-1.0f;
timer2=-1.0f;
bStatic=false;
bVisible=true;
bEnabled=true;
w=fnt->GetStringWidth(title);
rect.Set(_x-w/2, _y, _x+w/2, _y+fnt->GetHeight());
}
// This method is called when the control should be rendered
void hgeGUIMenuItem::Render()
{
fnt->SetColor(shadow.GetHWColor());
fnt->Render(rect.x1+offset+3, rect.y1+3, HGETEXT_LEFT, title);
fnt->SetColor(color.GetHWColor());
fnt->Render(rect.x1-offset, rect.y1-offset, HGETEXT_LEFT, title);
}
// This method is called each frame,
// we should update the animation here
void hgeGUIMenuItem::Update(float dt)
{
if(timer2 != -1.0f)
{
timer2+=dt;
if(timer2 >= delay+0.1f)
{
color=scolor2+dcolor2;
shadow=sshadow+dshadow;
offset=0.0f;
timer2=-1.0f;
}
else
{
if(timer2 < delay) { color=scolor2; shadow=sshadow; }
else { color=scolor2+dcolor2*(timer2-delay)*10; shadow=sshadow+dshadow*(timer2-delay)*10; }
}
}
else if(timer != -1.0f)
{
timer+=dt;
if(timer >= 0.2f)
{
color=scolor+dcolor;
offset=soffset+doffset;
timer=-1.0f;
}
else
{
color=scolor+dcolor*timer*5;
offset=soffset+doffset*timer*5;
}
}
}
// This method is called when the GUI
// is about to appear on the screen
void hgeGUIMenuItem::Enter()
{
hgeColor tcolor2;
scolor2.SetHWColor(0x00FFE060);
tcolor2.SetHWColor(0xFFFFE060);
dcolor2=tcolor2-scolor2;
sshadow.SetHWColor(0x00000000);
tcolor2.SetHWColor(0x30000000);
dshadow=tcolor2-sshadow;
timer2=0.0f;
}
// This method is called when the GUI
// is about to disappear from the screen
void hgeGUIMenuItem::Leave()
{
hgeColor tcolor2;
scolor2.SetHWColor(0xFFFFE060);
tcolor2.SetHWColor(0x00FFE060);
dcolor2=tcolor2-scolor2;
sshadow.SetHWColor(0x30000000);
tcolor2.SetHWColor(0x00000000);
dshadow=tcolor2-sshadow;
timer2=0.0f;
}
// This method is called to test whether the control
// have finished it's Enter/Leave animation
bool hgeGUIMenuItem::IsDone()
{
if(timer2==-1.0f) return true;
else return false;
}
// This method is called when the control
// receives or loses keyboard input focus
void hgeGUIMenuItem::Focus(bool bFocused)
{
hgeColor tcolor;
if(bFocused)
{
hge->Effect_Play(snd);
scolor.SetHWColor(0xFFFFE060);
tcolor.SetHWColor(0xFFFFFFFF);
soffset=0;
doffset=4;
}
else
{
scolor.SetHWColor(0xFFFFFFFF);
tcolor.SetHWColor(0xFFFFE060);
soffset=4;
doffset=-4;
}
dcolor=tcolor-scolor;
timer=0.0f;
}
// This method is called to notify the control
// that the mouse cursor has entered or left it's area
void hgeGUIMenuItem::MouseOver(bool bOver)
{
if(bOver) gui->SetFocus(id);
}
// This method is called to notify the control
// that the left mouse button state has changed.
// If it returns true - the caller will receive
// the control's ID
bool hgeGUIMenuItem::MouseLButton(bool bDown)
{
if(!bDown)
{
offset=4;
return true;
}
else
{
hge->Effect_Play(snd);
offset=0;
return false;
}
}
// This method is called to notify the
// control that a key has been clicked.
// If it returns true - the caller will
// receive the control's ID
bool hgeGUIMenuItem::KeyClick(int key, int chr)
{
if(key==HGEK_ENTER || key==HGEK_SPACE)
{
MouseLButton(true);
return MouseLButton(false);
}
return false;
}
# menuitem.h
#include <hge.h>
#include <hgegui.h>
#include <hgefont.h>
#include <hgecolor.h>
class hgeGUIMenuItem : public hgeGUIObject
{
public:
hgeGUIMenuItem(int id, hgeFont *fnt, HEFFECT snd, float x, float y, float delay, char *title);
virtual void Render();
virtual void Update(float dt);
virtual void Enter();
virtual void Leave();
virtual bool IsDone();
virtual void Focus(bool bFocused);
virtual void MouseOver(bool bOver);
virtual bool MouseLButton(bool bDown);
virtual bool KeyClick(int key, int chr);
private:
hgeFont *fnt;
HEFFECT snd;
float delay;
char *title;
hgeColor scolor, dcolor, scolor2, dcolor2, sshadow, dshadow;
hgeColor color, shadow;
float soffset, doffset, offset;
float timer, timer2;
};
- guichan 라이브러리 환경설정
- guichan 파일 다운
- 압축푼 후 컴파일
- guichan.lib, guichan_widget.lib, guichan_hge.lib 생성
- 예제파일 테스트
- hge.hpp, widgets.hpp, hgewidgets.cpp
이 글과 관련된 글
- [2010/05/26] [HGE] 설치방법 (1053)
- [2010/05/26] [HGE] 2D 게임엔진 - HGE (1375)

- hge , hge tutorial , gui
Things don't always turn out that way_ 