- 커플링 : B has A 인 관계
- 즉, A가 B를 가지고있고, B가 A를 가지고있을 때 서로서로 호출이 되어서 하나를 수정하면 다른 클래스에도 영향을 끼치게 되는 상황을 의미한다.
- 예시, 문열기 ‘ 떨어지는 물체 ‘ 조명 On ‘ 몹 도망 이 있다고 가정한다.
- 문 열때 ‘떨어지는 물체’의 이벤트를 위해 소유해야한다.
- 조명도 켜져야하니까 소유해야한다.
- 문 여는 타이밍에 몹도 도망가야하니까 몹도 소유하고 있어야한다.
- 이럴때 필요한게 ‘델리게이트’다.
- 문 한테 각 주체가 가지고 있는 함수의 주소를 줘서 호출을 시키는 구조다.
- 상속은 A is B 관계다.
//One Class
Class A
{
void Add()
{
ob->Test2();
}
B* obb;
}
//Another Class
Class B
{
A* ob;
void Test()
{
ob->Add();
}
void Test2()
{
}
}
델리게이트
- 실행을 위임하는 코드다.
- 특정 기능의 함수 ‘주소’만 가져와서 실행하면 주소에 있는 함수를 가진 ‘다른 주체’가 함수를 호출해주는 것이다.
04 예제, 트리거로 조명 키기
델리게이트 선언
- 기본 델리게이트 : 매개변수와 반환이 없는 델리게이트는 void형 함수라고 생각하면 편하다.
- C 에서의 foreach 문 → for(AActor* actor : GetWorld()→GetCurrentLevel()→Actors)
- actor 변수에 ‘월드 안의 현재 레벨의 엑터들’을 순차적으로 반복해서 가져온다.
- 헤더 파일 - 델리게이트 메크로 들어가기 - 델리게이트 이름 지정 - 델리게이트로 생성한 함수를 자료형 변수로 선언한다. - 델리게이트를 사용할 헤더파일 - 델리게이트 변수에 연결할 함수 선언
//델리게이트 header
DECLARE_DELEGATE(FBoxLightOverlap); //void funcName() 으로 생각해라
public:
FBoxLightOverlap OnBoxLightBeginOverlap;
//header
private:
UFUNCTION()
void OnLight(); //void 형태에 파라미터 없음
델리게이트 연결
- cpp 파일 - 현재 레벨에서 델리게이트가 선언된 클래스가 상속된 액터를 찾는 함수 호출하고 변수를 생성해서 저장 - null은 아닌지 확인 - 해당 변수를 델리게이트 함수를 호출하고 ‘함수 연결’ - 델리게이트 cpp 파일 - 컴포넌트 오버랩 이벤트에 델리게이트 함수가 연결되었는지 확인 - 연결되어있다면 실행
//cpp
AC04_Trigger* trigger = CHelpers::FindActor<AC04_Trigger>(GetWorld());
CheckNull(trigger);
trigger->OnBoxLightBeginOverlap.BindUFunction(this, "OnLight");
void AC04_Light::OnLight()
{
PointLight->SetVisibility(true);
}
//델리게이트 cpp
//이벤트가 연결되었다면?
if (OnBoxLightBeginOverlap.IsBound())
{
//이벤트 함수 실행
OnBoxLightBeginOverlap.Execute();
}
리턴 있는 델리게이트 함수
- ArgumentsType(파라미터 타입, 파라미터 명) : 파라미터 명은 ‘다이나믹 델리게이트’를 사용할때 사용한다.
- 파라미터 타입만 작성해도 된다. (기본적으로 그렇게 사용한다.)
- 델리게이트 헤더 파일 - 델리게이트 메크로 ‘RetVal(ReturnValue)’ 체크 : 이름 지정, 리턴 타입 지정, ArgumentsType(파라미터 타입, 파라미터 명) 지정 - 델리게이트 함수 선언 - 헤더 파일 - 델리게이트 함수에 연결할 함수 선언 - cpp 파일 - 함수 정의 및 연결 - 델리게이트 cpp 파일 - 연결된 함수 확인 및 실행
//델리게이트 header
DECLARE_DELEGATE_RetVal_OneParam(FString, FBoxLightColorOverlap, FLinearColor); //리턴 타입, 델리게이션 명, 파라미터 타입
//리턴 타입 있는 델리게이트
FBoxLightColorOverlap OnBoxLightColorOverlap;
//header
UFUNCTION()
FString OnRandomColor(FLinearColor InColor); //FString 형태에 파라미터 있음
//cpp
trigger->OnBoxLightColorOverlap.BindUFunction(this, "OnRandomColor");
//델리게이트 cpp
if (OnBoxLightColorOverlap.IsBound())
{
FString str = OnBoxLightColorOverlap.Execute(FLinearColor::MakeRandomColor());
CLog::Print(str);
}
2개 이상 위임받은 델리게이트
- 종류에 상관없이 누구든 똑같은 형태의 함수면 누구든 연결받을 수 있다.
- 다만, ‘리턴’을 쓰지 못한다.
- 리턴은 위임 받은 주체에서 처리 결과를 받아야하지만, 여러개를 위임받을때는 어느것의 결과를 받아야하는지 모르기 때문이다.
- 즉, 멀티캐스트 델리게이트 함수에서는 ‘리턴(반환)’을 사용하지 못한다.
- 싱글 캐스트 : 멀티캐스트를 쓰지 않은 델리게이트 함수를 의미한다.
멀티캐스트 델리게이트 선언
- 델리게이트 헤더 파일 - 델리게이트 메크로 선언 : MULTICAST 체크, 이름 지정, ArgumentsType(파라미터 타입) 2개 지정 - 델리게이트 자료형 함수 선언
//델리게이트 header
DECLARE_MULTICAST_DELEGATE_TwoParams(FMultiLightOverlap, int32, FLinearColor);
public:
FMultiLightOverlap OnMultiLightOverlap;
C++ 함수 모음
- 액터 클래스→IsA<상속 확인 클래스>() : 액터 클래스가 ‘상속 확인 클래스’에서 상속된 클래스인지 확인하고, 상속된 클래스라면 true를 반환하는 함수다.
델리게이트 함수
- 커스텀 델리게이트 함수 명.IsBound() : 델리게이트 함수와 연결된 함수가 있는지 확인하는 함수다.
- 커스텀 델리게이트 함수 명.Excute() : 델리게이트 함수와 연결된 함수를 실행하는 함수다.
- 커스텀 델리게이트 함수 명.ExcuteIfBound() : 연결된 함수가 있다면 실행시키는 함수다.