Skip to main content

Lock Or Reconfigure Interactable

Type: Plugin/Engine only

This example shows a normal interactable actor that can be locked or unlocked from server code using the real server setters exposed by UEDInteractableComponent.

Example

#pragma once

#include "CoreMinimal.h"
#include "GameFramework/Actor.h"
#include "MyAccessTerminal.generated.h"

class UArrowComponent;
class UEDInteractableComponent;
class USceneComponent;
class UStaticMeshComponent;

UCLASS()
class AMyAccessTerminal : public AActor
{
GENERATED_BODY()

public:
AMyAccessTerminal();

UFUNCTION(BlueprintCallable)
void SetLockedState(bool bLocked);

protected:
UPROPERTY(VisibleAnywhere)
TObjectPtr<USceneComponent> Root;

UPROPERTY(VisibleAnywhere)
TObjectPtr<UStaticMeshComponent> TerminalMesh;

UPROPERTY(VisibleAnywhere)
TObjectPtr<USceneComponent> WidgetHolder;

UPROPERTY(VisibleAnywhere)
TObjectPtr<UArrowComponent> CenterArrow;

UPROPERTY(VisibleAnywhere)
TObjectPtr<UEDInteractableComponent> InteractableComponent;
};
#include "MyAccessTerminal.h"

#include "Components/ArrowComponent.h"
#include "Components/EDInteractableComponent.h"
#include "Components/SceneComponent.h"
#include "Components/StaticMeshComponent.h"

AMyAccessTerminal::AMyAccessTerminal()
{
Root = CreateDefaultSubobject<USceneComponent>(TEXT("Root"));
SetRootComponent(Root);

TerminalMesh = CreateDefaultSubobject<UStaticMeshComponent>(TEXT("TerminalMesh"));
TerminalMesh->SetupAttachment(Root);
TerminalMesh->ComponentTags.Add(FName(TEXT("DimensionComponent")));

WidgetHolder = CreateDefaultSubobject<USceneComponent>(TEXT("WidgetHolder"));
WidgetHolder->SetupAttachment(Root);
WidgetHolder->ComponentTags.Add(FName(TEXT("WidgetHolderComponent")));

CenterArrow = CreateDefaultSubobject<UArrowComponent>(TEXT("CenterArrow"));
CenterArrow->SetupAttachment(TerminalMesh);
CenterArrow->ComponentTags.Add(FName(TEXT("CenterComponent")));

InteractableComponent = CreateDefaultSubobject<UEDInteractableComponent>(TEXT("InteractableComponent"));
}

void AMyAccessTerminal::SetLockedState(bool bLocked)
{
if (!HasAuthority() || !InteractableComponent)
{
return;
}

InteractableComponent->SetDenyInteractionServer(bLocked);
InteractableComponent->SetCooldownSharedByInteractableTagServer(true);
InteractableComponent->SetCooldownSecondsServer(bLocked ? 0.f : 0.5f);
}

Why use these setters

They keep the logic inside the plugin's own interaction state flow instead of bypassing it with ad-hoc booleans.