Edit:
Figured it out, I disabled the bCanEverTick in the player controller constructor. I guess that prevents the player controller from being able to do pretty much everything.
Googled everything I could find on this and none of the solutions are working. Been trying to get this working for a day, but nothing fixes the problem.
I’ve created a player controller and I’m setting bShowMouseCursor, bEnableClickEvents, and bEnableMouseOverEvents in the C++ constructor. I’ve created a BP with this player controller as the parent, and the blueprint editor shows these booleans set to true.
I have a game mode base which uses my player controller, and I’ve got the level setup to use this game mode and player controller.
I’ve got an actor with a static mesh (also tried box collision) where I’ve set the OnClicked function using the AddDynamic macro in BeginPlay. The OnClicked function doesn’t show in the blueprint of this actor, but I assume that is because I set in on BeginPlay. I’m just trying to print out a debug message to verify the click is working.
When I play the game, I see the cursor, click the mesh of the actor, but nothing happens. I’ve also tried this with a separate blueprint actor where I just added a Cube as the root and set the OnClicked event to print a message to the screen. This also does nothing.
The player controller has the trace channel set to visibility, and both the mesh and the collision box are set to block visibility. I’ve checked project settings, engine, input, mouse properties, use mouse for touch is turned off.
I’ve watched simple videos that setup the same exact thing. Does anyone have any ideas why OnClick events still wouldn’t be working after all of this?
Yes, the player controller trace channel is set to visibility, the static mesh of the actor with the OnClick function blocks visibility in collision, and the Player controller is set to be used in the level. I can turn off show mouse cursor in the player controller blueprint and the mouse won’t be there when I start the level.
Not sure how I would figure that out. If I go into the third person starter project and setup the same exact behavior everything works. In my other project it for some reason does nothing. I don’t have a character spawned in for the player, just using a camera. So I don’t see why the click would be blocked by something else.
Must be something with the player controller though. When I create a brand new player controller with these checked and play with it, the on click message does work in my project. So I’m not sure what is doesn’t like about my C++ player controller.
And I figured it out, kind of. I set PrimaryActorTick.bCanEverTick to false in my constructor because I didn’t think I would want to the player controller to tick. Apparently this just breaks the player controller entirely. I guess everything relies on the tick function…
Thanks for helping me out. Usually I don’t get responses that quickly. I appreciate it.
Congrats on finding the source of the problem. Happy coding.
Edit
If you want the click bind reaction in c++
header
#pragma once
#include "CoreMinimal.h"
#include "GameFramework/Actor.h"
#include "MyActor.generated.h"
class UStaticMeshComponent;
class UPrimitiveComponent;
UCLASS()
class YOUR_API AMyActor : public AActor
{
GENERATED_BODY()
public:
// Sets default values for this actor's properties
AMyActor();
protected:
// Called when the game starts or when spawned
virtual void BeginPlay() override;
public:
// Called every frame
virtual void Tick(float DeltaTime) override;
UPROPERTY(BlueprintReadWrite, EditAnywhere)
UStaticMeshComponent* MeshC = nullptr;
UFUNCTION()
void OnClickedAction(UPrimitiveComponent* TouchedComponent, FKey ButtonPressed);
};
cpp
#include "MyActor.h"
#include "Components/StaticMeshComponent.h"
// Sets default values
AMyActor::AMyActor()
{
PrimaryActorTick.bCanEverTick = true;
MeshC = CreateDefaultSubobject<UStaticMeshComponent>(TEXT("MeshComp"));
MeshC->SetCollisionEnabled(ECollisionEnabled::QueryAndPhysics);
MeshC->SetCollisionResponseToChannel(ECollisionChannel::ECC_Visibility, ECollisionResponse::ECR_Block);
}
// Called when the game starts or when spawned
void AMyActor::BeginPlay()
{
Super::BeginPlay();
MeshC->OnClicked.AddDynamic(this, &AMyActor::OnClickedAction);
}
// Called every frame
void AMyActor::Tick(float DeltaTime)
{
Super::Tick(DeltaTime);
}
void AMyActor::OnClickedAction(UPrimitiveComponent* TouchedComponent, FKey ButtonPressed)
{
if (GEngine) {
GEngine->AddOnScreenDebugMessage(-1, 2, FColor::Cyan, TEXT("Clicked!!"));
}
}
Because this forum post comes up on google quite early, here’s another potential issue that can prevent OnClick from working properly.
In my case OnMouseCursorOver only worked while actualy holding down the mouse button, and OnClick would not work at all.
In the project settings, I had the option “Use Mouse for touch” enabled for some reason. Apparently this option messes with the intended functionality.