League Of Legends - Link Select [winAPI 14] Collider(3)
๋ณธ๋ฌธ ๋ฐ”๋กœ๊ฐ€๊ธฐ
๐Ÿค“ Study/winAPI

[winAPI 14] Collider(3)

by GAMEMING 2024. 6. 9.
728x90

 

 

Collider ์ถฉ๋Œ์ฒด๋งˆ๋‹ค ์•„์ด๋””๋ฅผ ๊ณ ์œ ๋กœ ์ฃผ๋ ค๊ณ  ํ•˜๋Š”๋ฐ ๋งŒ์•ฝ ๊ฐ์ฒด๊ฐ€ ๋ณต์‚ฌ ๋˜์–ด ์ƒ์„ฑ๋˜๋Š” ๊ฒฝ์šฐ๋ผ๋ฉด ์–ด๋–ป๊ฒŒ ํ•ด์•ผ ํ• ๊นŒ? ๊ธฐ๋ณธ ๋ณต์‚ฌ ์ƒ์„ฑ์ž๋Š” ๊ทธ๋Œ€๋กœ ๋ณต์‚ฌํ•ด์ฃผ๊ธฐ ๋•Œ๋ฌธ์— ID๊ฐ€ ์ค‘๋ณต๋  ์ˆ˜ ์žˆ์Œ. ์ด๋Š” ์šฐ๋ฆฌ๊ฐ€ ๊ตฌํ˜„ํ•˜๊ณ ์ž ํ•˜๋Š” ๋ชฉํ‘œ์— ์œ„๋ฐฐ๋˜๊ธฐ ๋•Œ๋ฌธ์— ๊นŠ์€ ๋ณต์‚ฌ ํ•„์š”๊ฐ€ ํ•„์š”ํ•˜๋‹ค.

 

// Collider.h
class Object;	

class Collider	{
private:
	static UINT nextID;	

	Object* owner;
	Vec2	offsetPos;
	Vec2	finalPos;	

	Vec2	scale;		

	UINT	iID;	
	UINT	col;

public:
	Collider();
	Collider(const Collider& _ori);	// ๋ณต์‚ฌ์ƒ์„ฑ์ž
	~Collider();

	Collider& operator = (Collider& _ori) = delete;	// ๋Œ€์ž…์—ฐ์‚ฐ์ž

	void SetOffsetPos(Vec2 _pos) { offsetPos = _pos; }
	void SetScale(Vec2 _scale) { scale = _scale; }

	Vec2 GetOffsetPos() { return offsetPos; }
	Vec2 GetScale() { return scale; }

	Vec2 GetFinalPos() { return finalPos; }

	Object* GetObj() { return owner; }
	UINT GetID() { return iID; }

	void finalUpdate();
	void render(HDC _hdc);

	// ์ถฉ๋Œ ์‹œ์  ํ•จ์ˆ˜ ์ถ”๊ฐ€
	void OnCollision(Collider* _other);
	void OnCollisionEnter(Collider* _other);
	void OnCollisionExit(Collider* _other);

	friend class Object;
};

// Collider.cpp

Collider::Collider(const Collider& _ori)
	: owner(nullptr)
	, offsetPos(_ori.offsetPos)
	, scale(_ori.scale)
	, iID(nextID++)
{
}

 

 

๋Œ€์ž…์—ฐ์‚ฐ์ž ๋˜ํ•œ ๋ง์ด ์•ˆ๋˜๊ธฐ ๋•Œ๋ฌธ์— ๊ธˆ์ง€ ์‹œ์ผœ์ฃผ์–ด์•ผ ํ•œ๋‹ค. (delete ํ‚ค์›Œ๋“œ ์‚ฌ์šฉ)

 

 

์ €๋ฒˆ ์‹œ๊ฐ„์— ํ† ๋Œ€๋ฅผ ์งœ๋†จ๋‹ค. ํ‚ค ๊ฐ’์„ ๋งคํ•‘ ํ•ด์•ผ ํ•˜๋Š”๋ฐ ํ•ด๋‹น ์ฝ”๋“œ๋ฅผ ์ž‘์„ฑํ•ด๋ณด์ž.

 

// Collider.h
union COLLIDER_ID{
	struct {
		UINT leftID;
		UINT rightID;
	};
	ULONGLONG ID;
};


// Collider.cpp
void ColliderManager::CollisionUpdateGroup(GROUP_TYPE _left, GROUP_TYPE _right)
{
	Scene* currScene = SceneManager::Instance()->GetCurScene();
	const vector<Object*>& vecLeft = currScene->GetGroupObject(_left);	
	const vector<Object*>& vecRight = currScene->GetGroupObject(_right);
	map<ULONGLONG, bool>::iterator iter;

	for (size_t i = 0; i < vecLeft.size(); ++i) {
		if (nullptr == vecLeft[i]->GetCollider())	// ์ถฉ๋Œ์ฒด๊ฐ€ ์—†๋‹ค๋ฉด
			continue;
		for (size_t j = 0; j < vecRight.size(); ++j) {
			if (nullptr == vecRight[j]->GetCollider()
				|| (vecLeft[i] == vecRight[j]))	// ์ถฉ๋Œ์ฒด๊ฐ€ ์—†๊ฑฐ๋‚˜ ๋‚˜ ์ž์‹ ์ด๋ผ๋ฉด
				continue;

			Collider* leftCol = vecLeft[i]->GetCollider();
			Collider* rightCol = vecRight[j]->GetCollider();
			
			// ๋‘ ์ถฉ๋Œ์ฒด ์กฐํ•ฉ ์•„์ด๋”” ์ƒ์„ฑ
			COLLIDER_ID ID;		// ์ „์ฒด 8๋ฐ”์ดํŠธ (longlong)
			ID.leftID = leftCol->GetID();	// ๊ฐ๊ฐ 4๋ฐ”์ดํŠธ
			ID.rightID = rightCol->GetID();

			iter = mapColInfo.find(ID.ID);
			
			if (mapColInfo.end() == iter) {
				// ๋“ฑ๋ก์กฐ์ฐจ ๋˜์ง€ ์•Š์•˜๋˜ ๊ฒฝ์šฐ๋Š” ๋“ฑ๋กํ•ด์•ผ ํ•จ(์ถฉ๋Œํ•˜์ง€ ์•Š์•˜๋‹ค)
				mapColInfo.insert(make_pair(ID.ID, false));
				iter = mapColInfo.find(ID.ID);
			}

			if (IsCollision(leftCol, rightCol)) {
				// ํ˜„์žฌ ์ถฉ๋Œ ์ค‘์ด๋‹ค
				if (iter->second) {
					// ์ด์ „์—๋„ ์ถฉ๋Œํ•˜๊ณ  ์žˆ์—ˆ๋‹ค - ์ถฉ๋Œ ์ค‘
					leftCol->OnCollision(rightCol);
					rightCol->OnCollision(leftCol);
				}
				else {
					// ์ด์ „์—๋Š” ์ถฉ๋Œํ•˜์ง€ ์•Š์•˜๋‹ค - ๋ง‰ ์ถฉ๋Œํ•จ
					leftCol->OnCollisionEnter(rightCol);
					rightCol->OnCollisionEnter(leftCol);
					iter->second = true;
				}
			}
			else {	// ํ˜„์žฌ ์ถฉ๋Œํ•˜๊ณ  ์žˆ์ง€ ์•Š๋‹ค.
				if (iter->second) {
					// ์ด์ „์—๋Š” ์ถฉ๋Œํ•˜๊ณ  ์žˆ์—ˆ๋‹ค - ์ถฉ๋Œ์—์„œ ๋– ๋‚œ๊ฒƒ.
					leftCol->OnCollisionExit(rightCol);
					rightCol->OnCollisionExit(leftCol);
					iter->second = false;
				}
			}
		}
	}
}


bool ColliderManager::IsCollision(Collider* _leftCol, Collider* _rightCol)
{
	// ์ถฉ๋Œ์ฒด์˜ ์ตœ์ข… ์œ„์น˜ ์–ป์–ด์™€์•ผ ํ•จ.
	Vec2 leftPos = _leftCol->GetFinalPos();
	Vec2 leftScale = _leftCol->GetScale();

	Vec2 rightPos = _rightCol->GetFinalPos();
	Vec2 rightScale = _rightCol->GetScale();

	if (abs(rightPos.x - leftPos.x) < (leftScale.x + rightScale.x) / 2.f
		&& abs(rightPos.y - leftPos.y) < (leftScale.y + rightScale.y) / 2.f) {
		return true;
	}

	return false;
}

 

 

union์˜ ์„ค๋ช…์€ ์•„๋ž˜์˜ ํฌ์ŠคํŒ…์„ ์ฐธ๊ณ ํ•˜๋„๋ก ํ•˜์ž.

https://velog.io/@commi1106/C-Union-%EA%B3%B5%EC%9A%A9%EC%B2%B4

 

[C++] Union (๊ณต์šฉ์ฒด)

๊ณต์šฉ์ฒด(union)๋Š” ๊ตฌ์กฐ์ฒด(struct)์™€ ๊ฑฐ์˜ ๋™์ผํ•˜์ง€๋งŒ ๋ชจ๋“  ๋ฉค๋ฒ„ ๋ณ€์ˆ˜๊ฐ€ ํ•˜๋‚˜์˜ ๋ฉ”๋ชจ๋ฆฌ ๊ณต๊ฐ„์„ ๊ณต์œ ํ•œ๋‹ค๋Š” ์ ์ด ๋‹ค๋ฆ…๋‹ˆ๋‹ค.

velog.io

 

์ถฉ๋Œํ•˜๊ณ  ์žˆ๋Š” ์ค‘์ธ์ง€, ๋ง‰ ์ถฉ๋Œํ•˜์˜€๋Š”์ง€, ์ถฉ๋Œ์ด ๋๋‚ฌ๋Š”์ง€์— ๋”ฐ๋ผ์„œ ๊ฐ ์˜ค๋ธŒ์ ํŠธ์˜ ์ถฉ๋Œ์ฒด์—๊ฒŒ ์ƒ๋Œ€ ์˜ค๋ธŒ์ ํŠธ์™€์˜ ์ด๋ฒคํŠธ๋ฅผ ๋ณด๋‚ด์ค€๋‹ค. ์ด๋•Œ ๋งต์— ๋“ฑ๋ก๋˜์ง€ ์•Š์•˜๋‹ค๋Š” ๊ฒƒ์€ ์ด์ „ ํ”„๋ ˆ์ž„์— ์ถฉ๋Œํ•˜์ง€ ์•Š์€, ์ฆ‰ ํ˜„์žฌ ํ”„๋ ˆ์ž„์—์„œ ์ฒ˜์Œ ์ผ์–ด๋‚˜๋Š” ์ถฉ๋Œ ์ด๋ฒคํŠธ๋กœ ๋งต์— ๋“ฑ๋กํ•˜๋Š” ์ž‘์—…(insert)์„ ์ˆ˜ํ–‰ํ•˜์—ฌ์•ผ ํ•œ๋‹ค.

 

 

 

๋งŒ์•ฝ ํ˜„์žฌ ํ”„๋กœ๊ทธ๋žจ์—์„œ ์ถฉ๋Œํ•˜๋ฉด ๊ทธ ์ถฉ๋Œ๋ฐ•์Šค์˜ ์ƒ‰์„ ๋ณ€๊ฒฝํ•˜๊ณ ์ž ํ•œ๋‹ค๋ฉด ์•„๋ž˜์˜ ์ฝ”๋“œ๋ฅผ ์งœ์ฃผ๋ฉด ๋œ๋‹ค.

// Collider.cpp

void Collider::render(HDC _hdc)
{
	// ์ถ”๊ฐ€ ์˜์—ญ //
	PEN_TYPE pen = PEN_TYPE::GREEN;

	if (col)
		pen = PEN_TYPE::RED;
	//////////////
    
	SelectGDI p(_hdc, pen);
	SelectGDI b(_hdc, BRUSH_TYPE::HOLLOW);
	Rectangle(_hdc
		, (int)(finalPos.x - scale.x / 2.f)
		, (int)(finalPos.y - scale.y / 2.f)
		, (int)(finalPos.x + scale.x / 2.f)
		, (int)(finalPos.y + scale.y / 2.f));
}

 

 

์•„๋ž˜์™€ ๊ฐ™์ด ์ถฉ๋Œํ•˜๋ฉด ๊ทธ๋ฆฐ์—์„œ ๋ ˆ๋“œ๋กœ ๋ฐ”๋€Œ๋Š” ์ถฉ๋Œ ์˜์—ญ์„ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋‹ค.

 

 

 

๋นผ ๋จน์€ ์ฝ”๋“œ๊ฐ€ ์žˆ์„ ์ˆ˜ ์žˆ์Œ์œผ๋กœ ์•„๋ž˜์˜ ๊นƒํ—ˆ๋ธŒ ์ปค๋ฐ‹์„ ๋น„๊ตํ•ด์„œ ์ž‘์„ฑํ•˜๋„๋ก ํ•ด๋ผ.

 

 


 

 

์ƒ๊ฐํ•ด๋ณด์ž.

๊ฐ™์€ ์ถฉ๋Œ์ด ๋ฐœ์ƒํ•˜์˜€๋”๋ผ๋„ ํ•ด์•ผ ํ•  ์ผ์€ ๋‹ค๋ฅด๋‹ค. ์˜ˆ๋ฅผ ๋“ค์–ด player-monster๊ฐ„์˜ ์ถฉ๋Œ ์ฒ˜๋ฆฌ์ธ ๊ฒฝ์šฐ player๋Š” hp๊ฐ์†Œ, monster๋Š” ๋•Œ๋ฆฌ๋Š” ๋ชจ์…˜ ๋“ฑ ํ•ด์•ผ ํ•  ์ผ์ด ๋‹ค๋ฅด๋‹ค. ์ด๊ฑธ ์ƒ์† ๋ฐ›์•„์„œ ํ•ด์•ผ ํ• ๊นŒ? ๊ทธ๋Ÿฌ๋ฉด ๋„ˆ๋ฌด ๋ณต์žกํ•ด์ง„๋‹ค.

 

 

 

์ •๋‹ต์€ ๋‹คํ˜•์„ฑ์„ ์ด์šฉํ•˜์ž. ์ถฉ๋Œ์ฒด๋Š” ์ถฉ๋Œ์„ ์†Œ์œ ํ•˜๊ณ  ์žˆ๋Š” ์˜ค๋ธŒ์ ํŠธ ํด๋ž˜์Šค๋ฅผ ์ž์„ธํ•˜๊ฒŒ๋Š” ๋ชจ๋ฅด๋‚˜ ์ถฉ๋Œ์ฒด ๋‚ด๋ถ€์—์„œ ์˜ค๋ธŒ์ ํŠธ๋ฅผ ๊ฐ€๋ฅดํ‚ฌ ์ˆ˜๋Š” ์žˆ๋‹ค. (์œ„์—์„œ์˜ owner๊ฐ์ฒด)

 

์ถฉ๋Œ์ฒด ๋‚ด๋ถ€์—์„œ ์ถฉ๋Œ ์ด๋ฒคํŠธ๋ฅผ ๊ฐ€์ƒํ•จ์ˆ˜๋กœ ๋งŒ๋“ค์–ด ๋†จ์œผ๋ฉด ์ถฉ๋Œ์ฒด๋Š” ์˜ค๋ธŒ์ ํŠธ์— ์ด๋ฅผ ์•Œ๋ ค์ฃผ๊ณ  ์•Œ์•„์„œ ์ฒ˜๋ฆฌํ•˜๋„๋ก ํ•˜๋ฉด ๋˜์ง€ ์•Š์„๊นŒ?

 

Object.h์— ์•„๋ž˜์˜ ์ฝ”๋“œ๋ฅผ ๋„ฃ๋„๋ก ํ•˜์ž

 

 

ํ•ด๋‹น ์ •์˜๋Š” ์ž์‹ ํด๋ž˜์Šค์—์„œ ํ•  ๊ฒƒ์ด๋‹ค.

์ด๋ ‡๊ฒŒ ํ•ด ๋†“์œผ๋ฉด ์•„๋ž˜์˜ ์ฝ”๋“œ์ฒ˜๋Ÿผ ์ถฉ๋Œ์ฒด์—์„œ ์ด๋ฒคํŠธ์— ๋”ฐ๋ผ ์˜ค๋ธŒ์ ํŠธ์— ์•Œ๋ ค์ฃผ๋ฉด ๋  ๊ฒƒ์ด๋‹ค. 

void Collider::OnCollision(Collider* _other)
{
	owner->OnCollision(_other);
}

void Collider::OnCollisionEnter(Collider* _other)
{
	++col;
	owner->OnCollisionEnter(_other);
}

void Collider::OnCollisionExit(Collider* _other)
{
	--col;
	owner->OnCollisionExit(_other);
}

 

 

 

์ด์ œ ํ•ด๋‹น ์˜ค๋ธŒ์ ํŠธ ๊ฐ์ฒด์—์„œ ์‚ฌ์šฉํ•  ์ถฉ๋Œ ์ด๋ฒคํŠธ์— ๋Œ€ํ•œ ํ•จ์ˆ˜๋ฅผ ์ •์˜ํ•˜๋ฉด ๋œ๋‹ค.

// Monster.h
	virtual void OnCollisionEnter(Collider* _other);  // ์ถ”๊ฐ€


// Monster.cpp

void Monster::OnCollisionEnter(Collider* _other)
{
	Object* otherObj = _other->GetObj();
    
    // if (otherObj->GetName() == L"Missile") {
    		// ์ถฉ๋Œ ์ƒ๋Œ€๊ฐ€ ๋ฏธ์‚ฌ์ผ์ธ ๊ฒฝ์šฐ ๋‚˜ ์ž์‹ ์„ ์‚ญ์ œ
    //}
}

 

 

์œ„์˜ ์ฝ”๋“œ์—์„œ ๋ฌธ์ œ๊ฐ€ ๋˜๋Š” ๊ฒƒ์ด ์žˆ๋‹ค.

์˜ค๋ธŒ์ ํŠธ๋ฅผ ์‚ญ์ œํ•˜๊ฒŒ ๋˜๋Š” ๊ฒฝ์šฐ ํ•ด๋‹น ๋ฉ”๋ชจ๋ฆฌ๋ฅผ ์ ‘๊ทผํ•  ์ˆ˜ ์—†๋„๋ก ํ•ด์•ผ ํ•œ๋‹ค. ์ฆ‰ ์ฐธ์กฐํ•˜๊ณ  ์žˆ๋˜ ์• ๋“คํ•œํ…Œ ์ฃฝ์—ˆ๋‹ค๋Š” ์‚ฌ์‹ค์„ ์•Œ๋ ค์•ผ ํ•˜๋Š”๋ฐ ๋ชจ๋“  ์˜ค๋ธŒ์ ํŠธ๋ฅผ ์–ด๋–ป๊ฒŒ ์กฐ์‚ฌํ•˜๊ณ , ์ฝ”๋”ฉํ•  ๋•Œ๋„ ์‚ญ์ œ๋œ ์˜ค๋ธŒ์ ํŠธ๋ฅผ ๊ฑด๋“ค์ผ๊นŒ ๋ด ๊ฑฑ์ •ํ•˜๊ฒŒ ๋œ๋‹ค.


์‚ญ์ œ๋ฅผ ์–ด๋–ป๊ฒŒ ํ•ด์•ผํ•˜๋Š”๊ฐ€?, ์”ฌ ๋ณ€๊ฒฝ๋„ ๋ฌธ์ œ (A์”ฌ updateํ–ˆ๋Š”๋ฐ B์”ฌ์œผ๋กœ ์ฒด์ธ์ง€ ๋˜๋ฉด ?)
ํ‚ค ์ด๋ฒคํŠธ ๋งํ•  ๋•Œ๋„ ์–˜๊ธฐ ํ–ˆ์ง€๋งŒ ์–ด๋–ค ์ด๋ฒคํŠธ๊ฐ€ ๋ฐœ์ƒํ•˜๋ฉด ๋ชจ๋“  ํ”„๋ ˆ์ž„์— ๋™์ผํ•˜๊ฒŒ ์ ์šฉ๋˜์–ด์•ผ ํ•œ๋‹ค. ๊ฐ™์€ ํ”„๋ ˆ์ž„ ์‚ฌ๊ฑด์ž„์—๋„ ๋‹ค๋ฅด๊ฒŒ ๋ฐ›์•„ ๋“ค์—ฌ์งˆ ์ˆ˜๊ฐ€ ์žˆ๊ธฐ์— ์ค‘์š”ํ•œ ์ด๋ฒคํŠธ๋ฅผ ํƒ€์ž„ ๋‹จ์œ„๋กœ ๋™๊ธฐํ™” ํ•ด์•ผ ํ•œ๋‹ค. ( = ์ง€์—ฐ์ฒ˜๋ฆฌ )

 

๋‹ค์Œ ์‹œ๊ฐ„์— ์˜ค๋ธŒ์ ํŠธ๊ฐ€ "๋‚  ์ฃฝ์—ฌ์ฃผ์„ธ์š”" ํ•ด๋„ ๋ฐ”๋กœ ์ฃฝ์ด์ง€ ์•Š๊ณ  ๋ชจ๋“  ์—…๋ฐ์ดํŠธ๊ฐ€ ๋‹ค ๋˜๊ณ  ๋‹ค์Œ ์—…๋ฐ์ดํŠธ์—์„œ ์ ์šฉํ•  ๊ฒƒ์ด๋‹ค. ์ด๊ฒƒ์ด Event๋งค๋‹ˆ์ €.

 

 

https://github.com/MiyeongEom/GameBasic/commit/7a1699528ebab8de4cd97e2c4d05ba6f2f3d1594

 

~Collider(3) · MiyeongEom/GameBasic@7a16995

MiyeongEom committed Jun 9, 2024

github.com

 

'๐Ÿค“ Study > winAPI' ์นดํ…Œ๊ณ ๋ฆฌ์˜ ๋‹ค๋ฅธ ๊ธ€

[winAPI 16] Scene & Object  (1) 2024.06.10
[winAPI 15] Event Manager  (1) 2024.06.10
[winAPI 13] Collider(2)  (1) 2024.06.08
[winAPI 12] Collider(1)  (0) 2024.06.06
[winAPI 11] Resource Manager  (0) 2024.06.06