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
Antares
(Antares)
June 17, 2014, 2:42pm
2
Same problem here ! If you find a solution please tell me !
joelr
(joelr)
June 18, 2014, 4:06pm
3
joelr
(joelr)
June 18, 2014, 8:35pm
4
No exact answer yet, but the ShooterGame sample has an in-game menu that seems to work fine. I’ll look into that.
Antares
(Antares)
June 18, 2014, 8:37pm
5
Keep me up to date please ! But I think it may not use slate but canvas wich is a lot different
joelr
(joelr)
June 18, 2014, 8:58pm
6
Nope, it uses Slate, and animations to boot, which is also instructive. You should download the sample and have a look!
Antares
(Antares)
June 19, 2014, 7:13pm
7
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
joelr
(joelr)
June 19, 2014, 9:49pm
8
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?