728x90
반응형
private:
list<CObj*>* m_pBullet;
총알을 저장할 리스트를 포인터형으로 만들어주고,
CObj * CPlayer::Create_Bullet(int _iA) // 매개변수는 정해진 키 값을 전해주기위해 설정하였다.
{
CBullet* pBullet = new CBullet; // 동적할당
pBullet->Initialize(); // 총알에 대한 기본 위치, 이동할 속도에 대한 정보
pBullet->Set_Pos(m_tInfo.fX, m_tInfo.fY, _iA); // 메인스테이지와 연결해준다.
return pBullet;
}
여기는 리스트에 넣어줄 정보를 담은 함수이다.
if (GetAsyncKeyState(0x41) & 0x8000) // A
m_pBullet->emplace_back(Create_Bullet(0x41)); // 해당 키 값을 Bullet클래스로 전달
if (GetAsyncKeyState(0x44) & 0x8000) // D
m_pBullet->emplace_back(Create_Bullet(0x44));
if (GetAsyncKeyState(0x57) & 0x8000) // W
m_pBullet->emplace_back(Create_Bullet(0x57));
if (GetAsyncKeyState(0x53) & 0x8000) // S
m_pBullet->emplace_back(Create_Bullet(0x53));
키를 눌렀을 때 총알이 생성되도록 해당 키일때 emplace_back으로 원소 삽입 해준다.
if (m_iCheck == 0x41) // 받아 온 키 값을 조건식으로 사용함.
m_tInfo.fX -= m_fSpeed; // m_fSpeed(10.f)만큼 이동.
if (m_iCheck == 0x44)
m_tInfo.fX += m_fSpeed;
if (m_iCheck == 0x57)
m_tInfo.fY -= m_fSpeed;
if (m_iCheck == 0x53)
m_tInfo.fY += m_fSpeed;
메인함수를 보면 UpDate 함수와 Render함수에서 계속 0.01초마다 새로고침이 진행되고 있다. 그렇기 때문에 좌표값을 조절해주면 이동하는 것처럼 보이는 것이다.
<< main 함수 >>
while (WM_QUIT != msg.message) // msg 안에 메세지가 WM_QUIT 아닐경우 수행한다.
{
if (PeekMessage(&msg, nullptr, 0, 0, PM_REMOVE)) //PeekMessage -> 메세지가 있으면 가공해서 전해줘라
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
if (dwTime + 10 < GetTickCount()) // 만약 0.01초가 지나면 수행해라
{
mainGame.UpDate(); // 이 if문을 걸어주지 않으면 한 번 움직일 때 많은 반복을 하기 때문에 조건을 걸어줘야함!
mainGame.Render();
dwTime = GetTickCount(); // 다시 값을 넣어준다.
}
}
총알을 담은 리스트를 화면에 출력해주어야하는데 리스트를 출력할 위치는 UpDate나 Render함수에 해야한다!
void CMainGame::Render()
{
RECT rc = { 100, 100, 700, 500 };
Rectangle(m_hDC, 0, 0, WINCX, WINCY); // 빈 공간을 넣어줌으로써 잔상이 남지 않는다.
Rectangle(m_hDC, rc.left, rc.top, rc.right, rc.bottom); // 큰 사각형을 하나 만들었다.
list<CObj*>::iterator iter = m_listBullet.begin();
for (auto& pBullet : m_listBullet) // 총알 출력
{
pBullet->Render(m_hDC);
}
for (; iter != m_listBullet.end();) // 큰 사각형의 밖으로 총알이 나가면 총알이 삭제되도록..
{ //Get_fX() : X좌표, Get_fY(): Y좌표
if ((*iter)->Get_fX() <= rc.left || (*iter)->Get_fX() >= rc.right || (*iter)->Get_fY() <= rc.top || (*iter)->Get_fY() >= rc.bottom)
{
delete (*iter);
iter = m_listBullet.erase(iter);
}
else
++iter; // 조건에 만족하지 않으면 다음을 가리켜라
}
m_pPlayer->Render(m_hDC); // 총알이 나올 플레이어
}
Render함수는 화면이 계속 새로고침되기 때문에 그냥 도형만 출력하면 잔상이 남는 것처럼 보이므로 제일 처음에 화면을 벗어나는 크기의 사각형을 만들어 빈 공간을 넣어준다. -> 잔상이 남지 않음
사각형 밖으로 총알이 나가지 않도록 조건을 주고 사각형 밖이면 삭제해주는데 삭제할 때 동적할당한 공간을 먼저 지워주고 삭제하였다. 이 부분에서 반복자를 주의해야한다!
iter = m_listBullet.erase(iter); 이렇게 했을 때 iter은 다음을 가르키고 있기 때문에 후에 추가로 ++iter를 하면 오류가 날 수 있으니 주의하자!
저 조건을 만족하지 않으면 ++iter로 다음 iter를 가르키게 해줘야함!
프로그램을 실행하고 키를 누르면 총알이 발사된다.
현재 리스트의 원소는 동적할당이 되어있기 때문에 동적할당 해주는 것 잊지 않아야 한다!
for_each(m_listBullet.begin(), m_listBullet.end(), Safe_Delete<CObj*>);
m_listBullet.clear();
for_each알고리즘을 이용하여 동적할당 해제를 먼저 진행한 후 원소를 삭제하였다.
728x90
반응형
'API > API' 카테고리의 다른 글
API - 충돌 (IntersectRect 함수) (0) | 2021.06.01 |
---|---|
API - 움직이는 객체 맞추기 (0) | 2021.05.30 |
GetAsyncKeyState 함수 (0) | 2021.05.29 |
API - 도형 (총알 발사) (0) | 2021.05.29 |
API - 도형만들기 (0) | 2021.05.26 |