From 8926bf356c3355088044161b76e4a372c2e678ba Mon Sep 17 00:00:00 2001 From: Steve Streeting Date: Mon, 6 Dec 2021 16:12:14 +0000 Subject: [PATCH] InputImage now prefers the latest button input device for actions, this better differentiates between prompting for mouse button and keyboard --- .../Private/StevesUI/InputImage.cpp | 32 ++++++++++++++++--- .../Private/StevesUI/StevesUI.h | 11 +++++-- .../Public/StevesHelperCommon.h | 10 +++--- .../Public/StevesUI/InputImage.h | 6 ++-- 4 files changed, 47 insertions(+), 12 deletions(-) diff --git a/Source/StevesUEHelpers/Private/StevesUI/InputImage.cpp b/Source/StevesUEHelpers/Private/StevesUI/InputImage.cpp index 933426a..630849f 100644 --- a/Source/StevesUEHelpers/Private/StevesUI/InputImage.cpp +++ b/Source/StevesUEHelpers/Private/StevesUI/InputImage.cpp @@ -10,12 +10,13 @@ TSharedRef UInputImage::RebuildWidget() auto Ret = Super::RebuildWidget(); auto GS = GetStevesGameSubsystem(GetWorld()); - if (GS) + if (GS && !bSubbedToInputEvents) { + bSubbedToInputEvents = true; GS->OnInputModeChanged.AddUniqueDynamic(this, &UInputImage::OnInputModeChanged); - CurrentInputMode = GS->GetLastInputModeUsed(PlayerIndex); - UpdateImage(); + GS->OnButtonInputModeChanged.AddUniqueDynamic(this, &UInputImage::OnInputModeChanged); } + UpdateImage(); return Ret; } @@ -24,7 +25,10 @@ void UInputImage::OnInputModeChanged(int ChangedPlayerIdx, EInputMode InputMode) { if (ChangedPlayerIdx == PlayerIndex) { - CurrentInputMode = InputMode; + // auto GS = GetStevesGameSubsystem(GetWorld()); + // UE_LOG(LogTemp, Warning, TEXT("Updating image for input mode change: %s Button device: %s"), + // *UEnum::GetValueAsString(InputMode), + // *UEnum::GetValueAsString(GS->GetLastInputButtonPressed(ChangedPlayerIdx))); UpdateImage(); } } @@ -43,9 +47,29 @@ void UInputImage::BeginDestroy() if (GS) { GS->OnInputModeChanged.RemoveAll(this); + GS->OnButtonInputModeChanged.RemoveAll(this); } } +void UInputImage::SetVisibility(ESlateVisibility InVisibility) +{ + Super::SetVisibility(InVisibility); + + switch(InVisibility) + { + case ESlateVisibility::Collapsed: + case ESlateVisibility::Hidden: + break; + default: + case ESlateVisibility::Visible: + case ESlateVisibility::HitTestInvisible: + case ESlateVisibility::SelfHitTestInvisible: + // Make sure we update when our visibility is changed + UpdateImage(); + break; + }; +} + void UInputImage::SetFromAction(FName Name) { BindingType = EInputBindingType::Action; diff --git a/Source/StevesUEHelpers/Private/StevesUI/StevesUI.h b/Source/StevesUEHelpers/Private/StevesUI/StevesUI.h index d6aba8b..2227ce5 100644 --- a/Source/StevesUEHelpers/Private/StevesUI/StevesUI.h +++ b/Source/StevesUEHelpers/Private/StevesUI/StevesUI.h @@ -29,7 +29,8 @@ void SetWidgetFocusProperly(UWidget* Widget); template const T* GetPreferedActionOrAxisMapping(const TArray& AllMappings, const FName& Name, EInputImageDevicePreference DevicePreference, - bool bLastInputWasGamepad) + EInputMode LastInputDevice, + EInputMode LastButtonInputDevice) { const T* MouseMapping = nullptr; const T* KeyboardMapping = nullptr; @@ -53,8 +54,9 @@ const T* GetPreferedActionOrAxisMapping(const TArray& AllMappings, const FNam } const T* Preferred = nullptr; - if (GamepadMapping && bLastInputWasGamepad) + if (GamepadMapping && LastInputDevice == EInputMode::Gamepad) { + // Always prefer gamepad if used last Preferred = GamepadMapping; } else @@ -71,6 +73,11 @@ const T* GetPreferedActionOrAxisMapping(const TArray& AllMappings, const FNam case EInputImageDevicePreference::Gamepad_Mouse_Keyboard: Preferred = MouseMapping ? MouseMapping : KeyboardMapping; break; + + case EInputImageDevicePreference::Gamepad_Keyboard_Mouse_Button: + // Use the latest button press + Preferred = (MouseMapping && LastButtonInputDevice == EInputMode::Mouse) ? MouseMapping : KeyboardMapping; + break; default: break; } diff --git a/Source/StevesUEHelpers/Public/StevesHelperCommon.h b/Source/StevesUEHelpers/Public/StevesHelperCommon.h index 784a7c0..0208d4d 100644 --- a/Source/StevesUEHelpers/Public/StevesHelperCommon.h +++ b/Source/StevesUEHelpers/Public/StevesHelperCommon.h @@ -53,11 +53,13 @@ enum class EInputBindingType : uint8 UENUM(BlueprintType) enum class EInputImageDevicePreference : uint8 { - /// For actions, use Gamepad_Keyboard_Mouse, for axes, use Gamepad_Mouse_Keyboard + /// For actions, use Gamepad_Keyboard_Mouse_Button, for axes, use Gamepad_Mouse_Keyboard Auto, - /// Gamepad first, then keyboard, then mouse - this is usually best for actions (buttons) - Gamepad_Keyboard_Mouse UMETA(DisplayName="Prefer Gamepad (if active), then keyboard, then mouse"), + /// Gamepad first, then keyboard, then mouse + Gamepad_Keyboard_Mouse UMETA(DisplayName="Gamepad, Keyboard, Mouse"), /// Gamepad first, then mouse, then keyboard - this is usually best for axes - Gamepad_Mouse_Keyboard UMETA(DisplayName="Prefer Gamepad (if active), then mouse, then keyboard") + Gamepad_Mouse_Keyboard UMETA(DisplayName="Gamepad, Mouse, Keyboard"), + /// Gamepad first, then whichever of mouse or keyboard last had a BUTTON pressed (ignore axes) - this is usually best for actions (buttons) + Gamepad_Keyboard_Mouse_Button UMETA(DisplayName="Gamepad, Most Recent Button Keyboard/Mouse") }; diff --git a/Source/StevesUEHelpers/Public/StevesUI/InputImage.h b/Source/StevesUEHelpers/Public/StevesUI/InputImage.h index 0872063..a23b7df 100644 --- a/Source/StevesUEHelpers/Public/StevesUI/InputImage.h +++ b/Source/StevesUEHelpers/Public/StevesUI/InputImage.h @@ -38,9 +38,8 @@ protected: /// Custom theme to use for this input image set; if not supplied will use UStevesGameSubsystem::DefaultUiTheme UPROPERTY(EditAnywhere) UUiTheme* CustomTheme; - - EInputMode CurrentInputMode; + bool bSubbedToInputEvents = false; public: /// Tell this image to display the bound action for the current input method @@ -73,6 +72,9 @@ public: virtual void SetCustomTheme(UUiTheme* Theme); virtual void BeginDestroy() override; + + virtual void SetVisibility(ESlateVisibility InVisibility) override; + protected: virtual TSharedRef RebuildWidget() override;