How to change focus between Slate-Menu and Game?

I basically have a first-person view game and an in-game-menu with three buttons like the scheme below:.

CompoundWidget
[
	VerticalBox
	[
		Button
		Button
		Button
	]
];

When I hit the tab-key, the game is paused, the menu + cursor shows, when I hit tab again, it closes and the game is unpaused, everything fine.

My problem is, the menu does not receive mouse-focus. I have to click on the viewport first, only then do the buttons throw hover and click events. If I do that the same phenomenon occurs with my normal game-viewport.

Since it is very uncomfortable for the player to click somewhere before being able to do anything (he/she’s racing against a clock), the Slate documentation is down and Strategy and FPS-Sample are not very conclusive, I came to ask:

How do you change mouse-focus?

I found FSlateApplication::Get().SetKeyboardFocus(…); and FSlateApplication::Get().SetFocusToGameViewport() and used it like this:

void SMyMenuWidget::SetMenuVisibility(TAttribute<EVisibility> inVisibility)
{
	SetVisibility(inVisibility);

	if (inVisibility == EVisibility::Visible)
	{
		FSlateApplication::Get().SetKeyboardFocus(SharedThis(this));
	}
	else if (inVisibility == EVisibility::Collapsed || inVisibility == EVisibility::Hidden)
	{
		FSlateApplication::Get().SetFocusToGameViewport();
	}
}

FReply SMyMenuWidget::OnKeyboardFocusReceived(const FGeometry& MyGeometry, const FKeyboardFocusEvent& InKeyboardFocusEvent)
{
	return SCompoundWidget::OnKeyboardFocusReceived(MyGeometry, InKeyboardFocusEvent).CaptureMouse(SharedThis(this)).LockMouseToWidget(SharedThis(this));
}

What did I miss or do wrong?

Thx in advance,

equus

Same problem here ! If you find a solution please tell me !

Me too. Link to my own question here: How can I change focus to Slate and back? - Programming & Scripting - Unreal Engine Forums

No exact answer yet, but the ShooterGame sample has an in-game menu that seems to work fine. I’ll look into that.

Keep me up to date please ! But I think it may not use slate but canvas wich is a lot different

Nope, it uses Slate, and animations to boot, which is also instructive. You should download the sample and have a look!

Hi Guys !

Just SOLVE this problem =), thanks to the ShooterGame !

So basically this is what you have to do :

Add this in your widget :

/** says that we can support keyboard focus */
virtual bool SupportsKeyboardFocus() const OVERRIDE{ return true; }

FReply SBLCUIWidget::OnKeyboardFocusReceived(const FGeometry& MyGeometry, const FKeyboardFocusEvent& InKeyboardFocusEvent)
{
	return FReply::Handled().ReleaseMouseCapture().CaptureJoystick(SharedThis( this ), true);
}

Then when you want to open the menu simply do that :

GEngine->GameViewport->AddViewportWidgetContent(SNew(SWeakWidget).PossiblyNullContent(MyUIWidget.ToSharedRef()));
FSlateApplication::Get().SetKeyboardFocus(MyUIWidget.ToSharedRef());

And to close it :

GEngine->GameViewport->RemoveAllViewportWidgets();
FSlateApplication::Get().SetFocusToGameViewport();

Hope this will help you because its been 3 days I am on this !!

Bests :wink:

Simple answer:
Override these methods in your top widget:

virtual bool SupportsKeyboardFocus() const OVERRIDE { return true; }
FReply OnMouseButtonDown(const FGeometry& MyGeometry, const FPointerEvent& MouseEvent) OVERRIDE
{
    //Set the keyboard focus 
    return FReply::Handled().SetKeyboardFocus(SharedThis(this), EKeyboardFocusCause::SetDirectly);
}

Then in addition to

FSlateApplication::Get().SetKeyboardFocus(SharedThis(this));

also do

FSlateApplication::Get().ReleaseMouseCapture();

Thank you very much. Who would have thought that to get mouse focus on Slate Widgets, one has to release it?