You've already forked UnrealEngineUWP
mirror of
https://github.com/izzy2lost/UnrealEngineUWP.git
synced 2026-03-26 18:15:20 -07:00
Compatability fixes and minor changes.
Full changes: - Fixed error reading the minor engine version, which broke the netcode in the transition from 4.9 to 4.10 - Added '-UnitTestClientDebug' commandline parameter, which launches unit test clients with a valid render interface, to allow interaction when debugging - Added a 'MaxAutoCloseCount' config variable, to limit the number of times a unit test can be auto-aborted, before the unit test tool refuses to run it again - Fixed rare infinite recursion in unit test log window search - Added unit test failure condition, when trying to send an RPC when the net buffers are saturated - Increased the wait time to 2 minutes before auto-aborting, when a unit test crashes, due to long wait time for crash stack dump sometimes - Added better notification of unit tests aborts, in the status window - Prevent net connections timing out in developer mode - Updated comments to use VAX hashtags [CL 2634646 by John Barrett in Main branch]
This commit is contained in:
committed by
Shambler@OldUnreal.com
parent
a11f177636
commit
8331a99bfa
@@ -364,9 +364,11 @@ public:
|
||||
FOnSuspendStateChange OnServerSuspendState;
|
||||
|
||||
|
||||
#if TARGET_UE4_CL >= CL_DEPRECATEDEL
|
||||
private:
|
||||
/** Handle to the registered InternalNotifyNetworkFailure delegate */
|
||||
FDelegateHandle InternalNotifyNetworkFailureDelegateHandle;
|
||||
#endif
|
||||
|
||||
|
||||
/**
|
||||
@@ -605,6 +607,11 @@ protected:
|
||||
|
||||
virtual void ResetTimeout(FString ResetReason, bool bResetConnTimeout=false, uint32 MinDuration=0) override;
|
||||
|
||||
/**
|
||||
* Resets the net connection timeout
|
||||
*/
|
||||
void ResetConnTimeout();
|
||||
|
||||
|
||||
/**
|
||||
* Returns the requirements flags, that this unit test currently meets
|
||||
|
||||
@@ -14,7 +14,7 @@ class ANUTActor;
|
||||
/**
|
||||
* Enum for defining custom NetcodeUnitTest control channel commands (sent through NMT_NUTControl)
|
||||
*/
|
||||
// @todo JohnB: Fully document individually
|
||||
// @todo #JohnBDoc: Fully document individually
|
||||
namespace ENUTControlCommand
|
||||
{
|
||||
enum Type
|
||||
@@ -162,7 +162,7 @@ public:
|
||||
/**
|
||||
* Received by all clients, emits a ping to log
|
||||
*/
|
||||
// @todo JohnB: When the VM reflection helper is finished, remove NETCODEUNITTEST_API from this, and use reflection instead
|
||||
// @todo #JohnBRefactor: When the VM reflection helper is finished, remove NETCODEUNITTEST_API from this, and use reflection instead
|
||||
UFUNCTION(reliable, NetMulticast)
|
||||
NETCODEUNITTEST_API void NetMulticastPing();
|
||||
|
||||
|
||||
@@ -8,18 +8,23 @@
|
||||
|
||||
|
||||
/**
|
||||
* A net connection for enabling unit testing through barebones/minimal client connections
|
||||
*/
|
||||
* A net connection for enabling unit testing through barebones/minimal client connections
|
||||
*/
|
||||
UCLASS(transient)
|
||||
class UUnitTestNetConnection : public UIpConnection
|
||||
{
|
||||
GENERATED_UCLASS_BODY()
|
||||
|
||||
|
||||
virtual void InitBase(UNetDriver* InDriver, class FSocket* InSocket, const FURL& InURL, EConnectionState InState,
|
||||
int32 InMaxPacket = 0, int32 InPacketOverhead = 0) override;
|
||||
|
||||
virtual void InitConnection(UNetDriver* InDriver, EConnectionState InState, const FURL& InURL, int32 InConnectionSpeed = 0, int32 InMaxPacket = 0) override;
|
||||
virtual void InitBase(UNetDriver* InDriver, class FSocket* InSocket, const FURL& InURL, EConnectionState InState,
|
||||
int32 InMaxPacket=0, int32 InPacketOverhead=0) override;
|
||||
|
||||
#if TARGET_UE4_CL < CL_INITCONNPARAM
|
||||
virtual void InitConnection(UNetDriver* InDriver, EConnectionState InState, const FURL& InURL, int32 InConnectionSpeed=0) override;
|
||||
#else
|
||||
virtual void InitConnection(UNetDriver* InDriver, EConnectionState InState, const FURL& InURL, int32 InConnectionSpeed=0,
|
||||
int32 InMaxPacket=0) override;
|
||||
#endif
|
||||
|
||||
|
||||
virtual void LowLevelSend(void* Data, int32 Count) override;
|
||||
@@ -30,28 +35,28 @@ class UUnitTestNetConnection : public UIpConnection
|
||||
|
||||
|
||||
/**
|
||||
* Delegate for hooking 'LowLevelSend'
|
||||
*
|
||||
* @param Data The data being sent
|
||||
* @param Count The number of bytes being sent
|
||||
*/
|
||||
* Delegate for hooking 'LowLevelSend'
|
||||
*
|
||||
* @param Data The data being sent
|
||||
* @param Count The number of bytes being sent
|
||||
*/
|
||||
DECLARE_DELEGATE_TwoParams(FLowLevelSendDel, void* /*Data*/, int32 /*Count*/);
|
||||
|
||||
/**
|
||||
* Delegate for hooking 'ReceivedRawPacket'
|
||||
*
|
||||
* @param Data The data received
|
||||
* @param Count The number of bytes received
|
||||
*/
|
||||
* Delegate for hooking 'ReceivedRawPacket'
|
||||
*
|
||||
* @param Data The data received
|
||||
* @param Count The number of bytes received
|
||||
*/
|
||||
DECLARE_DELEGATE_TwoParams(FReceivedRawPacketDel, void* /*Data*/, int32& /*Count*/);
|
||||
|
||||
/**
|
||||
* Delegate for notifying on (and optionally blocking) replicated actor creation
|
||||
*
|
||||
* @param ActorClass The class of the actor being replicated
|
||||
* @param bActorChannel Whether or not this actor creation is from an actor channel
|
||||
* @return Whether or not to allow creation of the actor
|
||||
*/
|
||||
* Delegate for notifying on (and optionally blocking) replicated actor creation
|
||||
*
|
||||
* @param ActorClass The class of the actor being replicated
|
||||
* @param bActorChannel Whether or not this actor creation is from an actor channel
|
||||
* @return Whether or not to allow creation of the actor
|
||||
*/
|
||||
DECLARE_DELEGATE_RetVal_TwoParams(bool, FOnReplicatedActorSpawn, UClass* /*ActorClass*/, bool /*bActorChannel*/);
|
||||
|
||||
|
||||
@@ -68,3 +73,4 @@ class UUnitTestNetConnection : public UIpConnection
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
#include "UnitTest.generated.h"
|
||||
|
||||
|
||||
// @todo JohnB: For bugtracking/changelist info, consider adding auto-launching of P4/TTP/Browser-JIRA links,
|
||||
// @todo #JohnBFeature: For bugtracking/changelist info, consider adding auto-launching of P4/TTP/Browser-JIRA links,
|
||||
// upon double-clicking these entries in the status windows
|
||||
|
||||
|
||||
@@ -173,7 +173,7 @@ protected:
|
||||
bool bFirstTimeStats;
|
||||
|
||||
|
||||
// @todo JohnB: Merge the two below variables
|
||||
// @todo #JohnBRefactor: Merge the two below variables
|
||||
/** Whether or not the unit test has completed */
|
||||
bool bCompleted;
|
||||
|
||||
|
||||
@@ -26,6 +26,9 @@
|
||||
* -UnitTestClientParms="CommandlineParameters"
|
||||
* - Adds additional commandline parameters to unit test client instances
|
||||
*
|
||||
* -UnitTestClientDebug
|
||||
* - Launches unit test clients with a valid render interface (so you can interact with the client window), and a larger window
|
||||
*
|
||||
* -UnitTestCap=x
|
||||
* - Caps the maximum number of unit tests that can run at the same time
|
||||
*/
|
||||
|
||||
@@ -35,7 +35,7 @@ public:
|
||||
UPROPERTY(config)
|
||||
bool bCapUnitTestMemory;
|
||||
|
||||
// @todo JohnB: Add a bool, for specifying that unit tests can be terminated, when memory limits are breached
|
||||
// @todo #JohnBLowPri: Add a bool, for specifying that unit tests can be terminated, when memory limits are breached
|
||||
|
||||
/** When total physical memory usage, as a percentage, reaches this limit, no new unit tests can be started */
|
||||
UPROPERTY(config)
|
||||
@@ -45,6 +45,10 @@ public:
|
||||
UPROPERTY(config)
|
||||
uint8 AutoCloseMemoryPercent;
|
||||
|
||||
/** Limits the number of auto-aborts a particular unit test will allow, before it is no longer accepted for re-queueing */
|
||||
UPROPERTY(config)
|
||||
uint8 MaxAutoCloseCount;
|
||||
|
||||
|
||||
/** Holds a list of unit tests pending execution */
|
||||
UPROPERTY()
|
||||
@@ -88,6 +92,9 @@ public:
|
||||
|
||||
|
||||
private:
|
||||
/** The time at which the memory limit was last hit */
|
||||
double LastMemoryLimitHit;
|
||||
|
||||
/** When a unit test is force-closed, wait a number of ticks for global memory values to update, before closing any more */
|
||||
int32 MemoryTickCountdown;
|
||||
|
||||
@@ -201,8 +208,9 @@ public:
|
||||
*
|
||||
* @param InUnitTest The unit test to print results information for
|
||||
* @param bFinalSummary Whether or not this is the final summary printout (changes the formatting slightly)
|
||||
* @param bUnfinished Whether or not the unit test was aborted and could not be run
|
||||
*/
|
||||
void PrintUnitTestResult(UUnitTest* InUnitTest, bool bFinalSummary=false);
|
||||
void PrintUnitTestResult(UUnitTest* InUnitTest, bool bFinalSummary=false, bool bUnfinished=false);
|
||||
|
||||
/**
|
||||
* Prints the final unit test summary, when all active/pending unit tests have completed
|
||||
@@ -232,7 +240,7 @@ public:
|
||||
// Must override in subclasses, that need ticking
|
||||
virtual bool IsTickable() const override
|
||||
{
|
||||
// @todo JohnB: Find out how the CDO is getting registered for ticking - this is odd
|
||||
// @todo #JohnBLowPri: Find out how the CDO is getting registered for ticking - this is odd
|
||||
return !IsPendingKill() && !GIsServer && !HasAnyFlags(RF_ClassDefaultObject);
|
||||
}
|
||||
|
||||
|
||||
@@ -24,7 +24,7 @@ namespace UnrealBuildTool.Rules
|
||||
}
|
||||
);
|
||||
|
||||
// @todo JohnB: Currently don't support standalone commandlet, with static builds (can't get past linker error in Win32)
|
||||
// @todo #JohnBLowpri: Currently don't support standalone commandlet, with static builds (can't get past linker error in Win32)
|
||||
if (!Target.IsMonolithic)
|
||||
{
|
||||
PrivateDependencyModuleNames.AddRange
|
||||
|
||||
@@ -25,6 +25,11 @@
|
||||
#include "Regex.h"
|
||||
|
||||
|
||||
// @todo #JohnBMultiFakeClient: Eventually, move >all< of the minimal/headless client handling code, into a new/separate class,
|
||||
// so that a single unit test can have multiple minimal clients on a server.
|
||||
// This would be useful for licensees, for doing load testing:
|
||||
// https://udn.unrealengine.com/questions/247014/clientserver-automation.html
|
||||
|
||||
/**
|
||||
* UClientUnitTest
|
||||
*/
|
||||
@@ -498,7 +503,7 @@ void UClientUnitTest::NotifyProcessLog(TWeakPtr<FUnitTestProcess> InProcess, con
|
||||
}
|
||||
}
|
||||
|
||||
// @todo JohnB: Consider also, adding a way to communicate with launched clients,
|
||||
// @todo #JohnBLowPri: Consider also, adding a way to communicate with launched clients,
|
||||
// to reset their connection timeout upon server progress, if they fully startup before the server does
|
||||
}
|
||||
|
||||
@@ -586,7 +591,7 @@ void UClientUnitTest::NotifyProcessSuspendState(TWeakPtr<FUnitTestProcess> InPro
|
||||
OnServerSuspendState.ExecuteIfBound(InSuspendState);
|
||||
}
|
||||
|
||||
// @todo JohnB: Want to support client process debugging in future?
|
||||
// @todo #JohnBLowPri: Want to support client process debugging in future?
|
||||
}
|
||||
|
||||
|
||||
@@ -610,8 +615,8 @@ bool UClientUnitTest::NotifyConsoleCommandRequest(FString CommandContext, FStrin
|
||||
|
||||
if (!BadCmds.Contains(Command))
|
||||
{
|
||||
// @todo JohnB: Should this mark the log origin, as from the unit test?
|
||||
// @todo JohnB: In general, I'm not sure how I handle the log-origin of UI-triggered events;
|
||||
// @todo #JohnB: Should this mark the log origin, as from the unit test?
|
||||
// @todo #JohnB: In general, I'm not sure how I handle the log-origin of UI-triggered events;
|
||||
// they maybe should be captured/categorized better
|
||||
UNIT_LOG_BEGIN(this, ELogType::OriginConsole);
|
||||
bHandled = GEngine->Exec(TargetWorld, *Command, *GLog);
|
||||
@@ -625,7 +630,7 @@ bool UClientUnitTest::NotifyConsoleCommandRequest(FString CommandContext, FStrin
|
||||
}
|
||||
else if (CommandContext == TEXT("Server"))
|
||||
{
|
||||
// @todo JohnB: Perhaps add extra checks here, to be sure we're ready to send console commands?
|
||||
// @todo #JohnBBug: Perhaps add extra checks here, to be sure we're ready to send console commands?
|
||||
//
|
||||
// UPDATE: Yes, this is a good idea, because if the client hasn't gotten to the correct login stage
|
||||
// (NMT_Join or such, need to check when server rejects non-login control commands),
|
||||
@@ -658,7 +663,7 @@ bool UClientUnitTest::NotifyConsoleCommandRequest(FString CommandContext, FStrin
|
||||
}
|
||||
else if (CommandContext == TEXT("Client"))
|
||||
{
|
||||
// @todo JohnB
|
||||
// @todo #JohnBFeature
|
||||
|
||||
UNIT_LOG(ELogType::OriginConsole, TEXT("Client console commands not yet implemented"));
|
||||
}
|
||||
@@ -702,7 +707,14 @@ bool UClientUnitTest::SendRPCChecked(AActor* Target, const TCHAR* FunctionName,
|
||||
{
|
||||
if (TargetFunc->ParmsSize == ParmsSize + ParmsSizeCorrection)
|
||||
{
|
||||
Target->ProcessEvent(TargetFunc, Parms);
|
||||
if (UnitConn->IsNetReady(false))
|
||||
{
|
||||
Target->ProcessEvent(TargetFunc, Parms);
|
||||
}
|
||||
else
|
||||
{
|
||||
UNIT_LOG(ELogType::StatusFailure, TEXT("Failed to send RPC '%s', network saturated."), FunctionName);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -765,7 +777,7 @@ bool UClientUnitTest::PostSendRPC(FString RPCName, AActor* Target/*=NULL*/)
|
||||
}
|
||||
|
||||
|
||||
// @todo JohnB: This should be changed to work as compile-time conditionals, if possible
|
||||
// @todo #JohnBRefactor: This should be changed to work as compile-time conditionals, if possible
|
||||
bool UClientUnitTest::ValidateUnitTestSettings(bool bCDOCheck/*=false*/)
|
||||
{
|
||||
bool bSuccess = Super::ValidateUnitTestSettings();
|
||||
@@ -973,9 +985,17 @@ void UClientUnitTest::ResetTimeout(FString ResetReason, bool bResetConnTimeout/*
|
||||
|
||||
Super::ResetTimeout(ResetReason, bResetConnTimeout, MinDuration);
|
||||
|
||||
if (bResetConnTimeout && UnitConn != NULL && UnitConn->State != USOCK_Closed && UnitConn->Driver != NULL)
|
||||
if (bResetConnTimeout)
|
||||
{
|
||||
// @todo JohnB: This is a slightly hacky way of setting the timeout to a large value, which will be overridden by newly
|
||||
ResetConnTimeout();
|
||||
}
|
||||
}
|
||||
|
||||
void UClientUnitTest::ResetConnTimeout()
|
||||
{
|
||||
if (UnitConn != NULL && UnitConn->State != USOCK_Closed && UnitConn->Driver != NULL)
|
||||
{
|
||||
// @todo #JohnBHack: This is a slightly hacky way of setting the timeout to a large value, which will be overridden by newly
|
||||
// received packets, making it unsuitable for most situations (except crashes - but that could still be subject
|
||||
// to a race condition)
|
||||
UnitConn->LastReceiveTime = UnitConn->Driver->Time + (float)(TimeoutExpire - FPlatformTime::Seconds());
|
||||
@@ -989,7 +1009,7 @@ bool UClientUnitTest::ExecuteUnitTest()
|
||||
|
||||
bool bValidSettings = ValidateUnitTestSettings();
|
||||
|
||||
// @todo JohnB: Fix support for Steam eventually
|
||||
// @todo #JohnBLowPri: Fix support for Steam eventually
|
||||
bool bSteamAvailable = NUTNet::IsSteamNetDriverAvailable();
|
||||
|
||||
if (bValidSettings && !bSteamAvailable)
|
||||
@@ -1093,8 +1113,12 @@ bool UClientUnitTest::ConnectFakeClient(FUniqueNetIdRepl* InNetID/*=NULL*/)
|
||||
|
||||
if (GEngine != NULL)
|
||||
{
|
||||
#if TARGET_UE4_CL >= CL_DEPRECATEDEL
|
||||
InternalNotifyNetworkFailureDelegateHandle = GEngine->OnNetworkFailure().AddUObject(this,
|
||||
&UClientUnitTest::InternalNotifyNetworkFailure);
|
||||
#else
|
||||
GEngine->OnNetworkFailure().AddUObject(this, &UClientUnitTest::InternalNotifyNetworkFailure);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
@@ -1189,12 +1213,12 @@ bool UClientUnitTest::ConnectFakeClient(FUniqueNetIdRepl* InNetID/*=NULL*/)
|
||||
return bSuccess;
|
||||
}
|
||||
|
||||
// @todo JohnB: Reconsider naming of this function, if you modify the other functions using 'fake'
|
||||
// @todo #JohnBRefactor: Reconsider naming of this function, if you modify the other functions using 'fake'
|
||||
void UClientUnitTest::CleanupFakeClient()
|
||||
{
|
||||
if (UnitWorld != NULL && UnitNetDriver != NULL)
|
||||
{
|
||||
// @todo JohnB: As with the 'CreateFakePlayer' function, naming it 'fake' may not be optimal
|
||||
// @todo #JohnBRefactor: As with the 'CreateFakePlayer' function, naming it 'fake' may not be optimal
|
||||
NUTNet::DisconnectFakePlayer(UnitWorld, UnitNetDriver);
|
||||
|
||||
UnitNetDriver->Notify = NULL;
|
||||
@@ -1213,7 +1237,11 @@ void UClientUnitTest::CleanupFakeClient()
|
||||
|
||||
if (GEngine != NULL)
|
||||
{
|
||||
#if TARGET_UE4_CL >= CL_DEPRECATEDEL
|
||||
GEngine->OnNetworkFailure().Remove(InternalNotifyNetworkFailureDelegateHandle);
|
||||
#else
|
||||
GEngine->OnNetworkFailure().RemoveUObject(this, &UClientUnitTest::InternalNotifyNetworkFailure);
|
||||
#endif
|
||||
}
|
||||
|
||||
// Immediately cleanup (or rather, start of next tick, as that's earliest possible time) after sending the RPC
|
||||
@@ -1306,7 +1334,7 @@ TWeakPtr<FUnitTestProcess> UClientUnitTest::StartUnitTestClient(FString ConnectI
|
||||
{
|
||||
auto CurHandle = ReturnVal.Pin();
|
||||
|
||||
// @todo JohnB: If you add support for multiple clients, make the log prefix numbered, also try to differentiate colours
|
||||
// @todo #JohnBMultiClient: If you add support for multiple clients, make the log prefix numbered, also try to differentiate colours
|
||||
CurHandle->ProcessTag = TEXT("Client");
|
||||
CurHandle->BaseLogType = ELogType::Client;
|
||||
CurHandle->LogPrefix = TEXT("[CLIENT]");
|
||||
@@ -1365,7 +1393,7 @@ void UClientUnitTest::ShutdownUnitTestProcess(TSharedPtr<FUnitTestProcess> InHan
|
||||
UNIT_STATUS_LOG(ELogType::StatusVerbose, TEXT("%s"), *LogMsg);
|
||||
|
||||
|
||||
// @todo JohnB: Restore 'true' here, once the issue where killing child processes sometimes kills all processes, is fixed
|
||||
// @todo #JohnBHighPri: Restore 'true' here, once the issue where killing child processes sometimes kills all processes, is fixed
|
||||
FPlatformProcess::TerminateProc(InHandle->ProcessHandle);//, true);
|
||||
|
||||
#if TARGET_UE4_CL < CL_CLOSEPROC
|
||||
@@ -1523,7 +1551,8 @@ void UClientUnitTest::CheckOutputForError(TSharedPtr<FUnitTestProcess> InProcess
|
||||
InProcess->ErrorLogStage = EErrorLogStage::ELS_ErrorStart;
|
||||
|
||||
// Reset the timeout for both the unit test and unit test connection here, as callstack logs are prone to failure
|
||||
ResetTimeout(TEXT("Detected crash."), true);
|
||||
// (do it for at least two minutes as well, as it can take a long time to get a crashlog)
|
||||
ResetTimeout(TEXT("Detected crash."), true, 120);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1574,7 +1603,7 @@ void UClientUnitTest::CheckOutputForError(TSharedPtr<FUnitTestProcess> InProcess
|
||||
|
||||
|
||||
#if !UE_BUILD_SHIPPING
|
||||
// @todo JohnB: 'HookOrigin' is not optimal - try to at least make it a UClientUnitTest pointer
|
||||
// @todo #JohnB: 'HookOrigin' is not optimal - try to at least make it a UClientUnitTest pointer
|
||||
bool UClientUnitTest::InternalScriptProcessEvent(AActor* Actor, UFunction* Function, void* Parameters, void* HookOrigin)
|
||||
{
|
||||
bool bBlockEvent = false;
|
||||
@@ -1660,6 +1689,12 @@ void UClientUnitTest::UnitTick(float DeltaTime)
|
||||
}
|
||||
}
|
||||
|
||||
// Prevent net connection timeout in developer mode
|
||||
if (bDeveloperMode)
|
||||
{
|
||||
ResetConnTimeout();
|
||||
}
|
||||
|
||||
|
||||
PollProcessOutput();
|
||||
|
||||
@@ -1711,7 +1746,7 @@ void UClientUnitTest::PollProcessOutput()
|
||||
// Now split up the log into multiple lines
|
||||
TArray<FString> LogLines;
|
||||
|
||||
// @todo JohnB: Perhaps add support for both platforms line terminator, at some stage
|
||||
// @todo #JohnB: Perhaps add support for both platforms line terminator, at some stage
|
||||
#if TARGET_UE4_CL < CL_STRINGPARSEARRAY
|
||||
LogDump.ParseIntoArray(&LogLines, LINE_TERMINATOR, true);
|
||||
#else
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
#include "NetcodeUnitTestPCH.h"
|
||||
|
||||
// @todo JohnB: Need to tidy up and fully document this class; not all of the code below is clear
|
||||
// @todo #JohnBDoc: Need to tidy up and fully document this class; not all of the code below is clear
|
||||
|
||||
#include "NUTActor.h"
|
||||
#include "NUTUtilNet.h"
|
||||
@@ -338,7 +338,7 @@ void ANUTActor::Tick(float DeltaSeconds)
|
||||
|
||||
if (GameState != NULL)
|
||||
{
|
||||
// @todo JohnB: You want this to only happen if no remote players are present (perhaps give all players control instead,
|
||||
// @todo #JohnBReview: You want this to only happen if no remote players are present (perhaps give all players control instead,
|
||||
// if this becomes a problem - requires setting things up differently though)
|
||||
if (CurNetMode == NM_ListenServer || CurNetMode == NM_Standalone)
|
||||
{
|
||||
|
||||
@@ -30,7 +30,7 @@ void NUTUtil::GetUnitTestClassDefList(TArray<UUnitTest*>& OutUnitTestClassDefaul
|
||||
|
||||
void NUTUtil::SortUnitTestClassDefList(TArray<UUnitTest*>& InUnitTestClassDefaults)
|
||||
{
|
||||
// @todo JohnB: Convert these inline sort functions to lambda's now
|
||||
// @todo #JohnBRefactorLambda: Convert these inline sort functions to lambda's now
|
||||
struct FUnitTestDateSort
|
||||
{
|
||||
FORCEINLINE bool operator()(const UUnitTest& A, const UUnitTest& B) const
|
||||
@@ -69,7 +69,6 @@ void NUTUtil::SortUnitTestClassDefList(TArray<UUnitTest*>& InUnitTestClassDefaul
|
||||
|
||||
|
||||
// First reorder the unit test classes by date, then grab the unit test types by date, then group them by type/date
|
||||
// @todo JohnB: You can tweak the order here manually, e.g. by manually adding certain categories as hardcoded
|
||||
TArray<FString> ListTypes;
|
||||
|
||||
InUnitTestClassDefaults.Sort(FUnitTestDateSort());
|
||||
|
||||
@@ -23,7 +23,11 @@ void FFrameProfiler::Start()
|
||||
|
||||
const FStatsThreadState& Stats = FStatsThreadState::GetLocalState();
|
||||
|
||||
#if TARGET_UE4_CL >= CL_DEPRECATEDEL
|
||||
OnNewFrameDelegateHandle = Stats.NewFrameDelegate.AddRaw(this, &FFrameProfiler::OnNewFrame);
|
||||
#else
|
||||
Stats.NewFrameDelegate.AddRaw(this, &FFrameProfiler::OnNewFrame);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
@@ -33,13 +37,18 @@ void FFrameProfiler::Stop()
|
||||
{
|
||||
const FStatsThreadState& Stats = FStatsThreadState::GetLocalState();
|
||||
|
||||
#if TARGET_UE4_CL >= CL_DEPRECATEDEL
|
||||
Stats.NewFrameDelegate.Remove(OnNewFrameDelegateHandle);
|
||||
#else
|
||||
Stats.NewFrameDelegate.RemoveRaw(this, &FFrameProfiler::OnNewFrame);
|
||||
#endif
|
||||
|
||||
|
||||
StatsMasterEnableSubtract();
|
||||
bActive = false;
|
||||
|
||||
|
||||
// @todo JohnB: For the moment, these objects are not tracked after creation, and are responsible for deleting themselves
|
||||
// @todo #JohnB: For the moment, these objects are not tracked after creation, and are responsible for deleting themselves
|
||||
delete this;
|
||||
}
|
||||
}
|
||||
@@ -82,7 +91,6 @@ void FFrameProfiler::OnNewFrame(int64 Frame)
|
||||
// Since division is done using integers, the value must be pre-multiplied, or the division result is fractional/not-an-integer
|
||||
float FramePercent = (float)((TotalDuration * 10000) / TotalFrameTime) * 0.01f;
|
||||
|
||||
// @todo JohnB: Remove
|
||||
#if 0
|
||||
UE_LOG(LogUnitTest, Log, TEXT("Targeted stat found: Duration: %u, FrameTime: %f"),
|
||||
TotalDuration,
|
||||
|
||||
@@ -365,7 +365,8 @@ bool NUTNet::CreateFakePlayer(UWorld* InWorld, UNetDriver*& InNetDriver, FString
|
||||
FString VersionStr = GEngineVersion.ToString(EVersionComponent::Minor);
|
||||
int32 VersionDelim = VersionStr.Find(TEXT("."));
|
||||
int32 MajorVersion = FCString::Atoi(*VersionStr.Left(VersionDelim));
|
||||
int32 MinorVersion = FCString::Atoi(*VersionStr.Right(VersionDelim));
|
||||
int32 MinorVersion = FCString::Atoi(*VersionStr.Mid(VersionDelim+1));
|
||||
|
||||
|
||||
bool bOldProtocol = (MajorVersion <= 4 && MinorVersion <= 7) &&
|
||||
/** Exception for UT (treat 4.7 as having the new protocol) */
|
||||
|
||||
@@ -19,7 +19,7 @@ UUnitTestChannel::UUnitTestChannel(const FObjectInitializer& ObjectInitializer)
|
||||
}
|
||||
|
||||
/**
|
||||
* @todo JohnB
|
||||
* @todo #JohnBDoc
|
||||
*/
|
||||
void UUnitTestChannel::Init(UNetConnection* InConnection, int32 InChIndex, bool InOpenedLocally)
|
||||
{
|
||||
@@ -38,27 +38,23 @@ void UUnitTestChannel::Init(UNetConnection* InConnection, int32 InChIndex, bool
|
||||
}
|
||||
|
||||
/**
|
||||
* @todo JohnB
|
||||
* @todo #JohnBDoc
|
||||
*/
|
||||
void UUnitTestChannel::ReceivedBunch(FInBunch& Bunch)
|
||||
{
|
||||
// @todo JohnB: Add default behaviour for when not bound, to output channel data someplace (perhaps the log, if not too verbose?)
|
||||
|
||||
// @todo JohnB: Perhaps make the delegate a multicast one, since that may be useful for multiple processing
|
||||
|
||||
// Pass on to delegate
|
||||
ReceivedBunchDel.ExecuteIfBound(Bunch);
|
||||
}
|
||||
|
||||
/**
|
||||
* @todo JohnB
|
||||
* @todo #JohnBDoc
|
||||
*/
|
||||
void UUnitTestChannel::Tick()
|
||||
{
|
||||
Super::Tick();
|
||||
|
||||
// Copied from the control channel code
|
||||
// @todo JohnB: This can spam the log sometimes, upon unit test error; fix this
|
||||
// @todo #JohnBBug: This can spam the log sometimes, upon unit test error; fix this
|
||||
if (!OpenAcked)
|
||||
{
|
||||
int32 Count = 0;
|
||||
|
||||
@@ -37,8 +37,13 @@ void UUnitTestNetConnection::InitBase(UNetDriver* InDriver, class FSocket* InSoc
|
||||
#endif
|
||||
}
|
||||
|
||||
#if TARGET_UE4_CL < CL_INITCONNPARAM
|
||||
void UUnitTestNetConnection::InitConnection(UNetDriver* InDriver, EConnectionState InState, const FURL& InURL,
|
||||
int32 InConnectionSpeed, int32 InMaxPacket)
|
||||
int32 InConnectionSpeed/*=0*/)
|
||||
#else
|
||||
void UUnitTestNetConnection::InitConnection(UNetDriver* InDriver, EConnectionState InState, const FURL& InURL,
|
||||
int32 InConnectionSpeed/*=0*/, int32 InMaxPacket/*=0*/)
|
||||
#endif
|
||||
{
|
||||
Super::InitConnection(InDriver, InState, InURL, InConnectionSpeed);
|
||||
|
||||
@@ -89,7 +94,7 @@ void UUnitTestNetConnection::HandleClientPlayer(class APlayerController* PC, cla
|
||||
PlayerController = PC;
|
||||
OwningActor = PC;
|
||||
|
||||
// @todo JohnB: This might cause undesirable behaviour, if - for example - HandleDisconnect gets called by
|
||||
// @todo #JohnBReview: This might cause undesirable behaviour, if - for example - HandleDisconnect gets called by
|
||||
// RPC's, so may want to create a fake localplayer instead
|
||||
PC->Player = GEngine->GetFirstGamePlayer(NUTUtil::GetPrimaryWorld());
|
||||
|
||||
|
||||
@@ -15,7 +15,7 @@ UUnitTestNetDriver::UUnitTestNetDriver(const FObjectInitializer& ObjectInitializ
|
||||
}
|
||||
|
||||
/**
|
||||
* @todo JohnB
|
||||
* @todo #JohnBDoc
|
||||
*/
|
||||
bool UUnitTestNetDriver::InitConnectionClass()
|
||||
{
|
||||
@@ -36,7 +36,7 @@ bool UUnitTestNetDriver::InitConnectionClass()
|
||||
}
|
||||
|
||||
/**
|
||||
* @todo JohnB
|
||||
* @todo #JohnBDoc
|
||||
*/
|
||||
bool UUnitTestNetDriver::InitConnect(FNetworkNotify* InNotify, const FURL& ConnectURL, FString& Error)
|
||||
{
|
||||
|
||||
@@ -6,10 +6,6 @@
|
||||
#include "Net/UnitTestPackageMap.h"
|
||||
|
||||
|
||||
// @todo JohnB: Should probably add a CL-define which wraps this code, since not all codebases will expose PackageMapClient?
|
||||
// (probably better to just error, and force a code change for that, in that codebase - otherwise not all unit tests work)
|
||||
|
||||
|
||||
/**
|
||||
* Default constructor
|
||||
*/
|
||||
|
||||
@@ -40,7 +40,10 @@ class FNetcodeUnitTest : public INetcodeUnitTest
|
||||
{
|
||||
private:
|
||||
static FWorldDelegates::FWorldInitializationEvent::FDelegate OnWorldCreatedDelegate;
|
||||
|
||||
#if TARGET_UE4_CL >= CL_DEPRECATEDEL
|
||||
static FDelegateHandle OnWorldCreatedDelegateHandle;
|
||||
#endif
|
||||
|
||||
public:
|
||||
/**
|
||||
@@ -55,7 +58,11 @@ public:
|
||||
OnWorldCreatedDelegate = FWorldDelegates::FWorldInitializationEvent::FDelegate::CreateStatic(
|
||||
&FNetcodeUnitTest::OnWorldCreated);
|
||||
|
||||
#if TARGET_UE4_CL >= CL_DEPRECATEDEL
|
||||
OnWorldCreatedDelegateHandle = FWorldDelegates::OnPreWorldInitialization.Add(OnWorldCreatedDelegate);
|
||||
#else
|
||||
FWorldDelegates::OnPreWorldInitialization.Add(OnWorldCreatedDelegate);
|
||||
#endif
|
||||
|
||||
bSetDelegate = true;
|
||||
}
|
||||
@@ -97,13 +104,19 @@ public:
|
||||
}
|
||||
|
||||
// Now remove it, so it's only called once
|
||||
#if TARGET_UE4_CL >= CL_DEPRECATEDEL
|
||||
FWorldDelegates::OnPreWorldInitialization.Remove(OnWorldCreatedDelegateHandle);
|
||||
#else
|
||||
FWorldDelegates::OnPreWorldInitialization.Remove(OnWorldCreatedDelegate);
|
||||
#endif
|
||||
}
|
||||
};
|
||||
|
||||
FWorldDelegates::FWorldInitializationEvent::FDelegate FNetcodeUnitTest::OnWorldCreatedDelegate = NULL;
|
||||
|
||||
#if TARGET_UE4_CL >= CL_DEPRECATEDEL
|
||||
FDelegateHandle FNetcodeUnitTest::OnWorldCreatedDelegateHandle;
|
||||
#endif
|
||||
|
||||
|
||||
// Essential for getting the .dll to compile, and for the package to be loadable
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
#include "NUTUtil.h"
|
||||
|
||||
|
||||
// @todo JohnB: Some unit tests may require special automation flags, and you should automatically parse these from the unit test
|
||||
// @todo #JohnBAutomation: Some unit tests may require special automation flags, and you should automatically parse these from the unit test
|
||||
// class itself, if possible (and since this runs all unit tests, you should probably iterate all unit tests that will
|
||||
// be run, to check their requirements)
|
||||
|
||||
@@ -31,7 +31,7 @@ bool FNUTWaitForUnitTests::Update()
|
||||
/**
|
||||
* FAutomationConsoleCommand
|
||||
*
|
||||
* @todo JohnB: AutomationTestCommon.h already implements this, but is private
|
||||
* @todo #JohnBRefactor: AutomationTestCommon.h already implements this, but is private
|
||||
*/
|
||||
DEFINE_LATENT_AUTOMATION_COMMAND_ONE_PARAMETER(FAutomationConsoleCommand, FString, Command);
|
||||
|
||||
|
||||
@@ -21,7 +21,11 @@ FLogWindowManager::~FLogWindowManager()
|
||||
|
||||
if (CurEntry->LogWindow.IsValid())
|
||||
{
|
||||
#if TARGET_UE4_CL >= CL_DEPRECATEDEL
|
||||
CurEntry->LogWindow->MultiOnWindowClosed.Remove(OnWindowClosedDelegateHandles.FindRef(CurEntry->LogWindow.Get()));
|
||||
#else
|
||||
CurEntry->LogWindow->MultiOnWindowClosed.RemoveRaw(this, &FLogWindowManager::OnWindowClosed);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,7 +33,11 @@ FLogWindowManager::~FLogWindowManager()
|
||||
{
|
||||
if (OverflowWindows[i].IsValid())
|
||||
{
|
||||
#if TARGET_UE4_CL >= CL_DEPRECATEDEL
|
||||
OverflowWindows[i]->MultiOnWindowClosed.Remove(OnWindowClosedDelegateHandles.FindRef(OverflowWindows[i].Get()));
|
||||
#else
|
||||
OverflowWindows[i]->MultiOnWindowClosed.RemoveRaw(this, &FLogWindowManager::OnWindowClosed);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -74,7 +82,7 @@ void FLogWindowManager::Initialize(int InLogWidth, int InLogHeight)
|
||||
}
|
||||
|
||||
|
||||
// @todo JohnB: Remove this debug code
|
||||
// @todo #JohnBDebug: Remove this debug code
|
||||
#if 0
|
||||
for (int i = 0; i<GridSpaces.Num(); i++)
|
||||
{
|
||||
@@ -128,8 +136,12 @@ TSharedPtr<SLogWindow> FLogWindowManager::CreateLogWindow(FString Title, ELogTyp
|
||||
|
||||
if (ReturnVal.IsValid())
|
||||
{
|
||||
#if TARGET_UE4_CL >= CL_DEPRECATEDEL
|
||||
OnWindowClosedDelegateHandles.Add(ReturnVal.Get(),
|
||||
ReturnVal->MultiOnWindowClosed.AddRaw(this, &FLogWindowManager::OnWindowClosed));
|
||||
#else
|
||||
ReturnVal->MultiOnWindowClosed.AddRaw(this, &FLogWindowManager::OnWindowClosed);
|
||||
#endif
|
||||
|
||||
FSlateApplication::Get().AddWindow(ReturnVal.ToSharedRef());
|
||||
|
||||
|
||||
@@ -8,19 +8,19 @@
|
||||
#include "SMultiSelectTableRow.h"
|
||||
|
||||
|
||||
// @todo JohnB: It would be good to have both a 'Search' filter tab, and a 'Ctrl+F Find' button for each existing tab;
|
||||
// @todo #JohnBFeatureUI: It would be good to have both a 'Search' filter tab, and a 'Ctrl+F Find' button for each existing tab;
|
||||
// two different search abilities (should be easy to add too)
|
||||
|
||||
// @todo JohnB: Could change the 'close' button, to a '+' button, which clones the current tab and enables search filtering
|
||||
// @todo #JohnBFeatureUI: Could change the 'close' button, to a '+' button, which clones the current tab and enables search filtering
|
||||
|
||||
|
||||
// @todo JohnB: Perhaps have conditional tabs, which only appear if log entries of this type come up?
|
||||
// (such as: Warning, Error, Debug)
|
||||
// @todo #JohnBReview: Perhaps have conditional tabs, which only appear if log entries of this type come up?
|
||||
// (such as: Warning, Error, Debug) UPDATE: Is this not already present?
|
||||
|
||||
// @todo JohnB: Consider adding a "TabName (LineCount)" to the tab name (maybe just for important tabs, like Error/Warning)
|
||||
// @todo #JohnBFeatureUI: Consider adding a "TabName (LineCount)" to the tab name (maybe just for important tabs, like Error/Warning)
|
||||
|
||||
|
||||
// @todo JohnB: Change the opacity, of background highlight for selected log entries - really ugly at the moment
|
||||
// @todo #JohnBUI: Change the opacity, of background highlight for selected log entries - really ugly at the moment
|
||||
|
||||
|
||||
// Enable access to the private SEditableTextBox.EditableText variable, using the GET_PRIVATE macro
|
||||
@@ -33,7 +33,7 @@ IMPLEMENT_GET_PRIVATE_VAR(SButton, Style, const FButtonStyle*);
|
||||
IMPLEMENT_GET_PRIVATE_FUNC_CONST(SDockTab, GetCurrentStyle, const FDockTabStyle&, void, const);
|
||||
|
||||
|
||||
// @todo JohnB: Perhaps move widget searching to a NUTSlate.h file, or such?
|
||||
// @todo #JohnBRefactorUI: Perhaps move widget searching to a NUTSlate.h file, or such?
|
||||
|
||||
/**
|
||||
* Delegate used for recursively iterating a widgets child widgets, and testing if they match a search condition
|
||||
@@ -211,7 +211,7 @@ void SLogWidget::Construct(const FArguments& Args)
|
||||
})
|
||||
[
|
||||
SNew(SImage)
|
||||
// @todo JohnB: The scaled image looks a bit fuzzy, so perhaps don't do that
|
||||
// @todo #JohnBUI: The scaled image looks a bit fuzzy, so perhaps don't do that
|
||||
// (if you can figure out how to make it clip rather than scale though, do that)
|
||||
#if 1
|
||||
.Image(&FCoreStyle::Get().GetWidgetStyle<FSearchBoxStyle>("SearchBox").GlassImage)
|
||||
@@ -450,7 +450,7 @@ void SLogWidget::Construct(const FArguments& Args)
|
||||
SAssignNew(ConsoleComboBox, SComboBox<TSharedPtr<FString>>)
|
||||
.OptionsSource(&ConsoleContextList)
|
||||
.ToolTipText(FText::FromString(FString(TEXT("Select the context for executing console commands."))))
|
||||
// @todo JohnB: Too big to inline? Separate into its own function?
|
||||
// @todo #JohnBRefactorUI: Too big to inline? Separate into its own function?
|
||||
.OnGenerateWidget_Lambda(
|
||||
[](TSharedPtr<FString> Item)
|
||||
{
|
||||
@@ -471,12 +471,12 @@ void SLogWidget::Construct(const FArguments& Args)
|
||||
}
|
||||
else if (ItemStr == TEXT("Client"))
|
||||
{
|
||||
// @todo JohnB: Update when implemented
|
||||
// @todo #JohnBFeatureUI: Update when implemented
|
||||
ToolTipStr = TEXT("(Not yet implemented) ")
|
||||
TEXT("Execute the command on the client associated with this unit test.");
|
||||
}
|
||||
|
||||
// @todo JohnB: Custom context hints?
|
||||
// @todo #JohnB: Custom context hints?
|
||||
|
||||
return SNew(STextBlock)
|
||||
.Text(FText::FromString(ItemStr))
|
||||
@@ -500,7 +500,7 @@ void SLogWidget::Construct(const FArguments& Args)
|
||||
/**
|
||||
* Console command edit box
|
||||
*/
|
||||
// @todo JohnB: Borrow the auto-complete from SOutputLog's version of log windows
|
||||
// @todo #JohnBFeatureUI: Borrow the auto-complete from SOutputLog's version of log windows
|
||||
+SHorizontalBox::Slot()
|
||||
.HAlign(HAlign_Fill)
|
||||
.VAlign(VAlign_Center)
|
||||
@@ -510,7 +510,7 @@ void SLogWidget::Construct(const FArguments& Args)
|
||||
.HintText(FText::FromString(TEXT("Console")))
|
||||
.ToolTipText(FText::FromString(TEXT("Executes a console command within the specified context.")))
|
||||
.ClearKeyboardFocusOnCommit(false)
|
||||
// @todo JohnB: Too big to inline? Separate into its own function?
|
||||
// @todo #JohnBRefactorUI: Too big to inline? Separate into its own function?
|
||||
.OnTextCommitted_Lambda(
|
||||
[&](const FText& InText, ETextCommit::Type InCommitType)
|
||||
{
|
||||
@@ -658,7 +658,7 @@ TSharedRef<SDockTab> SLogWidget::SpawnLogTab(const FSpawnTabArgs& InSpawnTabArgs
|
||||
});
|
||||
|
||||
|
||||
// @todo JohnB: Code duplication - this is defined above too - move to an inline function
|
||||
// @todo #JohnBRefactorUI: Code duplication - this is defined above too - move to an inline function
|
||||
auto ArrayAddNew =
|
||||
[] (TArray<TSharedPtr<SWidget>>& InArray) -> TSharedPtr<SWidget>&
|
||||
{
|
||||
@@ -706,7 +706,7 @@ TSharedRef<SDockTab> SLogWidget::SpawnLogTab(const FSpawnTabArgs& InSpawnTabArgs
|
||||
*/
|
||||
SAssignNew(CurTabInfo->LogListView, SListView<TSharedRef<FLogLine>>)
|
||||
.ListItemsSource(&CurTabInfo->TabLogLines)
|
||||
// @todo JohnB: Probably large enough to separate to its own function now
|
||||
// @todo #JohnBRefactorUI: Probably large enough to separate to its own function now
|
||||
.OnGenerateRow_Lambda(
|
||||
[](TSharedRef<FLogLine> Item, const TSharedRef<STableViewBase>& OwnerTable)
|
||||
{
|
||||
@@ -1208,7 +1208,7 @@ void SLogWidget::ScrollToText(TSharedRef<FLogTabInfo> InTab, FString FindText, b
|
||||
int32 SearchDir = (bSearchUp ? -1 : 1);
|
||||
int32 FoundIdx = INDEX_NONE;
|
||||
|
||||
for (int32 i=FindStartIdx + SearchDir; i != FindStartIdx; i += SearchDir)
|
||||
for (int32 i=FindStartIdx + SearchDir; true; i += SearchDir)
|
||||
{
|
||||
// When the start/end of the array is reached, wrap-around to the other end
|
||||
if (i < 0 || i >= CurTabLogLines.Num())
|
||||
@@ -1216,6 +1216,12 @@ void SLogWidget::ScrollToText(TSharedRef<FLogTabInfo> InTab, FString FindText, b
|
||||
i = (bSearchUp ? CurTabLogLines.Num()-1 : 0);
|
||||
}
|
||||
|
||||
// Moved out of 'for' condition, and into the loop, to avoid infinite recursion in rare circumstances
|
||||
if (i == FindStartIdx)
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
if (CurTabLogLines[i]->LogLine->Contains(FindText))
|
||||
{
|
||||
FoundIdx = i;
|
||||
@@ -1230,7 +1236,7 @@ void SLogWidget::ScrollToText(TSharedRef<FLogTabInfo> InTab, FString FindText, b
|
||||
CurLogListView->RequestListRefresh();
|
||||
}
|
||||
|
||||
// @todo JohnB: Find some way of indicating a failed search
|
||||
// @todo #JohnBUI: Find some way of indicating a failed search
|
||||
|
||||
InTab->bLastFindWasUp = bSearchUp;
|
||||
}
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user