#pragma once
#include "CoreMinimal.h"
#include "Blueprint/UserWidget.h"
#include "CXChatInput.generated.h"
class UEditableTextBox;
UCLASS()
class CHATX_API UCXChatInput : public UUserWidget
{
GENERATED_BODY()
public:
UPROPERTY(meta = (BindWidget))
TObjectPtr<UEditableTextBox> EditableTextBox_ChatInput;
};
UPROPERTY
- 언리얼 리플렉션(리플렉션 = 에디터나 블루프린트에서 속성 관리 가능) 시스템에 등록하겠다는 표시
- 가비지 컬렉션 관리 + 에디터/블루프린트 연동 가능해짐
meta = (BindWidget)
- UMG(언리얼 UI 블루프린트) 위젯에 있는 같은 이름의 위젯과 자동으로 연결해주는 옵션
- 여기서는
EditableTextBox_ChatInput라는 이름의 UEditableTextBox가 UMG 위젯 블루프린트 안에 있어야 자동 바인딩됨
- 이름이 정확히 같아야 작동함 (대소문자 포함)
TObjectPtr<UEditableTextBox>
UEditableTextBox는 언리얼 엔진 기본 제공 입력 가능한 텍스트 박스 위젯 클래스.
TObjectPtr는 스마트 포인터(UE5에서 도입된 새로운 UObject 포인터 타입)
UEditableTextBox* 대신 쓰는 최신 안전한 방식
EditableTextBox_ChatInput
- C++ 클래스에서 실제로 참조할 변수 이름
- UMG 안에서 똑같은 이름의 위젯을 찾아 자동으로 매칭됨
메세지 캐싱
...
class CHATX_API ACXPlayerController : public APlayerController
{
...
public:
virtual void BeginPlay() override;
void SetChatMessageString(const FString& InChatMessageString);
protected:
...
FString ChatMessageString;
};
FString ChatMessageString;
- 이게 핵심 변수
- "내가 작성한 채팅 메시지를 잠시 저장(캐싱)" 해두는 용도
SetChatMessageString(const FString& InChatMessageString)
- 외부에서 입력한 문자열을
ChatMessageString에 넣어줌
- 예를 들어 UMG에서 텍스트 박스에
"안녕"이라고 치면 → 이 함수로 넘겨서 ChatMessageString에 저장
- 캐싱(Cache) 의미
- "임시로 보관한다"
- 입력한 채팅 메시지를 바로 서버로 보내지 않고, 우선 PlayerController에 보관해두는 것
- 나중에
SendChatToServer() 같은 함수를 호출할 때, 이 ChatMessageString을 읽어서 서버로 보내는 구조일 가능성 있음
채팅 위젯 바인딩하기
#include "UI/CXChatInput.h"
#include "Components/EditableTextBox.h"
#include "Player/CXPlayerController.h"
void UCXChatInput::NativeConstruct()
{
Super::NativeConstruct();
if (EditableTextBox_ChatInput->OnTextCommitted.IsAlreadyBound(this, &ThisClass::OnChatInputTextCommitted) == false)
{
EditableTextBox_ChatInput->OnTextCommitted.AddDynamic(this, &ThisClass::OnChatInputTextCommitted);
}
}
void UCXChatInput::NativeDestruct()
{
Super::NativeDestruct();
if (EditableTextBox_ChatInput->OnTextCommitted.IsAlreadyBound(this, &ThisClass::OnChatInputTextCommitted) == true)
{
EditableTextBox_ChatInput->OnTextCommitted.RemoveDynamic(this, &ThisClass::OnChatInputTextCommitted);
}
}
void UCXChatInput::OnChatInputTextCommitted(const FText& Text, ETextCommit::Type CommitMethod)
{
if (CommitMethod == ETextCommit::OnEnter)
{
APlayerController* OwningPlayerController = GetOwningPlayer();
if (IsValid(OwningPlayerController) == true)
{
ACXPlayerController* OwningCXPlayerController = Cast<ACXPlayerController>(OwningPlayerController);
if (IsValid(OwningCXPlayerController) == true)
{
OwningCXPlayerController->SetChatMessageString(Text.ToString());
EditableTextBox_ChatInput->SetText(FText());
}
}
}
}