Write some unit tests for the input buffer
This commit is contained in:
parent
ee8dff88ea
commit
3d4c56fcd9
@ -18,14 +18,14 @@ bool UFFInputBufferComponent::CheckInputSequence(const FFFInputSequence& InputSe
|
||||
{
|
||||
if(InputSequence.Sequence.IsEmpty())
|
||||
{
|
||||
UE_LOG(LogTemp, Error,
|
||||
UE_LOG(LogTemp, Warning,
|
||||
TEXT("FFInputBufferComponent :: CheckInputSequence - tried to check input sequence but it was empty"));
|
||||
return false;
|
||||
}
|
||||
|
||||
int CondIdx = InputSequence.Sequence.Num() - 1;
|
||||
int ElapsedFrames = 0;
|
||||
for(int InpIdx = InputBuffer.Num() - 1; InpIdx > 1; InpIdx--)
|
||||
for(int InpIdx = InputBuffer.Num() - 1; InpIdx > 0; InpIdx--)
|
||||
{
|
||||
int32 RequiredButtons = InputSequence.Sequence[CondIdx].RequiredButtons;
|
||||
EFFButtonState RequiredButtonState = InputSequence.Sequence[CondIdx].RequiredButtonState;
|
||||
@ -100,3 +100,8 @@ void UFFInputBufferComponent::DisableMostRecentInput()
|
||||
InputBuffer[InputBuffer.Num() - 1].DisabledButtons |= InputBuffer[InputBuffer.Num() - 1].Buttons;
|
||||
InputBuffer[InputBuffer.Num() - 2].DisabledButtons |= InputBuffer[InputBuffer.Num() - 2].Buttons;
|
||||
}
|
||||
|
||||
void UFFInputBufferComponent::FlushBuffer()
|
||||
{
|
||||
InputBuffer.Flush();
|
||||
}
|
||||
|
@ -101,6 +101,8 @@ public:
|
||||
|
||||
void DisableMostRecentInput();
|
||||
|
||||
void FlushBuffer();
|
||||
|
||||
protected:
|
||||
/** The underlying buffer data structure for holding past input states */
|
||||
TCircleBuffer<FFFInputState, 120> InputBuffer;
|
||||
|
139
Source/UnrealFightingFramework/Tests/InputBufferTests.cpp
Normal file
139
Source/UnrealFightingFramework/Tests/InputBufferTests.cpp
Normal file
@ -0,0 +1,139 @@
|
||||
// Project Sword & Gun Copyright Kevin Poretti
|
||||
|
||||
// FF includes
|
||||
#include "Input/FFInputBufferComponent.h"
|
||||
|
||||
// UE includes
|
||||
#include "CoreMinimal.h"
|
||||
#include "Misc/AutomationTest.h"
|
||||
|
||||
#if WITH_DEV_AUTOMATION_TESTS
|
||||
|
||||
IMPLEMENT_SIMPLE_AUTOMATION_TEST(FInputBufferTest, "FF.Input.InputBuffer",
|
||||
EAutomationTestFlags::ApplicationContextMask | EAutomationTestFlags::ProductFilter)
|
||||
bool FInputBufferTest::RunTest(const FString& Parameters)
|
||||
{
|
||||
TStrongObjectPtr<UWorld> World = TStrongObjectPtr(UWorld::CreateWorld(EWorldType::Game, false));
|
||||
// Create a dummy actor
|
||||
TStrongObjectPtr<AActor> InputBufferOwner = TStrongObjectPtr<AActor>(World->SpawnActor<AActor>());
|
||||
TestTrue(TEXT("Create InputBufferOwner"), InputBufferOwner.IsValid());
|
||||
UFFInputBufferComponent* InputBuffer =
|
||||
NewObject<UFFInputBufferComponent>(InputBufferOwner.Get(),
|
||||
UFFInputBufferComponent::StaticClass(), TEXT("InputBuffer"));
|
||||
InputBuffer->RegisterComponent();
|
||||
|
||||
// InputBuffer must be able to be created as a subobject of an actor
|
||||
{
|
||||
TestNotNull(TEXT("Create new InputBuffer component"), InputBuffer);
|
||||
}
|
||||
|
||||
// InputBuffer should not attempt to evaluate an input sequence if there is only one input in
|
||||
// the buffer and should return false
|
||||
{
|
||||
FFFInputState InputDown;
|
||||
InputDown.Buttons = 0x00000001;
|
||||
|
||||
InputBuffer->AddInput(InputDown);
|
||||
|
||||
FFFInputCondition PressedCondition;
|
||||
PressedCondition.RequiredButtons = 0x00000001;
|
||||
PressedCondition.RequiredButtonState = EFFButtonState::BTNS_Pressed;
|
||||
PressedCondition.TimeoutDuration = 0;
|
||||
|
||||
FFFInputSequence PressedSequence;
|
||||
PressedSequence.Sequence.Add(PressedCondition);
|
||||
TestFalse(TEXT("Don't try to detect a sequence if only one input is present in the buffer"),
|
||||
InputBuffer->CheckInputSequence(PressedSequence));
|
||||
}
|
||||
|
||||
InputBuffer->FlushBuffer();
|
||||
|
||||
// InputBuffer should not attempt to evaluate an input sequence if the sequence has no input conditions
|
||||
{
|
||||
FFFInputState InputUp;
|
||||
InputUp.Buttons = 0x00000000;
|
||||
FFFInputState InputDown;
|
||||
InputDown.Buttons = 0x00000001;
|
||||
|
||||
InputBuffer->AddInput(InputUp);
|
||||
InputBuffer->AddInput(InputDown);
|
||||
|
||||
FFFInputSequence EmptySequence;
|
||||
TestFalse(TEXT("Don't try to detect a sequence if the sequence has no input conditions"),
|
||||
InputBuffer->CheckInputSequence(EmptySequence));
|
||||
}
|
||||
|
||||
InputBuffer->FlushBuffer();
|
||||
|
||||
// InputBuffer must detect simple button pressed condition
|
||||
{
|
||||
FFFInputState InputUp;
|
||||
InputUp.Buttons = 0x00000000;
|
||||
FFFInputState InputDown;
|
||||
InputDown.Buttons = 0x00000001;
|
||||
|
||||
InputBuffer->AddInput(InputUp);
|
||||
InputBuffer->AddInput(InputDown);
|
||||
|
||||
FFFInputCondition PressedCondition;
|
||||
PressedCondition.RequiredButtons = 0x00000001;
|
||||
PressedCondition.RequiredButtonState = EFFButtonState::BTNS_Pressed;
|
||||
PressedCondition.TimeoutDuration = 0;
|
||||
|
||||
FFFInputSequence PressedSequence;
|
||||
PressedSequence.Sequence.Add(PressedCondition);
|
||||
TestTrue(TEXT("Detect a single button press in the buffer"),
|
||||
InputBuffer->CheckInputSequence(PressedSequence));
|
||||
}
|
||||
|
||||
InputBuffer->FlushBuffer();
|
||||
|
||||
// InputBuffer must detect simple button released condition
|
||||
{
|
||||
FFFInputState InputUp;
|
||||
InputUp.Buttons = 0x0000000;
|
||||
FFFInputState InputDown;
|
||||
InputDown.Buttons = 0x00000001;
|
||||
|
||||
InputBuffer->AddInput(InputDown);
|
||||
InputBuffer->AddInput(InputUp);
|
||||
|
||||
FFFInputCondition ReleasedCondition;
|
||||
ReleasedCondition.RequiredButtons = 0x00000001;
|
||||
ReleasedCondition.RequiredButtonState = EFFButtonState::BTNS_Released;
|
||||
ReleasedCondition.TimeoutDuration = 0;
|
||||
|
||||
FFFInputSequence ReleasedSequence;
|
||||
ReleasedSequence.Sequence.Add(ReleasedCondition);
|
||||
TestTrue(TEXT("Detect a single button release in the buffer"),
|
||||
InputBuffer->CheckInputSequence(ReleasedSequence));
|
||||
}
|
||||
|
||||
InputBuffer->FlushBuffer();
|
||||
|
||||
// InputBuffer must detect simple button down condition
|
||||
{
|
||||
FFFInputState InputUp;
|
||||
InputUp.Buttons = 0x0000000;
|
||||
FFFInputState InputDown;
|
||||
InputDown.Buttons = 0x00000001;
|
||||
|
||||
InputBuffer->AddInput(InputUp);
|
||||
InputBuffer->AddInput(InputDown);
|
||||
|
||||
FFFInputCondition DownCondition;
|
||||
DownCondition.RequiredButtons = 0x00000001;
|
||||
DownCondition.RequiredButtonState = EFFButtonState::BTNS_Down;
|
||||
DownCondition.TimeoutDuration = 0;
|
||||
|
||||
FFFInputSequence DownSequence;
|
||||
DownSequence.Sequence.Add(DownCondition);
|
||||
TestTrue(TEXT("Detect a single button press in the buffer"),
|
||||
InputBuffer->CheckInputSequence(DownSequence));
|
||||
}
|
||||
|
||||
World->DestroyWorld(false);
|
||||
return true;
|
||||
}
|
||||
|
||||
#endif //WITH_DEV_AUTOMATION_TESTS
|
@ -108,6 +108,16 @@ public:
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Flushes the buffer of all contents
|
||||
*/
|
||||
void Flush()
|
||||
{
|
||||
WriteIdx = 0;
|
||||
ReadIdx = 0;
|
||||
_Num = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Returns the element at an index supplied to the function.
|
||||
* This function will account for write index offset and wraparound of the supplied index.
|
||||
@ -119,7 +129,7 @@ public:
|
||||
{
|
||||
return Buffer[(ReadIdx + Index) % L];
|
||||
}
|
||||
|
||||
|
||||
FORCEINLINE bool IsEmpty() const
|
||||
{
|
||||
return _Num == 0;
|
||||
|
Loading…
Reference in New Issue
Block a user