天天看點

UE5 使用Slate制作對話視窗

最近使用Slate寫了一個UE内的編輯工具,剛好遇到了制作對話框的需求。是以,記錄一下實作的方法并分享出來。

目錄

分析視窗的構成和功能

構成

功能

編寫Slate

模态對話框

分析視窗的構成和功能

構成

首先我們要分析要制作的視窗,包含哪些内容。以下圖對話框為例。

UE5 使用Slate制作對話視窗

 此對話框,包含的元素有标題欄、輸入框、确認按鈕和取消按鈕。

讓我們來逐一分析這些元素用了哪些Slate元件:

标題欄 - SWindow

輸入框 - SEditableTextBox

确認按鈕、取消按鈕 - SButton

功能

這個視窗的功能,不但要記住使用者到底是點了确認還是取消,還要記住使用者在輸入框内輸入的内容。是以我們需要儲存這些對象的指針,友善對話框運作完畢後取得我們想要的内容。

分析完畢後,我們就可以使用Slate進行編寫了。

編寫Slate

首先是對話框整體,SWindow:

TSharedPtr<SWindow> MyDialog = SNew(SWindow)
			.Title(Title)                        // 視窗标題名
			.SizingRule(ESizingRule::Autosized)  // 根據内容大小設定尺寸
			.SupportsMinimize(false)             // 隐藏最小化按鈕
			.SupportsMaximize(false);            // 隐藏最大化按鈕
           

然後是内容輸入框,使用SEditableBox,并且在對話框運作完後擷取輸入的内容:

TSharedPtr<SEditableTextBox> TextBox = SNew(SEditableTextBox);

... 對話框運作過程 ...

// 視窗運作結束後,擷取輸入框的内容
InputString = TextBox->GetText().ToString();
           

最後編寫确認按鈕與取消按鈕,這兩個按鈕需要做到兩件事:

1. 記錄使用者按下了自身

2. 使用者按下自身後關閉對話框

TSharedPtr<SButton> OkBtn = SNew(SButton)
			.VAlign(VAlign_Center)
			.HAlign(HAlign_Center)
			[
				SNew(STextBlock)
				.Text(FText::FromString("OK"))
			];

TSharedPtr<SButton> CancelBtn = SNew(SButton)
			.VAlign(VAlign_Center)
			.HAlign(HAlign_Center)
			[
				SNew(STextBlock)
				.Text(FText::FromString("Cancel"))
			];
           

再為按鈕添加點選事件響應

bool bResult = false;
		
OkBtn->SetOnClicked(
			FOnClicked::CreateLambda([&]()->FReply
			{
				bResult = true;
				MyDialog->RequestDestroyWindow();
				return FReply::Handled();
			})
);


OkBtn->SetOnClicked(
			FOnClicked::CreateLambda([&]()->FReply
			{
				bResult = false;
				MyDialog->RequestDestroyWindow();
				return FReply::Handled();
			})
);
           

當對話框運作完畢後,我們可以根據bResult獲知使用者按下了确認按鈕還是取消按鈕。再根據TextBox->GetText().ToString()拿到輸入框的内容。

最後,我們把建立的各個Slate元件合并到一起,使用MyDialog的SetContent函數,将輸入框與按鈕加入到布局中。

MyDialog->SetContent(
			SNew(SVerticalBox)
			+ SVerticalBox::Slot()
			.Padding(5,8,5,5)
			[
				TextBox.ToSharedRef()
			]
			+ SVerticalBox::Slot()
			.Padding(5, 5, 5, 5)
			[
				SNew(SHorizontalBox)
				+ SHorizontalBox::Slot()
				.Padding(10,0)
				[
					OkBtn.ToSharedRef()
				]
				+ SHorizontalBox::Slot()
				.Padding(10, 0)
				[
					CancelBtn.ToSharedRef()
				]
			]
   );
           

​​​​​​​

模态對話框

一般來說,我們要做的對話框是模态的,即是指在使用者想要對對話框以外的應用程式進行操作時,必須首先對該對話框進行響應。是以我們要用到的核心代碼是:

FSlateApplication::Get().AddModalWindow(MyDialog, DialogParent);
           

該函數可以使得我們傳入的SWindow類型的MyDialog成為模态視窗,并阻塞使用者對UE的其他視窗進行操作。